production-taskbar / backend / config / settings / common.py
common.py
Raw
from os import environ, path

import pymysql
from django.utils.translation import gettext_lazy as _

# Fake PyMySQL's version and install as MySQLdb
pymysql.version_info = (1, 4, 3, "final", 0)
pymysql.install_as_MySQLdb()

# Build paths inside the project like this: BASE_DIR / 'subdir'.
BASE_DIR = path.abspath(path.join(path.dirname(__file__), "../", "../"))
PROJECT_ROOT = path.abspath(path.dirname(__file__))
SECRET_KEY = environ.get("SECRET_KEY", 'DUMMY_KEY')
ALLOWED_HOSTS = ["*"]

# region LDAP
AUTHENTICATION_BACKENDS = [
    "django_python3_ldap.auth.LDAPBackend",
    "django.contrib.auth.backends.ModelBackend",
]
LDAP_AUTH_URL = [
    f'ldap://{environ.get("LDAP_HOST")}:{environ.get("LDAP_PORT")}'
]
LDAP_AUTH_USER_FIELDS = {
    "username": "samAccountName",
    "first_name": "givenName",
    "last_name": "sn",
    "email": "mail",
}
LDAP_AUTH_ACTIVE_DIRECTORY_DOMAIN = environ.get("LDAP_DOMAIN")
LDAP_AUTH_CLEAN_USER_DATA = "django_python3_ldap.utils.clean_user_data"
LDAP_AUTH_CONNECTION_PASSWORD = environ.get("LDAP_PASSWORD")
LDAP_AUTH_CONNECTION_USERNAME = environ.get("LDAP_USERNAME")
LDAP_AUTH_FORMAT_SEARCH_FILTERS = "django_python3_ldap.utils.format_search_filters"
LDAP_AUTH_FORMAT_USERNAME = "django_python3_ldap.utils.format_username_active_directory_principal"
LDAP_AUTH_OBJECT_CLASS = "user"
LDAP_AUTH_SEARCH_BASE = environ.get("LDAP_BASE")
LDAP_AUTH_SYNC_USER_RELATIONS = "config.utils.ldap.sync_user_relations"
LDAP_AUTH_USE_TLS = False
LDAP_AUTH_USER_LOOKUP_FIELDS = ("username", )
# endregion

CORE_APPS = [
    "daphne",
]

COMMON_APPS = [
    "django.contrib.contenttypes",
    "grappelli.dashboard",
    "grappelli",
    "filebrowser",
    "django.contrib.admin",
    "django.contrib.auth",
    "django.contrib.sessions",
    "django.contrib.messages",
    "django.contrib.staticfiles",
    "corsheaders",
]

THIRD_PARTY_APPS = [
    'channels',
    'django_python3_ldap',
    'simple_history',
    'rest_framework',
    'rest_framework_api_key',
    'django_json_widget',
    'colorfield',
    'django_celery_results',
    'django_celery_beat',
    'ckeditor',
    'ckeditor_uploader',
    'import_export',
]

INSTALLED_APPS = (CORE_APPS + COMMON_APPS + THIRD_PARTY_APPS + [
    "config",
    "taskbar",
    "links",
    "helpdesk",
    "informing",
    "tgbot",
])

MIDDLEWARE = [
    'corsheaders.middleware.CorsMiddleware',
    'django.middleware.security.SecurityMiddleware',
    'django.middleware.cache.UpdateCacheMiddleware',
    'django.contrib.sessions.middleware.SessionMiddleware',
    'django.middleware.locale.LocaleMiddleware',
    'django.middleware.common.CommonMiddleware',
    'django.middleware.csrf.CsrfViewMiddleware',
    'django.middleware.cache.FetchFromCacheMiddleware',
    'simple_history.middleware.HistoryRequestMiddleware',
    'django.contrib.auth.middleware.AuthenticationMiddleware',
    'django.contrib.messages.middleware.MessageMiddleware',
    'django.middleware.clickjacking.XFrameOptionsMiddleware',
    'config.middleware.FilebrowserAccess'
]

ROOT_URLCONF = 'config.urls'

TEMPLATES = [
    {
        'BACKEND': 'django.template.backends.django.DjangoTemplates',
        "DIRS": [
            path.join(BASE_DIR, "templates").replace("\\", "/"),
        ],
        'APP_DIRS': True,
        'OPTIONS': {
            'context_processors': [
                'django.template.context_processors.debug',
                'django.template.context_processors.request',
                'django.contrib.auth.context_processors.auth',
                'django.template.context_processors.i18n',
                'django.contrib.messages.context_processors.messages',
            ],
        },
    },
]

