瀏覽代碼

add settings manager - split up settings and aggregate them using split_settings package

Mohammed Khan 1 年之前
父節點
當前提交
dbe7ac2f21

+ 4 - 4
backend/UnTube/asgi.py

@@ -8,14 +8,14 @@ https://docs.djangoproject.com/en/3.2/howto/deployment/asgi/
 """
 
 import os
-from dotenv import load_dotenv
+# from dotenv import load_dotenv
 from django.core.asgi import get_asgi_application
 
-settings_module = "UnTube.production" if 'UNTUBE' in os.environ else 'UnTube.settings'
+settings_module = 'backend.UnTube.settings'
 os.environ.setdefault('DJANGO_SETTINGS_MODULE', settings_module)
 
 # to use env variables on pythonanywhere
-project_folder = os.path.expanduser('/home/bakaabu')
-load_dotenv(os.path.join(project_folder, '.env'))
+# project_folder = os.path.expanduser('/home/bakaabu')
+# load_dotenv(os.path.join(project_folder, '.env'))
 
 application = get_asgi_application()

+ 0 - 50
backend/UnTube/production.py

@@ -1,50 +0,0 @@
-from .settings import *
-import os
-
-SECRET_KEY = os.environ['SECRET_KEY']
-YOUTUBE_V3_API_KEY = os.environ['YOUTUBE_V3_API_KEY']
-
-# configure the domain name using the environment variable found on pythonanywhere
-ALLOWED_HOSTS = ['bakaabu.pythonanywhere.com', '127.0.0.1', 'untube.it'] if 'UNTUBE' in os.environ else ['bakaabu.pythonanywhere.com', 'untube.it']
-SITE_ID = 10
-
-DEBUG = False
-CSRF_COOKIE_SECURE = True
-SESSION_COOKIE_SECURE = True
-SECURE_SSL_REDIRECT = True
-
-# WhiteNoise configuration
-MIDDLEWARE = [
-    'django.middleware.security.SecurityMiddleware',
-    # Add whitenoise middleware after the security middleware
-    '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',
-]
-
-STATICFILES_STORAGE = 'whitenoise.storage.CompressedManifestStaticFilesStorage'
-STATIC_ROOT = os.path.join(BASE_DIR, 'staticfiles')
-
-# DBHOST is only the server name
-hostname = os.environ['DBHOST']
-
-# Configure MySQL database on pythonanywhere
-# See https://django-mysql.readthedocs.io/en/latest/checks.html for options
-DATABASES = {
-    'default': {
-        'ENGINE': 'django.db.backends.mysql',
-        'NAME': f'{os.environ["DBUSER"]}${os.environ["DBNAME"]}',
-        'USER': f'{os.environ["DBUSER"]}',
-        'PASSWORD': f'{os.environ["DBPASS"]}',
-        'HOST': hostname,
-        'OPTIONS': {
-            'init_command': "SET sql_mode='STRICT_TRANS_TABLES', innodb_strict_mode=1",
-            'charset': 'utf8mb4',
-            "autocommit": True,
-        }
-    }
-}

+ 33 - 0
backend/UnTube/settings/__init__.py

@@ -0,0 +1,33 @@
+import os.path
+from pathlib import Path
+from split_settings.tools import include, optional
+
+# Build paths inside the project like this: BASE_DIR / 'subdir'.
+BASE_DIR = Path(__file__).resolve().parent.parent.parent.parent
+# BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
+
+# Namespacing our own custom environment variables
+ENVVAR_SETTINGS_PREFIX = 'UNTUBE_SETTINGS_'
+
+LOCAL_SETTINGS_PATH = os.getenv(f'{ENVVAR_SETTINGS_PREFIX}LOCAL_SETTINGS_PATH')
+
+# if local settings not specified in the environment
+if not LOCAL_SETTINGS_PATH:  # default to development mode - use local dev settings
+    LOCAL_SETTINGS_PATH = 'local/settings.dev.py'
+
+if not os.path.isabs(LOCAL_SETTINGS_PATH):
+    LOCAL_SETTINGS_PATH = str(BASE_DIR / LOCAL_SETTINGS_PATH)
+
+include(
+    'base.py',
+    # 'logging.py',
+    # 'rest_framework.py',
+    # 'channels.py',
+    # 'aws.py',
+    'custom.py',
+    optional(LOCAL_SETTINGS_PATH),  # `optional` means the file may or may not exist - it is fine if it does not
+    'envvars.py',
+    'docker.py',
+    'pythonanywhere.py',
+)
+

+ 5 - 16
backend/UnTube/settings.py → backend/UnTube/settings/base.py

@@ -10,24 +10,14 @@ For the full list of settings and their values, see
 https://docs.djangoproject.com/en/3.2/ref/settings/
 """
 import os
