forked from rc/aircox
- !88 pytest on existing tests - !89 reorganise settings (! see notes for deployment) Co-authored-by: bkfox <thomas bkfox net> Reviewed-on: rc/aircox#92
This commit is contained in:
180
aircox/conf.py
Executable file
180
aircox/conf.py
Executable file
@ -0,0 +1,180 @@
|
||||
import os
|
||||
|
||||
import inspect
|
||||
|
||||
from django.conf import settings as d_settings
|
||||
|
||||
|
||||
__all__ = ("Settings", "settings")
|
||||
|
||||
|
||||
# code from django-fox
|
||||
class BaseSettings:
|
||||
"""Utility class used to load and save settings, can be used as model.
|
||||
|
||||
Some members are excluded from being configuration:
|
||||
- Protected/private members;
|
||||
- On django model, "objects" and "Meta";
|
||||
- Class declaration and callables
|
||||
|
||||
Example:
|
||||
|
||||
```
|
||||
class MySettings(Settings):
|
||||
a = 13
|
||||
b = 12
|
||||
|
||||
my_settings = MySettings().load('MY_SETTINGS_KEY')
|
||||
print(my_settings.a, my_settings.get('b'))
|
||||
```
|
||||
|
||||
This will load values from django project settings.
|
||||
"""
|
||||
|
||||
def __init__(self, key, module=None):
|
||||
self.load(key, module)
|
||||
|
||||
def load(self, key, module=None):
|
||||
"""Load settings from module's item specified by its member name. When
|
||||
no module is provided, uses ``django.conf.settings``.
|
||||
|
||||
:param str key: module member name.
|
||||
:param module: configuration object.
|
||||
:returns self
|
||||
"""
|
||||
if module is None:
|
||||
module = d_settings
|
||||
settings = getattr(module, key, None)
|
||||
if settings:
|
||||
self.update(settings)
|
||||
return self
|
||||
|
||||
def update(self, settings):
|
||||
"""Update self's values from provided settings. ``settings`` can be an
|
||||
iterable of ``(key, value)``.
|
||||
|
||||
:param dict|Settings|iterable settings: value to update from.
|
||||
"""
|
||||
if isinstance(settings, (dict, Settings)):
|
||||
settings = settings.items()
|
||||
for key, value in settings:
|
||||
if self.is_config_item(key, value):
|
||||
setattr(self, key, value)
|
||||
|
||||
def get(self, key, default=None):
|
||||
"""Return settings' value for provided key."""
|
||||
return getattr(self, key, default)
|
||||
|
||||
def items(self):
|
||||
"""Iterate over items members, as tupple of ``key, value``."""
|
||||
for key in dir(self):
|
||||
value = getattr(self, key)
|
||||
if self.is_config_item(key, value):
|
||||
yield key, value
|
||||
|
||||
def is_config_item(self, key, value):
|
||||
"""Return True if key/value item is a configuration setting."""
|
||||
if key.startswith("_") or callable(value) or inspect.isclass(value):
|
||||
return False
|
||||
return True
|
||||
|
||||
|
||||
class Settings(BaseSettings):
|
||||
# --- Global & misc
|
||||
DEFAULT_USER_GROUPS = {
|
||||
"radio hosts": (
|
||||
# TODO include content_type in order to avoid clash with potential
|
||||
# extra applications
|
||||
# aircox
|
||||
"change_program",
|
||||
"change_episode",
|
||||
"change_diffusion",
|
||||
"add_comment",
|
||||
"change_comment",
|
||||
"delete_comment",
|
||||
"add_article",
|
||||
"change_article",
|
||||
"delete_article",
|
||||
"change_sound",
|
||||
"add_track",
|
||||
"change_track",
|
||||
"delete_track",
|
||||
# taggit
|
||||
"add_tag",
|
||||
"change_tag",
|
||||
"delete_tag",
|
||||
# filer
|
||||
"add_folder",
|
||||
"change_folder",
|
||||
"delete_folder",
|
||||
"can_use_directory_listing",
|
||||
"add_image",
|
||||
"change_image",
|
||||
"delete_image",
|
||||
),
|
||||
}
|
||||
"""Groups to assign to users at their creation, along with the permissions
|
||||
to add to each group."""
|
||||
PROGRAMS_DIR = "programs"
|
||||
"""Directory for the programs data."""
|
||||
|
||||
@property
|
||||
def PROGRAMS_DIR_ABS(self):
|
||||
return os.path.join(d_settings.MEDIA_ROOT, self.PROGRAMS_DIR)
|
||||
|
||||
# --- Programs & episodes
|
||||
EPISODE_TITLE = "{program.title} - {date}"
|
||||
"""Default title for episodes."""
|
||||
EPISODE_TITLE_DATE_FORMAT = "%-d %B %Y"
|
||||
"""Date format in episode title (python's strftime)"""
|
||||
|
||||
# --- Logs & archives
|
||||
LOGS_ARCHIVES_DIR = "logs/archives"
|
||||
"""Directory where to save logs' archives."""
|
||||
|
||||
@property
|
||||
def LOGS_ARCHIVES_DIR_ABS(self):
|
||||
return os.path.join(d_settings.PROJECT_ROOT, self.LOGS_ARCHIVES_DIR)
|
||||
|
||||
LOGS_ARCHIVES_AGE = 60
|
||||
"""In days, minimal age of a log before it is archived."""
|
||||
|
||||
# --- Sounds
|
||||
SOUND_ARCHIVES_SUBDIR = "archives"
|
||||
"""Sub directory used for the complete episode sounds."""
|
||||
SOUND_EXCERPTS_SUBDIR = "excerpts"
|
||||
"""Sub directory used for the excerpts of the episode."""
|
||||
SOUND_QUALITY = {
|
||||
"attribute": "RMS lev dB",
|
||||
"range": (-18.0, -8.0),
|
||||
"sample_length": 120,
|
||||
}
|
||||
"""Quality attributes passed to sound_quality_check from sounds_monitor
|
||||
(Soxi parameters)."""
|
||||
SOUND_FILE_EXT = (".ogg", ".flac", ".wav", ".mp3", ".opus")
|
||||
"""Extension of sound files."""
|
||||
SOUND_KEEP_DELETED = False
|
||||
"""Tag sounds as deleted instead of deleting them when file has been
|
||||
removed from filesystem (sound monitoring)."""
|
||||
|
||||
# --- Streamer & Controllers
|
||||
CONTROLLERS_WORKING_DIR = "/tmp/aircox"
|
||||
"""Controllers working directory."""
|
||||
|
||||
# --- Playlist import from CSV
|
||||
IMPORT_PLAYLIST_CSV_COLS = (
|
||||
"artist",
|
||||
"title",
|
||||
"minutes",
|
||||
"seconds",
|
||||
"tags",
|
||||
"info",
|
||||
)
|
||||
"""Columns for CSV file."""
|
||||
IMPORT_PLAYLIST_CSV_DELIMITER = ";"
|
||||
"""Column delimiter of csv text files."""
|
||||
IMPORT_PLAYLIST_CSV_TEXT_QUOTE = '"'
|
||||
"""Text delimiter of csv text files."""
|
||||
|
||||
|
||||
settings = Settings("AIRCOX")
|
Reference in New Issue
Block a user