trading: 日内T/长桥/六合彩文档与脚本 + quant-factor-mining 新目录
This commit is contained in:
@@ -1,48 +1,122 @@
|
||||
#!/bin/bash
|
||||
# 核验当前期预测 vs 实际开奖,记录命中率
|
||||
# 22:30 北京时间(开奖21:30后1小时)跑
|
||||
#
|
||||
# 流程 (2026-08-13 重写):
|
||||
# 1. curl v_xg.json (带 UA + proxy fallback) → Qi + Data.1-7 (真开彩, 2026-08-04 验证)
|
||||
# 2. 失败 fallback: 已有 draws 表数据 OR 提示用户手填
|
||||
# 3. draws 表空 → 自动 add_draw (触发 check_hits 更新所有 analysis hit 状态)
|
||||
# 4. 找 Qi 期分析 .md, 输出核验报告
|
||||
#
|
||||
# ⚠️ Qi→Nq 修复后: cron 11:30 北京 分析 Nq 期 (未开下期), 22:30 北京 verify 时 Qi 已经是新一期,
|
||||
# 分析文件就是 Qi 期 (刚开的那期), 不是 Qi-1
|
||||
#
|
||||
# 🚨 marksix6.com 真开彩验证源: 必须用 browser (Vue SSR, curl 拿不到), 不在本脚本里跑
|
||||
# (no_agent 模式没 browser 工具); cron 改 no_agent 时改这里
|
||||
|
||||
set -e
|
||||
|
||||
DB="$HOME/.hermes/trading/lottery.db"
|
||||
OUT_DIR="$HOME/.hermes/cron/output/lottery-verify"
|
||||
mkdir -p "$OUT_DIR"
|
||||
SKILL_DIR="$(cd "$(dirname "$0")/.." && pwd)"
|
||||
|
||||
# 当前期号 - 优先代理,失败直连(VPS 出口有时被墙)
|
||||
QI=$(curl -s --proxy http://127.0.0.1:7890 --max-time 8 "https://btc.tktk.app/data/v_xg.json" 2>/dev/null | python3 -c "import json,sys; d=json.load(sys.stdin); print(d.get('Qi',''))" 2>/dev/null)
|
||||
if [ -z "$QI" ]; then
|
||||
QI=$(curl -s --noproxy '*' --max-time 8 "https://btc.tktk.app/data/v_xg.json" 2>/dev/null | python3 -c "import json,sys; d=json.load(sys.stdin); print(d.get('Qi',''))" 2>/dev/null)
|
||||
fi
|
||||
if [ -z "$QI" ]; then
|
||||
echo "❌ 无法获取当前期号(代理+直连都失败)"
|
||||
exit 1
|
||||
# === Step 1: 取 v_xg.json (Qi + Data.1-7) ===
|
||||
fetch_v_xg() {
|
||||
local out
|
||||
# 优先代理,失败直连(VPS 出口有时被墙)
|
||||
out=$(curl -s --proxy http://127.0.0.1:7890 --max-time 8 \
|
||||
-A "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36" \
|
||||
"https://btc.tktk.app/data/v_xg.json" 2>/dev/null || true)
|
||||
if [ -z "$out" ] || echo "$out" | grep -q "请求出错\|Cann't connect"; then
|
||||
out=$(curl -s --noproxy '*' --max-time 8 \
|
||||
-A "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36" \
|
||||
"https://btc.tktk.app/data/v_xg.json" 2>/dev/null || true)
|
||||
fi
|
||||
# 校验是不是 JSON 且有 Qi
|
||||
if echo "$out" | python3 -c "import json,sys; d=json.loads(sys.stdin.read()); assert d.get('Qi')" 2>/dev/null; then
|
||||
echo "$out"
|
||||
fi
|
||||
}
|
||||
|
||||
V_XG=$(fetch_v_xg || true)
|
||||
NEED_FETCH=0
|
||||
if [ -z "$V_XG" ]; then
|
||||
NEED_FETCH=1
|
||||
echo "⚠️ v_xg.json 暂不可用 (DB 故障或网络被墙), 尝试从 draws 表读已有数据"
|
||||
fi
|
||||
|
||||
# 实际开奖结果
|
||||
ACTUAL=$(sqlite3 "$DB" "SELECT n1||','||n2||','||n3||','||n4||','||n5||','||n6||','||special FROM draws WHERE period='$QI';")
|
||||
# === Step 2: 解析 Qi + 真开彩 ===
|
||||
QI=""
|
||||
ACTUAL=""
|
||||
if [ "$NEED_FETCH" = "0" ]; then
|
||||
eval "$(echo "$V_XG" | python3 -c "
|
||||
import json, sys
|
||||
d = json.loads(sys.stdin.read())
|
||||
qi = d.get('Qi','')
|
||||
data = d.get('Data', {})
|
||||
nums = [int(data[str(i)]['number']) for i in range(1, 8) if str(i) in data]
|
||||
special = nums[6] if len(nums) >= 7 else 0
|
||||
print(f'QI={qi!r}')
|
||||
print(f'SPECIAL={special}')
|
||||
print(f'N1={nums[0] if len(nums)>0 else 0}')
|
||||
print(f'N2={nums[1] if len(nums)>1 else 0}')
|
||||
print(f'N3={nums[2] if len(nums)>2 else 0}')
|
||||
print(f'N4={nums[3] if len(nums)>3 else 0}')
|
||||
print(f'N5={nums[4] if len(nums)>4 else 0}')
|
||||
print(f'N6={nums[5] if len(nums)>5 else 0}')
|
||||
")"
|
||||
if [ -n "$QI" ]; then
|
||||
ACTUAL="$N1,$N2,$N3,$N4,$N5,$N6,$SPECIAL"
|
||||
echo "📡 v_xg.json: Qi=$QI 真开彩=$N1 $N2 $N3 $N4 $N5 $N6 特=$SPECIAL"
|
||||
fi
|
||||
fi
|
||||
|
||||
# === Step 3: 兜底从 draws 表读 (手填或之前入库) ===
|
||||
if [ -z "$ACTUAL" ]; then
|
||||
echo "❌ 期号 $QI 还没入库开奖结果"
|
||||
exit 1
|
||||
# v_xg 拿不到, 尝试从最近 Qi 期读
|
||||
if [ -z "$QI" ]; then
|
||||
QI=$(sqlite3 "$DB" "SELECT period FROM draws ORDER BY period DESC LIMIT 1;" 2>/dev/null || true)
|
||||
fi
|
||||
if [ -n "$QI" ]; then
|
||||
ACTUAL=$(sqlite3 "$DB" "SELECT n1||','||n2||','||n3||','||n4||','||n5||','||n6||','||special FROM draws WHERE period='$QI';" 2>/dev/null || true)
|
||||
fi
|
||||
if [ -z "$ACTUAL" ]; then
|
||||
echo "❌ 无法获取 $QI 期开奖结果 (v_xg.json 宕机 + draws 表空)"
|
||||
echo " 手动填: python3 $SKILL_DIR/scripts/lottery_特码.py add $QI <special> <n1..n6>"
|
||||
exit 1
|
||||
fi
|
||||
echo "📂 draws 表读 $QI 期: $ACTUAL"
|
||||
fi
|
||||
|
||||
IFS=',' read -r A1 A2 A3 A4 A5 A6 AS <<< "$ACTUAL"
|
||||
ACTUAL_FLAT="$A1 $A2 $A3 $A4 $A5 $A6"
|
||||
ACTUAL_SPECIAL="$AS"
|
||||
|
||||
# 找对应的分析文件 - 看 Qi 是几(7-19/21的cron跑的就是 Qi-1 期预测)
|
||||
QI_NUM=$((10#$QI))
|
||||
PREV_PERIOD=$((QI_NUM - 1))
|
||||
# 标题格式有几种:'077期热数据采集' / '热数据采集 · 077期' / '077期数据汇总'
|
||||
# 简单找包含期号+期 的最近文件
|
||||
ANALYSIS_FILE=$(grep -lE "${PREV_PERIOD}期数据汇总|${PREV_PERIOD}期热数据采集|热数据采集.*${PREV_PERIOD}期" "$HOME/.hermes/cron/output/5bec1f60f77f/"*.md 2>/dev/null | tail -1)
|
||||
[ -z "$ANALYSIS_FILE" ] && ANALYSIS_FILE=$(grep -l "${PREV_PERIOD}期" "$HOME/.hermes/cron/output/5bec1f60f77f/"*.md 2>/dev/null | tail -1)
|
||||
# === Step 4: 检查 draws 表, 没数据就入库 (v_xg 真开彩可用时) ===
|
||||
EXISTING=$(sqlite3 "$DB" "SELECT special FROM draws WHERE period='$QI';" 2>/dev/null || true)
|
||||
if [ -z "$EXISTING" ] && [ -n "$SPECIAL" ] && [ "$SPECIAL" != "0" ]; then
|
||||
echo "💾 draws 表 $QI 期空, 自动入库..."
|
||||
python3 "$SKILL_DIR/scripts/lottery_特码.py" add "$QI" "$SPECIAL" "$N1" "$N2" "$N3" "$N4" "$N5" "$N6" 2>&1 || echo "⚠️ add_draw 失败"
|
||||
fi
|
||||
|
||||
# === Step 5: 跑 check_hits (确保所有 analysis 行 hit 状态更新) ===
|
||||
python3 "$SKILL_DIR/scripts/lottery_特码.py" hits 2>&1 | tail -3
|
||||
|
||||
# === Step 6: 找 Qi 期分析 .md ===
|
||||
ANALYSIS_FILE=$(grep -lE "${QI}期" "$HOME/.hermes/cron/output/5bec1f60f77f/"*.md 2>/dev/null | tail -1)
|
||||
|
||||
# === Step 7: 查 analysis 表最近一条 ===
|
||||
ANALYSIS_HIT=$(sqlite3 "$DB" "SELECT actual_special || '|' || hit FROM analysis WHERE period='$QI' ORDER BY id DESC LIMIT 1;" 2>/dev/null || echo "|")
|
||||
|
||||
# === Step 8: 输出核验报告 ===
|
||||
OUT_FILE="$OUT_DIR/$(date +%Y-%m-%d_%H-%M-%S)_${QI}.md"
|
||||
{
|
||||
echo "## 🎯 核验报告 | $QI期"
|
||||
echo ""
|
||||
echo "**开奖时间**: $(date +%Y-%m-%d) 21:30 北京"
|
||||
echo "**核验时间**: $(date +%Y-%m-%d) 22:30 北京"
|
||||
echo "**数据源**: v_xg.json Data.1-7 (2026-08-04 marksix6.com 验证)"
|
||||
echo ""
|
||||
echo "### 实际开奖"
|
||||
echo "| 位置 | 号码 |"
|
||||
@@ -53,44 +127,63 @@ echo ""
|
||||
|
||||
if [ -n "$ANALYSIS_FILE" ]; then
|
||||
echo "### 分析文件"
|
||||
echo "📄 $ANALYSIS_FILE"
|
||||
echo "📄 \`$ANALYSIS_FILE\`"
|
||||
echo ""
|
||||
echo "### 预测 vs 实际"
|
||||
PREDICTED_SPECIAL=$(grep -o "特码重点.*\*\*[0-9]\+\*\*\|特码.*\*\*[0-9]\+\*\*" "$ANALYSIS_FILE" | head -1)
|
||||
PREDICTED_FLAT=$(grep "平码优先" "$ANALYSIS_FILE" | head -1)
|
||||
echo "**预测**: $PREDICTED_SPECIAL · $PREDICTED_FLAT"
|
||||
|
||||
# 提取 Top 5 候选 (新格式: "| 🥇 | **42** | 3 | 挂牌 另版挂 (42) |")
|
||||
TOP_CANDIDATES=$(grep -oE '\| \*\*[0-9]+\*\*' "$ANALYSIS_FILE" | head -5 | grep -oE '[0-9]+')
|
||||
echo "### 预测 Top 5"
|
||||
echo "| 排序 | 特码 |"
|
||||
echo "|---|---|"
|
||||
i=1
|
||||
for c in $TOP_CANDIDATES; do
|
||||
emoji=$([ $i -eq 1 ] && echo "🥇" || ([ $i -eq 2 ] && echo "🥈" || ([ $i -eq 3 ] && echo "🥉" || echo "$i")))
|
||||
echo "| $emoji | $c |"
|
||||
i=$((i+1))
|
||||
done
|
||||
echo ""
|
||||
echo "### 命中分析"
|
||||
|
||||
|
||||
HIT_SPECIAL="❌ 未中"
|
||||
if echo "$PREDICTED_SPECIAL" | grep -q "\*\*$AS\*\*"; then
|
||||
if echo " $TOP_CANDIDATES " | grep -q " $AS "; then
|
||||
HIT_SPECIAL="✅ **特码命中**"
|
||||
fi
|
||||
echo "### 命中"
|
||||
echo "- 特码 $AS: $HIT_SPECIAL"
|
||||
|
||||
HIT_FLAT=$(echo "$ACTUAL_FLAT" | tr ' ' '\n' | while read n; do
|
||||
if echo "$PREDICTED_FLAT" | grep -q "\*\*$n\*\*\|\b$n\b"; then
|
||||
echo "✅ $n"
|
||||
|
||||
HIT_FLAT=""
|
||||
for n in $A1 $A2 $A3 $A4 $A5 $A6; do
|
||||
if echo " $TOP_CANDIDATES " | grep -q " $n "; then
|
||||
HIT_FLAT="$HIT_FLAT ✅$n"
|
||||
fi
|
||||
done | tr '\n' ' ')
|
||||
echo "- 平码命中: ${HIT_FLAT:-无}"
|
||||
|
||||
TOTAL_HIT=$(echo "$ACTUAL_FLAT" | tr ' ' '\n' | while read n; do
|
||||
if grep -qE "\*\*$n\*\*| $n[、,,]|\b$n( |$)" "$ANALYSIS_FILE"; then
|
||||
echo "1"
|
||||
fi
|
||||
done | wc -l)
|
||||
done
|
||||
echo "- 平码命中:${HIT_FLAT:- 无}"
|
||||
|
||||
TOTAL=0
|
||||
if echo " $TOP_CANDIDATES " | grep -q " $AS "; then TOTAL=$((TOTAL+1)); fi
|
||||
for n in $A1 $A2 $A3 $A4 $A5 $A6; do
|
||||
if echo " $TOP_CANDIDATES " | grep -q " $n "; then TOTAL=$((TOTAL+1)); fi
|
||||
done
|
||||
echo ""
|
||||
echo "**总命中**: 特码 + 平码 共 $((TOTAL_HIT+0)) / 7 球"
|
||||
echo "**总命中**: Top 5 候选命中 $TOTAL / 7 球 (特码+平码)"
|
||||
else
|
||||
echo "### ⚠️ 未找到分析文件"
|
||||
echo " 查找路径: $HOME/.hermes/cron/output/5bec1f60f77f/"
|
||||
echo " 期号: $QI"
|
||||
fi
|
||||
|
||||
ACTUAL_FROM_DB=$(echo "$ANALYSIS_HIT" | cut -d'|' -f1)
|
||||
HIT_FROM_DB=$(echo "$ANALYSIS_HIT" | cut -d'|' -f2)
|
||||
if [ -n "$HIT_FROM_DB" ]; then
|
||||
HIT_ICON=$([ "$HIT_FROM_DB" = "1" ] && echo "✅ 中奖" || echo "❌ 未中")
|
||||
echo ""
|
||||
echo "### SQLite analysis 标记"
|
||||
echo "- actual_special: $ACTUAL_FROM_DB"
|
||||
echo "- hit: $HIT_ICON"
|
||||
fi
|
||||
|
||||
echo ""
|
||||
echo "---"
|
||||
echo "_生成时间: $(date '+%Y-%m-%d %H:%M:%S')_"
|
||||
echo "_生成时间: $(date '+%Y-%m-%d %H:%M:%S') 北京_"
|
||||
} > "$OUT_FILE"
|
||||
|
||||
cat "$OUT_FILE"
|
||||
cat "$OUT_FILE"
|
||||
Reference in New Issue
Block a user