Django 프로젝트를위한 JS 통합.
따라서 프로젝트에서 Django와 Next.js를 모두 사용하고 싶습니다. 두 가지 시나리오가 있습니다.
새로운 프로젝트를 시작하고 있으며 Django를 백엔드로 사용하고 Next.js를 프론트 엔드로 사용하려고합니다. Django는 API 요청 만 제공합니다. 모든 프론트 엔드 코드는 Next.js에 살고 있으며 Django 템플릿을 작성하지 않습니다.
이 시나리오에서는이 패키지가 필요하지 않습니다 (사용할 수는 있지만). 당신은 단순히 django와 next.js 서버를 모두 시작하고 공개 웹 서버를 다음에 가리 킵니다.
Django 템플릿과 Next.js가 동시에 필요하며 해당 페이지는 서로 쉽게 연결해야합니다. 어쩌면 Django 템플릿으로 렌더링 된 페이지가있는 기존 Django 프로젝트가있을 수 있으며 Next.js에서 새로운 페이지를 원합니다. 또는 프론트 엔드를 Next.js로 마이그레이션하고 싶지만 프로젝트가 크기 때문에 점차적으로 수행해야합니다.
이 시나리오 에서이 패키지는 당신을위한 것입니다!
stackoverflow에 대한 의견에서 :
동일한 서버에서 2 개의 포트를 실행하십시오. 하나는 Django (공개 대면)이고 하나는 Next.js (내부)를위한 것입니다. Django가 모든 웹 요청을 처리하도록하십시오. 각 요청에 대해 django보기에서 query next.js를 통해 HTML 응답을 얻으십시오. Django View에서 정확한 HTML 응답을 반환하십시오.
PYPI에서 최신 버전을 설치하십시오.
pip install django-nextjs django_nextjs.apps.DjangoNextJSConfig INSTALLED_APPS 에 추가하십시오.
환경에 따라 다음 .js URL을 설정하십시오.
개발 중에 ASGI에서 사이트에 서비스를 제공하는 경우 DJANGO 채널을 사용하고 다음 예제와 마찬가지로 NextJSProxyHttpConsumer NextJSProxyWebsocketConsumer asgi.py 에 추가하십시오.
참고 : ASGI 및 DJANGO 채널을 사용하는 것이 좋습니다. 다음 JS 12+에서 제대로 작동하려면 빠른 새로 고침 (핫 모듈 교체)을 위해 필요하므로 사용하는 것이 좋습니다.
import os
from django . core . asgi import get_asgi_application
from django . urls import re_path , path
os . environ . setdefault ( "DJANGO_SETTINGS_MODULE" , "myproject.settings" )
django_asgi_app = get_asgi_application ()
from channels . auth import AuthMiddlewareStack
from channels . routing import ProtocolTypeRouter , URLRouter
from django_nextjs . proxy import NextJSProxyHttpConsumer , NextJSProxyWebsocketConsumer
from django . conf import settings
# put your custom routes here if you need
http_routes = [ re_path ( r"" , django_asgi_app )]
websocket_routers = []
if settings . DEBUG :
http_routes . insert ( 0 , re_path ( r"^(?:_next|__next|next).*" , NextJSProxyHttpConsumer . as_asgi ()))
websocket_routers . insert ( 0 , path ( "_next/webpack-hmr" , NextJSProxyWebsocketConsumer . as_asgi ()))
application = ProtocolTypeRouter (
{
# Django's ASGI application to handle traditional HTTP and websocket requests.
"http" : URLRouter ( http_routes ),
"websocket" : AuthMiddlewareStack ( URLRouter ( websocket_routers )),
# ...
}
) 그렇지 않으면 (개발 중 WSGI에 따라 서빙하는 경우) urls.py 의 시작 부분에 다음을 추가하십시오.
path ( "" , include ( "django_nextjs.urls" )) 경고 : ASGI에서 일하는 경우 urls.py 에 추가하지 마십시오. 교착 상태가 발생할 수 있습니다.
생산시 Nginx 또는 Caddy와 같은 역 프록시를 사용하십시오.
| URL | 행동 |
|---|---|
/_next/static/... | NEXTJS_PATH/.next/static 디렉토리를 제공하십시오 |
/_next/... | http://localhost:3000 에 프록시 |
/next/... | NEXTJS_PATH/public/next DIRECTORY를 제공하십시오 |
nginx의 예제 구성 :
location /_next/static/ {
alias NEXTJS_PATH/.next/static/;
expires max;
add_header Cache-Control "public";
}
location /_next/ {
proxy_pass http://127.0.0.1:3000;
proxy_set_header Host $http_host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
}
location /next/ {
alias NEXTJS_PATH/public/next/;
expires max;
add_header Cache-Control "public";
}
다음에 시작합니다 .js 서버 :
# Development:
$ npm run dev
# Production:
$ npm run build
$ npm run startNext.js에서 페이지를 개발 한 다음 각 Next.js 페이지에 대한 Django URL을 정의하십시오. 다음은이 작업을 수행 할 수있는 방법의 예입니다.
from django_nextjs . views import nextjs_page
urlpatterns = [
path ( "/nextjs/page" , nextjs_page (), name = "nextjs_page" ),
]권장되지는 않지만 Django에 Next.js 페이지를 표시하기 전에 몇 가지 사용자 정의 단계를 추가해야 할 수도 있습니다. 그러나이 논리를 다음으로 옮기면 클라이언트 측 리디렉션 중에도 적용되도록 조언합니다 . 이 상황에서 자신을 발견하면 아래에 표시된대로 각 페이지에 대한 비동기식보기를 만들 수 있습니다.
from django_nextjs . render import render_nextjs_page
async def jobs ( request ):
# Your custom logic
return await render_nextjs_page ( request )다음.js가 django 코드에서 반환하는 HTML 코드를 수정할 수 있습니다.
NAVBAR 및 바닥 글에 대한 중복 코드를 피하는 것은 다음에 대한 공통 사용 사례입니다. 그것 없이는 두 개의 개별 버전의 Navbar와 바닥 글 (Django 템플릿 버전 및 Next.js 버전)을 작성하고 유지해야합니다. 그러나 Navbar에 대한 Django 템플릿을 만들고 Next.js에서 반환 된 <body> 태그의 시작 부분에서 코드를 삽입 할 수 있습니다.
이 기능을 활성화하려면 Next.js에서 문서 및 루트 레이아웃을 사용자 정의하고 다음을 조정해야합니다.
<body> 요소의 첫 번째 속성으로 id="__django_nextjs_body" 를 추가하십시오.<div id="__django_nextjs_body_begin" /> <body> 내 첫 요소로 추가하십시오.<body> 내부의 마지막 요소로 <div id="__django_nextjs_body_end" /> 추가하십시오.참고 : 현재 HTML 사용자 정의는 App Router (Next.js 13+)에서 작동하지 않습니다.
이 문서를 읽고 다음에 사용자 정의하십시오 .JS 문서 :
// pages/_document.jsx (or .tsx)
...
< body id = "__django_nextjs_body" >
< div id = "__django_nextjs_body_begin" />
< Main />
< NextScript />
< div id = "__django_nextjs_body_end" />
</ body >
. . . django_nextjs/document_base.html 확장하는 django 템플릿을 작성하십시오.
{% extends "django_nextjs/document_base.html" %}
{% block head %}
<!-- ... the content you want to place at the beginning of "head" tag ... -->
{{ block.super }}
<!-- ... the content you want to place at the end of "head" tag ... -->
{% endblock %}
{% block body %}
... the content you want to place at the beginning of "body" tag ...
... e.g. include the navbar template ...
{{ block.super }}
... the content you want to place at the end of "body" tag ...
... e.g. include the footer template ...
{% endblock %} 템플릿 이름을 nextjs_page 또는 render_nextjs_page 로 전달하십시오.
from django_nextjs . render import render_nextjs_page
from django_nextjs . views import nextjs_page
async def jobs ( request ):
return await render_nextjs_page ( request , template_name = "path/to/template.html" )
urlpatterns = [
path ( "/nextjs/page" , nextjs_page ( template_name = "path/to/template.html" ), name = "nextjs_page" ),
path ( "/jobs" , jobs , name = "jobs_page" )
]public 디렉토리에 파일을 추가하려면 해당 파일이 public/next 하위 디렉토리에 있어야합니다.settings.py 에 APPEND_SLASH = False 추가해야 할 수도 있습니다. 또한 urls.py 의 Nextjs 경로 끝에 추가 / 하지 마십시오.기본 설정 :
NEXTJS_SETTINGS = {
"nextjs_server_url" : "http://127.0.0.1:3000" ,
"ensure_csrf_token" : True ,
}nextjs_server_url Next.js Server의 URL ( npm run dev 또는 npm run start ).
ensure_csrf_token 사용자에게 CSRF 토큰이없는 경우 DJANGO의 django.middleware.csrf.get_token 으로 전화하여 다음.js 서버에 초기 요청에 포함되어 있는지 확인하십시오. django.middleware.csrf.CsrfViewMiddleware 설치되면 초기 응답에는 클라이언트의 CSRF 토큰 값을 지속하기위한 Set-Cookie 헤더가 포함됩니다. 이 동작은 기본적으로 활성화됩니다.
ensure_csrf_token 해야 할 때? 다음 getServerSideProps 에서 데이터를 가져 오기 위해 GraphQL 게시물 요청을 발행해야 할 수도 있습니다. 이것이 사용자의 첫 번째 요청 인 경우 CSRF 쿠키가 없으므로 GraphQL이 데이터 가져 오기에 게시물을 사용하기 때문에 요청이 실패하게됩니다. 그러나 getServerSideProps 기능이 부작용이없는 한 (즉, HTTP 안전하지 않은 방법이나 GraphQL 돌연변이를 사용하지 않음) 보안 관점에서 괜찮을 것입니다. 여기에서 자세히 알아보십시오.
pip install -e '.[dev]'pre-commit install 사용하여 사전 커밋 후크를 설치하십시오. MIT