Django + Heroku + S3: boto -> локальная переменная "region_name", на которую ссылается перед присваиванием
Я получаю очень странную ошибку, из-за которой я действительно застрял на многие часы.
Я впервые выполнил развертывание с Heroku и использую S3 для файлов мультимедиа. Первое, что я заметил, было то, что у меня никогда не было успешной миграции после установки boto и django-storages-redux, не знаю почему. Во всяком случае, я продолжал идти.
Кажется, мои конфигурации работали в AWS, так как мои статические файлы вошли в мое ведро в первый раз, когда я попробовал это сделать, но я получил некоторые img-файлы, не поступающие, поэтому я решил переустановить boto и django-registration-redux (чтобы посмотреть, это будет мигрировать правильно).
В конце концов, он никогда не переносился, как ожидалось, и теперь я получаю следующую ошибку:
UnboundLocalError: local variable 'region_name' referenced before assignment
в моем пакете БОТО, когда коллекторный.
Я не понимаю, почему миграция не работает и почему я начал получать эту ошибку, когда переустанавливал boto и django-storages-redux.
Терминал:
You have requested to collect static files at the destination
location as specified in your settings.
This will overwrite existing files!
Are you sure you want to do this?
Type 'yes' to continue, or 'no' to cancel: yes
Traceback (most recent call last):
File "/Users/Alex/Desktop/Allugare/src/manage.py", line 22, in <module>
execute_from_command_line(sys.argv)
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/django/core/management/__init__.py", line 367, in execute_from_command_line
utility.execute()
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/django/core/management/__init__.py", line 359, in execute
self.fetch_command(subcommand).run_from_argv(self.argv)
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/django/core/management/base.py", line 294, in run_from_argv
self.execute(*args, **cmd_options)
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/django/core/management/base.py", line 345, in execute
output = self.handle(*args, **options)
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/django/contrib/staticfiles/management/commands/collectstatic.py", line 193, in handle
collected = self.collect()
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/django/contrib/staticfiles/management/commands/collectstatic.py", line 124, in collect
handler(path, prefixed_path, storage)
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/django/contrib/staticfiles/management/commands/collectstatic.py", line 349, in copy_file
if not self.delete_file(path, prefixed_path, source_storage):
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/django/contrib/staticfiles/management/commands/collectstatic.py", line 255, in delete_file
if self.storage.exists(prefixed_path):
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/storages/backends/s3boto.py", line 439, in exists
if self.entries:
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/storages/backends/s3boto.py", line 302, in entries
for entry in self.bucket.list(prefix=self.location))
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/storages/backends/s3boto.py", line 301, in <genexpr>
self._entries = dict((self._decode_name(entry.key), entry)
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/boto/s3/bucketlistresultset.py", line 34, in bucket_lister
encoding_type=encoding_type)
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/boto/s3/bucket.py", line 473, in get_all_keys
'', headers, **params)
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/boto/s3/bucket.py", line 399, in _get_all
query_args=query_args)
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/boto/s3/connection.py", line 668, in make_request
retry_handler=retry_handler
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/boto/connection.py", line 1071, in make_request
retry_handler=retry_handler)
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/boto/connection.py", line 927, in _mexe
request.authorize(connection=self)
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/boto/connection.py", line 377, in authorize
connection._auth_handler.add_auth(self, **kwargs)
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/boto/auth.py", line 755, in add_auth
**kwargs)
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/boto/auth.py", line 574, in add_auth
string_to_sign = self.string_to_sign(req, canonical_request)
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/boto/auth.py", line 514, in string_to_sign
sts.append(self.credential_scope(http_request))
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/boto/auth.py", line 496, in credential_scope
region_name = self.determine_region_name(http_request.host)
File "/Users/Alex/Desktop/allugare/lib/python3.5/site-packages/boto/auth.py", line 690, in determine_region_name
return region_name
UnboundLocalError: local variable 'region_name' referenced before assignment
settings.py:
...
INSTALLED_APPS = (
#DJANGO APPS
'django.contrib.admin',
'django.contrib.auth',
'django.contrib.contenttypes',
'django.contrib.sessions',
'django.contrib.sites',
'django.contrib.messages',
'django.contrib.staticfiles',
#THIRD PARTY APPS
'allauth',
'allauth.account',
'allauth.socialaccount',
#Social Authentications
'allauth.socialaccount.providers.facebook',
# 'allauth.socialaccount.providers.instagram',
# 'allauth.socialaccount.providers.twitter',
'crispy_forms',
'django_messages',
'storages',
#MY APPS
'lares',
'mensagens',
'profiles',
)
...
STATIC_URL = '/static/'
STATIC_ROOT = os.path.join(BASE_DIR, "static-live", "static")
MEDIA_URL = '/media/'
MEDIA_ROOT = os.path.join(BASE_DIR, "static-live", "media")
STATICFILES_DIRS = (
os.path.join(BASE_DIR, "static"),
)
AWS_ACCESS_KEY_ID = "***"
AWS_SECRET_ACCESS_KEY = "***"
AWS_FILE_EXPIRE = 200
AWS_PRELOAD_METADATA = True
AWS_QUERYSTRING_AUTH = True
DEFAULT_FILE_STORAGE = 'allugare.utils.MediaRootS3BotoStorage'
STATICFILES_STORAGE = 'allugare.utils.StaticRootS3BotoStorage'
# DEFAULT_FILE_STORAGE = 'storages.backends.s3boto3.S3Boto3Storage'
# STATICFILES_STORAGE = 'storages.backends.s3boto3.S3Boto3Storage'
AWS_STORAGE_BUCKET_NAME = 's3allugare'
S3DIRECT_REGION = 'sa-east-1'
S3_URL = '//%s.s3.amazonaws.com/' % AWS_STORAGE_BUCKET_NAME
MEDIA_URL = '//%s.s3.amazonaws.com/media/' % AWS_STORAGE_BUCKET_NAME
MEDIA_ROOT = MEDIA_URL
STATIC_URL = S3_URL + 'static/'
ADMIN_MEDIA_PREFIX = STATIC_URL + 'admin/'
AWS_S3_HOST = 'sa-east-1.amazonaws.com'
import datetime
two_months = datetime.timedelta(days=61)
date_two_months_later = datetime.date.today() + two_months
expires = date_two_months_later.strftime("%A, %d %B %Y 20:00:00 GMT")
AWS_HEADERS = {
'Expires': expires,
'Cache-Control': 'max-age=%d' % (int(two_months.total_seconds()), ),
}
wsgi.py
"""
WSGI config for allugare project.
It exposes the WSGI callable as a module-level variable named ``application``.
For more information on this file, see
https://docs.djangoproject.com/en/1.10/howto/deployment/wsgi/
"""
import os
from django.core.wsgi import get_wsgi_application
os.environ.setdefault("DJANGO_SETTINGS_MODULE", "allugare.settings")
application = get_wsgi_application()
utils.py
from storages.backends.s3boto import S3BotoStorage
StaticRootS3BotoStorage = lambda: S3BotoStorage(location='static') # S3 bucket name -> static
MediaRootS3BotoStorage = lambda: S3BotoStorage(location='media') # S3 bucket name -> static
1 ответ
Хорошо, вот в чем дело, если вы не используете регион AWS по умолчанию, вы должны быть осторожны при обновлении своего региона, поскольку S3 имеет разные форматы в зависимости от региона.
Я в Южной Америке, поэтому я использую sa-east-1 (для Сан-Паулу).
Для меня это сработало, когда я изменил настройку: AWS_S3_HOST = 'sa-east-1.amazonaws.com' на AWS_S3_HOST = 's3-sa-east-1.amazonaws.com'
Наслаждайтесь!