WSGI_APPLICATION = 'config.wsgi.application'
ASGI_APPLICATION = "config.asgi.application"

STATICFILES_FINDERS = [
    "django.contrib.staticfiles.finders.FileSystemFinder",
    "django.contrib.staticfiles.finders.AppDirectoriesFinder",
]

# Database

DATABASES = {
    "default": {
        "ENGINE": "django.db.backends.mysql",
        "NAME": environ.get("MYSQL_DATABASE"),
        "USER": environ.get("MYSQL_USER"),
        "PASSWORD": environ.get("MYSQL_PASSWORD"),
        "HOST": environ.get("MYSQL_HOST"),
        "PORT": environ.get("MYSQL_PORT"),
    },
}

# Caching
CACHES = {
    'default': {
        'BACKEND': 'django.core.cache.backends.redis.RedisCache',
        'LOCATION': 'redis://redis:6379/1',
        'KEY_PREFIX': 'dcache'
    }
}

# 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',
    },
]

# Internationalization
# https://docs.djangoproject.com/en/3.2/topics/i18n/

LANGUAGE_CODE = "uk-ua"
TIME_ZONE = environ.get("TZ")
USE_I18N = True
USE_L10N = True
USE_TZ = True
LANGUAGES = [
    ('uk-ua', _('Ukrainian')),
]
LOCALE_PATHS = (
    path.join(BASE_DIR, 'config/locale'),
    path.join(BASE_DIR, 'informing/locale'),
)

GRAPPELLI_ADMIN_TITLE = _('SEBN Taskbar Manager administration')
GRAPPELLI_INDEX_DASHBOARD = 'config.admin_dashboard.AdminDashboard'
DEFAULT_AUTO_FIELD = 'django.db.models.BigAutoField'

# Celery
IMPORT_EXPORT_CELERY_INIT_MODULE = "sebn-taskbar-manager.celery"
CELERY_BROKER_URL = environ.get("CELERY_BROKER", "redis://redis:6379/0")
CELERY_RESULT_BACKEND = 'django-db'
CELERY_BEAT_SCHEDULER = 'django_celery_beat.schedulers:DatabaseScheduler'
CELERY_TIMEZONE = 'UTC'    #! Doesn`t use any local TZ because tasks start execute every millisecond
CELERY_ENABLE_UTC = True

CHANNEL_LAYERS = {
    'default': {
        'BACKEND': 'channels_redis.core.RedisChannelLayer',
        'CONFIG': {
            'hosts': [
                ('redis', 6379),
            ],
        },
    },
}

# CKEditor widget configuration
CKEDITOR_BROWSE_SHOW_DIRS = True
CKEDITOR_RESTRICT_BY_USER = False
CKEDITOR_RESTRICT_BY_DATE = False
CKEDITOR_UPLOAD_PATH = 'uploads/'
CKEDITOR_CONFIGS = {
    'default': {
        'toolbar': 'full',
        'height': 300,
        'width': 800,
    },
    'informing-content': {
        'toolbar': 'full',
        'height': 300,
        'width': '80vw',
        'uiColor': '#9AB8F3',
        'autoGrow_onStartup': True,
        'autoGrow_maxHeight': 1000,
        'extraPlugins': ','.join([
            'html5video',
            'html5audio',
            'video',
            'preview',
            'docfont',
            'autogrow',
            'clipboard',
            'lineutils',
        ]),
        'removePlugins': ','.join([
            'exportpdf',
            'smiley',
            'language',
        ]),
        'fullPage': True,
    },
}

# Django filebrowser settings
FILEBROWSER_MAX_UPLOAD_SIZE = 500 * 1024 * 1024    # 500mb
FILEBROWSER_DIRECTORY = ''
FILEBROWSER_NORMALIZE_FILENAME = True
FILEBROWSER_CONVERT_FILENAME = True
FILEBROWSER_EXTENSIONS = {
    'Image': ['.jpg', '.jpeg', '.gif', '.png', '.tif', '.tiff'],
    'Document': ['.pdf', '.doc', '.rtf', '.txt', '.xls', '.csv', '.pptx'],
    'Video': ['.mov', '.wmv', '.mpeg', '.mpg', '.avi', '.rm'],
    'Audio': [
        '.mp3', '.mp4', '.wav', '.aiff', '.midi', '.m4p', '.webm', '.mov'
    ],
    'Archive': ['.zip', '.rar', '.7z'],
}
FILEBROWSER_SELECT_FORMATS = {
    'file': ['Image', 'Document', 'Video', 'Audio', 'Archive'],
    'image': ['Image'],
    'document': ['Document'],
    'media': ['Video', 'Audio'],
}

# Django admin customization
LIST_PER_PAGE = 20