from __future__ import annotations from dataclasses import dataclass from pathlib import Path from collections.abc import Callable from backend.data import DataGateway, build_data_gateway from backend.database.repositories import RepositoryBundle, build_repository_bundle from backend.features.alerts import AlertService from backend.features.mentor.agent import MentorSkillRegistry from backend.features.review import TradeJournalService from backend.features.screener.engine import ScreenerEngine from backend.features.screener.tracking import StrategyTrackingService from backend.jobs import InProcessJobRunner, JobRegistry, SQLiteJobRunRepository from database import ReviewDatabase from backend.data.providers.ifind_client import IfindHttpClient from backend.data.realtime import WebRealtimeAggregator from backend.features.market.charts import MarketChartClient @dataclass(frozen=True) class ApplicationContainer: database: ReviewDatabase repositories: RepositoryBundle data_gateway: DataGateway ifind: IfindHttpClient screener: ScreenerEngine strategy_tracking: StrategyTrackingService alert_service: AlertService trade_journal: TradeJournalService mentor_skills: MentorSkillRegistry realtime_aggregator: WebRealtimeAggregator chart_data: MarketChartClient jobs: InProcessJobRunner def build_application_container( database: ReviewDatabase, credentials: dict[str, object], mentor_skills_dir: Path, private_mentor_skills_dir: Path, tushare_token_supplier: Callable[[], str] | None = None, ) -> ApplicationContainer: data_gateway = build_data_gateway(credentials, tushare_token_supplier) repositories = build_repository_bundle(database) jobs = InProcessJobRunner(JobRegistry.load(), SQLiteJobRunRepository(database)) return ApplicationContainer( database=database, repositories=repositories, data_gateway=data_gateway, ifind=data_gateway.ifind, screener=ScreenerEngine(database), strategy_tracking=StrategyTrackingService(repositories.strategy_tracking), alert_service=AlertService(repositories.alerts), trade_journal=TradeJournalService(repositories.trades), mentor_skills=MentorSkillRegistry(mentor_skills_dir, private_mentor_skills_dir), realtime_aggregator=data_gateway.realtime_observer, chart_data=data_gateway.chart_data, jobs=jobs, )