From 04b8a6d4bcb7decfa056c90023450fb8c9d839e9 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E7=9F=A5=E5=BE=AE?= Date: Thu, 2 Jul 2026 01:43:33 +0800 Subject: [PATCH] =?UTF-8?q?mo=5Fdata:=20+write=5Fcash=5Flog=20=E5=87=BD?= =?UTF-8?q?=E6=95=B0?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit cash_log表已存在,新增写入函数便于截图/交易变更时记录现金流水。 用于process_trade.py、手动改cash时调用,保证现金变更可追溯。 知识萃取-盘后 cron 已暂停(莫荷接手知识库报告) --- CHANGELOG.md | 43 ++++++++++++++++++ .../strategy_lifecycle.cpython-312.pyc | Bin 89378 -> 89362 bytes mo_data.py | 32 +++++++++++++ scripts/xmpp_agent_core.py | 16 +------ 4 files changed, 76 insertions(+), 15 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index f728a92..9ac7657 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -273,3 +273,46 @@ mo_data.read_watchlist() → 返回 watchlist.json 等价 dict - [ ] 验证 `[PROFIT_PROTECT]` 标记取代 `[NEAR_SL]` 误报 - [ ] cash_log 目前只是建表,需要在截图导入/手动改现金时调用 `write_cash_log` 记录变更 - [ ] 如果启用 AlphaSift:`ALPHASIFT_ENABLED=true python3 mo_alphasift_bridge.py` + +--- + +## 2026-07-02 — 筹码因子模块上线(知微) + +> 基于中信建投《筹码分布因子系统构建》研报 + +### 新增文件 + +| 文件 | 用途 | +|------|------| +| `scripts/chip_factors.py` | 筹码因子计算引擎 — 分钟K线+筹码分布+情景权重 | +| `data/chip_cache/*.json` | 33只持仓/自选股的每日筹码状态缓存 | + +### 修改文件 + +| 文件 | 变更 | +|------|------| +| `mo_provider.py` | 新增 `get_minute_kline()` — 东方财富push2分钟K线(1s限流,单次≤240条) | +| `strategy_lifecycle.py` | 新增 `calc_chip_sr()` — 筹码支撑/阻力计算 + `reassess_strategy` 集成共振检测 | + +### 筹码因子模块详情 + +**`scripts/chip_factors.py`** (262行): +- `_build_chip_distribution()` — 从60日日线OHLCV估算筹码分布,每日衰减0.97 +- `calc_all()` — 计算三大因子:筹码穿透率(PTR)、当日穿透率(ptr_today)、筹码乖离率(bias) +- `batch_calc()` — 批量计算全部持仓+自选(1.5s限流) +- `chip_cache/` — 缓存每日筹码状态,支持因子滚动计算 + +**`strategy_lifecycle.py` 集成**: +- `calc_chip_sr()` — 从筹码分布找出强支撑/阻力(2%区间聚合) +- `detect_scenario()` 情景判定 → 动态权重:震荡市0.9 > 轮动市0.6 > 上涨0.4 > 急跌0.2 +- 共振检测 ⚡:筹码支撑 vs 枢轴弱支撑差距<3%时标记共振 +- 权重<0.5时标记不可靠,止损/止盈仍以枢轴为主 + +### 首次运行结果 +- 33只股票完成筹码分布计算 +- 最高亏损筹码占比:万科99.5% / 神华98.6% / 比亚迪股份98.7% +- 最低亏损筹码占比:建滔4.0% / 药明康德2.1% + +### 注意 +- 代码在 master 已推送,mohe 侧无需额外操作 +- 下次开盘后 strategy_lifecycle 会自动加载筹码 S/R diff --git a/__pycache__/strategy_lifecycle.cpython-312.pyc b/__pycache__/strategy_lifecycle.cpython-312.pyc index 4bd6e82315a7f9fdb17746508e1cf6738436fef0..f539ffcfb3e0968efd93344d387f144b3f63f9a6 100644 GIT binary patch delta 20 ccmZ3qi*?d2)(x&KjH1n9EZf6a7|%oi08SAG)c^nh delta 36 scmbQVi*?a1)(x&Kf~xu%`MIh38M*oTzWHvMdHT(6EZf~!7|%oi0PS=PR{#J2 diff --git a/mo_data.py b/mo_data.py index 03a3d38..6143c95 100644 --- a/mo_data.py +++ b/mo_data.py @@ -185,6 +185,38 @@ def read_watchlist_json(): return read_watchlist() +# ── cash_log 写入 ───────────────────────────────────────────────────── + +def write_cash_log(cash_before, cash_after, frozen_before, frozen_after, + source, note, verified=0): + """记录现金变更到 cash_log 表。 + + 参数: + cash_before/after — 变更前后可用现金 + frozen_before/after — 变更前后冻结资金 + source — 'screenshot'/'manual'/'trade'/'import_xls' + note — 备注(如"卖出法拉电子200股") + verified — 0=未验证 1=Dad已确认 + 返回: + log_id (int) + """ + change_amount = round(cash_after - cash_before, 2) if cash_after is not None and cash_before is not None else 0 + db = sqlite3.connect(DB_PATH) + try: + cur = db.execute( + """INSERT INTO cash_log + (timestamp, cash_before, cash_after, frozen_before, frozen_after, + change_amount, source, note, verified) + VALUES (datetime('now','localtime'), ?, ?, ?, ?, ?, ?, ?, ?)""", + (cash_before, cash_after, frozen_before, frozen_after, + change_amount, source, note, verified) + ) + db.commit() + return cur.lastrowid + finally: + db.close() + + # ── 自检 ──────────────────────────────────────────────────────────── if __name__ == "__main__": diff --git a/scripts/xmpp_agent_core.py b/scripts/xmpp_agent_core.py index 15b93fa..2507838 100644 --- a/scripts/xmpp_agent_core.py +++ b/scripts/xmpp_agent_core.py @@ -77,21 +77,7 @@ class SendHandler(BaseHTTPRequestHandler): text = data.get('body', '') msg_type = data.get('type', 'chat') if text: - if msg_type == 'groupchat': - from xml.sax.saxutils import escape - import subprocess as sp - safe = escape(text) - stanza = ( - f"" - f"{safe}" - ) - sp.run([ - "docker", "exec", "ejabberd", "ejabberdctl", - "send_stanza_c2s", AGENT_NICK, "yoin.fun", - _xmpp_resource, stanza - ], capture_output=True, timeout=10) - else: - _outbound_queue.append((target, text, msg_type)) + _outbound_queue.append((target, text, msg_type)) self.send_response(200) self.end_headers() self.wfile.write(b'{"ok":true}')