DEBUG = False 설정으로 장고 정적 파일 액세스가 실패하는 이유는 무엇입니까?


356

Django를 내 주력으로 사용하여 앱을 만들고 있습니다. 지금까지 모두 DB 설정, 정적 디렉토리, URL, 뷰 등을 구성했습니다. 그러나 아름답고 사용자 정의 된 404.html 및 500.html 페이지를 렌더링하려는 순간 문제가 몰래 시작되었습니다.

사용자 지정 오류 처리에 대한 문서를 읽고 UrlsConf에서 필요한 구성을 설정하고 해당하는 뷰를 만들고 404.html과 500.html을 내 앱의 템플릿 디렉토리 (settings.py에도 지정됨)에 추가했습니다.

그러나 문서에``라고 말하면 you can actually view custom error views until Debug is Off내 물건을 테스트하기 위해 전원을 끌었습니다.

사용자 정의 404.html을 보는 데 실패 할뿐만 아니라 실제로로드됩니다. 오류 페이지에는 각각 멋진 이미지와 같은 그래픽 오류 메시지가 포함되어 있기 때문에 오류 페이지의 소스가로드되지만 다른 것은로드되지 않습니다! CSS 나 자바 스크립트도 연결되지 않았습니다!

일반적으로을 설정 DEBUG = False하면 모든보기가로드되지만 연결된 콘텐츠 (CSS, Javascript, Images 등)는로드되지 않습니다! 무슨 일이야? 정적 파일 및 DEBUG설정 과 관련하여 누락 된 것이 있습니까?


당신은 어떻게 호스팅하고 있습니까? 테스트 서버가있는 로컬 머신?
j_syk

테스트 서버가있는 로컬 시스템. 기본적으로 존재하지 않는 페이지에 액세스하고 런타임 오류를 발생시키는 시나리오를 로컬로 시뮬레이션하여 사용자 지정 오류 처리가 어떻게 작동하는지 알고 싶지만 정적 콘텐츠가로드되지 않습니다.
nemesisfixx

여기와 같은 서버 수준에서 수행하거나 urlpattern을 추가하여 장고 수준에서 처리 할 수 ​​있습니다. 나는 같은 문제에 대해 아래 질문을 찾았습니다. stackoverflow.com/questions/6405173/…
Pankaj Anand

답변:


353

Django는 디버그가 꺼지면 더 이상 정적 파일을 처리하지 않습니다. 프로덕션 웹 서버 (Apache 또는 무언가)가 처리해야합니다.


3
이것은 실제로 내 호기심을 해결하므로 이제는 이해가되며 필요한 경우 Apache로 실제로 처리 할 수 ​​있습니다. 내 설정에 문제가 있다고 생각했습니다. 감사
nemesisfixx

5
이 답변이 매우 유용하다는 것을 알았습니다. 다른 사람이 같은 상황에 처한 경우 (비상 대가있는 앱에 Google App Engine 사용) : app.yaml을 업데이트하는 것을 잊지 마십시오.
Lyndsey Ferguson

3
핸들러 : - URL : / 정적의 static_dir : 정적
린지 퍼거슨

475

여전히 로컬에서 정적 서버를 사용해야하는 경우 (예 : 디버그없이 테스트하기 위해) 안전하지 않은 모드에서 devserver를 실행할 수 있습니다.

manage.py runserver --insecure

6
이 플래그가 작동하는 동안 collectstatic 폴더의 컨텐츠를 제공하지 않습니다
Howie

5
마술이다. 감사합니다. 당신은 영웅입니다. 이 답변은 django 자체 이외의 다른 방법으로 정적 서비스를 제공하지 않고도 문제를 해결하므로 허용되는 답변과 병합되어야합니다.
Depado

1
이것이 내가 필요한 전부였습니다. 가장 좋은 방법은 환경 변수를 사용하여 개발 및 프로덕션 환경과 디버그 토글을 구별하는 것입니다.
Neeraj Gupta

1
제발 참고 : 그의 뜻으로 ManifestStaticFilesStorage하지 작업 code.djangoproject.com/ticket/19295
안드레아 Rabbaglietti

9
불안 때문에 이것에 대해 무엇을하지만 캔 누군가가 말해
카비 Vaidya

36

WhiteNoise 를 사용 하여 프로덕션에서 정적 파일을 제공 할 수 있습니다 .

설치:

pip install WhiteNoise

wsgi.py 파일을 다음 과 같이 변경하십시오 .

from django.core.wsgi import get_wsgi_application
from whitenoise.django import DjangoWhiteNoise

application = get_wsgi_application()
application = DjangoWhiteNoise(application)

그리고 당신은 갈 수 있습니다!

핸들 바 크리에이티브 블로그에 크레딧 .

그러나 실제로 프로덕션에서 정적 파일을 제공하는 것은 권장하지 않습니다. 프로덕션 웹 서버 (예 : nginx)가이를 처리해야합니다.


1
흥미롭게 들리지만 wgsi.py파일에 해당 줄을 추가하여 나에게 효과가 없었습니다 . 연결 한 설명서에 WhiteNoise 사용에 대한 다른 지침이 나와 있습니다. 다른 방법으로 시도하고 여기에서 업데이트하십시오.
DarkCygnus