-from pathlib import Path
 from backend.UnTube.secrets import SECRETS
+from backend.UnTube.settings import BASE_DIR
 
-# Build paths inside the project like this: BASE_DIR / 'subdir'.
+DEBUG = False
+SECRET_KEY = NotImplemented
 
-# PROJECT_ROOT = os.path.dirname(os.path.abspath(__file__))
-BASE_DIR = Path(__file__).resolve().parent.parent.parent
-# BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
-
-# Quick-start development settings - unsuitable for production
-# See https://docs.djangoproject.com/en/3.2/howto/deployment/checklist/
-
-# SECURITY WARNING: keep the secret key used in production secret!
-SECRET_KEY = SECRETS['SECRET_KEY']
 YOUTUBE_V3_API_KEY = SECRETS['YOUTUBE_V3_API_KEY']
 
-# SECURITY WARNING: don't run with debug turned on in production!
-DEBUG = True
 
 ALLOWED_HOSTS = ['127.0.0.1']
 
@@ -66,11 +56,10 @@ MIDDLEWARE = [
     'django.contrib.auth.middleware.AuthenticationMiddleware',
     'django.contrib.messages.middleware.MessageMiddleware',
     'django.middleware.clickjacking.XFrameOptionsMiddleware',
-
 ]
 
 ROOT_URLCONF = 'backend.UnTube.urls'  # path to the urls.py file in root UnTube app folder
