"""渠道被驱动适配器包。 聚合导出 11 个被驱动适配器实现与 ``DrivenAdapters`` 聚合 dataclass, 供框架层装配使用。``create_driven_adapters(db, outbox_config, redis_client, arq_pool, execution_port)`` factory 创建请求级适配器实例:需要共享 ``AsyncSession`` 的适配器(``ChannelPersistenceAdapter`` / ``ConversationAdapter`` / ``SqlAlchemyTransactionAdapter`` / ``AuditExportTaskRepositoryAdapter``)共享同一 ``db``;无状态适配器 (Logger / Tracer)使用模块级全局实例;``identity_resolver`` 默认为 ``None``,由插件注册时注入。``RedisConfigAdapter`` / ``RedisCacheAdapter`` 接受 ``redis_client``,``ARQQueueAdapter`` 接受 ``arq_pool``,``AgentRunAdapter`` 接受 ``execution_port``(构造注入,INV-5 / ADP-001 / ADP-005 / ADP-022)。 """ from __future__ import annotations from arq import ArqRedis from redis.asyncio import Redis from sqlalchemy.ext.asyncio import AsyncSession from yuxi.channels.contract.dtos.outbox import OutboxConfig from yuxi.channels.contract.ports.driven.agent_run_execution_port import ( AgentRunExecutionPort, ) from yuxi.channels.contract.ports.driven.aggregate import DrivenAdapters from .agent_run_adapter import AgentRunAdapter from .agent_run_execution_adapter import AgentRunExecutionAdapter from .arq_queue_adapter import ARQQueueAdapter from .audit_export_task_repository_adapter import AuditExportTaskRepositoryAdapter from .channel_persistence_adapter import ChannelPersistenceAdapter from .conversation_adapter import ConversationAdapter from .identity_resolver_adapter import IdentityResolverAdapter from .masking_adapter import MaskingAdapter from .opentelemetry_tracer_adapter import OpenTelemetryTracerAdapter from .redis_cache_adapter import RedisCacheAdapter from .redis_config_adapter import RedisConfigAdapter from .sqlalchemy_transaction_adapter import SqlAlchemyTransactionAdapter from .structured_logger_adapter import StructuredLoggerAdapter # 无状态适配器全局实例(Masking / Logger / Tracer),跨请求复用,避免重复构造。 # Masking 无状态无依赖,最先构造;Logger 注入 Masking 以便日志 kwargs 自动脱敏; # Tracer 注入 Logger 以便在追踪故障降级时记录日志(避免静默吞异常)。 _masking_adapter = MaskingAdapter() _logger_adapter = StructuredLoggerAdapter(masking_port=_masking_adapter) _tracer_adapter = OpenTelemetryTracerAdapter(_logger_adapter) def create_driven_adapters( db: AsyncSession, outbox_config: OutboxConfig, redis_client: Redis, arq_pool: ArqRedis, execution_port: AgentRunExecutionPort, ) -> DrivenAdapters: """创建被驱动适配器聚合实例。 请求级适配器(``ChannelPersistenceAdapter`` / ``ConversationAdapter`` / ``SqlAlchemyTransactionAdapter`` / ``AuditExportTaskRepositoryAdapter``) 共享同一 ``db`` 会话以保证事务一致性;无状态适配器(Logger / Tracer) 使用模块级全局实例;其余适配器按需构造。``ConversationAdapter`` 仅依赖 共享 ``db`` 会话(合并策略开关决策已上移至 usecase 层,``ConfigPort`` / ``PersistencePort`` 死依赖已移除)。``RedisConfigAdapter`` / ``RedisCacheAdapter`` 接受 ``redis_client`` 执行配置读写与缓存操作; ``ARQQueueAdapter`` 接受 ``arq_pool`` 入队;``AgentRunAdapter`` 接受 ``execution_port`` 委托 Agent 运行技术操作(构造注入,INV-5 / ADP-001 / ADP-005 / ADP-022)。``identity_resolver`` 默认为 ``None``,由插件注册时注入。 Args: db: SQLAlchemy 异步会话,由框架层注入,persistence / conversation / transaction 适配器共享此会话。 outbox_config: 发件箱配置,注入到 ``ChannelPersistenceAdapter`` 替代 直接读取全局 ``app_config``(§6.1 应用服务层禁止依赖具体技术适配器)。 redis_client: ``redis.asyncio.Redis`` 客户端实例,注入到 ``RedisConfigAdapter`` 与 ``RedisCacheAdapter``(构造注入,INV-5)。 arq_pool: ``arq.ArqRedis`` 连接池实例,注入到 ``ARQQueueAdapter`` 用于入队(构造注入,ADP-005)。 execution_port: ``AgentRunExecutionPort`` 实例,注入到 ``AgentRunAdapter`` 委托 Agent 运行技术操作(构造注入,ADP-001)。 Returns: DrivenAdapters 聚合实例。 """ config = RedisConfigAdapter(redis_client=redis_client, logger=_logger_adapter) persistence = ChannelPersistenceAdapter(db, outbox_config=outbox_config, logger=_logger_adapter) audit_export_task_repo = AuditExportTaskRepositoryAdapter(db, logger=_logger_adapter) return DrivenAdapters( persistence=persistence, conversation=ConversationAdapter(db, logger=_logger_adapter), agent_run=AgentRunAdapter(execution_port=execution_port, logger=_logger_adapter), queue=ARQQueueAdapter(arq_pool=arq_pool, logger=_logger_adapter), config=config, cache=RedisCacheAdapter(redis_client=redis_client, logger=_logger_adapter), logger=_logger_adapter, tracer=_tracer_adapter, masking=_masking_adapter, transaction=SqlAlchemyTransactionAdapter(db), audit_export_task_repo=audit_export_task_repo, identity_resolver=None, ) __all__ = [ "DrivenAdapters", "create_driven_adapters", "ChannelPersistenceAdapter", "ConversationAdapter", "AgentRunAdapter", "AgentRunExecutionAdapter", "ARQQueueAdapter", "AuditExportTaskRepositoryAdapter", "MaskingAdapter", "RedisConfigAdapter", "RedisCacheAdapter", "StructuredLoggerAdapter", "OpenTelemetryTracerAdapter", "IdentityResolverAdapter", "SqlAlchemyTransactionAdapter", ]