이것이 결국 솔루션으로 이끌었던 +1입니다. 실제로 작동시키기 위해 수행 한 추가 단계를 포함 하는 답변을 추가 했습니다.
DarkCygnus

manage.py runserver --insecure나를 위해 작동하지 않았다. 그러나 이것은 그렇습니다.
Jee

3
WhiteNoise 릴리스 4.0에서는 구성이 변경되었습니다. 이 줄을 wsgi.py에 추가하지 마십시오. 대신 'whitenoise.middleware.WhiteNoiseMiddleware'미들웨어에 추가하십시오 .
Doug Harris

* 권장하지 않는 이유는 무엇입니까? 여러 사이트에서 수년 동안 사용해 왔으며 훌륭하게 작동합니다. Heroku조차도 장고 템플릿에서 사용합니다.
Omar Gonzalez

33

urls.py에서 다음 줄을 추가했습니다.

from django.views.static import serve 

urlpatterns에 두 개의 URL을 추가하십시오.

url(r'^media/(?P<path>.*)$', serve,{'document_root': settings.MEDIA_ROOT}), 
url(r'^static/(?P<path>.*)$', serve,{'document_root': settings.STATIC_ROOT}), 

정적 및 미디어 파일은 DEBUG = FALSE 일 때 액세스 할 수있었습니다.
그것이 도움이되기를 바랍니다 :)


관리 패널 CSS 가로 드되지 않았습니까 ??
Thusitha Deepal

예. 작동하는 유일한 사람 !! 감사.
DrGeneral

대박! STATIC_ROOT 및 manage.py collectstatic을 설정하는 것을 잊지 마십시오.
DomingoR