-print(BASE_DIR)
+
 TEMPLATES = [
     {
         'BACKEND': 'django.template.backends.django.DjangoTemplates',
@@ -171,4 +160,4 @@ STATIC_ROOT = os.path.join(BASE_DIR, 'static')
 DEFAULT_AUTO_FIELD = 'django.db.models.BigAutoField'
 
 MEDIA_URL = '/media/'
-MEDIA_ROOT = Path(BASE_DIR / 'media')
+MEDIA_ROOT = os.path.join(BASE_DIR / 'media')

+ 8 - 0
backend/UnTube/settings/custom.py

@@ -0,0 +1,8 @@
+"""
+Settings specific to this application only (no Django or third party settings)
+"""
+
+IN_PYTHONANYWHERE = False  # PA has PYTHONANYWHERE_SITE in its env
+IN_DOCKER = False
+STOKEN_EXPIRATION_SECONDS = 10
+USE_ON_COMMIT_HOOK = True

+ 11 - 0
backend/UnTube/settings/docker.py

@@ -0,0 +1,11 @@
+import os
+
+if IN_DOCKER or os.path.isfile('/.dockerenv'):  # type: ignore # noqa: F821
+    print("IN DOCKER")
+    # We need it to serve static files with DEBUG=False
+    assert MIDDLEWARE[:1] == [  # type: ignore # noqa: F821
+        'django.middleware.security.SecurityMiddleware'
+    ]
+    MIDDLEWARE.insert(1, 'whitenoise.middleware.WhiteNoiseMiddleware')  # type: ignore # noqa: F821
+    DEFAULT_FILE_STORAGE = 'storages.backends.s3boto3.S3Boto3Storage'
+    STATICFILES_STORAGE = 'storages.backends.s3boto3.S3Boto3Storage'

+ 14 - 0
backend/UnTube/settings/envvars.py

@@ -0,0 +1,14 @@
+from backend.general.utils.collections import deep_update
+from backend.general.utils.settings import get_settings_from_environment
+
+"""
+This takes env variables with a matching prefix (set by you), strips out the prefix, and adds it to globals
+
+Eg. 
+export UNTUBE_SETTINGs_IN_DOCKER=true (environment variable)
+
+could be then referenced in the globals() dictionary as
+IN_DOCKER (where the value will be set to Pythonic True)
+"""
+# globals() is a dictionary of global variables
+deep_update(globals(), get_settings_from_environment(ENVVAR_SETTINGS_PREFIX))  # type: ignore

+ 46 - 0
backend/UnTube/settings/pythonanywhere.py

@@ -0,0 +1,46 @@
+if IN_PYTHONANYWHERE:  # type: ignore
+    # to use env variables on pythonanywhere
+    # from dotenv import load_dotenv
+    # project_folder = os.path.expanduser('/home/bakaabu')
+    # load_dotenv(os.path.join(project_folder, '.env'))
+
+    SECRET_KEY = os.environ['SECRET_KEY']  # type: ignore
+    YOUTUBE_V3_API_KEY = os.environ['YOUTUBE_V3_API_KEY']   # type: ignore
+
+    # WhiteNoise configuration
+    assert MIDDLEWARE[:1] == [  # type: ignore # noqa: F821
+        'django.middleware.security.SecurityMiddleware'
+    ] and not IN_DOCKER  # type: ignore # PA does not support dockerized apps
+    # Add whitenoise middleware after the security middleware
+    MIDDLEWARE.insert(1, 'whitenoise.middleware.WhiteNoiseMiddleware')  # type: ignore # noqa: F821
+
+    # configure the domain name using the environment variable found on pythonanywhere
+    ALLOWED_HOSTS = ['bakaabu.pythonanywhere.com', '127.0.0.1', 'untube.it']
+    SITE_ID = 10
+
+    CSRF_COOKIE_SECURE = True
+    SESSION_COOKIE_SECURE = True
+    SECURE_SSL_REDIRECT = True
+
+    STATICFILES_STORAGE = 'whitenoise.storage.CompressedManifestStaticFilesStorage'
+    STATIC_ROOT = os.path.join(BASE_DIR, 'staticfiles')  # type: ignore
+
+    # DBHOST is only the server name
+    hostname = os.environ['DBHOST']  # type: ignore
+
+    # Configure MySQL database on pythonanywhere
+    # See https://django-mysql.readthedocs.io/en/latest/checks.html for options
+    DATABASES = {
+        'default': {
+            'ENGINE': 'django.db.backends.mysql',
+            'NAME': f'{os.environ["DBUSER"]}${os.environ["DBNAME"]}',  # type: ignore
+            'USER': f'{os.environ["DBUSER"]}',  # type: ignore
+            'PASSWORD': f'{os.environ["DBPASS"]}',  # type: ignore
+            'HOST': hostname,
+            'OPTIONS': {
+                'init_command': "SET sql_mode='STRICT_TRANS_TABLES', innodb_strict_mode=1",
+                'charset': 'utf8mb4',
+                "autocommit": True,
+            }
+        }
+    }

+ 2 - 0
backend/UnTube/settings/templates/settings.dev.py

@@ -0,0 +1,2 @@
+DEBUG = True
+SECRET_KEY = "django-insecure-ycs22y+20sq67y(6dm6ynqw=dlhg!)%vuqpd@$p6rf3!#1h$u="

+ 1 - 1
backend/UnTube/wsgi.py

@@ -10,7 +10,7 @@ https://docs.djangoproject.com/en/3.2/howto/deployment/wsgi/
 import os
 from django.core.wsgi import get_wsgi_application
 
-settings_module = "UnTube.production" if 'UNTUBE' in os.environ else 'UnTube.settings'
+settings_module = 'backend.UnTube.settings'
 os.environ.setdefault('DJANGO_SETTINGS_MODULE', settings_module)
 
 # to use env variables on pythonanywhere

+ 1 - 1
backend/manage.py

@@ -6,7 +6,7 @@ import sys
 
 def main():
     """Run administrative tasks."""
-    settings_module = "backend.UnTube.production" if 'PYTHONANYWHERE_SITE' in os.environ else 'backend.UnTube.settings'
+    settings_module = 'backend.UnTube.settings'
     os.environ.setdefault('DJANGO_SETTINGS_MODULE', settings_module)
     try:
         from django.core.management import execute_from_command_line