0

I deployed my app on Heroku.

But the images in my static folder won't show up.


In my local environment, here is the screenshot

enter image description here

But on the project, the images fails to load

enter image description here


Here are code in multiple related files.

settings.py

from pathlib import Path
import os


# Build paths inside the project like this: BASE_DIR / 'subdir'.
BASE_DIR = Path(__file__).resolve().parent.parent


# SECURITY WARNING: don't run with debug turned on in production!
DEBUG = True

ALLOWED_HOSTS = []

# Application definition

INSTALLED_APPS = [
    'django.contrib.admin',
    'django.contrib.auth',
    'django.contrib.contenttypes',
    'django.contrib.sessions',
    'django.contrib.messages',
    'django.contrib.staticfiles',

    # additional django
    'django.contrib.sites',
    'django.contrib.sitemaps',

    'article',
    'taggit',
    'crispy_forms',
]

MIDDLEWARE = [
    'django.middleware.security.SecurityMiddleware',
    'whitenoise.middleware.WhiteNoiseMiddleware',
    'django.contrib.sessions.middleware.SessionMiddleware',
    'django.middleware.common.CommonMiddleware',
    'django.middleware.csrf.CsrfViewMiddleware',
    'django.contrib.auth.middleware.AuthenticationMiddleware',
    'django.contrib.messages.middleware.MessageMiddleware',
    'django.middleware.clickjacking.XFrameOptionsMiddleware',
]

ROOT_URLCONF = 'blog.urls'

TEMPLATES = [
    {
        'BACKEND': 'django.template.backends.django.DjangoTemplates',
        'DIRS': [os.path.join(BASE_DIR, 'templates')],
        'APP_DIRS': True,
        'OPTIONS': {
            'context_processors': [
                'django.template.context_processors.debug',
                'django.template.context_processors.request',
                'django.contrib.auth.context_processors.auth',
                'django.contrib.messages.context_processors.messages',
                'article.context_processors.common_context'
            ],
        },
    },
]

WSGI_APPLICATION = 'blog.wsgi.application'

# Password validation
# https://docs.djangoproject.com/en/3.2/ref/settings/#auth-password-validators

AUTH_PASSWORD_VALIDATORS = [
    {
        'NAME': 'django.contrib.auth.password_validation.UserAttributeSimilarityValidator',
    },
    {
        'NAME': 'django.contrib.auth.password_validation.MinimumLengthValidator',
    },
    {
        'NAME': 'django.contrib.auth.password_validation.CommonPasswordValidator',
    },
    {
        'NAME': 'django.contrib.auth.password_validation.NumericPasswordValidator',
    },
]

# Static files (CSS, JavaScript, Images)
# https://docs.djangoproject.com/en/3.2/howto/static-files/

STATIC_URL = '/static/'
STATIC_ROOT = os.path.join(BASE_DIR, 'staticfiles')


MEDIA_URL = '/media/'
MEDIA_ROOT = os.path.join(BASE_DIR, 'media')

# Default primary key field type
# https://docs.djangoproject.com/en/3.2/ref/settings/#default-auto-field

DEFAULT_AUTO_FIELD = 'django.db.models.BigAutoField'

CRISPY_TEMPLATE_PACK = 'bootstrap4'

SITE_ID = 1


if os.environ.get('DJANGO_PRODUCTION'):

    import dj_database_url

    DATABASES = {
        'default': dj_database_url.config(),
    }
    SECRET_KEY = os.environ.get('SECRET_KEY')

    # Allow all host headers.
    ALLOWED_HOSTS = [
        'ycy-blog.herokuapp.com',
        'www.ycyangtw.com',
    ]

    # Turn off DEBUG mode.
    DEBUG = (os.environ.get('DEBUG_VALUE') == 'True')

urls.py

