Initial commit: полный проект my_speaker

This commit is contained in:
2025-12-25 12:16:19 +03:00
commit 8279fbb35f
85 changed files with 6027 additions and 0 deletions
+204
View File
@@ -0,0 +1,204 @@
# app/api/settings.py
from fastapi import APIRouter, Depends, HTTPException, Request
from pydantic import BaseModel
from typing import Dict, Any, Optional
from app.core.security import require_auth
from app.core.config import get_settings, save_settings
from app.core.vad import restart_vad_and_stt
router = APIRouter(prefix="/api/settings", tags=["settings"])
class VADSettings(BaseModel):
mode: int = 1
sample_rate: int = 16000
frame_duration_ms: int = 30
ring_buffer_size: int = 20
speech_threshold: float = 0.5
energy_threshold: int = 1000
min_speech_duration_ms: int = 300
record_stop_delay_sec: float = 1.0
prebuffer_duration_sec: float = 1.0
max_record_duration_sec: float = 5.0
target_rms: float = 2000.0
max_gain: float = 5.0
noise_reduction_factor: float = 1.5
noise_update_alpha: float = 0.05
min_rms_threshold_factor: float = 2.0
gain_smoothing_alpha: float = 0.1
adaptive_energy_std_factor: float = 2.5
adaptive_energy: bool = True
noise_reduction_enabled: bool = True
auto_gain_enabled: bool = True
record_on_speech: bool = True
class SystemSettings(BaseModel):
history_maxlen: int = 100
polling_interval_ms: int = 500
logging_level: str = "INFO"
log_file: str = "logs/app.log"
log_save_file: bool = True
class STTSettings(BaseModel):
model_path: str = ""
class CommandsSettings(BaseModel):
commands_file: str = ""
class AuthSettings(BaseModel):
username: str = "admin"
password: str = "admin"
class TTSSettings(BaseModel):
host: str = "192.168.200.81"
port: int = 10200
timeout: int = 30
pause_duration: float = 0.5
post_stop_wait: float = 1.0
voice: str = "ru_RU-ruslan-medium"
save_TTS_files: bool = False
class AudioSettings(BaseModel):
playback_device: int = 2
capture_device: int = 2
playback_volume: int = 0
capture_volume: int = 90
class AllSettings(BaseModel):
vad: VADSettings
system: SystemSettings
stt: STTSettings
commands: CommandsSettings
auth: AuthSettings
tts: TTSSettings
audio_settings: AudioSettings
@router.get("", response_model=AllSettings)
async def get_all_settings(token: str = Depends(require_auth)):
"""Получение всех настроек"""
try:
config = get_settings()
return AllSettings(
vad=VADSettings(**config.vad.dict()),
system=SystemSettings(**config.system.dict()),
stt=STTSettings(**config.stt.dict()),
commands=CommandsSettings(**config.commands.dict()),
auth=AuthSettings(**config.auth.dict()),
tts=TTSSettings(**config.tts.dict()),
audio_settings=AudioSettings(**config.audio_settings.dict())
)
except Exception as e:
raise HTTPException(status_code=500, detail=str(e))
@router.put("/vad", response_model=VADSettings)
async def update_vad_settings(settings: VADSettings, token: str = Depends(require_auth)):
"""Обновление настроек VAD"""
try:
config = get_settings()
settings_dict = settings.dict()
for key, value in settings_dict.items():
setattr(config.vad, key, value)
save_settings(config)
return VADSettings(**config.vad.dict())
except Exception as e:
raise HTTPException(status_code=500, detail=str(e))
@router.put("/system", response_model=SystemSettings)
async def update_system_settings(settings: SystemSettings, token: str = Depends(require_auth)):
"""Обновление системных настроек"""
try:
config = get_settings()
settings_dict = settings.dict()
for key, value in settings_dict.items():
setattr(config.system, key, value)
save_settings(config)
return SystemSettings(**config.system.dict())
except Exception as e:
raise HTTPException(status_code=500, detail=str(e))
@router.put("/stt", response_model=STTSettings)
async def update_stt_settings(settings: STTSettings, token: str = Depends(require_auth)):
"""Обновление настроек STT"""
try:
config = get_settings()
settings_dict = settings.dict()
for key, value in settings_dict.items():
setattr(config.stt, key, value)
save_settings(config)
return STTSettings(**config.stt.dict())
except Exception as e:
raise HTTPException(status_code=500, detail=str(e))
@router.put("/commands", response_model=CommandsSettings)
async def update_commands_settings(settings: CommandsSettings, token: str = Depends(require_auth)):
"""Обновление настроек команд"""
try:
config = get_settings()
settings_dict = settings.dict()
for key, value in settings_dict.items():
setattr(config.commands, key, value)
save_settings(config)
return CommandsSettings(**config.commands.dict())
except Exception as e:
raise HTTPException(status_code=500, detail=str(e))
@router.put("/auth", response_model=AuthSettings)
async def update_auth_settings(settings: AuthSettings, token: str = Depends(require_auth)):
"""Обновление настроек авторизации"""
try:
config = get_settings()
settings_dict = settings.dict()
for key, value in settings_dict.items():
setattr(config.auth, key, value)
save_settings(config)
return AuthSettings(**config.auth.dict())
except Exception as e:
raise HTTPException(status_code=500, detail=str(e))
@router.put("/tts", response_model=TTSSettings)
async def update_tts_settings(settings: TTSSettings, token: str = Depends(require_auth)):
"""Обновление настроек TTS"""
try:
config = get_settings()
settings_dict = settings.dict()
for key, value in settings_dict.items():
setattr(config.tts, key, value)
save_settings(config)
return TTSSettings(**config.tts.dict())
except Exception as e:
raise HTTPException(status_code=500, detail=str(e))
@router.put("/audio_settings", response_model=AudioSettings)
async def update_audio_settings(settings: AudioSettings, token: str = Depends(require_auth)):
"""Обновление настроек аудио"""
try:
from volume import set_volume
config = get_settings()
old_settings = config.audio_settings.dict()
settings_dict = settings.dict()
# Обновляем настройки в конфигурации
for key, value in settings_dict.items():
setattr(config.audio_settings, key, value)
# Применяем настройки громкости, если они изменились
if old_settings['playback_volume'] != settings_dict['playback_volume']:
set_volume(settings_dict['playback_device'], settings_dict['playback_volume'], mixer_type='Playback')
if old_settings['capture_volume'] != settings_dict['capture_volume']:
set_volume(settings_dict['capture_device'], settings_dict['capture_volume'], mixer_type='Capture')
save_settings(config)
return AudioSettings(**config.audio_settings.dict())
except Exception as e:
raise HTTPException(status_code=500, detail=str(e))
@router.post("/restart")
async def restart_vad(request: Request, token: str = Depends(require_auth)):
"""Перезапуск VAD и STT с новыми настройками"""
try:
restart_vad_and_stt(request)
return {"status": "success", "message": "VAD и STT перезапущены"}
except Exception as e:
raise HTTPException(status_code=500, detail=str(e))