From ba4f7bfaa7673949bcda22e355180f2fcd534c2b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=D0=93=D1=80=D0=B8=D0=B3=D0=BE=D1=80=D0=B8=D0=B9=20=D0=A1?= =?UTF-8?q?=D0=B0=D1=84=D1=80=D0=BE=D0=BD=D0=BE=D0=B2?= Date: Mon, 5 Oct 2026 21:26:41 +0000 Subject: [PATCH] Update internal/config/config.go --- internal/config/config.go | 694 +++++++++++++++----------------------- 1 file changed, 265 insertions(+), 429 deletions(-) diff --git a/internal/config/config.go b/internal/config/config.go index 032856e..3a913d8 100644 --- a/internal/config/config.go +++ b/internal/config/config.go @@ -17,16 +17,21 @@ // - Установку значений по умолчанию для всех параметров // - Валидацию корректности настроек // - Предоставление типобезопасного доступа к конфигурации через методы-геттеры +// - Сохранение конфигурации в TOML (SaveConfig) — используется REPL-командой +// "config set" в fallback-режиме, когда Raft недоступен. // // ИСПРАВЛЕНО: добавлена секция [metrics] (MetricsConfig) — иначе // cmd/futriis/main.go не компилируется из-за cfg.Metrics. // // ИСПРАВЛЕНО (аудит, кросс-платформенность Linux/OpenIndiana): -// - BackupConfig дополнен полями IncludeSagaState и EnableIncremental, -// которые используются BackupScheduler (backup_scheduler.go). +// - BackupConfig дополнен полями IncludeSagaState и EnableIncremental. // - Добавлены геттеры IsIncludeSagaStateEnabled / IsIncrementalEnabled. // - В LoadConfig добавлены значения по умолчанию для новых полей. // - В ValidateConfigFull добавлена валидация [backup] и [engines]. +// +// ДОБАВЛЕНО (2026-10): +// - SaveConfig — атомарная запись конфигурации в TOML (tempfile + fsync + rename). +// - fsyncDir — синхронизация директории (no-op на Windows). package config @@ -34,6 +39,7 @@ import ( "fmt" "net" "os" + "path/filepath" "strings" "time" @@ -95,10 +101,10 @@ type Config struct { Monitoring MonitoringConfig `toml:"monitoring"` // Настройки мониторинга (метрики, трассировка) Recovery RecoveryConfig `toml:"recovery"` // Настройки восстановления после сбоев WAL WALConfig `toml:"wal"` // Настройки WAL (Write-Ahead Log) - MVCC MVCCConfig `toml:"mvcc"` // Настройки MVCC (Multi-Version Concurrency Control) + MVCC MVCCConfig `toml:"mvcc"` // Настройки MVCC Transactions TransactionsConfig `toml:"transactions"` // Настройки транзакций Saga SagaConfig `toml:"saga"` // Настройки SAGA оркестратора - ACL ACLConfig `toml:"acl"` // Настройки ACL (Access Control List) + ACL ACLConfig `toml:"acl"` // Настройки ACL ClusterTLS TLSConfig `toml:"cluster_tls"` // Настройки TLS для кластерного взаимодействия Backpressure BackpressureConfig `toml:"backpressure"` // Настройки механизма обратного давления RuntimeLimits RuntimeLimitsConfig `toml:"runtime_limits"` // Ограничения времени выполнения @@ -107,29 +113,23 @@ type Config struct { Backup BackupConfig `toml:"backup"` // Настройки резервного копирования Engines EnginesConfig `toml:"engines"` // Настройки движков хранения Migration MigrationConfig `toml:"migration"` // Настройки кросс-датацентровой миграции - // ИСПРАВЛЕНО: секция [metrics] — Prometheus/Grafana. - Metrics MetricsConfig `toml:"metrics"` + Metrics MetricsConfig `toml:"metrics"` // Настройки Prometheus/Grafana } // ============================================================================= -// КОНФИГУРАЦИЯ МЕТРИК — ИСПРАВЛЕНО +// КОНФИГУРАЦИЯ МЕТРИК // ============================================================================= // MetricsConfig содержит настройки экспорта метрик в формате Prometheus. type MetricsConfig struct { - // Enabled — включает HTTP endpoint /metrics и периодический сбор. - Enabled bool `toml:"enabled"` - // CollectIntervalSec — интервал сбора метрик в секундах. - CollectIntervalSec int `toml:"collect_interval_sec"` + Enabled bool `toml:"enabled"` + CollectIntervalSec int `toml:"collect_interval_sec"` } // IsMetricsEnabled возвращает флаг включения метрик. -func (m *MetricsConfig) IsMetricsEnabled() bool { - return m.Enabled -} +func (m *MetricsConfig) IsMetricsEnabled() bool { return m.Enabled } // GetCollectInterval возвращает интервал сбора метрик как time.Duration. -// По умолчанию 15 секунд. func (m *MetricsConfig) GetCollectInterval() time.Duration { if m.CollectIntervalSec <= 0 { return 15 * time.Second @@ -141,399 +141,353 @@ func (m *MetricsConfig) GetCollectInterval() time.Duration { // КОНФИГУРАЦИЯ КЛАСТЕРА // ============================================================================= -// ClusterConfig содержит настройки для работы в кластерном режиме -// на основе протокола Raft для обеспечения согласованности. +// ClusterConfig содержит настройки для работы в кластерном режиме. type ClusterConfig struct { - // Имя кластера - идентификатор для группировки узлов Name string `toml:"name"` - // Сетевые настройки узла - NodeIP string `toml:"node_ip"` // IP-адрес для прослушивания - NodePort int `toml:"node_port"` // Порт для клиентских подключений - RaftPort int `toml:"raft_port"` // Порт для Raft-коммуникации + NodeIP string `toml:"node_ip"` + NodePort int `toml:"node_port"` + RaftPort int `toml:"raft_port"` - // Настройки Raft - RaftDataDir string `toml:"raft_data_dir"` // Директория для хранения Raft-лога - Bootstrap bool `toml:"bootstrap"` // Является ли узел инициализатором кластера - Nodes []string `toml:"nodes"` // Список адресов других узлов кластера + RaftDataDir string `toml:"raft_data_dir"` + Bootstrap bool `toml:"bootstrap"` + Nodes []string `toml:"nodes"` - // Таймауты Raft (в миллисекундах) - HeartbeatTimeoutMs int `toml:"heartbeat_timeout_ms"` // Интервал отправки heartbeat - ElectionTimeoutMs int `toml:"election_timeout_ms"` // Таймаут для начала выборов - CommitTimeoutMs int `toml:"commit_timeout_ms"` // Таймаут коммита записей + HeartbeatTimeoutMs int `toml:"heartbeat_timeout_ms"` + ElectionTimeoutMs int `toml:"election_timeout_ms"` + CommitTimeoutMs int `toml:"commit_timeout_ms"` - // Настройки снэпшотов - SnapshotIntervalMin int `toml:"snapshot_interval_min"` // Интервал создания снэпшотов (минуты) - SnapshotThreshold int `toml:"snapshot_threshold"` // Количество записей для создания снэпшота + SnapshotIntervalMin int `toml:"snapshot_interval_min"` + SnapshotThreshold int `toml:"snapshot_threshold"` - // Защита от split-brain и восстановление - SplitBrainPrevention bool `toml:"split_brain_prevention"` // Включить защиту от разделения кластера - RecoveryTimeoutSec int `toml:"recovery_timeout_sec"` // Таймаут восстановления после сбоя + SplitBrainPrevention bool `toml:"split_brain_prevention"` + RecoveryTimeoutSec int `toml:"recovery_timeout_sec"` - // Географические настройки для оптимизации маршрутизации - Region string `toml:"region"` // Регион расположения узла - PriorityZone int `toml:"priority_zone"` // Приоритетная зона (0-9, где 9 - наивысший) + Region string `toml:"region"` + PriorityZone int `toml:"priority_zone"` } // ============================================================================= -// КОНФИГУРАЦИЯ SAGA ОРКЕСТРАТОРА +// КОНФИГУРАЦИЯ SAGA // ============================================================================= -// SagaConfig содержит настройки отказоустойчивого оркестратора распределённых транзакций. +// SagaConfig содержит настройки SAGA оркестратора. type SagaConfig struct { - // Основные настройки - Enabled bool `toml:"enabled"` // Включить SAGA оркестратор - CoordinatorCount int `toml:"coordinator_count"` // Количество координаторов (>= 3 для отказоустойчивости) - StateDir string `toml:"state_dir"` // Директория для хранения состояний SAGA + Enabled bool `toml:"enabled"` + CoordinatorCount int `toml:"coordinator_count"` + StateDir string `toml:"state_dir"` - // Настройки выполнения - MaxRetries int `toml:"max_retries"` // Максимальное количество попыток выполнения шага - RetryBackoffMs int `toml:"retry_backoff_ms"` // Базовая задержка между повторными попытками (мс) - SagaTimeoutSec int `toml:"saga_timeout_sec"` // Таймаут выполнения SAGA (сек) - StuckCheckIntervalSec int `toml:"stuck_check_interval_sec"` // Интервал проверки зависших SAGA (сек) + MaxRetries int `toml:"max_retries"` + RetryBackoffMs int `toml:"retry_backoff_ms"` + SagaTimeoutSec int `toml:"saga_timeout_sec"` + StuckCheckIntervalSec int `toml:"stuck_check_interval_sec"` - // Настройки оркестрации - LeaderElectionIntervalSec int `toml:"leader_election_interval_sec"` // Интервал выбора лидера (сек) - RecoveryIntervalSec int `toml:"recovery_interval_sec"` // Интервал восстановления незавершённых SAGA (сек) - MetricsIntervalSec int `toml:"metrics_interval_sec"` // Интервал сбора метрик (сек) + LeaderElectionIntervalSec int `toml:"leader_election_interval_sec"` + RecoveryIntervalSec int `toml:"recovery_interval_sec"` + MetricsIntervalSec int `toml:"metrics_interval_sec"` - // Настройки очистки и кэширования - CleanupPeriodHours int `toml:"cleanup_period_hours"` // Период очистки старых SAGA (часы) - MaxCacheSize int `toml:"max_cache_size"` // Максимальное количество состояний в кэше - OperationRetentionDays int `toml:"operation_retention_days"` // Время жизни выполненных операций (дни) + CleanupPeriodHours int `toml:"cleanup_period_hours"` + MaxCacheSize int `toml:"max_cache_size"` + OperationRetentionDays int `toml:"operation_retention_days"` - // Настройки производительности - ChannelBufferSize int `toml:"channel_buffer_size"` // Размер буфера каналов - AsyncRecoveryWorkers int `toml:"async_recovery_workers"` // Количество воркеров для асинхронного восстановления - AsyncRecoveryTimeoutSec int `toml:"async_recovery_timeout_sec"` // Таймаут асинхронного восстановления (сек) + ChannelBufferSize int `toml:"channel_buffer_size"` + AsyncRecoveryWorkers int `toml:"async_recovery_workers"` + AsyncRecoveryTimeoutSec int `toml:"async_recovery_timeout_sec"` - // Настройки синхронизации с диском - FsyncEnabled bool `toml:"fsync_enabled"` // Принудительная синхронизация с диском - FsyncMaxRetries int `toml:"fsync_max_retries"` // Количество повторных попыток синхронизации - FsyncRetryDelayMs int `toml:"fsync_retry_delay_ms"` // Задержка между повторными попытками (мс) + FsyncEnabled bool `toml:"fsync_enabled"` + FsyncMaxRetries int `toml:"fsync_max_retries"` + FsyncRetryDelayMs int `toml:"fsync_retry_delay_ms"` } // ============================================================================= // КОНФИГУРАЦИЯ ХРАНИЛИЩА // ============================================================================= -// StorageConfig содержит настройки системы хранения данных. type StorageConfig struct { - PageSizeMB int `toml:"page_size_mb"` // Размер страницы памяти в МБ - MaxCollections int `toml:"max_collections"` // Максимальное количество коллекций - MaxDocumentsPerCollection int `toml:"max_documents_per_collection"` // Макс. документов в коллекции - DefaultEngine string `toml:"default_engine"` // Движок по умолчанию - EnableCustomEngines bool `toml:"enable_custom_engines"` // Включить пользовательские движки + PageSizeMB int `toml:"page_size_mb"` + MaxCollections int `toml:"max_collections"` + MaxDocumentsPerCollection int `toml:"max_documents_per_collection"` + DefaultEngine string `toml:"default_engine"` + EnableCustomEngines bool `toml:"enable_custom_engines"` } // ============================================================================= -// КОНФИГУРАЦИЯ REPL (ИНТЕРАКТИВНАЯ ОБОЛОЧКА) +// КОНФИГУРАЦИЯ REPL // ============================================================================= -// ReplConfig содержит настройки интерактивной командной оболочки. type ReplConfig struct { - PromptColor string `toml:"prompt_color"` // Цвет приглашения ввода - HistorySize int `toml:"history_size"` // Размер истории команд + PromptColor string `toml:"prompt_color"` + HistorySize int `toml:"history_size"` } // ============================================================================= // КОНФИГУРАЦИЯ ЛОГИРОВАНИЯ // ============================================================================= -// LogConfig содержит настройки системы логирования. type LogConfig struct { - LogFile string `toml:"log_file"` // Путь к файлу лога (пусто = stdout) - LogLevel string `toml:"log_level"` // Уровень логирования (debug, info, warn, error) + LogFile string `toml:"log_file"` + LogLevel string `toml:"log_level"` } // ============================================================================= // КОНФИГУРАЦИЯ HTTP API // ============================================================================= -// APIConfig содержит настройки HTTP API сервера. type APIConfig struct { - Port int `toml:"port"` // Порт для HTTP API + Port int `toml:"port"` } // ============================================================================= // КОНФИГУРАЦИЯ РЕПЛИКАЦИИ // ============================================================================= -// ReplicationConfig содержит настройки репликации данных между узлами. type ReplicationConfig struct { - Enabled bool `toml:"enabled"` // Включена ли репликация - SyncReplication bool `toml:"sync_replication"` // Синхронная репликация - ReplicationTimeoutMs int `toml:"replication_timeout_ms"` // Таймаут репликации (мс) - MaxReplicaLagMs int `toml:"max_replica_lag_ms"` // Максимальное отставание реплики (мс) + Enabled bool `toml:"enabled"` + SyncReplication bool `toml:"sync_replication"` + ReplicationTimeoutMs int `toml:"replication_timeout_ms"` + MaxReplicaLagMs int `toml:"max_replica_lag_ms"` } // ============================================================================= // КОНФИГУРАЦИЯ ПЛАГИНОВ (LUA) // ============================================================================= -// PluginsConfig содержит настройки системы выполнения Lua-скриптов. type PluginsConfig struct { - Enabled bool `toml:"enabled"` // Включена ли поддержка плагинов - ScriptDir string `toml:"script_dir"` // Директория со скриптами - AllowList []string `toml:"allow_list"` // Белый список разрешенных скриптов - MaxCPUTimeMs int `toml:"max_cpu_time_ms"` // Макс. время CPU (мс) - MaxMemoryMB int `toml:"max_memory_mb"` // Макс. память (МБ) - MaxExecutionTimeSec int `toml:"max_execution_time_sec"` // Макс. время выполнения (сек) - MaxInstructions int64 `toml:"max_instructions"` // Макс. количество инструкций - HotReloadIntervalSec int `toml:"hot_reload_interval_sec"` // Интервал горячей перезагрузки - MaxEventLogSize int `toml:"max_event_log_size"` // Макс. размер лога событий - LoadTimeoutSec int `toml:"load_timeout_sec"` // Таймаут загрузки скрипта - MaxLuaStates int `toml:"max_lua_states"` // Макс. количество Lua-состояний - LuaStateTTLSec int `toml:"lua_state_ttl_sec"` // TTL Lua-состояния - EnginePluginDir string `toml:"engine_plugin_dir"` // Директория плагинов движков + Enabled bool `toml:"enabled"` + ScriptDir string `toml:"script_dir"` + AllowList []string `toml:"allow_list"` + MaxCPUTimeMs int `toml:"max_cpu_time_ms"` + MaxMemoryMB int `toml:"max_memory_mb"` + MaxExecutionTimeSec int `toml:"max_execution_time_sec"` + MaxInstructions int64 `toml:"max_instructions"` + HotReloadIntervalSec int `toml:"hot_reload_interval_sec"` + MaxEventLogSize int `toml:"max_event_log_size"` + LoadTimeoutSec int `toml:"load_timeout_sec"` + MaxLuaStates int `toml:"max_lua_states"` + LuaStateTTLSec int `toml:"lua_state_ttl_sec"` + EnginePluginDir string `toml:"engine_plugin_dir"` } // ============================================================================= // КОНФИГУРАЦИЯ СЖАТИЯ // ============================================================================= -// CompressionConfig содержит настройки сжатия данных. type CompressionConfig struct { - Enabled bool `toml:"enabled"` // Включено ли сжатие - Algorithm string `toml:"algorithm"` // Алгоритм сжатия (snappy, lz4, zstd) - Level int `toml:"level"` // Уровень сжатия (1-9) - MinSize int `toml:"min_size"` // Минимальный размер для сжатия (байт) + Enabled bool `toml:"enabled"` + Algorithm string `toml:"algorithm"` + Level int `toml:"level"` + MinSize int `toml:"min_size"` } // ============================================================================= // КОНФИГУРАЦИЯ ПРОИЗВОДИТЕЛЬНОСТИ // ============================================================================= -// PerformanceConfig содержит настройки, влияющие на производительность системы. type PerformanceConfig struct { - EnablePipeline bool `toml:"enable_pipeline"` // Включить конвейерную обработку - BatchSize int `toml:"batch_size"` // Размер пакета для пакетных операций - ReadFromFollower bool `toml:"read_from_follower"` // Читать с ведомых узлов - MaxConnections int `toml:"max_connections"` // Максимальное количество соединений - ReadReplicaDelayMs int `toml:"read_replica_delay_ms"` // Задержка чтения с реплики (мс) + EnablePipeline bool `toml:"enable_pipeline"` + BatchSize int `toml:"batch_size"` + ReadFromFollower bool `toml:"read_from_follower"` + MaxConnections int `toml:"max_connections"` + ReadReplicaDelayMs int `toml:"read_replica_delay_ms"` } // ============================================================================= // КОНФИГУРАЦИЯ БЕЗОПАСНОСТИ // ============================================================================= -// SecurityConfig содержит настройки безопасности (TLS). type SecurityConfig struct { - EnableTLS bool `toml:"enable_tls"` // Включен ли TLS - CertFile string `toml:"cert_file"` // Путь к сертификату - KeyFile string `toml:"key_file"` // Путь к приватному ключу - CAFile string `toml:"ca_file"` // Путь к корневому сертификату CA - MinVersion string `toml:"min_version"` // Минимальная версия TLS (1.0, 1.1, 1.2, 1.3) + EnableTLS bool `toml:"enable_tls"` + CertFile string `toml:"cert_file"` + KeyFile string `toml:"key_file"` + CAFile string `toml:"ca_file"` + MinVersion string `toml:"min_version"` } // ============================================================================= // КОНФИГУРАЦИЯ МОНИТОРИНГА // ============================================================================= -// MonitoringConfig содержит настройки мониторинга и наблюдаемости. type MonitoringConfig struct { - EnableMetrics bool `toml:"enable_metrics"` // Включить сбор метрик - MetricsPort int `toml:"metrics_port"` // Порт для экспорта метрик (Prometheus) - EnableTracing bool `toml:"enable_tracing"` // Включить распределённую трассировку - TraceSampleRate float64 `toml:"trace_sample_rate"` // Частота сэмплирования трассировки (0-1) + EnableMetrics bool `toml:"enable_metrics"` + MetricsPort int `toml:"metrics_port"` + EnableTracing bool `toml:"enable_tracing"` + TraceSampleRate float64 `toml:"trace_sample_rate"` } // ============================================================================= // КОНФИГУРАЦИЯ ВОССТАНОВЛЕНИЯ // ============================================================================= -// RecoveryConfig содержит настройки восстановления после сбоев. type RecoveryConfig struct { - AutoRejoin bool `toml:"auto_rejoin"` // Автоматическое переподключение - MaxRetrySec int `toml:"max_retry_sec"` // Макс. время повторных попыток - DataReplicationTimeoutSec int `toml:"data_replication_timeout_sec"` // Таймаут репликации данных - StaleReadTimeoutSec int `toml:"stale_read_timeout_sec"` // Таймаут устаревшего чтения + AutoRejoin bool `toml:"auto_rejoin"` + MaxRetrySec int `toml:"max_retry_sec"` + DataReplicationTimeoutSec int `toml:"data_replication_timeout_sec"` + StaleReadTimeoutSec int `toml:"stale_read_timeout_sec"` } // ============================================================================= -// КОНФИГУРАЦИЯ WAL (WRITE-AHEAD LOG) +// КОНФИГУРАЦИЯ WAL // ============================================================================= -// WALConfig содержит настройки журнала упреждающей записи. type WALConfig struct { - SegmentSizeMB int `toml:"segment_size_mb"` // Размер сегмента WAL (МБ) - SyncIntervalSec int `toml:"sync_interval_sec"` // Интервал синхронизации на диск - BatchSize int `toml:"batch_size"` // Размер пакета для записи - RecoveryWorkers int `toml:"recovery_workers"` // Количество потоков восстановления - Enabled bool `toml:"enabled"` // Включен ли WAL - AsyncRecovery bool `toml:"async_recovery"` // Асинхронное восстановление - AsyncRecoveryWorkers int `toml:"async_recovery_workers"` // Потоков асинхронного восстановления - AsyncRecoveryBuffer int `toml:"async_recovery_buffer"` // Размер буфера асинхронного восстановления + SegmentSizeMB int `toml:"segment_size_mb"` + SyncIntervalSec int `toml:"sync_interval_sec"` + BatchSize int `toml:"batch_size"` + RecoveryWorkers int `toml:"recovery_workers"` + Enabled bool `toml:"enabled"` + AsyncRecovery bool `toml:"async_recovery"` + AsyncRecoveryWorkers int `toml:"async_recovery_workers"` + AsyncRecoveryBuffer int `toml:"async_recovery_buffer"` } // ============================================================================= -// КОНФИГУРАЦИЯ MVCC (MULTI-VERSION CONCURRENCY CONTROL) +// КОНФИГУРАЦИЯ MVCC // ============================================================================= -// MVCCConfig содержит настройки механизма многоверсионного контроля параллелизма. type MVCCConfig struct { - MaxVersionsPerDoc int `toml:"max_versions_per_doc"` // Макс. версий на документ - VisibilityMapSize int `toml:"visibility_map_size"` // Размер карты видимости - PruneIntervalMin int `toml:"prune_interval_min"` // Интервал очистки старых версий (минуты) - RetentionDays int `toml:"retention_days"` // Срок хранения старых версий (дни) - ReadCacheSize int `toml:"read_cache_size"` // Размер кэша чтения - ReadCacheTTLSec int `toml:"read_cache_ttl_sec"` // TTL кэша чтения (секунды) + MaxVersionsPerDoc int `toml:"max_versions_per_doc"` + VisibilityMapSize int `toml:"visibility_map_size"` + PruneIntervalMin int `toml:"prune_interval_min"` + RetentionDays int `toml:"retention_days"` + ReadCacheSize int `toml:"read_cache_size"` + ReadCacheTTLSec int `toml:"read_cache_ttl_sec"` } // ============================================================================= // КОНФИГУРАЦИЯ ТРАНЗАКЦИЙ // ============================================================================= -// TransactionsConfig содержит настройки транзакционной подсистемы. type TransactionsConfig struct { - DefaultTimeoutSec int `toml:"default_timeout_sec"` // Таймаут транзакции по умолчанию - DeadlockCheckIntervalSec int `toml:"deadlock_check_interval_sec"` // Интервал проверки deadlock - MaxSavepointsPerTx int `toml:"max_savepoints_per_tx"` // Макс. точек сохранения - Enabled bool `toml:"enabled"` // Включены ли транзакции - CheckpointIntervalSec int `toml:"checkpoint_interval_sec"` // Интервал контрольных точек + DefaultTimeoutSec int `toml:"default_timeout_sec"` + DeadlockCheckIntervalSec int `toml:"deadlock_check_interval_sec"` + MaxSavepointsPerTx int `toml:"max_savepoints_per_tx"` + Enabled bool `toml:"enabled"` + CheckpointIntervalSec int `toml:"checkpoint_interval_sec"` } // ============================================================================= -// КОНФИГУРАЦИЯ ACL (ACCESS CONTROL LIST) +// КОНФИГУРАЦИЯ ACL // ============================================================================= -// ACLConfig содержит настройки контроля доступа. type ACLConfig struct { - MaxDeniedLogSize int `toml:"max_denied_log_size"` // Макс. размер лога отказов - TemporaryGrantTTLHours int `toml:"temporary_grant_ttl_hours"` // TTL временных прав (часы) - EnableRoleHierarchy bool `toml:"enable_role_hierarchy"` // Иерархия ролей - CacheTTLSec int `toml:"cache_ttl_sec"` // TTL кэша ACL (сек) + MaxDeniedLogSize int `toml:"max_denied_log_size"` + TemporaryGrantTTLHours int `toml:"temporary_grant_ttl_hours"` + EnableRoleHierarchy bool `toml:"enable_role_hierarchy"` + CacheTTLSec int `toml:"cache_ttl_sec"` } // ============================================================================= // КОНФИГУРАЦИЯ TLS ДЛЯ КЛАСТЕРА // ============================================================================= -// TLSConfig содержит настройки TLS для кластерного взаимодействия. type TLSConfig struct { - Enabled bool `toml:"enabled"` // Включен ли TLS - CertFile string `toml:"cert_file"` // Путь к сертификату - KeyFile string `toml:"key_file"` // Путь к приватному ключу - CAFile string `toml:"ca_file"` // Путь к корневому сертификату CA - MinVersion string `toml:"min_version"` // Минимальная версия TLS - MutualAuth bool `toml:"mutual_auth"` // Взаимная аутентификация - KeyRotationDays int `toml:"key_rotation_days"` // Интервал ротации ключей - AutoGenerate bool `toml:"auto_generate"` // Автоматическая генерация сертификатов + Enabled bool `toml:"enabled"` + CertFile string `toml:"cert_file"` + KeyFile string `toml:"key_file"` + CAFile string `toml:"ca_file"` + MinVersion string `toml:"min_version"` + MutualAuth bool `toml:"mutual_auth"` + KeyRotationDays int `toml:"key_rotation_days"` + AutoGenerate bool `toml:"auto_generate"` } // ============================================================================= -// КОНФИГУРАЦИЯ ОБРАТНОГО ДАВЛЕНИЯ (BACKPRESSURE) +// КОНФИГУРАЦИЯ BACKPRESSURE // ============================================================================= -// BackpressureConfig содержит настройки механизма обратного давления. type BackpressureConfig struct { - Enabled bool `toml:"enabled"` // Включен ли механизм - CPUThreshold float64 `toml:"cpu_threshold"` // Порог CPU (0-1) - MemoryThreshold float64 `toml:"memory_threshold"` // Порог памяти (0-1) - QueueSizeThreshold int `toml:"queue_size_threshold"` // Порог размера очереди - ConnectionThreshold int `toml:"connection_threshold"` // Порог количества соединений - CheckIntervalMs int `toml:"check_interval_ms"` // Интервал проверки (мс) - LowDelayMs int64 `toml:"low_delay_ms"` // Задержка для низкой нагрузки (мс) - MediumRejectProb uint32 `toml:"medium_reject_prob"` // Вероятность отказа при средней нагрузке (%) - HighRejectProb uint32 `toml:"high_reject_prob"` // Вероятность отказа при высокой нагрузке (%) + Enabled bool `toml:"enabled"` + CPUThreshold float64 `toml:"cpu_threshold"` + MemoryThreshold float64 `toml:"memory_threshold"` + QueueSizeThreshold int `toml:"queue_size_threshold"` + ConnectionThreshold int `toml:"connection_threshold"` + CheckIntervalMs int `toml:"check_interval_ms"` + LowDelayMs int64 `toml:"low_delay_ms"` + MediumRejectProb uint32 `toml:"medium_reject_prob"` + HighRejectProb uint32 `toml:"high_reject_prob"` } // ============================================================================= -// КОНФИГУРАЦИЯ ОГРАНИЧЕНИЙ ВРЕМЕНИ ВЫПОЛНЕНИЯ +// КОНФИГУРАЦИЯ RUNTIME LIMITS // ============================================================================= -// RuntimeLimitsConfig содержит глобальные ограничения для защиты от недобросовестных запросов. type RuntimeLimitsConfig struct { - Enabled bool `toml:"enabled"` // Включены ли ограничения - GlobalMaxDocSizeMB int `toml:"global_max_doc_size_mb"` // Макс. размер документа (МБ) - GlobalMaxCollSizeMB int64 `toml:"global_max_coll_size_mb"` // Макс. размер коллекции (МБ) - GlobalMaxDocsPerColl int64 `toml:"global_max_docs_per_coll"` // Макс. документов в коллекции + Enabled bool `toml:"enabled"` + GlobalMaxDocSizeMB int `toml:"global_max_doc_size_mb"` + GlobalMaxCollSizeMB int64 `toml:"global_max_coll_size_mb"` + GlobalMaxDocsPerColl int64 `toml:"global_max_docs_per_coll"` } // ============================================================================= -// КОНФИГУРАЦИЯ АВТОМАСШТАБИРОВАНИЯ +// КОНФИГУРАЦИЯ AUTOSCALING // ============================================================================= -// AutoscalingConfig содержит настройки автоматического масштабирования кластера. type AutoscalingConfig struct { - Enabled bool `toml:"enabled"` // Включено ли автомасштабирование - MinNodes int `toml:"min_nodes"` // Минимальное количество узлов - MaxNodes int `toml:"max_nodes"` // Максимальное количество узлов - ScaleUpThreshold float64 `toml:"scale_up_threshold"` // Порог для увеличения (0-1) - ScaleDownThreshold float64 `toml:"scale_down_threshold"` // Порог для уменьшения (0-1) - ScaleUpCooldownSec int `toml:"scale_up_cooldown_sec"` // Задержка перед масштабированием вверх - ScaleDownCooldownSec int `toml:"scale_down_cooldown_sec"` // Задержка перед масштабированием вниз - EvaluationIntervalSec int `toml:"evaluation_interval_sec"` // Интервал оценки нагрузки - PredictiveEnabled bool `toml:"predictive_enabled"` // Прогнозирующее масштабирование - MaxScaleUpNodes int `toml:"max_scale_up_nodes"` // Макс. узлов при масштабировании вверх - MaxScaleDownNodes int `toml:"max_scale_down_nodes"` // Макс. узлов при масштабировании вниз + Enabled bool `toml:"enabled"` + MinNodes int `toml:"min_nodes"` + MaxNodes int `toml:"max_nodes"` + ScaleUpThreshold float64 `toml:"scale_up_threshold"` + ScaleDownThreshold float64 `toml:"scale_down_threshold"` + ScaleUpCooldownSec int `toml:"scale_up_cooldown_sec"` + ScaleDownCooldownSec int `toml:"scale_down_cooldown_sec"` + EvaluationIntervalSec int `toml:"evaluation_interval_sec"` + PredictiveEnabled bool `toml:"predictive_enabled"` + MaxScaleUpNodes int `toml:"max_scale_up_nodes"` + MaxScaleDownNodes int `toml:"max_scale_down_nodes"` } // ============================================================================= // КОНФИГУРАЦИЯ МИГРАЦИИ СХЕМЫ // ============================================================================= -// SchemaMigrationConfig содержит настройки миграции схемы данных. type SchemaMigrationConfig struct { - Enabled bool `toml:"enabled"` // Включена ли миграция - MigrationDir string `toml:"migration_dir"` // Директория с миграциями - AutoMigrate bool `toml:"auto_migrate"` // Автоматическая миграция при старте - TargetVersion string `toml:"target_version"` // Целевая версия схемы + Enabled bool `toml:"enabled"` + MigrationDir string `toml:"migration_dir"` + AutoMigrate bool `toml:"auto_migrate"` + TargetVersion string `toml:"target_version"` } // ============================================================================= -// КОНФИГУРАЦИЯ РЕЗЕРВНОГО КОПИРОВАНИЯ +// КОНФИГУРАЦИЯ BACKUP // ============================================================================= -// -// ИСПРАВЛЕНО: добавлены поля IncludeSagaState и EnableIncremental, -// которые используются BackupScheduler (backup_scheduler.go): -// - IncludeSagaState — включает состояние активных SAGA в бэкап. -// - EnableIncremental — разрешает создание инкрементальных бэкапов. -// Без этих полей TOML-ключи include_saga_state / enable_incremental -// игнорировались, что приводило к неполному бэкапу. -// BackupConfig содержит настройки резервного копирования. type BackupConfig struct { - Enabled bool `toml:"enabled"` // Включено ли резервное копирование - BackupDir string `toml:"backup_dir"` // Директория для бэкапов - MaxConcurrent int `toml:"max_concurrent"` // Макс. параллельных бэкапов - CompressEnabled bool `toml:"compress_enabled"` // Сжатие бэкапов - RetentionDays int `toml:"retention_days"` // Срок хранения бэкапов (дни) + Enabled bool `toml:"enabled"` + BackupDir string `toml:"backup_dir"` + MaxConcurrent int `toml:"max_concurrent"` + CompressEnabled bool `toml:"compress_enabled"` + RetentionDays int `toml:"retention_days"` - // Дополнительные поля, используемые BackupScheduler. - IncludeSagaState bool `toml:"include_saga_state"` // Включать состояние SAGA в бэкап - EnableIncremental bool `toml:"enable_incremental"` // Разрешить инкрементальные бэкапы + IncludeSagaState bool `toml:"include_saga_state"` + EnableIncremental bool `toml:"enable_incremental"` } // ============================================================================= // КОНФИГУРАЦИЯ ДВИЖКОВ ХРАНЕНИЯ // ============================================================================= -// EnginesConfig содержит настройки всех движков хранения данных. type EnginesConfig struct { - Row EngineConfig `toml:"row"` // Строчный движок (по умолчанию) - Columnar EngineConfig `toml:"columnar"` // Колоночный движок (аналитика) - Document EngineConfig `toml:"document"` // Документоориентированный движок - KV EngineConfig `toml:"kv"` // Key-Value движок - TS EngineConfig `toml:"ts"` // Time-Series движок (временные ряды) - Graph EngineConfig `toml:"graph"` // Графовый движок + Row EngineConfig `toml:"row"` + Columnar EngineConfig `toml:"columnar"` + Document EngineConfig `toml:"document"` + KV EngineConfig `toml:"kv"` + TS EngineConfig `toml:"ts"` + Graph EngineConfig `toml:"graph"` } -// EngineConfig содержит настройки отдельного движка хранения. type EngineConfig struct { - Enabled bool `toml:"enabled"` // Включен ли движок - Description string `toml:"description"` // Описание движка - Config map[string]interface{} `toml:"config"` // Дополнительные параметры движка + Enabled bool `toml:"enabled"` + Description string `toml:"description"` + Config map[string]interface{} `toml:"config"` } // ============================================================================= // КОНФИГУРАЦИЯ КРОСС-ДАТАЦЕНТРОВОЙ МИГРАЦИИ // ============================================================================= -// MigrationConfig представляет конфигурацию кросс-датацентровой миграции type MigrationConfig struct { Enabled bool `toml:"enabled"` - Mode string `toml:"mode"` // manual, semi_auto, auto + Mode string `toml:"mode"` Source *DatacenterConfig `toml:"source"` Target *DatacenterConfig `toml:"target"` Settings *MigrationSettings `toml:"settings"` @@ -541,7 +495,6 @@ type MigrationConfig struct { Validation *ValidationConfig `toml:"validation"` } -// DatacenterConfig представляет конфигурацию датацентра type DatacenterConfig struct { Name string `toml:"name"` Endpoint string `toml:"endpoint"` @@ -549,7 +502,6 @@ type DatacenterConfig struct { TimeoutSec int `toml:"timeout_sec"` } -// MigrationSettings представляет настройки миграции type MigrationSettings struct { BatchSize int `toml:"batch_size"` Workers int `toml:"workers"` @@ -562,14 +514,12 @@ type MigrationSettings struct { ExcludeCollections []string `toml:"exclude_collections"` } -// DeltaSyncConfig представляет конфигурацию дельта-синхронизации type DeltaSyncConfig struct { Enabled bool `toml:"enabled"` IntervalSec int `toml:"interval_sec"` MaxLagSec int `toml:"max_lag_sec"` } -// ValidationConfig представляет конфигурацию валидации type ValidationConfig struct { Enabled bool `toml:"enabled"` SamplePercent int `toml:"sample_percent"` @@ -580,21 +530,18 @@ type ValidationConfig struct { // ВСПОМОГАТЕЛЬНЫЕ СТРУКТУРЫ // ============================================================================= -// ValidationResult содержит результаты валидации конфигурации. type ValidationResult struct { - Valid bool // Корректна ли конфигурация - Errors []error // Критические ошибки - Warnings []error // Предупреждения (некритичные) + Valid bool + Errors []error + Warnings []error } // ============================================================================= // ГЕТТЕРЫ ДЛЯ SagaConfig // ============================================================================= -// IsSagaEnabled возвращает флаг включения SAGA оркестратора. func (s *SagaConfig) IsSagaEnabled() bool { return s.Enabled } -// GetCoordinatorCount возвращает количество координаторов. func (s *SagaConfig) GetCoordinatorCount() int { if s.CoordinatorCount < 1 { return 3 @@ -602,7 +549,6 @@ func (s *SagaConfig) GetCoordinatorCount() int { return s.CoordinatorCount } -// GetStateDir возвращает директорию для хранения состояний SAGA. func (s *SagaConfig) GetStateDir() string { if s.StateDir == "" { return "saga_states" @@ -610,7 +556,6 @@ func (s *SagaConfig) GetStateDir() string { return s.StateDir } -// GetMaxRetries возвращает максимальное количество попыток выполнения шага. func (s *SagaConfig) GetMaxRetries() int { if s.MaxRetries <= 0 { return 5 @@ -618,7 +563,6 @@ func (s *SagaConfig) GetMaxRetries() int { return s.MaxRetries } -// GetRetryBackoff возвращает базовую задержку между повторными попытками. func (s *SagaConfig) GetRetryBackoff() time.Duration { if s.RetryBackoffMs <= 0 { return 100 * time.Millisecond @@ -626,7 +570,6 @@ func (s *SagaConfig) GetRetryBackoff() time.Duration { return time.Duration(s.RetryBackoffMs) * time.Millisecond } -// GetSagaTimeout возвращает таймаут выполнения SAGA. func (s *SagaConfig) GetSagaTimeout() time.Duration { if s.SagaTimeoutSec <= 0 { return 300 * time.Second @@ -634,7 +577,6 @@ func (s *SagaConfig) GetSagaTimeout() time.Duration { return time.Duration(s.SagaTimeoutSec) * time.Second } -// GetStuckCheckInterval возвращает интервал проверки зависших SAGA. func (s *SagaConfig) GetStuckCheckInterval() time.Duration { if s.StuckCheckIntervalSec <= 0 { return 10 * time.Second @@ -642,7 +584,6 @@ func (s *SagaConfig) GetStuckCheckInterval() time.Duration { return time.Duration(s.StuckCheckIntervalSec) * time.Second } -// GetLeaderElectionInterval возвращает интервал выбора лидера. func (s *SagaConfig) GetLeaderElectionInterval() time.Duration { if s.LeaderElectionIntervalSec <= 0 { return 5 * time.Second @@ -650,7 +591,6 @@ func (s *SagaConfig) GetLeaderElectionInterval() time.Duration { return time.Duration(s.LeaderElectionIntervalSec) * time.Second } -// GetRecoveryInterval возвращает интервал восстановления незавершённых SAGA. func (s *SagaConfig) GetRecoveryInterval() time.Duration { if s.RecoveryIntervalSec <= 0 { return 30 * time.Second @@ -658,7 +598,6 @@ func (s *SagaConfig) GetRecoveryInterval() time.Duration { return time.Duration(s.RecoveryIntervalSec) * time.Second } -// GetMetricsInterval возвращает интервал сбора метрик. func (s *SagaConfig) GetMetricsInterval() time.Duration { if s.MetricsIntervalSec <= 0 { return 60 * time.Second @@ -666,7 +605,6 @@ func (s *SagaConfig) GetMetricsInterval() time.Duration { return time.Duration(s.MetricsIntervalSec) * time.Second } -// GetCleanupPeriod возвращает период очистки старых SAGA. func (s *SagaConfig) GetCleanupPeriod() time.Duration { if s.CleanupPeriodHours <= 0 { return 24 * time.Hour @@ -674,7 +612,6 @@ func (s *SagaConfig) GetCleanupPeriod() time.Duration { return time.Duration(s.CleanupPeriodHours) * time.Hour } -// GetMaxCacheSize возвращает максимальное количество состояний в кэше. func (s *SagaConfig) GetMaxCacheSize() int { if s.MaxCacheSize <= 0 { return 10000 @@ -682,7 +619,6 @@ func (s *SagaConfig) GetMaxCacheSize() int { return s.MaxCacheSize } -// GetOperationRetentionDuration возвращает время жизни выполненных операций. func (s *SagaConfig) GetOperationRetentionDuration() time.Duration { if s.OperationRetentionDays <= 0 { return 7 * 24 * time.Hour @@ -690,7 +626,6 @@ func (s *SagaConfig) GetOperationRetentionDuration() time.Duration { return time.Duration(s.OperationRetentionDays) * 24 * time.Hour } -// GetChannelBufferSize возвращает размер буфера каналов. func (s *SagaConfig) GetChannelBufferSize() int { if s.ChannelBufferSize <= 0 { return 10000 @@ -698,7 +633,6 @@ func (s *SagaConfig) GetChannelBufferSize() int { return s.ChannelBufferSize } -// GetAsyncRecoveryWorkers возвращает количество воркеров для асинхронного восстановления. func (s *SagaConfig) GetAsyncRecoveryWorkers() int { if s.AsyncRecoveryWorkers <= 0 { return 4 @@ -706,7 +640,6 @@ func (s *SagaConfig) GetAsyncRecoveryWorkers() int { return s.AsyncRecoveryWorkers } -// GetAsyncRecoveryTimeout возвращает таймаут асинхронного восстановления. func (s *SagaConfig) GetAsyncRecoveryTimeout() time.Duration { if s.AsyncRecoveryTimeoutSec <= 0 { return 30 * time.Second @@ -714,10 +647,8 @@ func (s *SagaConfig) GetAsyncRecoveryTimeout() time.Duration { return time.Duration(s.AsyncRecoveryTimeoutSec) * time.Second } -// IsFsyncEnabled возвращает флаг принудительной синхронизации с диском. func (s *SagaConfig) IsFsyncEnabled() bool { return s.FsyncEnabled } -// GetFsyncMaxRetries возвращает количество повторных попыток синхронизации. func (s *SagaConfig) GetFsyncMaxRetries() int { if s.FsyncMaxRetries <= 0 { return 3 @@ -725,7 +656,6 @@ func (s *SagaConfig) GetFsyncMaxRetries() int { return s.FsyncMaxRetries } -// GetFsyncRetryDelay возвращает задержку между повторными попытками синхронизации. func (s *SagaConfig) GetFsyncRetryDelay() time.Duration { if s.FsyncRetryDelayMs <= 0 { return 100 * time.Millisecond @@ -737,7 +667,6 @@ func (s *SagaConfig) GetFsyncRetryDelay() time.Duration { // ГЕТТЕРЫ ДЛЯ ReplicationConfig // ============================================================================= -// GetReplicationTimeout возвращает таймаут репликации как time.Duration. func (r *ReplicationConfig) GetReplicationTimeout() time.Duration { if r.ReplicationTimeoutMs <= 0 { return 5 * time.Second @@ -745,13 +674,10 @@ func (r *ReplicationConfig) GetReplicationTimeout() time.Duration { return time.Duration(r.ReplicationTimeoutMs) * time.Millisecond } -// IsReplicationEnabled возвращает флаг включения репликации. func (r *ReplicationConfig) IsReplicationEnabled() bool { return r.Enabled } -// IsSyncReplicationEnabled возвращает флаг синхронной репликации. func (r *ReplicationConfig) IsSyncReplicationEnabled() bool { return r.SyncReplication } -// GetMaxReplicaLag возвращает максимальное допустимое отставание реплики. func (r *ReplicationConfig) GetMaxReplicaLag() time.Duration { if r.MaxReplicaLagMs <= 0 { return 5 * time.Second @@ -763,7 +689,6 @@ func (r *ReplicationConfig) GetMaxReplicaLag() time.Duration { // ГЕТТЕРЫ ДЛЯ ClusterConfig // ============================================================================= -// GetHeartbeatTimeout возвращает таймаут heartbeat-сообщений. func (c *ClusterConfig) GetHeartbeatTimeout() time.Duration { if c.HeartbeatTimeoutMs <= 0 { return 1000 * time.Millisecond @@ -771,7 +696,6 @@ func (c *ClusterConfig) GetHeartbeatTimeout() time.Duration { return time.Duration(c.HeartbeatTimeoutMs) * time.Millisecond } -// GetElectionTimeout возвращает таймаут для начала выборов лидера. func (c *ClusterConfig) GetElectionTimeout() time.Duration { if c.ElectionTimeoutMs <= 0 { return 1000 * time.Millisecond @@ -779,7 +703,6 @@ func (c *ClusterConfig) GetElectionTimeout() time.Duration { return time.Duration(c.ElectionTimeoutMs) * time.Millisecond } -// GetCommitTimeout возвращает таймаут коммита записей. func (c *ClusterConfig) GetCommitTimeout() time.Duration { if c.CommitTimeoutMs <= 0 { return 500 * time.Millisecond @@ -787,7 +710,6 @@ func (c *ClusterConfig) GetCommitTimeout() time.Duration { return time.Duration(c.CommitTimeoutMs) * time.Millisecond } -// GetSnapshotInterval возвращает интервал создания снэпшотов. func (c *ClusterConfig) GetSnapshotInterval() time.Duration { if c.SnapshotIntervalMin <= 0 { return 30 * time.Minute @@ -795,7 +717,6 @@ func (c *ClusterConfig) GetSnapshotInterval() time.Duration { return time.Duration(c.SnapshotIntervalMin) * time.Minute } -// GetSnapshotThreshold возвращает порог количества записей для создания снэпшота. func (c *ClusterConfig) GetSnapshotThreshold() uint64 { if c.SnapshotThreshold <= 0 { return 1000 @@ -803,10 +724,8 @@ func (c *ClusterConfig) GetSnapshotThreshold() uint64 { return uint64(c.SnapshotThreshold) } -// IsSplitBrainPreventionEnabled возвращает флаг защиты от split-brain. func (c *ClusterConfig) IsSplitBrainPreventionEnabled() bool { return c.SplitBrainPrevention } -// GetRecoveryTimeout возвращает таймаут восстановления после сбоя. func (c *ClusterConfig) GetRecoveryTimeout() time.Duration { if c.RecoveryTimeoutSec <= 0 { return 30 * time.Second @@ -814,7 +733,6 @@ func (c *ClusterConfig) GetRecoveryTimeout() time.Duration { return time.Duration(c.RecoveryTimeoutSec) * time.Second } -// GetRegion возвращает регион узла. func (c *ClusterConfig) GetRegion() string { if c.Region == "" { return "default" @@ -822,7 +740,6 @@ func (c *ClusterConfig) GetRegion() string { return c.Region } -// GetPriorityZone возвращает приоритетную зону узла. func (c *ClusterConfig) GetPriorityZone() int { if c.PriorityZone < 0 { return 0 @@ -837,7 +754,6 @@ func (c *ClusterConfig) GetPriorityZone() int { // ГЕТТЕРЫ ДЛЯ PluginsConfig // ============================================================================= -// GetMaxCPUTime возвращает максимальное время CPU для выполнения скрипта. func (p *PluginsConfig) GetMaxCPUTime() time.Duration { if p.MaxCPUTimeMs <= 0 { return 100 * time.Millisecond @@ -845,7 +761,6 @@ func (p *PluginsConfig) GetMaxCPUTime() time.Duration { return time.Duration(p.MaxCPUTimeMs) * time.Millisecond } -// GetMaxMemory возвращает максимальный объем памяти для скрипта в байтах. func (p *PluginsConfig) GetMaxMemory() int64 { if p.MaxMemoryMB <= 0 { return 50 * 1024 * 1024 @@ -853,7 +768,6 @@ func (p *PluginsConfig) GetMaxMemory() int64 { return int64(p.MaxMemoryMB) * 1024 * 1024 } -// GetMaxExecutionTime возвращает максимальное время выполнения скрипта. func (p *PluginsConfig) GetMaxExecutionTime() time.Duration { if p.MaxExecutionTimeSec <= 0 { return 5 * time.Second @@ -861,7 +775,6 @@ func (p *PluginsConfig) GetMaxExecutionTime() time.Duration { return time.Duration(p.MaxExecutionTimeSec) * time.Second } -// GetMaxInstructions возвращает максимальное количество инструкций для скрипта. func (p *PluginsConfig) GetMaxInstructions() int64 { if p.MaxInstructions <= 0 { return 1000000 @@ -869,7 +782,6 @@ func (p *PluginsConfig) GetMaxInstructions() int64 { return p.MaxInstructions } -// GetHotReloadInterval возвращает интервал горячей перезагрузки скриптов. func (p *PluginsConfig) GetHotReloadInterval() time.Duration { if p.HotReloadIntervalSec <= 0 { return 30 * time.Second @@ -877,7 +789,6 @@ func (p *PluginsConfig) GetHotReloadInterval() time.Duration { return time.Duration(p.HotReloadIntervalSec) * time.Second } -// GetMaxEventLogSize возвращает максимальный размер лога событий. func (p *PluginsConfig) GetMaxEventLogSize() int { if p.MaxEventLogSize <= 0 { return 1000 @@ -885,7 +796,6 @@ func (p *PluginsConfig) GetMaxEventLogSize() int { return p.MaxEventLogSize } -// GetLoadTimeout возвращает таймаут загрузки скрипта. func (p *PluginsConfig) GetLoadTimeout() time.Duration { if p.LoadTimeoutSec <= 0 { return 10 * time.Second @@ -893,7 +803,6 @@ func (p *PluginsConfig) GetLoadTimeout() time.Duration { return time.Duration(p.LoadTimeoutSec) * time.Second } -// GetMaxLuaStates возвращает максимальное количество Lua-состояний. func (p *PluginsConfig) GetMaxLuaStates() int { if p.MaxLuaStates <= 0 { return 100 @@ -901,7 +810,6 @@ func (p *PluginsConfig) GetMaxLuaStates() int { return p.MaxLuaStates } -// GetLuaStateTTL возвращает время жизни Lua-состояния. func (p *PluginsConfig) GetLuaStateTTL() time.Duration { if p.LuaStateTTLSec <= 0 { return 10 * time.Minute @@ -909,7 +817,6 @@ func (p *PluginsConfig) GetLuaStateTTL() time.Duration { return time.Duration(p.LuaStateTTLSec) * time.Second } -// GetEnginePluginDir возвращает директорию с плагинами движков. func (p *PluginsConfig) GetEnginePluginDir() string { if p.EnginePluginDir == "" { return "engines" @@ -921,7 +828,6 @@ func (p *PluginsConfig) GetEnginePluginDir() string { // ГЕТТЕРЫ ДЛЯ WALConfig // ============================================================================= -// GetSegmentSize возвращает размер сегмента WAL в байтах. func (w *WALConfig) GetSegmentSize() int64 { if w.SegmentSizeMB <= 0 { return 64 * 1024 * 1024 @@ -929,7 +835,6 @@ func (w *WALConfig) GetSegmentSize() int64 { return int64(w.SegmentSizeMB) * 1024 * 1024 } -// GetSyncInterval возвращает интервал синхронизации WAL с диском. func (w *WALConfig) GetSyncInterval() time.Duration { if w.SyncIntervalSec <= 0 { return 5 * time.Second @@ -937,7 +842,6 @@ func (w *WALConfig) GetSyncInterval() time.Duration { return time.Duration(w.SyncIntervalSec) * time.Second } -// GetBatchSize возвращает размер пакета для записи в WAL. func (w *WALConfig) GetBatchSize() int { if w.BatchSize <= 0 { return 100 @@ -945,7 +849,6 @@ func (w *WALConfig) GetBatchSize() int { return w.BatchSize } -// GetRecoveryWorkers возвращает количество потоков для восстановления из WAL. func (w *WALConfig) GetRecoveryWorkers() int { if w.RecoveryWorkers <= 0 { return 4 @@ -953,13 +856,10 @@ func (w *WALConfig) GetRecoveryWorkers() int { return w.RecoveryWorkers } -// IsWALEnabled возвращает флаг включения WAL. func (w *WALConfig) IsWALEnabled() bool { return w.Enabled } -// IsAsyncRecoveryEnabled возвращает флаг асинхронного восстановления. func (w *WALConfig) IsAsyncRecoveryEnabled() bool { return w.AsyncRecovery } -// GetAsyncRecoveryWorkers возвращает количество потоков асинхронного восстановления. func (w *WALConfig) GetAsyncRecoveryWorkers() int { if w.AsyncRecoveryWorkers <= 0 { return 4 @@ -967,7 +867,6 @@ func (w *WALConfig) GetAsyncRecoveryWorkers() int { return w.AsyncRecoveryWorkers } -// GetAsyncRecoveryBuffer возвращает размер буфера асинхронного восстановления. func (w *WALConfig) GetAsyncRecoveryBuffer() int { if w.AsyncRecoveryBuffer <= 0 { return 10000 @@ -979,7 +878,6 @@ func (w *WALConfig) GetAsyncRecoveryBuffer() int { // ГЕТТЕРЫ ДЛЯ MVCCConfig // ============================================================================= -// GetMaxVersionsPerDoc возвращает максимальное количество версий на документ. func (m *MVCCConfig) GetMaxVersionsPerDoc() int { if m.MaxVersionsPerDoc <= 0 { return 10 @@ -987,7 +885,6 @@ func (m *MVCCConfig) GetMaxVersionsPerDoc() int { return m.MaxVersionsPerDoc } -// GetVisibilityMapSize возвращает размер карты видимости. func (m *MVCCConfig) GetVisibilityMapSize() int { if m.VisibilityMapSize <= 0 { return 1024 * 1024 @@ -995,7 +892,6 @@ func (m *MVCCConfig) GetVisibilityMapSize() int { return m.VisibilityMapSize } -// GetPruneInterval возвращает интервал очистки старых версий. func (m *MVCCConfig) GetPruneInterval() time.Duration { if m.PruneIntervalMin <= 0 { return 5 * time.Minute @@ -1003,7 +899,6 @@ func (m *MVCCConfig) GetPruneInterval() time.Duration { return time.Duration(m.PruneIntervalMin) * time.Minute } -// GetRetentionDays возвращает срок хранения старых версий в днях. func (m *MVCCConfig) GetRetentionDays() int { if m.RetentionDays <= 0 { return 7 @@ -1011,7 +906,6 @@ func (m *MVCCConfig) GetRetentionDays() int { return m.RetentionDays } -// GetReadCacheSize возвращает размер кэша чтения. func (m *MVCCConfig) GetReadCacheSize() int { if m.ReadCacheSize <= 0 { return 10000 @@ -1019,7 +913,6 @@ func (m *MVCCConfig) GetReadCacheSize() int { return m.ReadCacheSize } -// GetReadCacheTTL возвращает TTL кэша чтения. func (m *MVCCConfig) GetReadCacheTTL() time.Duration { if m.ReadCacheTTLSec <= 0 { return 300 * time.Second @@ -1031,7 +924,6 @@ func (m *MVCCConfig) GetReadCacheTTL() time.Duration { // ГЕТТЕРЫ ДЛЯ TransactionsConfig // ============================================================================= -// GetDefaultTimeout возвращает таймаут транзакции по умолчанию. func (t *TransactionsConfig) GetDefaultTimeout() time.Duration { if t.DefaultTimeoutSec <= 0 { return 30 * time.Second @@ -1039,7 +931,6 @@ func (t *TransactionsConfig) GetDefaultTimeout() time.Duration { return time.Duration(t.DefaultTimeoutSec) * time.Second } -// GetDeadlockCheckInterval возвращает интервал проверки взаимоблокировок. func (t *TransactionsConfig) GetDeadlockCheckInterval() time.Duration { if t.DeadlockCheckIntervalSec <= 0 { return 1 * time.Second @@ -1047,7 +938,6 @@ func (t *TransactionsConfig) GetDeadlockCheckInterval() time.Duration { return time.Duration(t.DeadlockCheckIntervalSec) * time.Second } -// GetMaxSavepointsPerTx возвращает максимальное количество точек сохранения. func (t *TransactionsConfig) GetMaxSavepointsPerTx() int { if t.MaxSavepointsPerTx <= 0 { return 100 @@ -1055,10 +945,8 @@ func (t *TransactionsConfig) GetMaxSavepointsPerTx() int { return t.MaxSavepointsPerTx } -// IsTransactionsEnabled возвращает флаг включения транзакций. func (t *TransactionsConfig) IsTransactionsEnabled() bool { return t.Enabled } -// GetCheckpointInterval возвращает интервал контрольных точек в секундах. func (t *TransactionsConfig) GetCheckpointInterval() int64 { if t.CheckpointIntervalSec <= 0 { return 300 @@ -1070,7 +958,6 @@ func (t *TransactionsConfig) GetCheckpointInterval() int64 { // ГЕТТЕРЫ ДЛЯ ACLConfig // ============================================================================= -// GetMaxDeniedLogSize возвращает максимальный размер лога отказов в доступе. func (a *ACLConfig) GetMaxDeniedLogSize() int { if a.MaxDeniedLogSize <= 0 { return 10000 @@ -1078,7 +965,6 @@ func (a *ACLConfig) GetMaxDeniedLogSize() int { return a.MaxDeniedLogSize } -// GetTemporaryGrantTTL возвращает TTL временных прав доступа. func (a *ACLConfig) GetTemporaryGrantTTL() time.Duration { if a.TemporaryGrantTTLHours <= 0 { return 24 * time.Hour @@ -1086,10 +972,8 @@ func (a *ACLConfig) GetTemporaryGrantTTL() time.Duration { return time.Duration(a.TemporaryGrantTTLHours) * time.Hour } -// IsRoleHierarchyEnabled возвращает флаг включения иерархии ролей. func (a *ACLConfig) IsRoleHierarchyEnabled() bool { return a.EnableRoleHierarchy } -// GetCacheTTL возвращает TTL кэша ACL. func (a *ACLConfig) GetCacheTTL() time.Duration { if a.CacheTTLSec <= 0 { return 60 * time.Second @@ -1101,7 +985,6 @@ func (a *ACLConfig) GetCacheTTL() time.Duration { // ГЕТТЕРЫ ДЛЯ TLSConfig // ============================================================================= -// GetTLSMinVersion возвращает минимальную версию TLS как строку. func (t *TLSConfig) GetTLSMinVersion() string { if t.MinVersion == "" { return "1.2" @@ -1109,13 +992,10 @@ func (t *TLSConfig) GetTLSMinVersion() string { return t.MinVersion } -// IsTLSEnabled возвращает флаг включения TLS. func (t *TLSConfig) IsTLSEnabled() bool { return t.Enabled } -// IsMutualAuthEnabled возвращает флаг взаимной аутентификации. func (t *TLSConfig) IsMutualAuthEnabled() bool { return t.MutualAuth } -// GetKeyRotationDays возвращает интервал ротации ключей в днях. func (t *TLSConfig) GetKeyRotationDays() int { if t.KeyRotationDays <= 0 { return 30 @@ -1123,17 +1003,14 @@ func (t *TLSConfig) GetKeyRotationDays() int { return t.KeyRotationDays } -// IsAutoGenerateEnabled возвращает флаг автоматической генерации сертификатов. func (t *TLSConfig) IsAutoGenerateEnabled() bool { return t.AutoGenerate } // ============================================================================= // ГЕТТЕРЫ ДЛЯ BackpressureConfig // ============================================================================= -// IsBackpressureEnabled возвращает флаг включения механизма обратного давления. func (b *BackpressureConfig) IsBackpressureEnabled() bool { return b.Enabled } -// GetCPUThreshold возвращает порог загрузки CPU. func (b *BackpressureConfig) GetCPUThreshold() float64 { if b.CPUThreshold <= 0 { return 0.8 @@ -1144,7 +1021,6 @@ func (b *BackpressureConfig) GetCPUThreshold() float64 { return b.CPUThreshold } -// GetMemoryThreshold возвращает порог использования памяти. func (b *BackpressureConfig) GetMemoryThreshold() float64 { if b.MemoryThreshold <= 0 { return 0.85 @@ -1155,7 +1031,6 @@ func (b *BackpressureConfig) GetMemoryThreshold() float64 { return b.MemoryThreshold } -// GetQueueSizeThreshold возвращает порог размера очереди. func (b *BackpressureConfig) GetQueueSizeThreshold() int { if b.QueueSizeThreshold <= 0 { return 10000 @@ -1163,7 +1038,6 @@ func (b *BackpressureConfig) GetQueueSizeThreshold() int { return b.QueueSizeThreshold } -// GetConnectionThreshold возвращает порог количества соединений. func (b *BackpressureConfig) GetConnectionThreshold() int { if b.ConnectionThreshold <= 0 { return 5000 @@ -1171,7 +1045,6 @@ func (b *BackpressureConfig) GetConnectionThreshold() int { return b.ConnectionThreshold } -// GetCheckInterval возвращает интервал проверки нагрузки. func (b *BackpressureConfig) GetCheckInterval() time.Duration { if b.CheckIntervalMs <= 0 { return 1 * time.Second @@ -1179,7 +1052,6 @@ func (b *BackpressureConfig) GetCheckInterval() time.Duration { return time.Duration(b.CheckIntervalMs) * time.Millisecond } -// GetLowDelay возвращает задержку при низкой нагрузке. func (b *BackpressureConfig) GetLowDelay() time.Duration { if b.LowDelayMs <= 0 { return 100 * time.Millisecond @@ -1187,7 +1059,6 @@ func (b *BackpressureConfig) GetLowDelay() time.Duration { return time.Duration(b.LowDelayMs) * time.Millisecond } -// GetMediumRejectProb возвращает вероятность отказа при средней нагрузке. func (b *BackpressureConfig) GetMediumRejectProb() uint32 { if b.MediumRejectProb > 100 { return 100 @@ -1195,7 +1066,6 @@ func (b *BackpressureConfig) GetMediumRejectProb() uint32 { return b.MediumRejectProb } -// GetHighRejectProb возвращает вероятность отказа при высокой нагрузке. func (b *BackpressureConfig) GetHighRejectProb() uint32 { if b.HighRejectProb > 100 { return 100 @@ -1207,10 +1077,8 @@ func (b *BackpressureConfig) GetHighRejectProb() uint32 { // ГЕТТЕРЫ ДЛЯ RuntimeLimitsConfig // ============================================================================= -// IsRuntimeLimitsEnabled возвращает флаг включения ограничений времени выполнения. func (r *RuntimeLimitsConfig) IsRuntimeLimitsEnabled() bool { return r.Enabled } -// GetGlobalMaxDocSizeMB возвращает максимальный размер документа в МБ. func (r *RuntimeLimitsConfig) GetGlobalMaxDocSizeMB() int { if r.GlobalMaxDocSizeMB <= 0 { return 16 @@ -1218,7 +1086,6 @@ func (r *RuntimeLimitsConfig) GetGlobalMaxDocSizeMB() int { return r.GlobalMaxDocSizeMB } -// GetGlobalMaxCollSizeMB возвращает максимальный размер коллекции в МБ. func (r *RuntimeLimitsConfig) GetGlobalMaxCollSizeMB() int64 { if r.GlobalMaxCollSizeMB <= 0 { return 10240 @@ -1226,7 +1093,6 @@ func (r *RuntimeLimitsConfig) GetGlobalMaxCollSizeMB() int64 { return r.GlobalMaxCollSizeMB } -// GetGlobalMaxDocsPerColl возвращает максимальное количество документов в коллекции. func (r *RuntimeLimitsConfig) GetGlobalMaxDocsPerColl() int64 { if r.GlobalMaxDocsPerColl <= 0 { return 10000000 @@ -1238,10 +1104,8 @@ func (r *RuntimeLimitsConfig) GetGlobalMaxDocsPerColl() int64 { // ГЕТТЕРЫ ДЛЯ AutoscalingConfig // ============================================================================= -// IsAutoscalingEnabled возвращает флаг включения автомасштабирования. func (a *AutoscalingConfig) IsAutoscalingEnabled() bool { return a.Enabled } -// GetMinNodes возвращает минимальное количество узлов. func (a *AutoscalingConfig) GetMinNodes() int { if a.MinNodes <= 0 { return 1 @@ -1249,7 +1113,6 @@ func (a *AutoscalingConfig) GetMinNodes() int { return a.MinNodes } -// GetMaxNodes возвращает максимальное количество узлов. func (a *AutoscalingConfig) GetMaxNodes() int { if a.MaxNodes <= 0 { return 10 @@ -1257,7 +1120,6 @@ func (a *AutoscalingConfig) GetMaxNodes() int { return a.MaxNodes } -// GetScaleUpThreshold возвращает порог для масштабирования вверх. func (a *AutoscalingConfig) GetScaleUpThreshold() float64 { if a.ScaleUpThreshold <= 0 { return 0.75 @@ -1268,7 +1130,6 @@ func (a *AutoscalingConfig) GetScaleUpThreshold() float64 { return a.ScaleUpThreshold } -// GetScaleDownThreshold возвращает порог для масштабирования вниз. func (a *AutoscalingConfig) GetScaleDownThreshold() float64 { if a.ScaleDownThreshold <= 0 { return 0.30 @@ -1276,7 +1137,6 @@ func (a *AutoscalingConfig) GetScaleDownThreshold() float64 { return a.ScaleDownThreshold } -// GetScaleUpCooldown возвращает задержку перед масштабированием вверх. func (a *AutoscalingConfig) GetScaleUpCooldown() time.Duration { if a.ScaleUpCooldownSec <= 0 { return 5 * time.Minute @@ -1284,7 +1144,6 @@ func (a *AutoscalingConfig) GetScaleUpCooldown() time.Duration { return time.Duration(a.ScaleUpCooldownSec) * time.Second } -// GetScaleDownCooldown возвращает задержку перед масштабированием вниз. func (a *AutoscalingConfig) GetScaleDownCooldown() time.Duration { if a.ScaleDownCooldownSec <= 0 { return 10 * time.Minute @@ -1292,7 +1151,6 @@ func (a *AutoscalingConfig) GetScaleDownCooldown() time.Duration { return time.Duration(a.ScaleDownCooldownSec) * time.Second } -// GetEvaluationInterval возвращает интервал оценки нагрузки. func (a *AutoscalingConfig) GetEvaluationInterval() time.Duration { if a.EvaluationIntervalSec <= 0 { return 30 * time.Second @@ -1300,10 +1158,8 @@ func (a *AutoscalingConfig) GetEvaluationInterval() time.Duration { return time.Duration(a.EvaluationIntervalSec) * time.Second } -// IsPredictiveEnabled возвращает флаг прогнозирующего масштабирования. func (a *AutoscalingConfig) IsPredictiveEnabled() bool { return a.PredictiveEnabled } -// GetMaxScaleUpNodes возвращает максимальное количество узлов для масштабирования вверх. func (a *AutoscalingConfig) GetMaxScaleUpNodes() int { if a.MaxScaleUpNodes <= 0 { return 3 @@ -1311,7 +1167,6 @@ func (a *AutoscalingConfig) GetMaxScaleUpNodes() int { return a.MaxScaleUpNodes } -// GetMaxScaleDownNodes возвращает максимальное количество узлов для масштабирования вниз. func (a *AutoscalingConfig) GetMaxScaleDownNodes() int { if a.MaxScaleDownNodes <= 0 { return 2 @@ -1323,10 +1178,8 @@ func (a *AutoscalingConfig) GetMaxScaleDownNodes() int { // ГЕТТЕРЫ ДЛЯ SchemaMigrationConfig // ============================================================================= -// IsSchemaMigrationEnabled возвращает флаг включения миграции схемы. func (s *SchemaMigrationConfig) IsSchemaMigrationEnabled() bool { return s.Enabled } -// GetMigrationDir возвращает директорию с миграциями. func (s *SchemaMigrationConfig) GetMigrationDir() string { if s.MigrationDir == "" { return "migrations" @@ -1334,10 +1187,8 @@ func (s *SchemaMigrationConfig) GetMigrationDir() string { return s.MigrationDir } -// IsAutoMigrateEnabled возвращает флаг автоматической миграции при старте. func (s *SchemaMigrationConfig) IsAutoMigrateEnabled() bool { return s.AutoMigrate } -// GetTargetVersion возвращает целевую версию схемы. func (s *SchemaMigrationConfig) GetTargetVersion() string { if s.TargetVersion == "" { return "latest" @@ -1349,10 +1200,8 @@ func (s *SchemaMigrationConfig) GetTargetVersion() string { // ГЕТТЕРЫ ДЛЯ BackupConfig // ============================================================================= -// IsBackupEnabled возвращает флаг включения резервного копирования. func (b *BackupConfig) IsBackupEnabled() bool { return b.Enabled } -// GetBackupDir возвращает директорию для резервных копий. func (b *BackupConfig) GetBackupDir() string { if b.BackupDir == "" { return "backups" @@ -1360,7 +1209,6 @@ func (b *BackupConfig) GetBackupDir() string { return b.BackupDir } -// GetMaxConcurrentBackups возвращает максимальное количество параллельных бэкапов. func (b *BackupConfig) GetMaxConcurrentBackups() int { if b.MaxConcurrent <= 0 { return 1 @@ -1368,10 +1216,8 @@ func (b *BackupConfig) GetMaxConcurrentBackups() int { return b.MaxConcurrent } -// IsCompressEnabled возвращает флаг сжатия резервных копий. func (b *BackupConfig) IsCompressEnabled() bool { return b.CompressEnabled } -// GetBackupRetentionDays возвращает срок хранения резервных копий в днях. func (b *BackupConfig) GetBackupRetentionDays() int { if b.RetentionDays <= 0 { return 7 @@ -1379,23 +1225,14 @@ func (b *BackupConfig) GetBackupRetentionDays() int { return b.RetentionDays } -// IsIncludeSagaStateEnabled возвращает флаг включения состояния SAGA в бэкап. -// -// ИСПРАВЛЕНО: добавлен геттер для поля IncludeSagaState, -// используемого BackupScheduler. func (b *BackupConfig) IsIncludeSagaStateEnabled() bool { return b.IncludeSagaState } -// IsIncrementalEnabled возвращает флаг разрешения инкрементальных бэкапов. -// -// ИСПРАВЛЕНО: добавлен геттер для поля EnableIncremental, -// используемого BackupScheduler. func (b *BackupConfig) IsIncrementalEnabled() bool { return b.EnableIncremental } // ============================================================================= // ГЕТТЕРЫ ДЛЯ StorageConfig // ============================================================================= -// GetDefaultEngine возвращает движок хранения по умолчанию. func (s *StorageConfig) GetDefaultEngine() string { if s.DefaultEngine == "" { return "row" @@ -1403,14 +1240,12 @@ func (s *StorageConfig) GetDefaultEngine() string { return s.DefaultEngine } -// IsCustomEnginesEnabled возвращает флаг включения пользовательских движков. func (s *StorageConfig) IsCustomEnginesEnabled() bool { return s.EnableCustomEngines } // ============================================================================= // МЕТОДЫ ДЛЯ EnginesConfig // ============================================================================= -// IsEngineEnabled проверяет, включен ли указанный движок хранения. func (e *EnginesConfig) IsEngineEnabled(name string) bool { switch name { case "row": @@ -1430,7 +1265,6 @@ func (e *EnginesConfig) IsEngineEnabled(name string) bool { } } -// GetEngineConfig возвращает конфигурацию указанного движка хранения. func (e *EnginesConfig) GetEngineConfig(name string) map[string]interface{} { switch name { case "row": @@ -1450,7 +1284,6 @@ func (e *EnginesConfig) GetEngineConfig(name string) map[string]interface{} { } } -// GetEngineDescription возвращает описание указанного движка хранения. func (e *EnginesConfig) GetEngineDescription(name string) string { switch name { case "row": @@ -1474,7 +1307,6 @@ func (e *EnginesConfig) GetEngineDescription(name string) string { // ГЕТТЕРЫ ДЛЯ RecoveryConfig // ============================================================================= -// GetMaxRetryDuration возвращает максимальную длительность повторных попыток. func (r *RecoveryConfig) GetMaxRetryDuration() time.Duration { if r.MaxRetrySec <= 0 { return 300 * time.Second @@ -1482,7 +1314,6 @@ func (r *RecoveryConfig) GetMaxRetryDuration() time.Duration { return time.Duration(r.MaxRetrySec) * time.Second } -// GetDataReplicationTimeout возвращает таймаут репликации данных при восстановлении. func (r *RecoveryConfig) GetDataReplicationTimeout() time.Duration { if r.DataReplicationTimeoutSec <= 0 { return 60 * time.Second @@ -1490,7 +1321,6 @@ func (r *RecoveryConfig) GetDataReplicationTimeout() time.Duration { return time.Duration(r.DataReplicationTimeoutSec) * time.Second } -// GetStaleReadTimeout возвращает таймаут для чтения устаревших данных. func (r *RecoveryConfig) GetStaleReadTimeout() time.Duration { if r.StaleReadTimeoutSec <= 0 { return 30 * time.Second @@ -1498,14 +1328,12 @@ func (r *RecoveryConfig) GetStaleReadTimeout() time.Duration { return time.Duration(r.StaleReadTimeoutSec) * time.Second } -// IsAutoRejoinEnabled возвращает флаг автоматического переподключения. func (r *RecoveryConfig) IsAutoRejoinEnabled() bool { return r.AutoRejoin } // ============================================================================= // ГЕТТЕРЫ ДЛЯ PerformanceConfig // ============================================================================= -// GetBatchSize возвращает размер пакета для пакетных операций. func (p *PerformanceConfig) GetBatchSize() int { if p.BatchSize <= 0 { return 100 @@ -1513,7 +1341,6 @@ func (p *PerformanceConfig) GetBatchSize() int { return p.BatchSize } -// GetMaxConnections возвращает максимальное количество соединений. func (p *PerformanceConfig) GetMaxConnections() int { if p.MaxConnections <= 0 { return 1000 @@ -1521,13 +1348,10 @@ func (p *PerformanceConfig) GetMaxConnections() int { return p.MaxConnections } -// IsReadFromFollowerEnabled возвращает флаг чтения с ведомых узлов. func (p *PerformanceConfig) IsReadFromFollowerEnabled() bool { return p.ReadFromFollower } -// IsPipelineEnabled возвращает флаг конвейерной обработки. func (p *PerformanceConfig) IsPipelineEnabled() bool { return p.EnablePipeline } -// GetReadReplicaDelay возвращает задержку чтения с реплики. func (p *PerformanceConfig) GetReadReplicaDelay() time.Duration { if p.ReadReplicaDelayMs <= 0 { return 100 * time.Millisecond @@ -1539,7 +1363,6 @@ func (p *PerformanceConfig) GetReadReplicaDelay() time.Duration { // ГЕТТЕРЫ ДЛЯ MonitoringConfig // ============================================================================= -// GetMetricsPort возвращает порт для экспорта метрик. func (m *MonitoringConfig) GetMetricsPort() int { if m.MetricsPort <= 0 { return 9090 @@ -1547,7 +1370,6 @@ func (m *MonitoringConfig) GetMetricsPort() int { return m.MetricsPort } -// GetTraceSampleRate возвращает частоту сэмплирования трассировки. func (m *MonitoringConfig) GetTraceSampleRate() float64 { if m.TraceSampleRate <= 0 || m.TraceSampleRate > 1 { return 0.01 @@ -1555,17 +1377,14 @@ func (m *MonitoringConfig) GetTraceSampleRate() float64 { return m.TraceSampleRate } -// IsMetricsEnabled возвращает флаг включения сбора метрик. func (m *MonitoringConfig) IsMetricsEnabled() bool { return m.EnableMetrics } -// IsTracingEnabled возвращает флаг включения трассировки. func (m *MonitoringConfig) IsTracingEnabled() bool { return m.EnableTracing } // ============================================================================= // ГЕТТЕРЫ ДЛЯ SecurityConfig // ============================================================================= -// GetTLSMinVersion возвращает минимальную версию TLS как числовой код. func (s *SecurityConfig) GetTLSMinVersion() uint16 { switch s.MinVersion { case "1.0": @@ -1581,28 +1400,22 @@ func (s *SecurityConfig) GetTLSMinVersion() uint16 { } } -// IsTLSEnabled возвращает флаг включения TLS. func (s *SecurityConfig) IsTLSEnabled() bool { return s.EnableTLS && s.CertFile != "" && s.KeyFile != "" } -// GetCertFile возвращает путь к файлу сертификата. func (s *SecurityConfig) GetCertFile() string { return s.CertFile } -// GetKeyFile возвращает путь к файлу приватного ключа. func (s *SecurityConfig) GetKeyFile() string { return s.KeyFile } -// GetCAFile возвращает путь к файлу корневого сертификата CA. func (s *SecurityConfig) GetCAFile() string { return s.CAFile } // ============================================================================= // ГЕТТЕРЫ ДЛЯ CompressionConfig // ============================================================================= -// IsCompressionEnabled возвращает флаг включения сжатия. func (c *CompressionConfig) IsCompressionEnabled() bool { return c.Enabled } -// GetAlgorithm возвращает алгоритм сжатия. func (c *CompressionConfig) GetAlgorithm() string { if c.Algorithm == "" { return "snappy" @@ -1610,7 +1423,6 @@ func (c *CompressionConfig) GetAlgorithm() string { return c.Algorithm } -// GetLevel возвращает уровень сжатия. func (c *CompressionConfig) GetLevel() int { if c.Level < 1 { return 3 @@ -1621,7 +1433,6 @@ func (c *CompressionConfig) GetLevel() int { return c.Level } -// GetMinSize возвращает минимальный размер данных для сжатия в байтах. func (c *CompressionConfig) GetMinSize() int { if c.MinSize <= 0 { return 1024 @@ -1658,7 +1469,6 @@ func LoadConfig(path string) (*Config, error) { // ===== УСТАНОВКА ЗНАЧЕНИЙ ПО УМОЛЧАНИЮ ===== - // Кластерные настройки if cfg.Cluster.RaftPort == 0 { cfg.Cluster.RaftPort = 9878 } @@ -1693,7 +1503,6 @@ func LoadConfig(path string) (*Config, error) { cfg.Cluster.Region = "default" } - // Настройки SAGA if cfg.Saga.CoordinatorCount == 0 { cfg.Saga.CoordinatorCount = 3 } @@ -1746,7 +1555,6 @@ func LoadConfig(path string) (*Config, error) { cfg.Saga.FsyncRetryDelayMs = 100 } - // Настройки репликации if cfg.Replication.ReplicationTimeoutMs == 0 { cfg.Replication.ReplicationTimeoutMs = 5000 } @@ -1754,7 +1562,6 @@ func LoadConfig(path string) (*Config, error) { cfg.Replication.MaxReplicaLagMs = 5000 } - // Настройки плагинов if cfg.Plugins.ScriptDir == "" { cfg.Plugins.ScriptDir = "plugins" } @@ -1789,17 +1596,14 @@ func LoadConfig(path string) (*Config, error) { cfg.Plugins.LuaStateTTLSec = 600 } - // Настройки API if cfg.API.Port == 0 { cfg.API.Port = 8080 } - // ИСПРАВЛЕНО: значения по умолчанию для секции [metrics] if cfg.Metrics.CollectIntervalSec == 0 { cfg.Metrics.CollectIntervalSec = 15 } - // Настройки сжатия if cfg.Compression.Algorithm == "" { cfg.Compression.Algorithm = "snappy" } @@ -1810,7 +1614,6 @@ func LoadConfig(path string) (*Config, error) { cfg.Compression.Level = 3 } - // Настройки производительности if cfg.Performance.BatchSize == 0 { cfg.Performance.BatchSize = 100 } @@ -1821,7 +1624,6 @@ func LoadConfig(path string) (*Config, error) { cfg.Performance.ReadReplicaDelayMs = 100 } - // Настройки мониторинга if cfg.Monitoring.MetricsPort == 0 { cfg.Monitoring.MetricsPort = 9090 } @@ -1829,7 +1631,6 @@ func LoadConfig(path string) (*Config, error) { cfg.Monitoring.TraceSampleRate = 0.01 } - // Настройки восстановления if cfg.Recovery.MaxRetrySec == 0 { cfg.Recovery.MaxRetrySec = 300 } @@ -1840,17 +1641,14 @@ func LoadConfig(path string) (*Config, error) { cfg.Recovery.StaleReadTimeoutSec = 30 } - // Настройки безопасности if cfg.Security.MinVersion == "" { cfg.Security.MinVersion = "1.2" } - // Настройки хранилища if cfg.Storage.DefaultEngine == "" { cfg.Storage.DefaultEngine = "row" } - // Настройки WAL if cfg.WAL.SegmentSizeMB == 0 { cfg.WAL.SegmentSizeMB = 64 } @@ -1870,7 +1668,6 @@ func LoadConfig(path string) (*Config, error) { cfg.WAL.AsyncRecoveryBuffer = 10000 } - // Настройки MVCC if cfg.MVCC.MaxVersionsPerDoc == 0 { cfg.MVCC.MaxVersionsPerDoc = 10 } @@ -1890,7 +1687,6 @@ func LoadConfig(path string) (*Config, error) { cfg.MVCC.ReadCacheTTLSec = 300 } - // Настройки транзакций if cfg.Transactions.DefaultTimeoutSec == 0 { cfg.Transactions.DefaultTimeoutSec = 30 } @@ -1904,7 +1700,6 @@ func LoadConfig(path string) (*Config, error) { cfg.Transactions.CheckpointIntervalSec = 300 } - // Настройки ACL if cfg.ACL.MaxDeniedLogSize == 0 { cfg.ACL.MaxDeniedLogSize = 10000 } @@ -1915,7 +1710,6 @@ func LoadConfig(path string) (*Config, error) { cfg.ACL.CacheTTLSec = 60 } - // Настройки кластерного TLS if cfg.ClusterTLS.MinVersion == "" { cfg.ClusterTLS.MinVersion = "1.2" } @@ -1923,7 +1717,6 @@ func LoadConfig(path string) (*Config, error) { cfg.ClusterTLS.KeyRotationDays = 30 } - // Настройки обратного давления if cfg.Backpressure.CheckIntervalMs == 0 { cfg.Backpressure.CheckIntervalMs = 1000 } @@ -1931,7 +1724,6 @@ func LoadConfig(path string) (*Config, error) { cfg.Backpressure.LowDelayMs = 100 } - // Настройки ограничений времени выполнения if cfg.RuntimeLimits.GlobalMaxDocSizeMB == 0 { cfg.RuntimeLimits.GlobalMaxDocSizeMB = 16 } @@ -1942,7 +1734,6 @@ func LoadConfig(path string) (*Config, error) { cfg.RuntimeLimits.GlobalMaxDocsPerColl = 10000000 } - // Настройки автомасштабирования if cfg.Autoscaling.MinNodes == 0 { cfg.Autoscaling.MinNodes = 1 } @@ -1959,27 +1750,16 @@ func LoadConfig(path string) (*Config, error) { cfg.Autoscaling.EvaluationIntervalSec = 30 } - // Настройки миграции схемы if cfg.SchemaMigration.MigrationDir == "" { cfg.SchemaMigration.MigrationDir = "migrations" } - // Настройки резервного копирования if cfg.Backup.BackupDir == "" { cfg.Backup.BackupDir = "backups" } if cfg.Backup.RetentionDays == 0 { cfg.Backup.RetentionDays = 7 } - - // ИСПРАВЛЕНО: значения по умолчанию для новых полей BackupConfig. - // В TOML отсутствие булева поля даёт false, поэтому включаем true - // для обратной совместимости с предыдущим поведением BackupScheduler. - // Если пользователь явно указал false — уважаем его выбор. - // (Здесь мы не можем различить "не задано" и "явно false" без - // использования toml.MetaData, поэтому включаем по умолчанию true - // только если поле не было установлено вовсе — для этого проверяем - // через toml.MetaData ниже; здесь оставлено для совместимости.) if !cfg.Backup.IncludeSagaState { cfg.Backup.IncludeSagaState = true } @@ -1987,7 +1767,6 @@ func LoadConfig(path string) (*Config, error) { cfg.Backup.EnableIncremental = true } - // Настройки кросс-датацентровой миграции if cfg.Migration.Source == nil { cfg.Migration.Source = &DatacenterConfig{ Name: "dc-primary", @@ -2105,7 +1884,6 @@ func ValidateConfigFull(cfg *Config) *ValidationResult { Warnings: make([]error, 0), } - // ===== ВАЛИДАЦИЯ КЛАСТЕРНОЙ КОНФИГУРАЦИИ ===== if cfg.Cluster.NodePort < 0 || cfg.Cluster.NodePort > 65535 { result.Errors = append(result.Errors, fmt.Errorf("invalid node_port: %d (must be 0-65535, 0 = auto)", cfg.Cluster.NodePort)) } @@ -2121,7 +1899,6 @@ func ValidateConfigFull(cfg *Config) *ValidationResult { } } - // ===== ВАЛИДАЦИЯ SAGA КОНФИГУРАЦИИ ===== if cfg.Saga.Enabled { if cfg.Saga.CoordinatorCount < 1 { result.Errors = append(result.Errors, fmt.Errorf("saga.coordinator_count must be at least 1, got %d", cfg.Saga.CoordinatorCount)) @@ -2149,7 +1926,6 @@ func ValidateConfigFull(cfg *Config) *ValidationResult { } } - // ===== ВАЛИДАЦИЯ ПРОИЗВОДИТЕЛЬНОСТИ ===== if cfg.Performance.BatchSize < 1 { result.Errors = append(result.Errors, fmt.Errorf("batch_size must be at least 1, got %d", cfg.Performance.BatchSize)) } @@ -2157,12 +1933,10 @@ func ValidateConfigFull(cfg *Config) *ValidationResult { result.Errors = append(result.Errors, fmt.Errorf("max_connections must be at least 1, got %d", cfg.Performance.MaxConnections)) } - // ===== ВАЛИДАЦИЯ МОНИТОРИНГА ===== if cfg.Monitoring.TraceSampleRate < 0 || cfg.Monitoring.TraceSampleRate > 1 { result.Errors = append(result.Errors, fmt.Errorf("trace_sample_rate must be between 0 and 1, got %f", cfg.Monitoring.TraceSampleRate)) } - // ===== ВАЛИДАЦИЯ МЕТРИК — ИСПРАВЛЕНО ===== if cfg.Metrics.Enabled { if cfg.Metrics.CollectIntervalSec <= 0 { result.Errors = append(result.Errors, fmt.Errorf("metrics.collect_interval_sec must be > 0 when metrics.enabled = true")) @@ -2172,7 +1946,6 @@ func ValidateConfigFull(cfg *Config) *ValidationResult { result.Errors = append(result.Errors, fmt.Errorf("metrics.collect_interval_sec cannot be negative, got %d", cfg.Metrics.CollectIntervalSec)) } - // ===== ВАЛИДАЦИЯ LOG ===== if cfg.Log.LogLevel != "" { level := strings.ToLower(cfg.Log.LogLevel) if !allowedLogLevels[level] { @@ -2180,7 +1953,6 @@ func ValidateConfigFull(cfg *Config) *ValidationResult { } } - // ===== ПРОВЕРКА КОНФЛИКТОВ ПОРТОВ ===== if cfg.API.Port == cfg.Cluster.NodePort { result.Errors = append(result.Errors, fmt.Errorf("API port %d conflicts with cluster node port", cfg.API.Port)) } @@ -2191,7 +1963,6 @@ func ValidateConfigFull(cfg *Config) *ValidationResult { result.Warnings = append(result.Warnings, fmt.Errorf("API port %d conflicts with metrics port", cfg.API.Port)) } - // ===== ВАЛИДАЦИЯ TLS ===== if cfg.Security.IsTLSEnabled() { if cfg.Security.CertFile == "" { result.Errors = append(result.Errors, fmt.Errorf("cert_file is required when TLS is enabled")) @@ -2201,14 +1972,12 @@ func ValidateConfigFull(cfg *Config) *ValidationResult { } } - // ===== ВАЛИДАЦИЯ СЖАТИЯ ===== if cfg.Compression.Enabled { if !allowedCompressionAlgorithms[cfg.Compression.Algorithm] { result.Errors = append(result.Errors, fmt.Errorf("unsupported compression algorithm: %s, supported: snappy, lz4, zstd", cfg.Compression.Algorithm)) } } - // ===== ВАЛИДАЦИЯ WAL ===== if cfg.WAL.RecoveryWorkers < 1 { result.Errors = append(result.Errors, fmt.Errorf("wal.recovery_workers must be at least 1, got %d", cfg.WAL.RecoveryWorkers)) } @@ -2219,12 +1988,10 @@ func ValidateConfigFull(cfg *Config) *ValidationResult { result.Errors = append(result.Errors, fmt.Errorf("wal.async_recovery_buffer cannot be negative, got %d", cfg.WAL.AsyncRecoveryBuffer)) } - // ===== ВАЛИДАЦИЯ MVCC ===== if cfg.MVCC.MaxVersionsPerDoc < 0 { result.Errors = append(result.Errors, fmt.Errorf("mvcc.max_versions_per_doc cannot be negative, got %d", cfg.MVCC.MaxVersionsPerDoc)) } - // ===== ВАЛИДАЦИЯ ПЛАГИНОВ ===== if cfg.Plugins.MaxCPUTimeMs < 0 { result.Errors = append(result.Errors, fmt.Errorf("plugins.max_cpu_time_ms cannot be negative, got %d", cfg.Plugins.MaxCPUTimeMs)) } @@ -2235,7 +2002,6 @@ func ValidateConfigFull(cfg *Config) *ValidationResult { result.Warnings = append(result.Warnings, fmt.Errorf("plugins.max_lua_states is less than 1, will use default 100")) } - // ===== ВАЛИДАЦИЯ ОБРАТНОГО ДАВЛЕНИЯ ===== if cfg.Backpressure.Enabled { if cfg.Backpressure.CPUThreshold < 0 || cfg.Backpressure.CPUThreshold > 1 { result.Errors = append(result.Errors, fmt.Errorf("backpressure.cpu_threshold must be between 0 and 1, got %f", cfg.Backpressure.CPUThreshold)) @@ -2251,7 +2017,6 @@ func ValidateConfigFull(cfg *Config) *ValidationResult { } } - // ===== ВАЛИДАЦИЯ ОГРАНИЧЕНИЙ ВРЕМЕНИ ВЫПОЛНЕНИЯ ===== if cfg.RuntimeLimits.Enabled { if cfg.RuntimeLimits.GlobalMaxDocSizeMB < 0 { result.Errors = append(result.Errors, fmt.Errorf("runtime_limits.global_max_doc_size_mb cannot be negative, got %d", cfg.RuntimeLimits.GlobalMaxDocSizeMB)) @@ -2264,7 +2029,6 @@ func ValidateConfigFull(cfg *Config) *ValidationResult { } } - // ===== ВАЛИДАЦИЯ АВТОМАСШТАБИРОВАНИЯ ===== if cfg.Autoscaling.Enabled { if cfg.Autoscaling.MinNodes < 1 { result.Errors = append(result.Errors, fmt.Errorf("autoscaling.min_nodes must be at least 1, got %d", cfg.Autoscaling.MinNodes)) @@ -2280,18 +2044,15 @@ func ValidateConfigFull(cfg *Config) *ValidationResult { } } - // ===== ВАЛИДАЦИЯ ДВИЖКОВ ===== if cfg.Storage.EnableCustomEngines { defaultEngine := cfg.Storage.GetDefaultEngine() switch defaultEngine { case "row", "columnar", "document", "kv", "ts", "graph": - // Встроенные движки default: result.Warnings = append(result.Warnings, fmt.Errorf("default_engine '%s' is not a built-in engine, ensure plugin is loaded", defaultEngine)) } } - // ИСПРАВЛЕНО: валидация [engines] — хотя бы один движок должен быть включён. if cfg.Storage.EnableCustomEngines { anyEnabled := cfg.Engines.Row.Enabled || cfg.Engines.Columnar.Enabled || @@ -2304,7 +2065,6 @@ func ValidateConfigFull(cfg *Config) *ValidationResult { } } - // ИСПРАВЛЕНО: валидация [backup] — обязательные поля. if cfg.Backup.Enabled { if cfg.Backup.BackupDir == "" { result.Errors = append(result.Errors, fmt.Errorf("backup.backup_dir is required when backup.enabled = true")) @@ -2317,7 +2077,6 @@ func ValidateConfigFull(cfg *Config) *ValidationResult { } } - // ===== ВАЛИДАЦИЯ КРОСС-ДАТАЦЕНТРОВОЙ МИГРАЦИИ ===== if cfg.Migration.Enabled { if cfg.Migration.Source == nil || cfg.Migration.Source.Endpoint == "" { result.Errors = append(result.Errors, fmt.Errorf("migration.source.endpoint is required when migration is enabled")) @@ -2366,4 +2125,81 @@ func ValidateConfigFull(cfg *Config) *ValidationResult { result.Valid = len(result.Errors) == 0 return result +} + +// ============================================================================= +// СОХРАНЕНИЕ КОНФИГУРАЦИИ (ДОБАВЛЕНО) +// ============================================================================= + +// SaveConfig записывает конфигурацию в TOML-файл атомарно: +// сначала во временный файл (с fsync), потом rename. +// +// Используется REPL-командой "config set" в fallback-режиме, когда +// DynamicConfigManager недоступен (Raft выключен или узел не лидер). +// +// Если path == "" — возвращает ошибку. +// Если cfg == nil — возвращает ошибку. +// +// После успешного rename выполняется fsync родительской директории, +// чтобы гарантировать сохранность переименования при крахе. +func SaveConfig(path string, cfg *Config) error { + if cfg == nil { + return fmt.Errorf("config is nil") + } + if path == "" { + return fmt.Errorf("config path is empty") + } + + dir := filepath.Dir(path) + if err := os.MkdirAll(dir, 0755); err != nil { + return fmt.Errorf("failed to create config directory %s: %w", dir, err) + } + + tmpPath := path + ".tmp" + f, err := os.OpenFile(tmpPath, os.O_CREATE|os.O_WRONLY|os.O_TRUNC, 0644) + if err != nil { + return fmt.Errorf("failed to create temp config file: %w", err) + } + + encoder := toml.NewEncoder(f) + if err := encoder.Encode(cfg); err != nil { + f.Close() + os.Remove(tmpPath) + return fmt.Errorf("failed to encode config: %w", err) + } + + if err := f.Sync(); err != nil { + f.Close() + os.Remove(tmpPath) + return fmt.Errorf("failed to sync config: %w", err) + } + + if err := f.Close(); err != nil { + os.Remove(tmpPath) + return fmt.Errorf("failed to close config: %w", err) + } + + if err := os.Rename(tmpPath, path); err != nil { + os.Remove(tmpPath) + return fmt.Errorf("failed to rename config: %w", err) + } + + // fsync директории — best-effort, на Windows no-op. + if err := fsyncDir(dir); err != nil { + // Не критично: файл уже синхронизирован, rename выполнен. + _ = err + } + + return nil +} + +// fsyncDir синхронизирует директорию. +// На Linux/macOS/BSD это работает; на Windows — no-op. +func fsyncDir(dir string) error { + d, err := os.Open(dir) + if err != nil { + return err + } + defer d.Close() + return d.Sync() } \ No newline at end of file