from django.contrib import admin, sitemaps
from django.urls import path
from django.urls.conf import include
from django.contrib.sitemaps.views import sitemap
from django.conf.urls.static import static
from django.conf import settings
from article.sitemaps import PostSitemap

sitemaps = {
    'posts': PostSitemap,
}


urlpatterns = [
    path('admin_page/', admin.site.urls),
    path('', include('article.urls', namespace='article')),


    path(
        'sitemap.xml', sitemap, {'sitemaps': sitemaps},
        name='django.contrib.sitemaps.views.sitemap'
    ),
] + static(settings.STATIC_URL, document_root=settings.STATIC_ROOT) \
    + static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)

test_static.html

{% load static %}
<!DOCTYPE html>
<html lang="en">
<head>
    <meta charset="UTF-8">
    <meta http-equiv="X-UA-Compatible" content="IE=edge">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
</head>
<body>
    <h1>
        hello
    </h1>
    <img src="{% static 'article/cover/fed-fund-rate_cover.jpg' %}">
</body>
</html>

I have been through lots of similar questions on stackoverflow,

but still can not solve

What is exactly happend?

thanks for help

Yang
  • 218
  • 3
  • 9
  • 1
    Did you create `collectstaticfiles` and configured collectstatic files in `settings.py`? – mhhabib Aug 14 '21 at 10:11
  • Hi, mhhabib. Do you mean `STATIC_ROOT` or something else? `STATIC_ROOT` is in `settings.py` already. – Yang Aug 14 '21 at 10:29
  • Before deploying to Heroku your static file should be collected like to staticfiles `python manage.py collectstatic` – mhhabib Aug 14 '21 at 10:31
  • Just tried `python manage.py collectstatic` and push again, still doesn't work :( . Tks – Yang Aug 14 '21 at 10:37

4 Answers4

0

Have you collected the static files?

Try running:

heroku run python manage.py collectstatic --dry-run --noinput
Marmik Patel
  • 21
  • 1
  • 4
  • 1
    Hi Marmik. Just tried, but still doesn't work. Tks. – Yang Aug 14 '21 at 10:34
  • Points need to be check, install whitenoise, configure STATIC_ROOT correctly, and don't forget to add middleware `'whitenoise.middleware.WhiteNoiseMiddleware'`, Thank you. – Marmik Patel Aug 14 '21 at 11:15
  • Install whitelnoise, configure `STATIC_ROOT` and add middleware were all done, btw, `STATIC_ROOT = os.path.join(BASE_DIR, 'staticfiles')` is correct for heroku right? – Yang Aug 14 '21 at 11:31
  • actually there is some cache. try checking this [feed](https://stackoverflow.com/questions/21141315/django-static-files-on-heroku) – Marmik Patel Aug 14 '21 at 11:38
  • tks, I am sure the images have been uploaded successfully, it shows message during push to Heroku. Or do you think I set the wrong path? – Yang Aug 14 '21 at 12:27
0

in your urls.py use this

urlpatterns += static(settings.STATIC_URL, document_root = settings.STATIC_ROOT)
urlpatterns += static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT)

instead of

+ static(settings.STATIC_URL, document_root=settings.STATIC_ROOT) \
    + static(settings.MEDIA_URL, document_root=settings.MEDIA_ROOT) 

then run py manage.py collectstatic and then push to heroku master

Shreyash mishra
  • 738
  • 1
  • 7
  • 30
  • Hi, Shreyash. I tried both earlier. They showed the same result. The problem has been solved. Tks. – Yang Aug 14 '21 at 13:39
0

Brief Summary.

Due to the name of the folder of images is contained in .gitignore file which is cover and I didn't notice that. Those files were not been upload actually.

I use heroku run bash to check my project structure then find out the cover folder won't show up in any way. Then I check .gitignore to figure out what exactly happened.

Tks everyone.

Yang
  • 218
  • 3
  • 9
0

Another idea is to add STATICFILES_DIRS = [BASE_DIR / "static"] to your settings.py