From 9357d57a2810f6ced7b924238ff0b9cabff5739f Mon Sep 17 00:00:00 2001 From: Jakob Ketterl Date: Sat, 6 Feb 2021 21:55:47 +0100 Subject: [PATCH] move temporary_directyr to core config; implement override logic --- docker/scripts/run.sh | 11 +++++++-- openwebrx.conf | 1 + owrx/audio.py | 4 ++-- owrx/config.py | 50 ++++++++++++++++++++++++---------------- owrx/dsp.py | 4 ++-- owrx/feature.py | 4 ++-- owrx/fft.py | 5 ++-- owrx/service/__init__.py | 4 ++-- 8 files changed, 50 insertions(+), 33 deletions(-) diff --git a/docker/scripts/run.sh b/docker/scripts/run.sh index cbbb0c7..052f4ca 100755 --- a/docker/scripts/run.sh +++ b/docker/scripts/run.sh @@ -1,10 +1,17 @@ #!/bin/bash set -euo pipefail -mkdir -p /etc/openwebrx/ +mkdir -p /etc/openwebrx/openwebrx.conf.d +mkdir -p /var/lib/openwebrx mkdir -p /tmp/openwebrx/ if [[ ! -f /etc/openwebrx/config_webrx.py ]] ; then - sed 's/temporary_directory = "\/tmp"/temporary_directory = "\/tmp\/openwebrx"/' < "/opt/openwebrx/config_webrx.py" > "/etc/openwebrx/config_webrx.py" + cp config_webrx.py /etc/openwebrx +fi +if [[ ! -f /etc/openwebrx/openwebrx.conf.d/20-temporary-directory.conf ]] ; then + cat << EOF > /etc/openwebrx/openwebrx.conf.d/20-temporary-directory.conf +[core] +temporary_directory = /tmp/openwebrx +EOF fi if [[ ! -f /etc/openwebrx/bands.json ]] ; then cp bands.json /etc/openwebrx/ diff --git a/openwebrx.conf b/openwebrx.conf index 072d3e4..b0d8500 100644 --- a/openwebrx.conf +++ b/openwebrx.conf @@ -1,5 +1,6 @@ [core] data_directory = /var/lib/openwebrx +temporary_directory = /tmp [web] port = 8073 diff --git a/owrx/audio.py b/owrx/audio.py index 7ac3733..092b55d 100644 --- a/owrx/audio.py +++ b/owrx/audio.py @@ -1,5 +1,5 @@ from abc import ABC, ABCMeta, abstractmethod -from owrx.config import Config +from owrx.config import Config, CoreConfig from owrx.metrics import Metrics, CounterMetric, DirectMetric import threading import wave @@ -151,7 +151,7 @@ class AudioWriter(object): self.dsp = dsp self.source = source self.profile = profile - self.tmp_dir = Config.get()["temporary_directory"] + self.tmp_dir = CoreConfig().get_temporary_directory() self.wavefile = None self.wavefilename = None self.switchingLock = threading.Lock() diff --git a/owrx/config.py b/owrx/config.py index 35f6328..7761a11 100644 --- a/owrx/config.py +++ b/owrx/config.py @@ -1,8 +1,9 @@ -from owrx.property import PropertyManager, PropertyLayer +from owrx.property import PropertyLayer import importlib.util import os import logging import json +from glob import glob from abc import ABC, abstractmethod from configparser import ConfigParser @@ -28,7 +29,7 @@ class ConfigMigrator(ABC): pass def renameKey(self, config, old, new): - if old in config and not new in config: + if old in config and new not in config: config[new] = config[old] del config[old] @@ -61,6 +62,7 @@ class CoreConfig(object): defaults = { "core": { "data_directory": "/var/lib/openwebrx", + "temporary_directory": "/tmp", }, "web": { "port": 8073, @@ -69,18 +71,41 @@ class CoreConfig(object): def __init__(self): config = ConfigParser() - config.read(["./openwebrx.conf", "/etc/openwebrx/openwebrx.conf"]) + overrides_dir = "/etc/openwebrx/openwebrx.conf.d" + if os.path.exists(overrides_dir) and os.path.isdir(overrides_dir): + overrides = glob(overrides_dir + "/*.conf") + else: + overrides = [] + # sequence things together + config.read(["./openwebrx.conf", "/etc/openwebrx/openwebrx.conf"] + overrides) self.data_directory = config.get( "core", "data_directory", fallback=CoreConfig.defaults["core"]["data_directory"] ) + CoreConfig.checkDirectory(self.data_directory, "data_directory") + self.temporary_directory = config.get( + "core", "temporary_directory", fallback=CoreConfig.defaults["core"]["temporary_directory"] + ) + CoreConfig.checkDirectory(self.temporary_directory, "temporary_directory") self.web_port = config.getint("web", "port", fallback=CoreConfig.defaults["web"]["port"]) + @staticmethod + def checkDirectory(dir, key): + if not os.path.exists(dir): + raise ConfigError(key, "{dir} doesn't exist".format(dir=dir)) + if not os.path.isdir(dir): + raise ConfigError(key, "{dir} is not a directory".format(dir=dir)) + if not os.access(dir, os.W_OK): + raise ConfigError(key, "{dir} is not writable".format(dir=dir)) + def get_web_port(self): return self.web_port def get_data_directory(self): return self.data_directory + def get_temporary_directory(self): + return self.temporary_directory + class Config: sharedConfig = None @@ -142,23 +167,8 @@ class Config: @staticmethod def validateConfig(): - pm = Config.get() - errors = [Config.checkTempDirectory(pm)] - - return [e for e in errors if e is not None] - - @staticmethod - def checkTempDirectory(pm: PropertyManager): - key = "temporary_directory" - if key not in pm or pm[key] is None: - return ConfigError(key, "temporary directory is not set") - if not os.path.exists(pm[key]): - return ConfigError(key, "temporary directory doesn't exist") - if not os.path.isdir(pm[key]): - return ConfigError(key, "temporary directory path is not a directory") - if not os.access(pm[key], os.W_OK): - return ConfigError(key, "temporary directory is not writable") - return None + # no config check atm + return [] @staticmethod def _migrate(config): diff --git a/owrx/dsp.py b/owrx/dsp.py index 20d377e..2b076d8 100644 --- a/owrx/dsp.py +++ b/owrx/dsp.py @@ -7,6 +7,7 @@ from owrx.source import SdrSource, SdrSourceEventClient from owrx.property import PropertyStack, PropertyLayer, PropertyValidator from owrx.property.validators import OrValidator, RegexValidator, BoolValidator from owrx.modes import Modes +from owrx.config import CoreConfig from csdr import csdr import threading import re @@ -70,7 +71,6 @@ class DspManager(csdr.output, SdrSourceEventClient): "digimodes_enable", "samp_rate", "digital_voice_unvoiced_quality", - "temporary_directory", "center_freq", "start_mod", "start_freq", @@ -132,7 +132,6 @@ class DspManager(csdr.output, SdrSourceEventClient): self.props.wireProperty("mod", self.dsp.set_demodulator), self.props.wireProperty("digital_voice_unvoiced_quality", self.dsp.set_unvoiced_quality), self.props.wireProperty("dmr_filter", self.dsp.set_dmr_filter), - self.props.wireProperty("temporary_directory", self.dsp.set_temporary_directory), self.props.wireProperty("wfm_deemphasis_tau", self.dsp.set_wfm_deemphasis_tau), self.props.filter("center_freq", "offset_freq").wire(set_dial_freq), ] @@ -140,6 +139,7 @@ class DspManager(csdr.output, SdrSourceEventClient): self.dsp.csdr_dynamic_bufsize = self.props["csdr_dynamic_bufsize"] self.dsp.csdr_print_bufsizes = self.props["csdr_print_bufsizes"] self.dsp.csdr_through = self.props["csdr_through"] + self.dsp.set_temporary_directory(CoreConfig().get_temporary_directory()) if self.props["digimodes_enable"]: diff --git a/owrx/feature.py b/owrx/feature.py index a918371..0a50dc2 100644 --- a/owrx/feature.py +++ b/owrx/feature.py @@ -4,7 +4,7 @@ from operator import and_ import re from distutils.version import LooseVersion import inspect -from owrx.config import Config +from owrx.config import CoreConfig import shlex import os from datetime import datetime, timedelta @@ -147,7 +147,7 @@ class FeatureDetector(object): return inspect.getdoc(self._get_requirement_method(requirement)) def command_is_runnable(self, command, expected_result=None): - tmp_dir = Config.get()["temporary_directory"] + tmp_dir = CoreConfig().get_temporary_directory() cmd = shlex.split(command) env = os.environ.copy() # prevent X11 programs from opening windows if called from a GUI shell diff --git a/owrx/fft.py b/owrx/fft.py index c434f7a..c76d1ff 100644 --- a/owrx/fft.py +++ b/owrx/fft.py @@ -1,4 +1,4 @@ -from owrx.config import Config +from owrx.config import Config, CoreConfig from csdr import csdr import threading from owrx.source import SdrSource, SdrSourceEventClient @@ -26,7 +26,6 @@ class SpectrumThread(csdr.output, SdrSourceEventClient): "csdr_dynamic_bufsize", "csdr_print_bufsizes", "csdr_through", - "temporary_directory", ) self.dsp = dsp = csdr.dsp(self) @@ -50,7 +49,6 @@ class SpectrumThread(csdr.output, SdrSourceEventClient): props.wireProperty("fft_size", dsp.set_fft_size), props.wireProperty("fft_fps", dsp.set_fft_fps), props.wireProperty("fft_compression", dsp.set_fft_compression), - props.wireProperty("temporary_directory", dsp.set_temporary_directory), props.filter("samp_rate", "fft_size", "fft_fps", "fft_voverlap_factor").wire(set_fft_averages), ] @@ -59,6 +57,7 @@ class SpectrumThread(csdr.output, SdrSourceEventClient): dsp.csdr_dynamic_bufsize = props["csdr_dynamic_bufsize"] dsp.csdr_print_bufsizes = props["csdr_print_bufsizes"] dsp.csdr_through = props["csdr_through"] + dsp.set_temporary_directory(CoreConfig().get_temporary_directory()) logger.debug("Spectrum thread initialized successfully.") def start(self): diff --git a/owrx/service/__init__.py b/owrx/service/__init__.py index 540e3c3..89b048a 100644 --- a/owrx/service/__init__.py +++ b/owrx/service/__init__.py @@ -6,7 +6,7 @@ from csdr.csdr import dsp, output from owrx.wsjt import WsjtParser from owrx.aprs import AprsParser from owrx.js8 import Js8Parser -from owrx.config import Config +from owrx.config import Config, CoreConfig from owrx.source.resampler import Resampler from owrx.property import PropertyLayer from js8py import Js8Frame @@ -255,7 +255,7 @@ class ServiceHandler(SdrSourceEventClient): d.set_secondary_demodulator(mode) d.set_audio_compression("none") d.set_samp_rate(source.getProps()["samp_rate"]) - d.set_temporary_directory(Config.get()["temporary_directory"]) + d.set_temporary_directory(CoreConfig().get_temporary_directory()) d.set_service() d.start() return d