- 新增 signal_rules 两条流解析与消化口径(含 0~1 / 0~100 置信度归一) - 新增 signal_service,独立消费组,不与 trading_service 抢消息 - 接入调度位 signal_digest 与两个运维端点 - test_batch5_units 8 例;全量 118 例 |
||
|---|---|---|
| .idea | ||
| app | ||
| config | ||
| scripts | ||
| .dockerignore | ||
| .env.example | ||
| .gitignore | ||
| Dockerfile | ||
| POSITION_MGMT_DESIGN.md | ||
| QMT_INTERFACE_REQUIREMENTS.md | ||
| README.md | ||
| ddl_pms_v1.sql | ||
| docker-compose.yml | ||
| requirements.txt | ||
README.md
tradingSystem — 综合交易系统(PMS 持仓管理)
命令驱动的持仓管理系统:用户通过管理页面下达大方向命令(总规模/仓位上限/升降仓/对某股做T)→ 持仓系统制订分股分批方案并管理账本(批次、摊薄成本、安全垫、纪律)→ 决策系统负责研判与择时(其形态计算、每日定时分析等核心功能照旧运行)→ 下游系统(QMT 侧)挂单成交。
架构要点:持仓系统 ↔ 决策系统直接交互;持仓系统 ↔ 下游系统交互;决策系统与下游断开——对下游的管理权限(建仓审批、卖出指挥)由决策系统移交持仓系统,其全部分析产出保留并成为持仓系统的输入。上游量化系统输出不变,持仓系统的建仓计划围绕上游输出建立。
仓位框架:百分比制(规模 200 万 / 总仓 ≤60% / 单股 ≤8% / ≤15 只,均为用户参数命令、页面可调),单股分批 50/25/25,含一手可行性检查,行业集中度硬性拦截(划分依据留接口)。决策方式:规则引擎为主,定性研判委托决策系统(持仓系统不自建研判栈)。安全垫三义:分批建仓留缓冲、浮盈垫后加仓、做T降成本(命令授权制)。
文档与交付物
| 文件 | 内容 |
|---|---|
POSITION_MGMT_DESIGN.md |
总体设计 V0.4(定稿,开发启动):命令系统与管理页面/账本/仓位框架/动作引擎/两道关口/择时执行/下游通道。功能一次性开发,上线按依赖分三步切换 |
QMT_INTERFACE_REQUIREMENTS.md |
与 QMT 侧下游系统协商用的数据与接口需求清单(含资金快照、统一指令通道建议 DDL),按编号答复回填 |
ddl_pms_v1.sql |
PMS 全部自有表建表语句(153 代理侧,10 张) |
config/settings.py |
配置(基础设施键名对齐 bionic;业务参数为初值,页面调参持久化到 pms_runtime_param 后优先) |
模块地图
app/
core/ 纯逻辑, 零外部依赖, 可单测 —— 系统的算数与纪律都在这里
sizer.py 批次拆分与一手合并 / 组合约束 / 风险敞口披露
cushion.py 摊薄成本 / 安全垫状态机 / 保垫触发 / 卖出核销次序
command_spec.py 命令目录(A/B/C 全量 27 类) / 参数校验 / 双状态机 / 冲突识别
planner.py 方案生成器: 降仓凑额四档 / 升仓 / 建仓 / 清仓 / 行业 / 撤单
recon.py 成交认领与入账映射 / 对账差异与修正 / 除权检测 / T+1 可用量
rule_gate.py 规则闸终检: 上限/一手/可卖/冻结/刹车/行业/不追高 (减持只放行不阻拦)
exec_timing.py 择时实现B: 分日配额 / 分笔 / 买卖出手判定 / 14:45 兜底 / 窗口收口
action_engine.py 动作引擎: FILL 回踩补足 / ADD 盈利加仓 / DCA 补仓 / TRIM 保垫减仓
signal_rules.py 决策系统两条信号流的解析与消化口径 (含置信度尺度归一)
tradedays.py 交易日历: 调度守卫与执行窗口计算
db/session.py 三库连接 + **严格单表访问守卫** (JOIN/逗号连表/跨表子查询一律拒绝)
repo/ 单表数据访问: pms_repo (自有 10 表) / downstream_repo (下游只读三表)
services/ 编排层
param_store.py 运行参数中心 (表值优先于 settings 初值, 页面调参即时生效)
portfolio.py 组合快照 (账本+行情+行业 → 方案/规则闸/页面的统一输入)
command_service.py 命令下达→校验→冲突→生效/规划→进度推进→撤销
executor.py 方案→指令→分日出手→窗口收口 (规则闸与择时的编排落点)
dispatcher.py 下发通道三适配器: shadow(默认) / plan_x / channel_y
proposal_service.py 自主提议: 扫描→规则闸→研判闸→按自主档位分流 (执行/入队)
judge.py 研判闸客户端 (决策系统未接通时自动降级为人工确认)
signal_service.py 盘中信号订阅 (db2 广播 + db3 风控卖出) → 卖出指令或提议
ledger_service.py 成交回放 / 对账 / 除权 / 盘前 / 日终结算 / 运营日报
market.py 行情 (Redis db13) 与参考位 (决策系统主口径 + 兜底自算)
industry.py 行业划分可插拔适配器 (custom_table / gp_stock_category / 停用)
web/ FastAPI + 单页 (Vue3 + ElementPlus),页面四块 + 运维/日报抽屉
scheduler.py Celery beat 调度总表 (设计 §10 八个调度位 + 三条守卫)
scripts/
run_tests.py 一次跑完全部单测 (见下方「Docker 部署」)
test_core_units.py 仓位与安全垫核心逻辑 14 例
test_batch2_units.py 命令 / 方案 / 回放对账 纯逻辑 35 例
test_batch3_units.py 规则闸 / 择时执行器实现B 纯逻辑 18 例
test_batch4_units.py 动作引擎 四类自主动作触发与数量口径 11 例
test_batch5_units.py 决策系统信号流解析与消化口径 8 例
test_wiring.py 装配自检: 服务层→核心→落表 全链路 (内存桩) 32 例
init_db.py 建表 (应用 ddl_pms_v1.sql, 幂等, 默认演练)
check_db.py 实机连通性与表结构自检 (需真实 .env)
三条铁律
- 命令至上:自动决策不得突破用户命令参数;冲突时命令优先;命令间冲突由用户裁决。
- 分工不越权:持仓系统管「做什么、多少」,决策系统管「该不该、何时」,下游只管执行;研判不可用时降级为保守规则 + 人工确认,不自建第二套研判。
- 先记账后动作 + 故障即守成:指令先落表再下发;故障不产生新指令;账本与下游定期对账,以下游为实际持仓事实源。
Docker 部署(项目统一以容器方式构建运行)
服务共用一个镜像:pms-web(管理页面,端口 38100)+ pms-beat / pms-worker(Celery 调度与执行,挂在 sched profile 下)。
# 服务器首次部署
git clone <仓库地址> && cd tradingSystem
cp .env.example .env && vim .env # 填入真实连接串 (.env 不入库)
docker compose build # 默认走清华 PyPI 镜像; 可 --build-arg PIP_INDEX_URL=... 覆盖
# 构建验证 (不连库, 秒级): 应输出 ALL SUITES PASS
docker compose run --rm pms-web python scripts/run_tests.py
# 建表 (幂等; 不加 --yes 只演练打印)
docker compose run --rm pms-web python scripts/init_db.py --yes
# 实机自检 (连库, 需 .env): 库连通 + pms_* 十表 + 下游表完整列定义 + 行情 Redis
docker compose run --rm pms-web python scripts/check_db.py
docker compose up -d # 管理页面
curl http://127.0.0.1:38100/health # 健康检查 + 配置装载自证 + 库连通自证
# 浏览器打开 http://<服务器IP>:38100/ → 参数设置 / 命令台 / 持仓与账本 / 提议确认
docker compose --profile sched up -d # 启用调度器 (beat + worker)
docker compose logs -f pms-beat pms-worker
# 日常更新
git pull && docker compose build && docker compose up -d
基础镜像 python:3.11-slim 拉取慢时,先给服务器 Docker 配置 registry 镜像加速。日志落 ./logs(已挂载卷);容器时区 Asia/Shanghai。管理页面的前端资源(Vue3 / ElementPlus / axios)走 unpkg CDN,浏览器需能访问外网;若内网隔离,把页面头部三行 <script>/<link> 换成本地文件即可(页面本身无构建步骤)。
依赖版本坑:redis 必须锁在 5.x。redis-py 6.x 默认按 RESP3 握手(先发 HELLO 3),而 208/150 两台 Redis 是 6.0 以前的版本,会回 unknown command HELLO,行情与 Celery 总线一起断。requirements.txt 已锁版本,代码侧另有 protocol=2 双保险;升级依赖时别把这条放开。
调度总表(--profile sched 生效,设计 §10)
| 调度 | 时间 | 任务 | 本批状态 |
|---|---|---|---|
| 盘前准备 | 交易日 08:50 | T+1 可卖重置 / 参考位取数 / 刹车结算 | ✅ |
| 命令轮询 | 每 1 分钟(全天) | 新命令解析 → 方案生成 → 状态机推进 | ✅ |
| 成交回放 | 交易时段每 5 分钟 | trading_order 增量回放 + 盘中轻对账 |
✅ |
| 盘中执行 | 交易时段每 1 分钟 | 方案转指令 → 自主提议扫描 → 择时出手(规则闸终检 → 下发 → 记子单) | ✅ |
| 信号消化 | 交易时段每 1 分钟 | 订阅 db2 盘中广播 + db3 风控卖出 → 卖出指令或提议 | ✅ |
| T 仓平回 | 14:50 | 做T强制平回 | 🔜 二期(现只自证 T 仓为 0) |
| 日终结算 | 15:10 | 除权检测 / 全量对账 / 安全垫 / 命令进度日结 | ✅ |
| 运营日报 | 15:30 | 关注区 + 全量统计(页面「日报」按钮可查) | ✅ |
调度器三条守卫:交易日守卫、故障即守成(任务内异常吞掉记 ERROR,绝不因调度异常产生新指令)、全局暂停执行(休假模式下除对账与日报外全部跳过)。
指令下发通道(设计 §9,参数 PMS_DISPATCH_MODE,默认 shadow)
| 模式 | 行为 | 什么时候用 |
|---|---|---|
shadow(默认) |
指令照常过规则闸、照常置 DISPATCHED,但不写下游。你在 QMT 侧人工执行,成交由回放按 FIFO 认领回账本 | 直连服务就绪前的一期口径(设计 §9:命令类降仓/清仓由用户人工执行、PMS 记账跟踪) |
plan_x |
买入写 trading_buy_plan |
⚠️ 已作废:架构已定 trading_service 全量退出业务,此模式不再使用(代码暂留,勿在实盘开启) |
channel_y |
写统一指令表 pms_order_request |
新 QMT 直连服务就绪后启用,由它消费本表 |
目标架构(2026-07-28 已定):
trading_service全量退出业务,只保留看板与统计展示;新写一个 QMT 直连服务承担挂单与订单/持仓/资金回写;PMS 只管决策与账本。三者之间的数据接口待协定后另行成文。
影子模式下的完整闭环:页面下命令 → 方案落表 → 方案转指令 → 择时按日配额给出「今天该出多少、什么价」→ 你照着在 QMT 下单 → 5 分钟一次的回放把成交认领回批次账本 → 命令进度自动推进。整条链路除了「人手下单」这一步,其余与实盘接管后完全一致。
自主提议的分流(设计 §6 / §7)
动作引擎每分钟扫一遍持仓,产出 FILL / ADD / DCA / TRIM 四类候选,然后依次过三道:
- 规则闸(一级,纯代码)——不过就拒,未通过项落评审账本。自主动作受组合刹车约束(命令驱动不受)。
- 研判闸(二级,仅补足/加仓/补仓,委托决策系统)——
PMS_JUDGE_API_BASE为空即视为未接通,按设计自动降级为人工确认并记 ERROR,绝不把「研判拿不到」当成「研判通过」。 - 按自主档位分流——
full执行、propose_only入队(一期默认)、off不扫描。
两条无条件覆盖档位的规矩:减持方向不设确认门槛(TRIM 保垫减仓任何档位都直接落指令);−15% 及更深的补仓永远需用户确认(即便档位是 full 也强制入队)。同一只票的同一动作若已有在途提议或在途指令,不重复提。
已实现 / 待开发
已实现:建表 DDL 与建表脚本;配置与运行参数中心;仓位规划器与安全垫账;命令系统(27 类命令全目录 + 双状态机 + 冲突识别);方案生成器(降仓凑额四档、升仓、建仓分批、清仓/减至、行业清仓与限额、暂停买入撤单);账本回放与对账引擎(成交认领、外部成交并入 BASE 告警、以下游为准修正、除权检测、T+1 可用量、连续不一致升级);规则闸终检;择时执行器实现 B(分日配额、分笔、VWAP/回踩/不追高、14:45 兜底、停牌一字板顺延、窗口耗尽收口);三模式下发通道;动作引擎四类自主动作 + 研判闸客户端 + 提议分流;决策系统信号消化(两条流独立消费组订阅、置信度分档转清仓指令或提议);管理页面四块 + 运维/日报抽屉;调度器八个调度位;单测 118 例。
待开发:T0 做T(二期)、择时实现 A(委托决策系统盘中择时,等 bionic 侧接口)、新 QMT 直连服务的对接(等接口协定)。研判闸客户端已就位,等 bionic 侧 process_intraday_audit 新增 PMS 请求 direction 后,在页面填 PMS_JUDGE_API_BASE 即接通。
待外部协商:QMT_INTERFACE_REQUIREMENTS.md 的 A/B/C/D 各项——尤其 A1(trading_position 完整 DDL 与可用数量列)、A2(trading_order 状态枚举与来源标识)、B1(统一指令通道)。在来源标识到位前,回放按「同股同向 + 下发早于成交 + FIFO」贪心认领,认领不上即判外部成交并告警;持仓数量列用候选名探测,探测结果可经页面「运维 → 导出下游表结构」查看,也是回填 D1 的现成材料。
开发约定
- 开发机与服务器经 git 同步代码;构建与运行统一走 Docker(
docker compose build→ 容器内python scripts/run_tests.py→up -d),测试结果回传后迭代。 - 153 代理侧数据库严格单表访问;该纪律已落到
app/db/session.py的静态守卫,违规 SQL 在执行前抛MultiTableSQL。持仓系统内部代码统一 Tushare 点式(600000.SH),读决策系统结论表时转前缀式。 - 配置分两层:基础设施连接串在
.env(服务器手工维护,不入库,模板见.env.example);业务参数在config/settings.py只是初值,上线后经管理页面修改并持久化到pms_runtime_param表。业务代码禁止直接读 settings 取业务参数,一律走services/param_store.py。 - 新增纯逻辑一律进
app/core/(零外部依赖 + 配套单测);需要连库的编排进app/services/,并保证连库失败时降级而非崩页。 - 里程碑(设计定稿、建表、各期上线)及时 git 提交。