2
요즘 대체 url(:re_path(
Leopd

19

개발시 정적 서브보기를 사용하는 경우 DEBUG = True가 있어야합니다.

경고

DEBUG가 True 인 경우에만 작동합니다.

이 견해는 매우 비효율적이며 아마도 안전하지 않기 때문입니다. 이것은 로컬 개발만을위한 것이며 프로덕션 환경에서 사용해서는 안됩니다.

문서 : 개발자의 정적 파일 제공

편집 : 404 및 500 템플릿을 테스트하기 위해 URL을 추가 할 수 있습니다 .URL에서 일반적인보기 direct_to_template을 사용하십시오.

from django.views.generic.simple import direct_to_template

urlpatterns = patterns('',
    ('^404testing/$', direct_to_template, {'template': '404.html'})
)

1
프로덕션에서 정적 파일을 어떻게 제공합니까? NVM, 방금 봤어 감사.

특정 디렉토리를 호스팅하도록 웹 서버를 설정합니다. 가장 일반적으로 Apache 또는 Nginx를 사용합니다. 문서 는 약간 들어갑니다.
j_syk

@j_syk 덕분에, 나는 이미 제안한 것과 비슷한 다른 오류가없는 메커니즘을 통해 404.html 및 500.html을 보는이 접근법을 이미 시도했습니다. 그러나 테스트 페이지에서 계속 실행하면서 프로덕션에서와 같이 페이지를 올바르게 렌더링하는 것이 완전히 불가능한지 알고 싶었습니다. 디버그가 꺼져있을 때 Apache에 정적 파일 처리를 위임하면 문제가 해결됩니다. 기여해 주셔서 감사합니다.
nemesisfixx

@mcnemesis 정확히 어떻게 될지 잘 모르겠지만 TEMPLATE_DEBUG = False, DEBUG = True를 설정하십시오. 예쁜 오류를 끄면 404/500 템플릿으로 갈지 확실하지 않습니다
j_syk

예상대로이 작업을 수행해도 긍정적 인 결과를 얻지 못했지만 여전히 감사합니다.
nemesisfixx

17

Johnny의 대답 은 훌륭하지만 거기에 설명 된 줄을 추가해도 여전히 효과가 없었습니다. 그 대답을 바탕으로 실제로 나를 위해 일한 단계는 다음과 같습니다.

  1. 설명 된대로 WhiteNoise 를 설치하십시오 .

    pip install WhiteNoise
  2. 만들기 STATIC_ROOT변수를 당신에 백색 잡음을 추가 MIDDLEWARE에서 변수 settings.py:

    #settings.py
    MIDDLEWARE = [
        'django.middleware.security.SecurityMiddleware',
        'whitenoise.middleware.WhiteNoiseMiddleware', #add whitenoise
        'django.contrib.sessions.middleware.SessionMiddleware',
        ...
    ]
    
    #...
    
    STATIC_ROOT = os.path.join(BASE_DIR, 'staticfiles') ##specify static root
  3. 그런 다음 wsgi.pyJohnny의 답변에 설명 된 대로 파일을 수정하십시오 .

    #wsgi.py
    from django.core.wsgi import get_wsgi_application
    from whitenoise.django import DjangoWhiteNoise
    
    application = get_wsgi_application()
    application = DjangoWhiteNoise(application)
  4. 그런 다음 변경 사항을 서버에 배포하십시오 (git 또는 사용하는 것과 함께).

  5. 마지막으로 서버 collectstatic에서 옵션을 실행하십시오 manage.py. 그러면 정적 폴더의 모든 파일이 STATIC_ROOT이전에 지정한 디렉토리 로 복사됩니다 .

    $ python manage.py collectstatic

    이제 staticfiles이러한 요소가 포함 된 새 폴더가 나타납니다.

이 단계를 수행 한 후 이제 서버를 실행할 수 있으며 프로덕션 모드에서 정적 파일을 볼 수 있습니다.

업데이트 : 이 버전을 한 경우에는 <4 변경 로그 는 선언이 더 이상 필요하다고 나타냅니다 WSGI_APPLICATION = 'projectName.wsgi.application'당신에 settings.py파일.


나는 그에 따라 그것을했고, 개발에 대해서는 잘했지만 생산에는 없었습니다. DEBUG == False
Anna Huang

@AnnaHuang 개발과 생산에서 무엇을 의미합니까? 별도의 환경이나 기계가 있습니까? 그들은 같은 방식으로 구성되어 있습니까?
DarkCygnus

13

실제로 Django 앱에서 정적 파일을 안전하고 안전하게 제공 할 수 있습니다 DEBUG=True.

장고 자체를 사용하는 대신 WSGI 파일 ( github ) 에서 dj_static 을 사용 하십시오 .

# requirements.txt:

...
dj-static==0.0.6


# YOURAPP/settings.py:

...
STATIC_ROOT = 'staticdir'
STATIC_URL = '/staticpath/'

# YOURAPP/wsgi.py:

...
from django.core.wsgi import get_wsgi_application
from dj_static import Cling

application = Cling(get_wsgi_application())

2
나는 더 많은 기능을 갖춘 whitenoise를 발견 했다 .
Robin Winslow

7

urls.py 프로젝트를 열고 if 문을 찾으십시오.

if settings.DEBUG:
    urlpatterns += patterns(
        'django.views.static',
        (r'^media/(?P<path>.*)','serve',{'document_root': settings.MEDIA_ROOT}), )

True로 설정을 변경할 수 있으며 항상 작동합니다. 그러나 프로젝트가 심각한 경우 위에서 언급 한 다른 솔루션에 대해 생각해야합니다.

if True:
    urlpatterns += patterns(
        'django.views.static',
        (r'^media/(?P<path>.*)','serve',{'document_root': settings.MEDIA_ROOT}), )

django 1.10에서는 다음과 같이 작성할 수 있습니다.

urlpatterns += [ url(r'^media/(?P<path>.*)$', serve, { 'document_root': settings.MEDIA_ROOT, }), url(r'^static/(?P<path>.*)$', serve, { 'document_root': settings.STATIC_ROOT }), ]

3
코드는 정확하지만 Django 1.10에서는 미디어에 대한 구성이며 정적은 다음과 같습니다. urlpatterns + = [url (r '^ media / (? P <path>. *) $', serve, { 'document_root': 설정 .MEDIA_ROOT,}), url (r '^ static / (? P <path>. *) $', 서브, { 'document_root': settings.STATIC_ROOT}),]
Roberth Solís

6

여러 가지 방법으로 디버깅 할 수 있습니다. 여기 내 접근 방식이 있습니다.

localsettings.py :

DEBUG = False
DEBUG404 = True

urls.py :

from django.conf import settings
import os

if settings.DEBUG404:
    urlpatterns += patterns('',
        (r'^static/(?P<path>.*)$', 'django.views.static.serve',
         {'document_root': os.path.join(os.path.dirname(__file__), 'static')} ),
    )

문서를 읽으십시오.)

https://docs.djangoproject.com/en/2.0/howto/static-files/#limiting-use-to-debug-true


0

url ()에 대한 문자열 뷰 인수 지원은 더 이상 사용되지 않으며 Django 1.10에서 제거됩니다.

내 솔루션은 위의 Conrado 솔루션에 대한 작은 수정입니다.

from django.conf import settings
import os
from django.views.static import serve as staticserve

if settings.DEBUG404:
    urlpatterns += patterns('',
        (r'^static/(?P<path>.*)$', staticserve,
            {'document_root': os.path.join(os.path.dirname(__file__), 'static')} ),
        )

0

가장 안전하지는 않지만 소스 코드에서 변경할 수 있습니다. 로 이동Python/2.7/site-packages/django/conf/urls/static.py

그런 다음 다음과 같이 편집하십시오.

if settings.DEBUG or (prefix and '://' in prefix):

따라서 settings.debug==False코드에 영향을 미치지 않으면 실행 후에도 python manage.py runserver --runserver정적 파일을 실행하십시오.

참고 : 정보는 테스트 목적으로 만 사용해야합니다


0

내 프로젝트 / urls.py를 다음과 같이 변경했는데 나에게 도움이되었습니다.

이 줄 추가 : from django.conf.urls import url

url (r '^ media / (? P. *) $'를 추가하고 urlpatterns에 { 'document_root': settings.MEDIA_ROOT,})를 게재하십시오.

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.