Конфигурация¶
Настройки читаются из .env библиотекой python-decouple (AutoConfig с поиском в
/workdir). Шаблон — env-dist; всё, чего нет в .env, берётся из значений по
умолчанию в network/settings.py.
Важно
Секреты никогда не хардкодятся и не попадают в образ. В коде — только
config("VAR_NAME", default=...). .env монтируется в контейнер во время выполнения.
Ниже — все переменные, которые читает network/settings.py, по разделам; в env-dist
они же с умолчаниями. Полноту обоих списков проверяет
network/base/test_settings_documented.py: переменная, которой нет в одном из них,
роняет CI.
Базовые¶
Переменная |
По умолчанию |
Назначение |
|---|---|---|
|
|
При |
|
|
Режим отладки и Django Debug Toolbar |
|
нет |
Секретный ключ Django. Обязателен: без него портал не стартует |
|
|
Список через запятую; |
|
пусто |
Список через запятую |
|
|
В Docker переопределяется на PostgreSQL |
|
|
Сколько секунд держать соединение с БД между запросами; |
|
|
Хранилище сессий Django: чтение из кэша, запись насквозь в БД |
|
|
Каталог переводов |
|
|
Имена маршрутов входа и перехода после него |
|
|
Каталог хоста для медиа |
|
|
Каталог хоста для кэша сервиса |
|
пусто |
Тег образа, который деплой записал в |
|
GitLab Pages проекта |
Куда ведёт |
|
GitLab Pages |
Куда ведёт остальной |
|
|
Не используется: код, который его читал, снят при инициализации форка ( |
Безопасность¶
Переменная |
По умолчанию |
Назначение |
|---|---|---|
|
|
Срок HSTS, с |
|
пусто |
Заголовок прокси, подтверждающий HTTPS, в виде |
|
включён, если задан |
Редирект на HTTPS. Без заголовка прокси за nginx он зациклится |
|
пусто |
Сколько прокси перед gunicorn дописывают |
|
|
Cookie только по HTTPS. Выключать только на стенде, который действительно работает по HTTP, иначе туда никто не войдёт |
Content Security Policy¶
Каждая переменная — список источников через запятую для одной директивы. Значение
заменяет умолчание целиком, поэтому переопределение повторяет всё, что ещё нужно;
пустое значение означает 'none'. Значения с кавычками в .env берутся в двойные
кавычки: CSP_FRAME_ANCESTORS="'none'".
'unsafe-inline' и 'unsafe-eval' в умолчаниях нет: атрибут style="…" в разметке
браузер отбрасывает, и так задумано (см. фронтенд).
К style-src код сам добавляет nonce, но только на двух страницах со звуковым плеером
(наблюдение и оценка), — через переменную его не задать и не убрать.
Переменная |
Директива |
По умолчанию |
|---|---|---|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
Внешние сервисы¶
Переменная |
Назначение |
|---|---|
|
Рендер карт станций и наблюдений |
|
SatNOGS DB — источник спутников и передатчиков |
|
SatNOGS Network — источник данных для |
|
Исходящий HTTP(S)-прокси только для API |
|
Как портал представляется nanosats.eu, Wikidata и Wikimedia Commons при импорте паспортных данных. Wikimedia требует от автоматических клиентов осмысленного агента с контактом — адрес в нём должен быть рабочим |
|
Хост Launch Library 2, источника календаря запусков. По умолчанию боевой |
|
Сколько запросов в час задача |
|
Таймаут запроса к форуму сообщества, с ( |
|
Не используется: значок-ссылка на вики для владельца на странице станции снят редизайном раздела ( |
Орбитальные данные¶
Переменная |
По умолчанию |
Назначение |
|---|---|---|
|
пусто |
Учётка Space-Track для загрузки каталога |
|
|
Насколько дней приоритетный источник может отставать и всё ещё выигрывать |
|
|
Предельный возраст TLE для публичной выдачи |
|
файл CelesTrak |
Индексы солнечной и геомагнитной активности для прогноза схода |
|
|
Высота перигея, ниже которой спутник считается сошедшим |
|
|
Насколько далеко вперёд считается прогноз схода |
|
|
До какого срока прогноз опирается на суточные индексы; дальше дата показывается как оценка |
|
|
Глубина чтения фида подтверждённых сходов Space-Track |
|
|
Сколько дней ни один источник не публикует TLE, прежде чем молчание считается сходом |
Примечание
Дата схода считается по модели атмосферы NRLMSIS, которой управляют индексы
F10.7 и Ap из SPACE_WEATHER_URL. Суточное разрешение у этих индексов есть
примерно на полтора месяца вперёд, дальше известна только сглаженная кривая
солнечного цикла — поэтому дата за границей DECAY_DAILY_FORECAST_DAYS
показывается со знаком «≈».
Баллистический коэффициент не берётся из B* в TLE: это подгоночный
параметр SGP4, вбирающий разницу между реальностью и его собственной грубой
атмосферой, и в другой модели он занижает сопротивление в разы. Вместо этого
коэффициент подгоняется под наблюдаемый спад самого спутника.
Если индексы недоступны и в кеше их нет, суточная задача расчёта орбитальных параметров не выполняется: прежние даты точнее, чем посчитанные без атмосферы.
Примечание
Прогноз даты схода и перевод спутника в статус «Сошёл с орбиты» — разные
вещи. Статус меняет суточная задача confirm_satellite_reentries, и по
прогнозу она этого не делает никогда: нужен либо подтверждённый сход из фида
Space-Track, либо молчание всех источников TLE дольше DECAY_TLE_SILENCE_DAYS
вместе с уже прошедшей прогнозной датой. Без учётки Space-Track работает только
второе правило. Подробности — в Спутники и передатчики.
Примечание
На dev-стенде и в проде учётные данные Space-Track подставляются при деплое из
CI/CD-переменных GitLab (SPACE_TRACK_*_DEV и SPACE_TRACK_*_PROD), а не берутся из
env-dist на сервере. Стенд и прод используют разные аккаунты, чтобы не упереться
в лимиты сессий Space-Track. Подробности — в Орбитальные данные (TLE) и CI/CD и деплой.
Планирование наблюдений¶
Переменная |
По умолчанию |
Назначение |
|---|---|---|
|
|
Минимальный отступ начала наблюдения, мин — для станции без живого MQTT; станция на связи заявляет свой порог в секундах (см. Планирование наблюдений) |
|
— |
Горизонт планирования |
|
|
Минимальная длительность, с |
|
|
Порог разбиения длинного окна, с |
|
— |
Пауза между частями разбитого окна |
|
— |
Ограничение выборки при планировании |
|
|
Аккаунт, от имени которого планирует сетевое расписание |
|
|
Квота на спутники-нарушители частот: сколько наблюдений за период |
|
|
Порог числа наблюдений, ниже которого форма планирования предупреждает |
|
|
Сколько переиспользуется ответ с прогнозом пролётов. Коротко намеренно: флаг пересечения отражает текущее расписание |
|
|
Предельное окно и лимит частоты |
Для наблюдений новых запусков — отдельный набор: LAUNCH_BREAK_DURATION,
LAUNCH_SPLIT_DURATION (480), LAUNCH_MIN_ELEVATION (5),
LAUNCH_GOOD_ELEVATION (25), LAUNCH_MIN_HORIZON (0), LAUNCH_MIN_PERIOD (48),
LAUNCH_WAITING_FOR_SATELLITE.
Станции¶
Переменная |
По умолчанию |
Назначение |
|---|---|---|
|
|
Период сердцебиения станции, с |
|
|
Горизонт «ближайших» наблюдений, ч |
|
|
Лимит антенн |
|
|
Лимит диапазонов на антенну |
|
|
Допустимые границы диапазона антенны |
|
|
Границы VHF для классификации |
|
|
Границы UHF |
|
|
Границы L-диапазона |
|
|
Границы S-диапазона |
|
|
Отвечает ли |
|
|
На сколько аудио может расходиться с длительностью наблюдения, прежде чем оно оценивается как «failed» |
|
|
Насколько метка времени кадра может выходить за окно наблюдения — допуск на дрейф часов станции |
|
— |
Период проверки станций без результатов |
|
|
Сколько пустых наблюдений подряд считать проблемой |
|
— |
Сколько ждать после конца наблюдения, прежде чем считать его провалившимся |
|
пусто |
Адрес для уведомлений о проблемных станциях |
|
|
Применять ли ночной задаче поправки |
Хранение артефактов¶
Аудио, водопады и данные могут лежать локально или в S3-совместимом хранилище — независимо друг от друга:
Переменная |
Назначение |
|---|---|
|
Аудио в S3 |
|
Водопады в S3 |
|
Демодулированные данные в S3 |
|
Доступ к бакету |
|
Отдельный приватный бакет для суточных дампов БД, те же ключи |
|
Локальные пути и URL |
|
Каталог для загрузок, не поместившихся в память ( |
Архивация аудио (упаковка в zip и выгрузка на archive.org) включается отдельно:
ZIP_AUDIO_FILES, AUDIO_FILES_PER_ZIP (1000), ZIP_FILE_PREFIX,
ARCHIVE_ZIP_FILES, ZIP_FILES_PER_ITEM (10), ARCHIVE_COLLECTION,
ARCHIVE_MEDIA_TYPE (data), ITEM_IDENTIFIER_PREFIX, ITEM_TITLE_PREFIX,
ARCHIVE_SKIP_TIME (48 ч), REMOVE_ARCHIVED_AUDIO_FILES, REMOVE_ARCHIVED_ZIP_FILE,
S3_ACCESS_KEY, S3_SECRET_KEY, S3_RETRIES_ON_SLOW_DOWN, S3_RETRIES_SLEEP.
Сроки блокировок в кэше, с: ZIP_AUDIO_LOCK_EXPIRATION (600, дописывание файла в
архив), ZIP_TASK_LOCK_EXPIRATION (3600, задача упаковки),
ARCHIVE_TASK_LOCK_EXPIRATION (86400, задача выгрузки), ARCHIVE_ZIP_LOCK_EXPIRATION
(21600, выгрузка одного архива). ARCHIVE_AUDIO_LOCK_EXPIRATION не используется:
задача, которая его читала, снята в 22119248.
Примечание
Задачи zip_audio_files и archive_audio_zip_files регистрируются в расписании только
если соответствующий флаг включён и USE_S3_STORAGE_FOR_AUDIO выключен — при
хранении аудио в S3 паковать нечего.
Данные наблюдений и проверка¶
Переменная |
По умолчанию |
Назначение |
|---|---|---|
|
|
Сколько хранится выгрузка кадров, прежде чем её удалит периодическая задача |
|
|
Срок блокировки задачи обработки аудио |
|
|
Сколько наблюдений подгружает за раз страница массовой проверки |
|
|
Сколько порций страница проверки подгружает сразу при открытии и сколько держит загруженными впереди и позади текущей |
|
список аналоговых режимов |
Не используется: синхронизация демодулированных данных в SatNOGS DB, которая его читала, снята в |
Статика¶
Переменная |
По умолчанию |
Назначение |
|---|---|---|
|
|
Сборка скриптов и стилей страниц в общие файлы django-compressor. JS не минифицируется: минификатор ломал tom-select и mapbox-gl (комментарий |
|
|
Собирать заранее: |
|
|
Кэш, в котором компрессор хранит имена собранных файлов |
|
dart-sass из |
Путь к dart-sass для SCSS. Задаётся там, где нет ни того ни другого — например в тестовой джобе CI |
Registry образов станций¶
Читаются Compose, а не settings.py: сервис registry в docker-compose.yml —
pull-through cache Docker Hub для станций. Устройство и сниппет nginx — в
CI/CD и деплой.
Переменная |
Назначение |
|---|---|
|
|
|
Порт на loopback, куда nginx проксирует |
|
Read-only токен Docker Hub. Пусто — анонимно: работает, но промахи кэша упираются в лимит Docker Hub по IP |
MQTT-брокер¶
Живой канал со станциями (сервисы mosquitto и mqtt-bridge под профилем
mqtt). Устройство и сниппет nginx — в CI/CD и деплой.
Переменная |
Назначение |
|---|---|
|
|
|
Адрес брокера для публикации и моста; в compose — |
|
Служебный логин портала на брокере. Проверяется самим порталом в |
Авторизация через Keycloak¶
OIDC_AUTH (False) включает вход через OIDC-провайдера. Дополнительно:
OIDC_RP_CLIENT_ID, OIDC_RP_CLIENT_SECRET, OIDC_OP_AUTHORIZATION_ENDPOINT,
OIDC_OP_TOKEN_ENDPOINT, OIDC_OP_USER_ENDPOINT, OIDC_OP_JWKS_ENDPOINT,
OIDC_OP_LOGOUT_ENDPOINT, OIDC_KEYCLOAK_URL, OIDC_REALM,
OIDC_ADMIN_SERVICE_ID, OIDC_ADMIN_SERVICE_SECRET.
Лимиты попыток входа¶
Локальный вход и регистрация идут через django-allauth, и его лимиты действуют
по умолчанию, без отдельных переменных: пять неверных паролей на одно имя
пользователя за пять минут блокируют имя (даже с верным паролем), плюс десять
неудачных попыток в минуту с одного IP; регистрация — 20 в минуту с IP, сброс
пароля — 20 в минуту с IP и 5 в минуту на адрес. Блокировка по имени показывается
ошибкой формы входа, лимиты по IP — страницей 429. Счётчики живут в кэше
(CACHE_BACKEND): с Redis они общие для всех воркеров, с locmem — на процесс.
Переопределяются словарём ACCOUNT_RATE_LIMITS в settings.py
(ключи login_failed, login, signup, reset_password; False отключает всё).
Вход через OIDC этим лимитам не подчиняется. Проверка —
network/users/test_login_rate_limit.py.
Celery, кэш, лимиты API¶
Переменная |
По умолчанию |
|---|---|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
InfluxDB¶
Необязательная интеграция для телеметрии: USE_INFLUX, INFLUX_URL, INFLUX_TOKEN,
INFLUX_BUCKED, INFLUX_ORG.
Почта¶
EMAIL_HOST, EMAIL_PORT, EMAIL_USE_TLS, EMAIL_USE_SSL, EMAIL_HOST_USER,
EMAIL_HOST_PASSWORD, DEFAULT_FROM_EMAIL, SERVER_EMAIL, EMAIL_ADMIN,
EMAIL_TIMEOUT.
По этой же почте уходят необработанные ошибки: обработчик mail_admins на
логгере django.request шлёт трассировку каждого 500 на EMAIL_ADMIN. Фильтр
require_debug_false гасит отправку при DEBUG=True, поэтому локальный запуск
никому не пишет. Ограничения частоты нет: цикл отказов даст письмо на каждый
запрос.
Важно
Так что EMAIL_HOST и EMAIL_ADMIN на сервере — не декоративные. Пока они не
настроены, об ошибках портала не узнаёт никто: обработчик отработает, письмо не
уйдёт, а AdminEmailHandler проглотит сбой SMTP молча, чтобы не ронять запрос.