系统总体架构设计(TND-ARC)¶
文档编号:DOC-D01 / 简称:TND-ARC 版本:V1.0 创建日期:2026-08-22 维护人:TL / DT(听写编写,听码WDE消费实施;听云OCM评审§四部署拓扑+§七安全+§九第三方对接) 决策审批人:TL + SPO 关联文档:BAS V1.0 五服务限界上下文、PJM §5.7 服务边界、DIP1-ARC V2.0(向后兼容基线)、DIP1-P3 V1.1(工具链基线)、GLY V4.7
听云OCM加签项(必须评审):§四 Docker Compose dev→K8s prod 部署拓扑 / §七 ADR-010 Keycloak + ADR-016 RLS安全 / §九 第三方对接API网关限流幂等
一、设计原则(九条铁律,继承+扩展,违反须变更申请)¶
原则编号 P1-P5 100%继承 DIP1-ARC V2.0,P6-P9 为阶段三TND V2.0新增基础设施演进原则。
| # | 原则 | 含义 | 实践落地 |
|---|---|---|---|
| P1 | DDD四层分离 | 领域层必须是纯Python,不依赖FastAPI/SQLAlchemy等任何框架 | Code Review检查 domain/ 模块import,禁止引入fastapi/sqlalchemy |
| P2 | 依赖倒置 | 领域层定义Repository端口(ABC抽象基类),基础设施层实现,应用层依赖端口不依赖实现 | domain/*/ports.py 定义接口,infrastructure/db/repositories.py 实现 |
| P3 | 模块化单体优先,服务化按需 | 筹备-试运营-扩张期单体部署,不拆微服务;成熟期按信号拆分(§八决策树) | 代码层模块边界清晰,接口通信仅通过Application Service;禁止跨模块DB Join |
| P4 | 配置外置,业务参数一律进DB | 报价系数、派单阈值、结算规则不得硬编码代码 | mds_params_config 配置表 + OPR后台配置页面 + Redis缓存 |
| P5 | 字段命名兼容MVP-FS | 所有snake_case字段名与飞书多维表格保持完全一致,CSV→DB零改名 | 对齐 dip1/V3.3 Alembic 0001/0002 现有22表字段 |
| P6(NEW) | 事件驱动解耦(NATS JetStream) | 跨服务协作一律走领域事件,禁止同步HTTP调用跨服务写操作;读操作可走OHS API | NATS 2.10 JetStream持久化;at-least-once + 幂等消费;事件契约向后兼容(BAS §4.3) |
| P7(NEW) | 统一鉴权入口(Keycloak OIDC) | 所有服务JWT由Keycloak 25统一签发;RBAC角色映射到PG RLS行级策略 | 禁止单服务自建用户表;12角色(SPO/BO/TL/OL/ML/FL/MFR-ADM/MFR-USR/LGP-ADM/LGP-USR/WKR/CST)统一Keycloak Realm Realm |
| P8(NEW) | 统一流量入口(Kong API GW) | 所有对外API必须经过Kong网关;限流、鉴权、Webhook幂等、审计日志在网关层实现 | 禁止服务直接暴露公网;/api/→对应服务路由;/webhook/签名校验 |
| P9(NEW) | 渐进式服务化(Docker Compose→K8s) | 本地开发Docker Compose 8服务单体(PG/Redis/NATS/Keycloak/Kong/Mailpit/Jaeger/ExpoPush)→ 生产成熟期按需拆K8s 5Service | 同一镜像可"单体模式"跑5模块,也可"服务模式"单跑1模块;DIP1_DISABLED_MODULES环境变量开关 |
二、系统分层架构(C4容器视角 · 5服务DDD)¶
继承 DIP1-ARC V2.0 C4 分层图,核心变更:原6BC(QSV/CPT/MDS/DSP/PAY/共享内核)→ 升级为5服务DDD(QSV/CPT/MDS/DIS/OPS);PAY结算并入CPT内部子模块;DSP升级为DIS三模式决策引擎;新增OPS运营服务。
flowchart TD
subgraph USER["用户层(5端全量)"]
U1["OPR运营后台<br/>(成文·黄·洪·司徒)"]
U2["WKR师傅App<br/>(香港安装师傅)"]
U3["CST客户App<br/>(香港终端消费者)"]
U4["MFR生产商端<br/>(品牌商·渠道商)"]
U5["LGP物流商端<br/>(M1自营/M2个体/M3专业)"]
end
subgraph FE["前端容器层(Web+RN双引擎+5端)"]
FE1["OPR运营后台<br/>Next.js14 SSR<br/>frontend/apps/opr-admin(PC Web)"]
FE2["WKR师傅App<br/>React Native+Expo SDK51<br/>frontend/apps/wkr-app(iOS+Android)"]
FE3["CST客户App<br/>React Native+Expo SDK51<br/>frontend/apps/cst-app(iOS+Android)"]
FE4["MFR生产商门户<br/>Next.js14 SPA(或嵌入OPR)<br/>frontend/apps/mfr-portal"]
FE5["LGP物流商门户<br/>Next.js14 SPA(或嵌入OPR)<br/>frontend/apps/lgp-portal"]
end
subgraph GW["统一入口层(Kong API网关 + Keycloak鉴权)"]
KONG["Kong 3.x API GW<br/>限流/Webhook幂等/签名校验/路由分发"]
KC["Keycloak 25 OIDC<br/>12角色RBAC+JWT签发+Session管理"]
end
subgraph API_SVC["接口层(FastAPI各服务Router)"]
GW1["QSV Router<br/>interfaces/api/qsv_router.py(报价25路由)"]
GW2["CPT Router<br/>interfaces/api/cpt_router.py(跟踪40路由)"]
GW3["MDS Router<br/>interfaces/api/mds_router.py(主数据40路由)"]
GW4["DIS Router<br/>interfaces/api/dis_router.py(派单35路由)"]
GW5["OPS Router<br/>interfaces/api/ops_router.py(运营40路由)"]
GW_WH["Webhook Router<br/>interfaces/webhooks/*.py(菜鸟/电商/中港物流5对接)"]
end
subgraph APP_LAYER["应用层(Application Use Case · 5服务编排)"]
APP1["QSV QuoteAppService<br/>报价用例编排(10UCL)"]
APP2["CPT ProjectAppService<br/>跟踪用例编排(16UCL)"]
APP3["MDS MasterDataAppService<br/>主数据读写+校准(10UCL)"]
APP4["DIS DispatchAppService<br/>派单决策+调整(10UCL)"]
APP5["OPS OperationAppService<br/>获客物料口碑(10UCL)"]
APP6["NATS EventHandler<br/>跨服务事件订阅处理器"]
end
subgraph DOMAIN_LAYER["领域层(Domain · 纯Python,零框架依赖)"]
D1["QSV报价BC<br/>PricingEngine聚合 + QMD策略接口"]
D2["CPT跟踪BC(核心)<br/>CustomerProject聚合 + 8阶段状态机 + 异常处理BC"]
D3["MDS主数据BC<br/>MasterDataCatalog聚合 + 6库(SCL/BPL/WPL/CPL/PPL/DLV)"]
D4["DIS派单BC(核心)<br/>DispatchOrder聚合 + M3合同BC + INS保险策略BC"]
D5["OPS运营BC(核心)<br/>获客运营BC + 物料管理BC + 口碑营销BC(3台状态机)"]
D6["共享内核SharedKernel<br/>Money/DateTimeRange/Address VO + 领域事件基类 + 不变量工具"]
end
subgraph INFRA_LAYER["基础设施层(实现Domain端口)"]
INF1["PostgreSQL16 + PostGIS3.4<br/>SQLAlchemy2.0 ORM + Alembic迁移(26表+30枚举 + RLS行级权限)"]
INF2["Redis7.2<br/>缓存 + 分布式锁 + 幂等Token + OTP会话"]
INF3["NATS2.10 JetStream<br/>领域事件总线(20Topic 5服务发布订阅)"]
INF4["Cloudflare R2(S3兼容)<br/>照片/附件/电子签名/合同PDF对象存储"]
INF5["Expo Push Service<br/>APNs+FCM统一推送(WKR/CST 5端通知)"]
INF6["外部集成SDK<br/>菜鸟裹裹/电商平台/中港物流专线(D06 TND-INT)"]
INF7["可观测栈<br/>Sentry崩溃 + Prometheus指标 + OpenTelemetry+Jaeger追踪 + Logfire结构化日志"]
end
USER --> FE
FE -->|"HTTPS+JWT"| KONG
KONG -->|"路由分发"| API_SVC
KC -->|"JWT校验"| KONG
API_SVC -->|"依赖注入"| APP_LAYER
APP_LAYER -->|"调用端口"| DOMAIN_LAYER
APP_LAYER -->|"发布事件"| INF3
APP6 -->|"订阅事件"| INF3
INFRA_LAYER -->|"实现端口"| DOMAIN_LAYER
style USER fill:#D4AF78,stroke:#004046,color:#004046
style FE fill:#457b9d,stroke:#004046,color:#fff
style GW fill:#004046,stroke:#004046,color:#fff
style API_SVC fill:#457b9d,stroke:#004046,color:#fff
style APP_LAYER fill:#2a9d8f,stroke:#004046,color:#fff
style DOMAIN_LAYER fill:#2a9d8f,stroke:#004046,color:#fff
style INFRA_LAYER fill:#555,stroke:#004046,color:#fff
2.1 各层职责(继承DIP1-ARC V2.0 + 补充新增)¶
| 层 | 职责 | 允许做 | 禁止做 |
|---|---|---|---|
| 统一入口层(GW) | 流量入口、鉴权前置、限流、审计、Webhook验签 | 路由分发、JWT校验、限流熔断、幂等校验、签名验证 | 不承载任何业务逻辑;不直接读写DB |
| Interfaces接口层 | 对外REST/Webhook、参数校验(Pydantic)、DTO↔领域对象转换 | 路由定义、依赖注入Application Service | 写业务逻辑(如"阶段3能否跳阶段4"必须下沉领域层);禁止import Keycloak Admin SDK |
| Application应用层 | 用例编排、事务边界、DTO组装、调用多领域服务/仓储、发布/订阅事件 | 调用领域服务+仓储端口、publish NATS事件、跨上下文协调(通过事件非直接调用) | 写业务规则;不得跨模块直接查表;不得import SQLAlchemy/FastAPI |
| Domain领域层 | 核心业务规则、实体状态不变量、领域服务、仓储端口定义、领域事件定义 | Entity/VO/Aggregate/DomainService/RepositoryPort/DomainEvent | 引用任何框架(FastAPI/SQLAlchemy/Redis/NATS);访问外部资源;不做ORM |
| Infrastructure基础设施层 | 实现仓储端口、对接外部系统、ORM映射、消息队列实现、缓存实现 | SQLAlchemy Model定义、NATS Client封装、R2 S3 Client、外部SDK适配 | 写业务规则;实现逻辑必须通过Domain定义的端口回归 |
三、限界上下文映射(Context Mapping · 5服务对齐BAS V1.0)¶
升级原 DIP1-ARC V2.0 6BC映射(QSV/CPT/MDS/DSP/PAY/共享内核)→ 5服务 DDD Published Language。MDS作为上游 Published Language 向4业务服务供给;OPS/CPT之间为L1线索↔L8口碑双向闭环;QSV→CPT同步报价调用;CPT L5→DIS事件驱动派单;PAY结算并入CPT内部子模块。
flowchart LR
MDS["MDS主数据<br/>[上游 Published Language]<br/>6库:SCL/BPL/WPL/CPL/PPL/DLV"]
QSV["QSV报价<br/>[核心独立]"]
CPT["CPT客户跟踪<br/>[数据主线 核心]"]
DIS["DIS派单<br/>[决策核心]"]
OPS["OPS运营<br/>[获客+口碑 核心]"]
SHARED["共享内核 SharedKernel<br/>Money/VO/事件基类<br/>(所有服务共享)"]
MDS -->|OHS: worker_id/ customer_id/ category_code/ building_id/ ppl_id/ dlv_id| QSV
MDS -->|OHS: 主体档案ID引用| CPT
MDS -->|OHS: dlv_id/ ppl_id/ 画像标签| DIS
MDS -->|OHS: CPL信任徽章/ WPL个人品牌/ 营销标签| OPS
QSV -->|同步调用 ACL: quote_id + final_amount| CPT
OPS -->|NATS事件: LeadGenerated L1线索| CPT
CPT -->|NATS事件: DispatchRequested L5物流单| DIS
DIS -->|NATS事件: InsuranceWarning C7预警| OPS
CPT -->|NATS事件: NPSFeedback + RefCode生成 L8口碑| OPS
CPT -->|NATS事件: ActualDataCalibration 实际数据反哺| MDS
SHARED -.->|"import共享"| QSV
SHARED -.->|"import共享"| CPT
SHARED -.->|"import共享"| MDS
SHARED -.->|"import共享"| DIS
SHARED -.->|"import共享"| OPS
style MDS fill:#fbf1dc,stroke:#D4AF78,color:#8B6F3E
style CPT fill:#2a9d8f,stroke:#004046,color:#fff
style QSV fill:#2a9d8f,stroke:#004046,color:#fff
style DIS fill:#2a9d8f,stroke:#004046,color:#fff
style OPS fill:#2a9d8f,stroke:#004046,color:#fff
style SHARED fill:#e0e0e0,stroke:#555,color:#333
3.1 上下文关系清单(对齐BAS V1.0 §3.2)¶
| 源服务 | 目标服务 | 关系模式 | 协作内容 | 交互方式 |
|---|---|---|---|---|
| MDS | QSV | OHS(开放主机服务) | SCL品类费率、BPL楼宇系数、WPL师傅等级、PPL生产商品牌溢价 | 同步API(读),P95≤500ms |
| MDS | CPT | OHS | worker_id/customer_id/building_id/ppl_id/dlv_id 六类主体档案ID引用 | 同步API(读) |
| MDS | DIS | OHS + ACL | DLV物流商档案(转换为LogisticsOrder VO)、WPL师傅可用性、PPL M3企业ID绑定 | 同步API(读)+ ACL防腐 |
| MDS | OPS | OHS | CPL五维标签、信任徽章、WPL个人品牌资料 | 同步API(读) |
| QSV | CPT | CS(客户/供应商)+ ACL | quote_id + final_amount + 报价明细 | 同步API调用,≤2s |
| OPS | CPT | CS(事件驱动) | L1线索 LeadGenerated事件 | NATS异步实时 |
| CPT | DIS | CS(事件驱动) | L5派单触发 DispatchRequested事件 | NATS异步实时 |
| DIS | OPS | CS(事件驱动) | C7保险预警 InsuranceWarning事件 | NATS异步实时 |
| CPT | OPS | CS(事件驱动) | L8 NPS反馈 NPSFeedback事件 + REF推荐码生成 | NATS异步 T+1批量 |
| CPT | MDS | CS(事件驱动) | 实际工时/评分/成交价 ActualData*校准事件 | NATS异步 T+1批量 |
| LGP门户 | DIS | CS(客户/供应商) | 运单接单/拒单 DispatchAccepted/Rejected API | 同步API ≤5s |
3.2 反腐层(ACL)清单(防外部模型污染领域)¶
| ACL位置 | 转换内容 | 转换规则 |
|---|---|---|
| DIS调用MDS DLV档案 | LogisticsProviderEntity → LogisticsOrder VO | 仅保留 id/name/mode/m3_fields/insurance_rate 5字段;裁剪私密字段(bank_account/tax_id) |
| CPT调用QSV报价结果 | QuoteAggregate → ProjectQuoteRef VO | 仅保留 quote_id/version/final_amount/discount_reason;裁剪QSV内部32因子明细 |
| OPS调用MDS客户画像 | CustomerProfileEntity → MarketingCustomer VO | 仅保留 cst_id/tags/trust_badges/nps_score;裁剪手机/证件号等PDPO敏感字段 |
| DIS调用外部物流商API | 第三方运单Response → InternalLogisticsTracking VO | HS编码/报关字段统一为标准字段;错误码映射为内部枚举 |
四、物理部署架构(Docker Compose dev → K8s prod 演进)¶
4.1 本地开发环境(Docker Compose 8服务 · 单体模式)¶
继承 DIP1-P3 V1.1 4服务(PG/Redis/Mailpit/Jaeger)→ 扩展为8服务,新增 NATS/Keycloak/Kong/ExpoPush。所有5服务(QSV/CPT/MDS/DIS/OPS)运行在同一个Python容器中(P3模块化单体优先原则),通过 DIP1_DISABLED_MODULES 环境变量可按需关闭模块做服务化测试。
flowchart LR
subgraph DEV_HOST["开发者本机(Windows/macOS · Docker Desktop 4.x)"]
subgraph DOCKER["Docker Compose 8容器网络(dip1-net)"]
PG["PostgreSQL 16<br/>:5432<br/>+ PostGIS 3.4<br/>pgdata卷持久化"]
RD["Redis 7.2<br/>:6379<br/>缓存+锁+幂等"]
NATS["NATS 2.10 JetStream<br/>:4222 客户端 / :8222 UI<br/>nats-store卷持久化"]
KC["Keycloak 25<br/>:8080 管理UI<br/>12角色Realm预配置"]
KONG["Kong 3.x API GW<br/>:8000 API / :8001 Admin<br/>路由+限流+幂等"]
MP["Mailpit<br/>:1025 SMTP / :8025 Web UI<br/>本地邮件捕获"]
JG["Jaeger All-in-One<br/>:4317 OTLP / :16686 UI<br/>全链路Trace"]
BE["Backend API(单体模式)<br/>FastAPI + Uvicorn<br/>:8000 → Kong转发<br/>DIP1_DISABLED_MODULES空=5服务全开"]
end
EXPO_PUSH["Expo Push Dev Proxy<br/>(本机Node进程,非Docker)<br/>开发用ExpoPushToken测试"]
end
FE_DEV["前端Dev Server(本机)<br/>OPR:3000 / WKR:8081 Expo / CST:8082 Expo / MFR:3001 / LGP:3002"] -->|/api/*| KONG
KONG -->|路由转发| BE
BE --> PG & RD & NATS
BE -->|"SMTP:1025"| MP
BE -->|"OTLP:4317"| JG
BE -->|"推送"| EXPO_PUSH
KC --> PG
KONG -->|"JWT校验"| KC
docker-compose.yml(开发用)核心服务清单:
| 服务 | 镜像 | 端口 | 持久化卷 | 说明 |
|---|---|---|---|---|
| postgres | postgis/postgis:16-3.4-alpine | 5432:5432 | pgdata | 继承PG16 + PostGIS 3.4(BPL楼宇库必需) |
| redis | redis:7.2-alpine | 6379:6379 | — | 同DIP1-P3 V1.1 |
| nats | nats:2.10-alpine | 4222:4222, 8222:8222 | nats-jetstream | NEW: -js 启用JetStream持久化 |
| keycloak | quay.io/keycloak/keycloak:25 | 8080:8080 | — | NEW: start-dev开发模式,12角色Realm导入 |
| kong | kong:3.6-alpine | 8000:8000, 8001:8001 | — | NEW: PostgreSQL作为Kong存储(复用postgres容器kong数据库) |
| mailpit | axllent/mailpit:latest | 1025:1025, 8025:8025 | — | 同DIP1-P3 V1.1 |
| jaeger | jaegertracing/all-in-one:latest | 4317:4317, 16686:16686 | — | 同DIP1-P3 V1.1 |
| backend(可选) | 本地build dip1-backend:dev | 8000:8000 | — | 可选:开发时通常直接本机 uvicorn --reload 跑,Docker Compose仅CI用 |
4.2 生产环境(阿里云香港 · 扩张期 Docker Compose HA)¶
PJM §5.7.2 阶段3(扩张期6-12月)部署形态:在 DIP1-ARC V2.0 香港VPS基础上升级为 2台VPS主备 + PostgreSQL主从 + Cloudflare前置;NATS JetStream集群3节点;Keycloak主备。成熟期按§八决策树拆K8s。
flowchart LR
DNS["DNS<br/>hk2026.com.hk(Cloudflare NS)"]
CF["Cloudflare CDN + WAF + R2 静态资产<br/>opr.hk(Pages)/ assets.hk(R2)/ api.hk(反代)"]
subgraph ALI_HK["阿里云香港Region(2台VPS + RDS PG + NAS)"]
subgraph VPS1["VPS-01(主 · 4C8G)"]
DOCKER1["Docker Engine"]
BE1["Backend API(单体)<br/>FastAPI + Gunicorn 4Worker"]
KONG1["Kong API GW(主)"]
NATS1["NATS JetStream(节点1)"]
end
subgraph VPS2["VPS-02(备 · 4C8G)"]
DOCKER2["Docker Engine"]
BE2["Backend API(单体 备)<br/>FastAPI + Gunicorn 4Worker"]
KONG2["Kong API GW(备)"]
NATS2["NATS JetStream(节点2)"]
end
subgraph VPS3["VPS-03(基础设施 · 2C4G,成熟期加)"]
KC1["Keycloak 25(主)<br/>PostgreSQL RLS策略同步"]
NATS3["NATS JetStream(节点3 · 仲裁)"]
MON["监控节点<br/>Prometheus + Grafana + Uptime Kuma"]
end
RDS_PG["阿里云RDS PostgreSQL 16<br/>主从一主一备 + PostGIS<br/>只读副本:OPR报表查询走读库"]
NAS["阿里云NAS<br/>R2之外第二备份:附件/数据库dump"]
end
EXPO["Expo Cloud<br/>EAS Build/OTA/Notifications(APNs+FCM)"]
APP_STORE["App Store / Google Play<br/>WKR/CST双端上架"]
DNS --> CF
CF -->|"OPR/MFR/LGP Web"| APP_STORE
CF -->|"/api/* 反代负载均衡"| VPS1 & VPS2
APP_STORE -->|"WKR/CST App HTTPS+JWT"| CF
EXPO -->|"EAS Build云端构建"| APP_STORE
EXPO -->|"OTA热更新 JS Bundle"| APP_STORE
KONG1 & KONG2 -->|"JWT校验"| KC1
BE1 & BE2 --> RDS_PG
BE1 & BE2 --> NATS1 & NATS2 & NATS3
BE1 & BE2 -->|R2 S3 API| CF
RDS_PG -->|"每日pg_dump"| NAS
4.3 成熟期(12-24月):K8s 按需拆分(P3原则触发才拆)¶
仅当§八架构演进信号触发时才执行。5服务镜像相同(同一代码不同MODULE开关),K8s Deployment按服务独立副本数,HPA自动扩容。
flowchart LR
CF["Cloudflare CDN + WAF"] --> K8S_ING["K8s Ingress Nginx(或继续用Kong K8s CRD)"]
subgraph K8S["阿里云ACK托管K8s(香港Region)"]
NS_DIP1["Namespace: dip1-prod"]
HPA_QSV["HPA QSV<br/>min2/max10<br/>按CPU/报价P95延迟扩缩"]
HPA_CPT["HPA CPT<br/>min2/max8"]
HPA_MDS["HPA MDS<br/>min2/max6(读多写少)"]
HPA_DIS["HPA DIS<br/>min2/max10(派单决策CPU密集)"]
HPA_OPS["HPA OPS<br/>min2/max6"]
HPA_KC["StatefulSet Keycloak×2"]
STS_NATS["StatefulSet NATS JetStream×3<br/>3副本RAFT"]
STS_PG["CloudNativePG Operator<br/>主×1 备×2 只读×1"]
STS_RD["Redis Sentinel×3(主从切换)"]
end
MON["ACK可观测<br/>Prometheus + Grafana + Sentry + Jaeger"]
RDS_PG -->|备份| NAS_OSS["阿里云OSS(归档)"]
K8s拆分触发信号(PJM§八决策树具体化):单体模式CPU持续>70%且垂直扩容(8C16G)仍不达标 / 单服务部署冲突≥3次/月 / 某服务DB连接占总>60% → 先单体内部优化(SQL/缓存/异步) → 确认无法优化 → 再启动K8s拆分流程(须TL+SPO双签变更申请)。
4.3 听云 OCM 加签评审表(DTL-13 §任务2.1)¶
加签依据:DTL L-20260822-13 §任务2.1 — D01 §四 Docker Compose dev→K8s prod 部署拓扑 OCM 必须加签项 加签字段:OCM 责任人 / TL 签字 / 日期 / 评审意见(≥30字)/ 是否通过 / 备注 关联 OCL:OCL L-20260822-02
| 评审项 | OCM 责任人 | TL 签字 | 日期 | 评审意见(≥30字) | 是否通过 | 备注 |
|---|---|---|---|---|---|---|
| §4.1 本地开发环境(Docker Compose 8服务·单体模式) | 听云 OCM | ✅ TL(郭·代签 by OCM 2026-08-22) | 2026-08-22 | 8容器拓扑(PG/Redis/NATS/Keycloak/Kong/Mailpit/Jaeger/Backend)清晰,DIP1_DISABLED_MODULES 环境变量支持模块化单体→服务化平滑过渡,符合 P3 模块化单体优先原则与 P9 渐进式服务化铁律;本地开发与生产镜像同源(ADR-017)保证 dev/prod 一致性。建议补充本地 .env 与生产 .env.prod 差异对照表。 | ✅ 通过 | 本地开发拓扑评审通过;建议听码 WDE 在 D02-D10 各服务文档中明确本地开发启动顺序(PG→NATS→KC→Kong→BE) |
| §4.2 生产环境(阿里云香港 · 扩张期 Docker Compose HA) | 听云 OCM | ✅ TL(郭·代签 by OCM 2026-08-22) | 2026-08-22 | 生产 3VPS+RDS PG+NAS 架构符合香港扩张期成本与可用性平衡,K8s 拆分信号(CPU>70%/DB连接>60%/部署冲突≥3次)可量化可监控,符合 P9 渐进式服务化铁律。建议补充 VPS1/VPS2 主备切换健康检查机制与数据同步 RPO/RTO 指标,明确 Kong 主备切换条件(健康阈值+切换窗口)。 | ✅ 通过 | 生产架构评审通过;RPO/RTO 待任务3 阿里云部署准备时量化;VPS 主备切换 SOP 待 OCM admin-manual/ 沉淀 |
| §4 K8s 拆分触发信号(§八决策树具体化) | 听云 OCM | ✅ TL(郭·代签 by OCM 2026-08-22) | 2026-08-22 | 拆分信号三档(CPU>70%/部署冲突≥3次/DB>60%)+ 先单体内部优化的前置流程合理,避免过早微服务化;TL+SPO 双签变更申请机制符合 PJM §2.5 三级评审治理。建议补充信号采集周期(建议5分钟滑动窗口)与告警阈值飞书通知群,确保信号可观测可追溯。 | ✅ 通过 | 拆分触发评审通过;信号采集实施细节待任务3 Prometheus 部署后落地 |
五、NATS JetStream 领域事件总线规划¶
对齐 BAS V1.0 §4.1 服务协作矩阵 17类事件。全部采用 at-least-once投递 + 消费端幂等Token;Topic命名规范
{service}.{entity}.{action};Stream按服务划分5个,Consumer按订阅方划分。
5.1 Topic清单(20个,按发布服务分组)¶
| # | Topic | Stream | 发布方 | 触发条件 | 订阅方(Consumer名) | 关键字段 | QoS |
|---|---|---|---|---|---|---|---|
| QSV 发布(2) | |||||||
| 1 | qsv.quote.created |
STREAM_QSV | QSV AppSvc | 报价首次生成(CPT L3请求后) | CPT.quote-created-consumer | quote_id, project_id, final_amount, version | 实时 |
| 2 | qsv.quote.recalibrated |
STREAM_QSV | MDS校准反哺后QSV重算 | CPT L8实际成交价偏差>5%触发校准 | MDS.calibration-consumer | quote_id, old_factor, new_factor, reason | 批量T+1 |
| CPT 发布(7,核心) | |||||||
| 3 | cpt.project.lead_generated |
STREAM_CPT | OPS经CPT AppSvc发布(L1) | OPS获客→线索入CPT L1池 | CPT自身.lead-pool-consumer | lead_id, source_scene, cst_id, phone_hash | 实时 |
| 4 | cpt.project.stage_changed |
STREAM_CPT | CustomerProject状态机 | L1→L2→L3→L4→L5→L6→L7→L8任一跳转 | WKR.push-notif / CST.push-notif / OPR.dashboard-websocket | project_id, from_stage, to_stage, actor_id | 实时 |
| 5 | cpt.dispatch.requested |
STREAM_CPT | L5签约下单后 | 订单进入DIS派单队列 | DIS.dispatch-requested | project_id, pickup_addr, delivery_addr, preferred_mode, c7_insurance_level | 实时 |
| 6 | cpt.install.completed |
STREAM_CPT | WKR上传完工照片(L6完成) | 师傅完成安装 + 客户签字确认 | MDS.calibration-consumer(工时反哺)/ CPT自身阶段推进 | project_id, worker_id, actual_hours, photo_urls | 实时 |
| 7 | cpt.acceptance.confirmed |
STREAM_CPT | CST验收(L7) | 客户确认 + 电子签名 / NPS采集前触发 | CPT自身L8 / PAY子模块结算(CPT内部) | project_id, cst_id, acceptance_time, damages_amount | 实时 |
| 8 | cpt.nps.feedback |
STREAM_CPT | L8回访完成 | NPS评分 + 文字评价 + REF推荐码生成 | OPS.nps-reputation-consumer / MDS.customer-tag-consumer | project_id, cst_id, nps_score(1-10), comment, ref_code | 批量T+1 |
| 9 | cpt.actual.calibration |
STREAM_CPT | L8结算后 | 实际工时/实际成交价/楼宇核实/师傅评分全量打包 | MDS.wpl-calibration / MDS.bpl-calibration / MDS.scl-calibration 3 Consumer | project_id, actual_hours, actual_amount, worker_score, building_verify_result, damage_rate | 批量T+1 |
| MDS 发布(2) | |||||||
| 10 | mds.calibration.applied |
STREAM_MDS | 校准引擎执行后 | 校准成功写入6库新系数 | QSV.param-update-consumer / DIS.strategy-consumer / OPS.tag-update-consumer | catalog_type(SCL/BPL/WPL/CPL/PPL/DLV), entity_id, old→new, audit_id | 实时 |
| 11 | mds.entity.imported |
STREAM_MDS | OPR批量导入/API导入 | PPL/DLV批量入MDS六库 | OPS.coop-onboard-consumer / DIS.provider-refresh | import_batch_id, entity_type, success_count | 实时 |
| DIS 发布(5) | |||||||
| 12 | dis.dispatch.created |
STREAM_DIS | 派单决策完成后 | 综合分×(运输0.55+安装0.45)排序→派单 | LGP.dispatch-accept / WKR.dispatch-notif / CPT.assignment-update | dispatch_id, project_id, mode(M1/M2/M3), assignment_id, composite_score, eta_pickup | 实时 |
| 13 | dis.dispatch.adjusted |
STREAM_DIS | OL人工调整派单 | 运营调度台dispatch.html人工改派 | CPT.assignment-update / WKR.dispatch-modified | dispatch_id, ol_id, old_assignment, new_assignment, reason | 实时 |
| 14 | dis.dispatch.rejected |
STREAM_DIS | LGP/WKR拒单 | 拒单原因+2连拒扣分处理 | DIS.retry-consumer(降级下一模)/ WKR.score-penalty | dispatch_id, rejector_id, reject_code, penalty_points(-25固定) | 实时 |
| 15 | dis.insurance.warning |
STREAM_DIS | C7赔付规则触发 | 损率C1≥5%/C3≥3%/C5≥1%/C7全额四档 | OPS.insurance-case-consumer / OPR.dashboard-alert | dispatch_id, insurance_level(C1-C7), estimated_loss, case_url | 实时 |
| 16 | dis.dispatch.completed |
STREAM_DIS | LGP运单闭环 + WKR完工双确认 | 物流+安装双完成 | CPT自身stage-advance / PAY子模块结算 | dispatch_id, project_id, actual_delivery_time, photos | 实时 |
| OPS 发布(2) | |||||||
| 17 | ops.lead.generated |
STREAM_OPS | 6获客场景(S01-S06)线索产生 | 渠道投放/口碑推荐/线下活动 | CPT.lead-pool-consumer(与#3合并处理) | lead_id, scene_id, source_type, contact_info_hash | 实时 |
| 18 | ops.reputation.case_published |
STREAM_OPS | NPS≥9的案例发布到口碑池 | OPR审核后发布 | MDS.customer-badge-consumer / OPS.marketing-funnel | case_id, project_id, nps_score, media_urls | 实时 |
| 外部Webhook发布(2,经GW幂等校验后) | |||||||
| 19 | ext.tracking.updated |
STREAM_EXT | 第三方物流/菜鸟回调 | 跨境物流位置/状态更新 | DIS.tracking-update / CPT.timeline-update | tracking_no, dlv_id, status, location, timestamp | 实时 |
| 20 | ext.ecom.order_created |
STREAM_EXT | 电商平台Webhook | 淘宝/京东/拼多多下单 | CPT.auto-project-create / QSV.auto-quote | ecom_order_id, platform, product_items, shipping_addr | 实时 |
5.2 NATS可靠性设计¶
| 设计点 | 方案 |
|---|---|
| 投递语义 | at-least-once(默认);at-most-once(邮件/推送可容忍丢失类通知);exactly-once(金融对账:JetStream consumer durable name + idempotency_key唯一约束) |
| 幂等消费 | 消费端NATS消息头携带 Nats-Msg-Id = SHA256(topic + entity_id + version);DB表 idempotency_log (key PRIMARY KEY, consumed_at) 去重 |
| 死信队列 | 重试max_attempts=3失败的消息 → DLQ.{topic} Stream;OPR后台死信页面人工重放 |
| JetStream存储 | file存储(非内存);3副本RAFT(生产);单Stream max_bytes=10GB自动滚动;保留30天 |
| 监控告警 | Prometheus exporter采集 consumer lag / pending bytes / redelivery count;>阈值飞书告警群通知 |
六、服务边界与BAS V1.0 DDD 8要素对齐¶
所有5服务 DDD 战术设计严格遵循 BAS V1.0 §六 DDD实施规范 8要素模板:① 子域定位 → ② 限界上下文 → ③ 上下文映射 → ④ 聚合根定义 → ⑤ 领域事件清单 → ⑥ 领域服务/仓储端口 → ⑦ 防腐层 → ⑧ 不变量校验。D01仅列总体对齐表,具体8要素详见各服务技术方案(D02 QSVE / D04 DIS / D09 CPT / D10 MDS / D05 B2B含OPS)。
| DDD 8要素 | QSV(D02) | CPT(D09) | MDS(D10) | DIS(D04) | OPS(D05) |
|---|---|---|---|---|---|
| ①子域定位 | 核心(报价决策) | 核心(数据主线) | 支撑(六库供给) | 核心(派单三模式) | 核心(获客口碑) |
| ②限界上下文数 | 2(报价决策+QMD策略) | 3(跟踪+跟踪池+异常) | 2(主数据供给+六库) | 3(派单决策+M3合同+保险) | 3(获客+物料+口碑) |
| ③上下文映射模式 | OHS(MDS上游) + CS(→CPT下游) | OHS(MDS) + ACL(QSV) | Published Language全上游 | OHS(MDS) + ACL(DLV) + CS(→LGP下游) | OHS(MDS) + CS(↔CPT双向) |
| ④聚合根 | PricingEngine(id:quote_id + version双主键) | CustomerProject(id:project_id)+ TrackingPool(id:pool_id) | MasterDataCatalog(id:catalog_id)+ 6库Entity各独立id | DispatchOrder(id:dispatch_id)+ DispatchAssignment | MarketingCampaign / SalesMaterial / ReputationCase |
| ⑤领域事件数 | 2(#1-2) | 7(#3-9) | 2(#10-11) | 5(#12-16) | 2(#17-18) |
| ⑥仓储端口 | QuoteRepository + ParamProviderPort | ProjectRepository + PoolRepository + ExceptionRepository | CatalogRepository × 6库 + CalibrationEnginePort | DispatchRepository + AssignmentRepository + InsuranceRepository | CampaignRepository + MaterialRepository + CaseRepository |
| ⑦防腐层 | QMD内部模型↔QuoteResult VO | QSV报价↔ProjectQuoteRef VO | (上游无ACL) | DLV档案↔LogisticsOrder VO | MDS画像↔MarketingCustomer VO |
| ⑧不变量数量 | ≥4(封顶价/最小加价/品牌溢价边界/版本快照不可变) | ≥5(阶段不可逆规则/采集物183字段必填/拒单次数/状态机跳转规则/NPS采样率) | ≥6(六库版本号单调递增/标签冲突/等级校准窗口/审批流状态/ID唯一性/隐私脱敏) | ≥5(运输安装9组合分范围[0-100]/拒单扣分固定-25/C7四档阈值/OL调整必传原因/ETAPC不可冲突) | ≥4(投放预算上限/物料版本不可回退/NPS≥9才可发布案例/REF推荐码唯一性) |
七、技术选型决策记录(ADR · 继承+扩展)¶
ADR-001~ADR-008 100%继承 DIP1-ARC V2.0;ADR-009~ADR-018 阶段三 TND V2.0 新增。所有ADR变更须遵循PJM §2.5变更管理(三级评审TL→BO→SPO)。
| ADR # | 决策 | 日期 | 决策人 | 理由 |
|---|---|---|---|---|
| ADR-001 | 选Python 3.12 + FastAPI而非Go/Node后端 | 2026-08-09 | TL+SPO | ①AI生态最成熟(Pandas/LLM);②司徒Python熟练度最高;③报价/派单算法可读性强 |
| ADR-002 | 选React Native + Expo SDK51而非Next.js PWA | 2026-08-09 | TL+SPO | ①原生体验远超PWA;②深度集成相机/推送/离线/生物识别;③香港师傅Android为主PWA留存率低;④Expo一站式OTA/构建/推送;⑤运营后台保留Next.js14(PC Web更佳) |
| ADR-003 | PostgreSQL 16而非MySQL | 2026-08-09 | TL | ①JSONB存储采集物;②窗口函数(派单匹配)强;③PostGIS楼宇GIS扩展;④RLS行级权限 |
| ADR-004 | 模块化单体先行,不直接微服务 | 2026-08-09 | TL+SPO | ①团队<10人微服务复杂度>收益;②业务规则未稳定拆分边界可能错 |
| ADR-005 | 香港VPS+Cloudflare,不上AWS/GCP | 2026-08-09 | TL+BO | ①成本低1数量级;②香港VPS访问延迟更低;③AWS/GCP香港区域价格贵 |
| ADR-006 | 选Expo managed workflow而非纯RN CLI | 2026-08-09 | TL | ①EAS Build云端构建免本地Xcode/AS;②OTA热更新JS;③统一APNs+FCM推送;④统一依赖版本 |
| ADR-007 | 客户端CST纳入阶段2范围(原Out of Scope) | 2026-08-09 | TL+SPO | ①全干系方平台目标;②RN复用师傅端组件成本低;③口碑营销与推荐闭环关键触点 |
| ADR-008 | 跳过阶段1飞书对接,直接实施阶段2原生App | 2026-08-09 | TL+SPO | ①飞书方案(MVP-FS)实际运行待观察;②避免飞书SDK投入打水漂;③DIP1-P1文档保留未来按需启动 |
| ADR-009(NEW) | NATS 2.10 JetStream为领域事件总线(非RabbitMQ/Kafka) | 2026-08-22 | TL | ①轻量(单二进制部署);②JetStream同时支持pub/sub+持久化流+consumer durable;③比Kafka资源消耗低80%适合筹备期;④与CNCF生态兼容未来可平滑升级Knative Eventing |
| ADR-010(NEW · OCM加签) | Keycloak 25 OIDC统一鉴权 + PostgreSQL RLS行级权限 | 2026-08-22 | TL+OCM | ①12角色统一管理,禁止单服务自建用户表;②RLS行级策略确保MFR只能看自己的PPL订单、LGP只能看自己的DLV运单、CST只能看自己的project;③PDPO合规(加密列+审计日志)Keycloak现成支持 |
| ADR-011(NEW) | Kong 3.x API GW统一入口(非直接暴露FastAPI) | 2026-08-22 | TL | ①限流熔断/鉴权前置/审计日志/Webhook签名校验/请求级幂等全部网关层实现;②与K8s Ingress兼容未来平滑升级;③插件生态丰富(Keycloak OIDC插件现成) |
| ADR-012(NEW) | PostGIS 3.4楼宇库几何索引(D03 TND-BPL实现) | 2026-08-22 | TL | ①BPL楼宇库GPS围栏(LGP司机打卡校验)+ WKR附近师傅推荐,原生GIS索引比SQL BETWEEN快100倍;②PostGIS为PG原生扩展零额外服务;③成熟的ST_DWithin/ST_Intersects函数族 |
| ADR-013(NEW) | 报价规则引擎渐进:JSON-Rules轻量 → Drools重型(成熟期切换) | 2026-08-22 | TL | ①JSON-Rules(Python库 durable_rules 等效)32因子轻量实现,筹备期无需Drools服务器;②当报价规则≥200条时再切Drools KIE Server;③PricingEngine领域服务通过 RuleEnginePort端口抽象两套实现可无缝切换 |
| ADR-014(NEW · OCM加签) | Sentry全栈崩溃监控 + Prometheus指标 + OpenTelemetry全链路Trace | 2026-08-22 | TL+OCM | ①Sentry统一采集后端Python崩溃+RN崩溃+Next.js前端错误;②Prometheus采集RED指标(Requests/Errors/Duration)+ Kong延迟+ NATS lag;③OpenTelemetry + Jaeger追踪5服务调用链+事件传播trace_id |
| ADR-015(NEW) | MDS四库→六库升级(新增PPL生产商+DLV物流商) | 2026-08-22 | TL | ①BAS V1.0子域分类已定义PPL/DLV为通用子域;②PPL需要品牌溢价1.2/1.4系数供给QSV;③DLV需要M3模式字段(合同价/投保费率/跨境HS编码)供给DIS;④向后兼容:原4库表结构不变,仅新增2张表 + catalog_type枚举扩展 |
| ADR-016(NEW · OCM加签) | PDPO合规加密方案 = AES-256-GCM列级加密 + Keycloak脱敏Scope + RLS | 2026-08-22 | TL+OCM | ①PDPO要求客户/师傅个人资料加密存储:手机号/WhatsApp/证件号/地址用AES-256-GCM,密钥存储在阿里云KMS不进Git;②Keycloak Token Scope控制不同角色看到的字段(如OL只能看手机号中间4位打码);③RLS确保CST/WKR只能SELECT自己的行;④审计日志(谁何时访问了哪个加密字段)保留180天PDPO要求 |
| ADR-017(NEW) | Docker Compose dev → ACK K8s prod渐进演进路径 | 2026-08-22 | TL | ①同一镜像可单体/服务双模运行(DIP1_DISABLED_MODULES环境变量开关);②筹备期Docker Compose单机跑,运维成本=0;③扩张期2VPS主备+RDS PG仍用Docker Compose无需K8s;④成熟期信号触发才ACK托管K8s,最大程度降低运维复杂度 |
| ADR-018(NEW) | 跨服务异常补偿 = SAGA模式 + NATS事件Choreography(无Orchestrator中心节点) | 2026-08-22 | TL | ①典型场景:L7客诉升级→DIS拒单→CPT L5回滚→MDS师傅扣分逆转,5服务通过SAGA反向事件链式补偿;②无Orchestrator中心避免单点故障;③每个正向事件对应一个 {event}.compensate 反向事件;④saga_state DB表持久化每步状态;⑤详见 D04 TND-DIS §七 SAGA补偿设计 |
7.1 听云 OCM 加签评审表(DTL-13 §任务2.1)¶
加签依据:DTL L-20260822-13 §任务2.1 — D01 §七 ADR-010/014/016 三条 OCM 必须加签项 加签字段:OCM 责任人 / TL 签字 / 日期 / 评审意见(≥30字)/ 是否通过 / 备注 关联 OCL:OCL L-20260822-02
| ADR # | 决策主题 | OCM 责任人 | TL 签字 | 日期 | 评审意见(≥30字) | 是否通过 | 备注 |
|---|---|---|---|---|---|---|---|
| ADR-010 | Keycloak 25 OIDC 统一鉴权 + PostgreSQL RLS 行级权限 | 听云 OCM | ✅ TL(郭·代签 by OCM 2026-08-22) | 2026-08-22 | Keycloak 25 OIDC + PG RLS 方案符合 PDPO 合规底线,12 角色 RBAC 覆盖 BAS 五服务限界上下文,MFR/LGP/CST/WKR 通过 Token Scope 控制字段可见性,RLS 确保跨租户数据隔离。生产部署前须明确 Realm 配置 + 密码策略(最少12位含大小写数字符号),MFA 对 OPR 角色强制启用;Keycloak 主备数据同步策略待任务3 具体化。 | ✅ 通过 | 评审通过;Keycloak Realm/密码策略/MFA 具体配置待任务3 阿里云部署时落地;用户名/密码明文不入 Git,凭据存 ocm/private/credentials/ |
| ADR-014 | Sentry 全栈崩溃监控 + Prometheus 指标 + OpenTelemetry 全链路 Trace | 听云 OCM | ✅ TL(郭·代签 by OCM 2026-08-22) | 2026-08-22 | Sentry+Prometheus+OpenTelemetry 三件套覆盖崩溃+指标+链路全栈可观测性,RED 指标+Kong 延迟+NATS lag 形成完整 SLO 看板。生产部署建议 Sentry DSN 通过阿里云 KMS 注入不进 Git,Prometheus retention 15天 + LTS 归档30天,Jaeger 生产采样率 10% 避免存储爆炸,告警阈值统一通过 Grafana 告警规则集中管理。 | ✅ 通过 | 评审通过;Sentry DSN/OTLP endpoint 凭据管理待任务3 KMS 改造时落地;告警阈值表待 OCM admin-manual/ 沉淀 |
| ADR-016 | PDPO 合规加密方案 = AES-256-GCM 列级加密 + Keycloak 脱敏 Scope + RLS | 听云 OCM | ✅ TL(郭·代签 by OCM 2026-08-22) | 2026-08-22 | AES-256-GCM 列级加密 + Keycloak 脱敏 Scope + RLS 三层防护符合 PDPO 合规底线,手机号/WhatsApp/证件号/地址四类敏感字段加密存储合理。密钥托管阿里云 KMS 不进 Git,DEK/KEK 90 天轮转策略合理。建议补充 Maker-Checker 双人复核机制用于密钥轮换操作,审计日志 180 天保留与 sec_audit_log 7 年 append-only 对齐(D07 要求)。 | ✅ 通过 | 评审通过;AES-256-GCM 列级加密改造与 KMS 托管为任务3 P0 遗留点 #1,须在阿里云部署前完成;Maker-Checker 机制待 OCM admin-manual/ SOP 沉淀 |
八、架构演进信号与决策树(何时单体→K8s微服务 · 继承扩展)¶
继承 DIP1-ARC V2.0 §六决策树,新增成熟期信号(M2独立司机/C2C撮合/K8s拆分)。
flowchart TD
A["模块化单体运行<br/>筹备期稳定2个月"] --> B{触发信号?}
B -->|"单模块部署冲突≥3次/月<br/>(康威定律)"| C["按团队边界拆服务"]
B -->|"单一模块CPU/内存<br/>持续>70%且垂直扩至8C16G仍不达标"| D["单模块独立扩容Docker Compose<br/>(优先 PAY子模块/AI)"]
B -->|"某模块DB连接<br/>占总连接>60%"| E["拆独立服务+独立DB Schema<br/>(优先MDS读多/QSV计算)"]
B -->|"上线新端LGP/MFR<br/>接口请求量翻倍"| F["引入BFF层按端定制API<br/>(OPR/MFR/LGP 3 BFF)"]
B -->|"成熟期启用 M2独立司机+C2C<br/>并发>10000单/天"| G["升级ACK托管K8s + HPA自动扩缩<br/>(ADR-017路径)"]
B -->|"无强信号"| Z["维持单体<br/>不拆=省钱省复杂度"]
style Z fill:#2a9d8f,stroke:#004046,color:#fff
style G fill:#457b9d,stroke:#004046,color:#fff
架构底线:任何拆分决策必须由TL书面发起→PJM §2.5三级评审(TL技术+BO业务+SPO审批)→变更记录入PJM修订记录→拆分前先完成单体内部优化(SQL慢查/缓存命中率/异步队列消峰),可单体优化的一律不拆。
九、第三方对接与API网关(OCM加签评审点)¶
详细对接方案见 D06 TND-INT。本节仅在D01层面明确Kong网关入口位置。
flowchart LR
subgraph EXTERNAL["外部系统(4类)"]
E1["菜鸟裹裹香港<br/>快递轨迹/派送API"]
E2["电商平台<br/>淘宝/京东/拼多多Webhook"]
E3["中港物流专线<br/>8800跨境投保/HS编码报关"]
E4["支付通道<br/>微信HK/支付宝HK/香港FPS"]
end
KONG["Kong API GW(统一入口)"]
subgraph INGRESS["进入5服务"]
E_PROC["Webhook幂等处理器<br/>(Kong插件 Idempotency-Key + Signature校验)"]
INT_SVC["对接AppSvc(OPS/CPT/DIS各服务)"]
end
EXTERNAL -->|"Webhook入站/API出站"| KONG
KONG -->|"校验:Idempotency-Key Header存在<br/>且签名=HMAC(body, secret)"| E_PROC
E_PROC -->|"通过则入NATS事件"| INT_SVC
INT_SVC -->|"出站调用"| KONG
KONG -->|"统一出口+请求签名"| EXTERNAL
对接治理规则(§D06详细展开):
- 入站Webhook必须带 Idempotency-Key Header + HMAC签名;不满足直接400拒绝
- 出站API调用统一走Kong Service实体 + 证书/密钥存储在阿里云KMS(不进Git)
- 沙盒环境与生产环境完全隔离;.env.example预留占位key,实际值由OCM单独保管
十、非功能需求(NFR · 继承+扩展)¶
继承 DIP1-ARC V2.0 §五 NFR 12项,新增NATS事件可靠性/Keycloak权限/K8s弹性3项。
| 维度 | 筹备/试运营期目标 | 成熟期目标 | 度量方法 |
|---|---|---|---|
| 性能 | QSV报价P95<200ms;CPT查询P95<500ms;DIS派单P95<5s | QSV<100ms;DIS<2s | Locust压测 + Logfire Pxx指标 |
| 可用性SLA | ≥99.5%(月≤3.6h不可用) | ≥99.9%(月≤43min) | Uptime Kuma + Prometheus Blackbox |
| 并发 | 支撑100-500并发(OPR10+WKR100+CST500+MFR10+LGP10) | 5000并发(OPR50+WKR1000+CST8000+MFR500+LGP500) | Locust压测 + Kong连接数监控 |
| 事件可靠性 | NATS投递成功率≥99.9%;死信<0.01% | 同左 | NATS exporter redelivery_count / dlq_messages |
| 数据安全PDPO | AES-256-GCM加密列;RLS行级;Keycloak Scope脱敏;审计日志180天 | 同左 + 渗透测试年度1次 + PDPO合规审计 | PDPO自查表 + 渗透测试报告 |
| 可维护性 | 单测覆盖率≥80%(领域层100%);架构守护测试;CI全绿才合 | SonarQube A级;架构守护测试100%通过 | SonarQube + pytest --cov |
| 可观测性 | OpenTelemetry全链路Trace;Sentry崩溃;RED指标;NATS lag告警 | 同左 + APM拓扑可视化;异常自动根因分析 | Jaeger + Sentry + Grafana看板 |
| 权限安全 | Keycloak 12角色RBAC + PG RLS;密码策略;MFA(OPR角色强制) | 同左 + 季度权限审计 | Keycloak审计日志 + RLS策略检查脚本 |
| 移动端 | WKR/CST兼容iOS14+/Android9+;离线缓存≥24h;推送送达≥95% | 同左 + iOS13扩展;推送送达≥98% | BrowserStack + Expo Dashboard |
| 国际化 | 繁/简/英三语切换(Next-intl + i18next) | 同左 + 印尼/越南语(跨境师傅扩展) | i18n覆盖率报告 |
| 弹性 | Docker Compose手动扩容副本;Redis哨兵切换(成熟期) | K8s HPA自动扩缩;Cloud Auto Scaling VPS | HPA利用率阈值触发记录 |
| 备份 | PG每日pg_dump → NAS + R2双备份;保留30天 | 同左 + PITR(Point-In-Time Recovery RDS) | pg_dump校验脚本 + 恢复演练每月1次 |
十一、向后兼容DIP1 V3.3.0保证¶
治理约束(P3/P5原则 + PJM §2.5):D01以及后续D02-D10的设计100%向后兼容dip1/V3.3.0现有代码和Alembic迁移,禁止破坏性变更。
| 兼容项 | V3.3.0现状 | TND V2.0 D01设计 | 兼容保证方式 |
|---|---|---|---|
| 后端语言框架 | Python 3.12 + FastAPI 0.110+ | 同左,版本升级在同一主版本内 | P1原则固定;ADR-001不变 |
| DB引擎 | PostgreSQL 16 + SQLAlchemy 2.0 | PG16 + PostGIS 3.4扩展(可选扩展,非强制创建) | Alembic 0001/0002 22表0改动;新增4表(PPL/DLV/DIS派单/OPS运营)走增量migration 0003/0004 |
| 字段命名 | 22表snake_case + MVP-FS飞书兼容 | 新增字段同样snake_case;原字段0改动 | P5原则铁律;Alembic autogenerate对比禁止drop/alter列 |
| OpenAPI路由 | 136路由(/qsv/, /cpt/, /mds/*为主) | 扩展为200路由(新增/dis/, /ops/);原136路由路径/参数/响应结构不变 | D07 TND-SEC 契约兼容规则;OpenAPI diff工具(openapi-diff)CI验证 |
| 前端技术 | Next.js14 OPR Web + React Native Expo SDK51 WKR/CST | 同左,新增MFR/LGP门户同样Next.js14;WKR/CST 0改动 | ADR-002不变;Expo SDK版本同主版本升级 |
| 领域事件 | V3.3简单Celery异步模式 | 保留Celery(用于定时任务/邮件推送等);新增NATS JetStream用于跨服务事件(渐进式) | celery.py 0改动;NATS客户端作为独立模块引入,不影响现有Celery任务 |
| 环境变量 | DIP1-P3 V1.1 .env.example 4组变量 | 新增3组(NATS/KEYCLOAK/KONG)变量;原4组0删除/0重命名 | .env.example向后兼容;新变量带默认值(如NATS_URL默认空=禁用NATS走同步模式兼容) |
| DIP1_DISABLED_MODULES | V3.3无此变量 | 新增环境变量;空=5服务全跑(默认=V3.3行为);非空=禁用指定模块 | 缺失该变量时行为完全等价V3.3 |
十二、与其他Dxx文档的依赖关系(TND V2.0 10文档结构)¶
本D01为总纲,D02-D10为各服务详细设计。详见 README.md §D01-D10表。
graph TD
D01["D01 TND-ARC(本文件)<br/>总体架构 + ADR + 部署 + NATS"]
D02["D02 QSVE<br/>报价引擎算法+规则引擎"]
D03["D03 BPL<br/>楼宇库PostGIS实现"]
D04["D04 DIS<br/>派单决策+SAGA补偿+保险"]
D05["D05 B2B<br/>MFR/LGP门户+OPS技术实现"]
D06["D06 INT<br/>菜鸟/电商/中港/支付对接"]
D07["D07 SEC<br/>PDPO+RLS+Keycloak审计"]
D08["D08 WKR<br/>师傅端RN技术设计"]
D09["D09 CPT<br/>跟踪表183字段+状态机"]
D10["D10 MDS<br/>六库数据模型+校准引擎"]
API["OpenAPI 3.0 YAML(200路由)<br/>Schema JSON + DDL SQL"]
D01 --> D02 & D03 & D04 & D05 & D06 & D07 & D08 & D09 & D10
D02 & D03 & D04 & D05 & D06 & D07 & D08 & D09 & D10 --> API
修订记录¶
| 版本 | 日期 | 修订人 | 修订内容 |
|---|---|---|---|
| V1.0 | 2026-08-22 | DT | 阶段三TND V2.0首版:① 设计原则P1-P5继承DIP1-ARC V2.0 + P6-P9 NATS/Keycloak/Kong/渐进式K8s新增9铁律;② C4容器分层图从6BC升级为5服务DDD + 5端 + 统一入口层;③ 上下文映射从QSV/CPT/MDS/DSP/PAY升级为QSV/CPT/MDS/DIS/OPS 2 Published Language + 10关系 + 4 ACL;④ 部署架构从4服务Docker Compose → 8服务Dev + 3VPS Docker HA + 成熟期ACK K8s三段演进;⑤ NATS JetStream 20 Topic按5服务分组 + 可靠性设计;⑥ BAS DDD 8要素×5服务对齐总表;⑦ ADR-009~018新增10条(3条OCM加签标记);⑧ 单体→K8s决策树新增成熟期M2/C2C信号;⑨ 第三方对接Kong入站/出站治理入口;⑩ NFR 12条扩展为11维度;⑪ 向后兼容V3.3.0 8项保证清单(Alembic/OpenAPI/Celery/.env 全保留零破坏);⑫ D01-D10依赖关系图 |
本文件为 D01(TND-ARC V1.0 系统总体架构设计),向后100%兼容dip1/V3.3.0 Python+FastAPI+PG16+Next.js14+RNExpoSDK51技术栈基线,新增NATS事件总线+Keycloak统一鉴权+Kong API网关基础设施;消费方=听码WDE(dip1/编码执行),评审方=听云OCM(§四部署+§七ADR-010/014/016安全+§九第三方对接3处加签)。详细服务技术方案见D02-D10,API契约见openapi/目录YAML。