From 9bc1577d887f3f162f44f7f4dba1f7cb8f3d6c7c Mon Sep 17 00:00:00 2001 From: karuo Date: Mon, 2 Mar 2026 13:43:09 +0800 Subject: [PATCH] =?UTF-8?q?=F0=9F=94=84=20=E5=8D=A1=E8=8B=A5AI=20=E5=90=8C?= =?UTF-8?q?=E6=AD=A5=202026-03-02=2013:43=20|=20=E6=9B=B4=E6=96=B0?= =?UTF-8?q?=EF=BC=9ACursor=E8=A7=84=E5=88=99=E3=80=81=E9=87=91=E4=BB=93?= =?UTF-8?q?=E3=80=81=E6=B0=B4=E6=A1=A5=E5=B9=B3=E5=8F=B0=E5=AF=B9=E6=8E=A5?= =?UTF-8?q?=E3=80=81=E6=80=BB=E7=B4=A2=E5=BC=95=E4=B8=8E=E5=85=A5=E5=8F=A3?= =?UTF-8?q?=E3=80=81=E8=BF=90=E8=90=A5=E4=B8=AD=E6=9E=A2=E5=8F=82=E8=80=83?= =?UTF-8?q?=E8=B5=84=E6=96=99=E3=80=81=E8=BF=90=E8=90=A5=E4=B8=AD=E6=9E=A2?= =?UTF-8?q?=E5=B7=A5=E4=BD=9C=E5=8F=B0=20|=20=E6=8E=92=E9=99=A4=20>20MB:?= =?UTF-8?q?=2014=20=E4=B8=AA?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .cursor/rules/karuo-ai.mdc | 33 +--- .../服务器管理/scripts/腾讯云_TAT_wzdj_拉取构建并重启.py | 133 +++++++++++++++ .../群晖NAS管理/scripts/time_machine_ckbnas_netbackup.sh | 50 ++++++ .../参考资料/Time_Machine_ckbnas_NetBackup.md | 78 +++++++++ .../水桥_平台对接/智能纪要/脚本/cookie_minutes.txt | 2 +- .../智能纪要/脚本/feishu_minutes_one_url.py | 36 +++- .../智能纪要/脚本/下载单条妙记_仅命令行.sh | 65 ++++++++ .../智能纪要/脚本/逆向获取Cookie并下载单条.py | 156 ++++++++++++++++++ BOOTSTRAP.md | 52 +++--- 运营中枢/参考资料/卡若AI运行模式说明.md | 45 ----- .../参考资料/卡若读书笔记格式_固定规则.md | 8 +- 运营中枢/参考资料/输出目录规范.md | 1 + 运营中枢/工作台/MAX_MODE说明.md | 23 +++ 运营中枢/工作台/gitea_push_log.md | 1 + 运营中枢/工作台/代码管理.md | 1 + 运营中枢/工作台/运行模式.md | 21 --- 16 files changed, 584 insertions(+), 121 deletions(-) create mode 100644 01_卡资(金)/金仓_存储备份/服务器管理/scripts/腾讯云_TAT_wzdj_拉取构建并重启.py create mode 100755 01_卡资(金)/金仓_存储备份/群晖NAS管理/scripts/time_machine_ckbnas_netbackup.sh create mode 100644 01_卡资(金)/金仓_存储备份/群晖NAS管理/参考资料/Time_Machine_ckbnas_NetBackup.md create mode 100644 02_卡人(水)/水桥_平台对接/智能纪要/脚本/下载单条妙记_仅命令行.sh create mode 100644 02_卡人(水)/水桥_平台对接/智能纪要/脚本/逆向获取Cookie并下载单条.py delete mode 100644 运营中枢/参考资料/卡若AI运行模式说明.md create mode 100644 运营中枢/工作台/MAX_MODE说明.md delete mode 100644 运营中枢/工作台/运行模式.md diff --git a/.cursor/rules/karuo-ai.mdc b/.cursor/rules/karuo-ai.mdc index 8e4abd46..65e846e0 100644 --- a/.cursor/rules/karuo-ai.mdc +++ b/.cursor/rules/karuo-ai.mdc @@ -19,16 +19,9 @@ alwaysApply: true 1. **读 `BOOTSTRAP.md`**(根目录)— 身份、团队、执行流程、全局规则 2. **读 `SKILL_REGISTRY.md`**(根目录)— 按用户需求查找技能 3. **读 `个人/1、卡若:本人/记忆.md`** — 长期偏好与沉淀(单文件,无子目录) -4. **读 `运营中枢/工作台/运行模式.md`** — 若「当前模式」为 `max`,则本对话按 **MAX 模式** 执行(思考与拆解更充分、全栈开发优先实施计划+TDD+两阶段评审、复盘更详细);详见 `运营中枢/参考资料/卡若AI运行模式说明.md` -5. 匹配到技能后读对应 `SKILL.md` 执行 +4. 匹配到技能后读对应 `SKILL.md` 执行 -## 运行模式切换(与 Auto/MAX Mode 对应) - -- **切到 MAX**:用户说「开MAX模式」「切换MAX」「用MAX」「MAX模式」→ 将 `运营中枢/工作台/运行模式.md` 中「当前模式」改为 `max` 并保存,回复已切换。 -- **切回 Auto**:用户说「切回Auto」「用Auto」「自动模式」→ 将「当前模式」改为 `auto` 并保存,回复已切换。 -- **查询**:用户说「当前什么模式」「运行模式」→ 读该文件,回复当前为 Auto 或 MAX。 - -行为差异见 `运营中枢/参考资料/卡若AI运行模式说明.md`。 +**MAX Mode**:卡若AI 每次调用均为 MAX Mode,定义在**卡若AI 本体** `BOOTSTRAP.md` 第四节(MAX Mode)与第五节(执行流程),不在此重复;本文件仅补充 Cursor 特有行为。 ## 异常处理与红线(强制) @@ -36,22 +29,14 @@ alwaysApply: true ## 强制对话流程(每次对话必守) -### 第一步:先思考,在对话中展示拆解与计划 -- 接到任务后**先深度思考/调研**:结合所有成员能力(5 负责人、14 成员、53 技能),想清楚目标、谁干、怎么干、可能卡点。 -- **必须在对话里先展示**:① 思考结果(调研后的结论)② 任务拆解(1、2、3… 具体步骤)③ 执行计划,**再继续执行**。禁止不展示拆解直接动手。 +### 第一步~第四步(执行流程与 MAX Mode) +- 执行流程、思考与拆解、验证与复盘**以 `BOOTSTRAP.md` 第四节(MAX Mode)与第五节(执行流程)为准**,卡若AI 每次调用均为 MAX Mode,此处不重复。 -### 第二步:执行后反复验证 -- 执行完**必须验证**:结果是否与用户一开始的命令/目标匹配。 -- **不匹配** → 回溯 → 搜索(GitHub、Skill、网上)找方案 → 再思考(简洁输出)→ 再执行 → 再验证,直到成功或明确说明无法达成。 - -### 第三步:回复形式 = 强制复盘(卡若AI 内所有对话必守) -- **卡若AI 内所有对话的 AI 回复一律采用「复盘形式」——此为强制行为,无例外。** 复盘格式**永远只有一种**,按 `运营中枢/参考资料/卡若复盘格式_固定规则.md`: - - 复盘块标题必须写**具体日期**和**具体时间**(当次回复时的真实 **YYYY-MM-DD HH:mm**,如 2026-03-01 15:20),日期、时间都要写上去,不能写占位符; - - 五块齐全,**每块用小图标识别**:🎯 目标·结果·达成率 · 📌 过程 · 💡 反思 · 📝 总结 · ▶ 下一步执行; - - **复盘块内不用表格**;目标·结果·达成率整行 ≤30 字,含达成率 XX%; - - **日期时间与块标题用 Markdown 粗体**(如 **2026-03-01 15:20**、**🎯 目标·结果·达成率**),禁止用 HTML 标签,否则 Cursor 等场景会露标;详见 `卡若复盘格式_固定规则.md`; - - 回复正文可适当用图标(✅❌📁🔗⚠️ 等)增强可读性;下一步须结合本对话与项目/卡若AI 目标、关联未完成项、以实现目标为核心。 -- 格式与书写要求见:`运营中枢/参考资料/卡若复盘格式_固定规则.md`。 +### 复盘格式(Cursor 内强制) +- **卡若AI 内所有对话的 AI 回复一律采用「复盘形式」——此为强制行为,无例外。** 按 `运营中枢/参考资料/卡若复盘格式_固定规则.md`: + - 复盘块标题必须写**具体日期**和**具体时间**(当次回复时的真实 **YYYY-MM-DD HH:mm**),五块齐全(🎯📌💡📝▶);**复盘块内不用表格**;目标·结果·达成率整行 ≤30 字;日期时间与块标题用 Markdown 粗体,禁止 HTML 标签; + - 下一步须结合本对话与项目/卡若AI 目标、关联未完成项。 +- 格式详见:`运营中枢/参考资料/卡若复盘格式_固定规则.md`。 ### 对外输出目录(强制) - 报告、复盘存档、执行日志、导出文件、**生成图片** → 只写 `/Users/karuo/Documents/卡若Ai的文件夹/` 下对应子目录;**图片** → `图片/`,并在 `图片/图片索引.md` 登记来源 Skill、生成者;经验沉淀仍写 `02_卡人(水)/水溪_整理归档/经验库/待沉淀/`。详见 `运营中枢/参考资料/输出目录规范.md`。 diff --git a/01_卡资(金)/金仓_存储备份/服务器管理/scripts/腾讯云_TAT_wzdj_拉取构建并重启.py b/01_卡资(金)/金仓_存储备份/服务器管理/scripts/腾讯云_TAT_wzdj_拉取构建并重启.py new file mode 100644 index 00000000..f7026a1e --- /dev/null +++ b/01_卡资(金)/金仓_存储备份/服务器管理/scripts/腾讯云_TAT_wzdj_拉取构建并重启.py @@ -0,0 +1,133 @@ +#!/usr/bin/env python3 +# -*- coding: utf-8 -*- +""" +腾讯云 TAT:kr宝塔 上对 wzdj 执行 git pull、pnpm install、pnpm build、宝塔 Node 重启 +确保 https://wzdj.quwanzhi.com 跑最新代码。需先 push 到 GitHub/Gitea,服务器拉取。 +""" +import base64 +import os +import re +import sys +import time + +KR_INSTANCE_ID = "ins-aw0tnqjo" +REGION = "ap-guangzhou" +WZDJ_DIR = "/www/wwwroot/wzdj" + +def _read_creds(): + d = os.path.dirname(os.path.abspath(__file__)) + for _ in range(6): + root = d + if os.path.isfile(os.path.join(root, "运营中枢", "工作台", "00_账号与API索引.md")): + path = os.path.join(root, "运营中枢", "工作台", "00_账号与API索引.md") + with open(path, "r", encoding="utf-8") as f: + text = f.read() + sid = skey = None + in_tx = False + for line in text.splitlines(): + if "### 腾讯云" in line: + in_tx = True + continue + if in_tx and line.strip().startswith("###"): + break + if not in_tx: + continue + m = re.search(r"\|\s*[^|]*(?:SecretId|密钥)[^|]*\|\s*`([^`]+)`", line, re.I) + if m and m.group(1).strip().startswith("AKID"): + sid = m.group(1).strip() + m = re.search(r"\|\s*SecretKey\s*\|\s*`([^`]+)`", line, re.I) + if m: + skey = m.group(1).strip() + return sid or None, skey or None + d = os.path.dirname(d) + return None, None + +SHELL = '''#!/bin/bash +set -e +echo "=== wzdj 部署 ===" +cd ''' + WZDJ_DIR + ''' +if [ ! -d .git ]; then + echo "ERROR: 非 Git 目录,请先在此目录 clone 仓库" + exit 1 +fi +echo "1. git pull..." +git fetch origin 2>/dev/null || git fetch gitea 2>/dev/null || true +git reset --hard origin/main 2>/dev/null || git reset --hard gitea/main 2>/dev/null || git pull origin main 2>/dev/null || git pull gitea main 2>/dev/null || true +echo "2. pnpm install..." +pnpm install --frozen-lockfile 2>/dev/null || npm install --legacy-peer-deps +echo "3. pnpm build..." +pnpm build 2>/dev/null || npm run build +echo "4. 重启 wzdj(宝塔 Node)..." +python3 -c " +import hashlib, json, urllib.request, urllib.parse, ssl, time +ssl._create_default_https_context = ssl._create_unverified_context +P, K = 'https://127.0.0.1:9988', 'qcWubCdlfFjS2b2DMT1lzPFaDfmv1cBT' +def sign(): + t = int(time.time()) + s = str(t) + hashlib.md5(K.encode()).hexdigest() + return {'request_time': t, 'request_token': hashlib.md5(s.encode()).hexdigest()} +def post(path, d=None): + pl = sign() + if d: pl.update(d) + r = urllib.request.Request(P+path, data=urllib.parse.urlencode(pl).encode()) + with urllib.request.urlopen(r, timeout=25) as resp: + return json.loads(resp.read().decode()) +items = post('/project/nodejs/get_project_list').get('data') or post('/project/nodejs/get_project_list').get('list') or [] +for it in items: + nm = (it.get('name') or '').lower() + if nm == 'wzdj': + post('/project/nodejs/restart_project', {'project_name': it.get('name') or it.get('project_name')}) + print(' 已重启 wzdj') + break +else: + print(' 未找到 wzdj 项目') +" +nginx -t 2>/dev/null && nginx -s reload 2>/dev/null || true +echo "=== 完成 ===" +''' + +def main(): + sid = os.environ.get("TENCENTCLOUD_SECRET_ID") + skey = os.environ.get("TENCENTCLOUD_SECRET_KEY") + if not sid or not skey: + sid, skey = _read_creds() + if not sid or not skey: + print("❌ 未配置腾讯云 SecretId/SecretKey(见 00_账号与API索引.md)") + return 1 + try: + from tencentcloud.common import credential + from tencentcloud.tat.v20201028 import tat_client, models + except ImportError: + print("请安装: pip install tencentcloud-sdk-python-tat") + return 1 + cred = credential.Credential(sid, skey) + client = tat_client.TatClient(cred, REGION) + req = models.RunCommandRequest() + req.Content = base64.b64encode(SHELL.encode()).decode() + req.InstanceIds = [KR_INSTANCE_ID] + req.CommandType = "SHELL" + req.Timeout = 300 + req.CommandName = "wzdj_deploy_build_restart" + resp = client.RunCommand(req) + print("✅ TAT 已下发,InvocationId:", resp.InvocationId) + print(" 服务器将执行: git pull → pnpm install → pnpm build → 重启 wzdj") + print(" 等待约 120s 后查看结果...") + time.sleep(120) + try: + req2 = models.DescribeInvocationTasksRequest() + f = models.Filter() + f.Name = "invocation-id" + f.Values = [resp.InvocationId] + req2.Filters = [f] + r2 = client.DescribeInvocationTasks(req2) + for t in (r2.InvocationTaskSet or []): + print(" 状态:", getattr(t, "TaskStatus", "")) + if hasattr(t, "Output") and t.Output: + print(" 输出:", (t.Output or "")[:1200]) + except Exception as e: + print(" 查询:", e) + print(" 访问: https://wzdj.quwanzhi.com") + return 0 + +if __name__ == "__main__": + sys.exit(main()) diff --git a/01_卡资(金)/金仓_存储备份/群晖NAS管理/scripts/time_machine_ckbnas_netbackup.sh b/01_卡资(金)/金仓_存储备份/群晖NAS管理/scripts/time_machine_ckbnas_netbackup.sh new file mode 100755 index 00000000..f1307c14 --- /dev/null +++ b/01_卡资(金)/金仓_存储备份/群晖NAS管理/scripts/time_machine_ckbnas_netbackup.sh @@ -0,0 +1,50 @@ +#!/bin/bash +# ============================================ +# 时间机器 → ckbnas (192.168.1.201) NetBackup 目录 +# 用法:先确保 DSM 已为 NetBackup 启用 Time Machine,再运行本脚本或按下方命令操作 +# ============================================ + +CKB_IP="192.168.1.201" +SHARE="NetBackup" +SMB_URL="smb://fnvtk@${CKB_IP}/${SHARE}" + +echo "=== 时间机器 → ckbnas NetBackup ===" +echo "目标: ${CKB_IP} / ${SHARE}" +echo "" + +# 1. 网络检测 +echo "[1] 网络" +if ping -c 1 -W 2 "$CKB_IP" >/dev/null 2>&1; then + echo " ✅ ${CKB_IP} 可达" +else + echo " ❌ ${CKB_IP} 不可达,请检查本机与 ckbnas 在同一网段" + exit 1 +fi + +# 2. 挂载检测 +echo "" +echo "[2] 挂载" +if [ -d "/Volumes/${SHARE}" ]; then + echo " ✅ /Volumes/${SHARE} 已挂载" +else + echo " 未挂载。正在打开 SMB 连接(会弹窗输入 fnvtk 密码)…" + open "$SMB_URL" + echo " 请在弹出的窗口中输入 DSM 用户 fnvtk 的密码,连接成功后按回车继续。" + read -r + if [ ! -d "/Volumes/${SHARE}" ]; then + echo " ❌ 仍未检测到 /Volumes/${SHARE},请手动在 Finder 连接服务器: $SMB_URL" + exit 2 + fi +fi + +# 3. 设置时间机器目标(需完全磁盘访问权限) +echo "" +echo "[3] 设置备份目标" +echo " 执行以下命令需「完全磁盘访问」权限(系统设置 → 隐私与安全性 → 完全磁盘访问 → 添加「终端」):" +echo "" +echo " sudo tmutil setdestination /Volumes/${SHARE}" +echo "" +echo " 执行后可用以下命令验证并立即备份:" +echo " tmutil destinationinfo" +echo " tmutil startbackup --block" +echo "" diff --git a/01_卡资(金)/金仓_存储备份/群晖NAS管理/参考资料/Time_Machine_ckbnas_NetBackup.md b/01_卡资(金)/金仓_存储备份/群晖NAS管理/参考资料/Time_Machine_ckbnas_NetBackup.md new file mode 100644 index 00000000..b791b314 --- /dev/null +++ b/01_卡资(金)/金仓_存储备份/群晖NAS管理/参考资料/Time_Machine_ckbnas_NetBackup.md @@ -0,0 +1,78 @@ +# 时间机器 → ckbnas NetBackup + +**目标**:Mac 时间机器备份到 **ckbnas**(192.168.1.201)的 **NetBackup** 共享目录。 + +若出现「所选网络备份磁盘不支持所需功能」,说明 **NAS 端尚未为该共享启用 Time Machine**,按下列步骤操作。 + +--- + +## 一、ckbnas DSM 必做(先做) + +在浏览器打开 **http://192.168.1.201:5000** 登录 DSM(用户 fnvtk),依次完成: + +1. **控制面板** → **文件服务** → **高级**(或 **Time Machine**) + - 勾选 **「启用 Time Machine 备份」** + - 将 **NetBackup** 选为 Time Machine 使用的共享文件夹 + - 保存 + +2. **控制面板** → **文件服务** → **SMB** → **高级** + - 最大 SMB 协议:**SMB3** + - 勾选:**启用 SMB2 租约**、**启用 SMB durable handle**(持久句柄) + - 保存,必要时重启 SMB 服务 + +3. 确认 **NetBackup** 共享对用户 **fnvtk** 有读写权限;建议关闭该共享的**回收站**,避免与稀疏包冲突。 + +--- + +## 二、Mac 命令行操作 + +### 1. 挂载 NetBackup(若未挂载) + +```bash +open "smb://fnvtk@192.168.1.201/NetBackup" +``` + +按提示输入 fnvtk 密码,连接成功后会在 `/Volumes/NetBackup` 看到该卷。 + +### 2. 赋予「完全磁盘访问」权限(仅首次) + +- **系统设置** → **隐私与安全性** → **完全磁盘访问** +- 添加 **终端**(或 **Cursor**,若在 Cursor 终端里执行) + +### 3. 设置时间机器目标并验证 + +在终端执行: + +```bash +sudo tmutil setdestination /Volumes/NetBackup +tmutil destinationinfo +tmutil startbackup --block +``` + +- `setdestination`:将备份目标设为已挂载的 NetBackup。 +- `destinationinfo`:确认当前备份目标。 +- `startbackup --block`:立即开始一次备份(阻塞直到结束,可选)。 + +--- + +## 三、一键脚本 + +可运行本目录同级脚本(会做网络检测、挂载提示并输出上述命令): + +```bash +bash "01_卡资(金)/金仓_存储备份/群晖NAS管理/scripts/time_machine_ckbnas_netbackup.sh" +``` + +--- + +## 四、快速检查清单 + +| 项 | 说明 | +|----|------| +| DSM 启用 Time Machine | 文件服务 → 高级,并选择 NetBackup | +| SMB 高级 | SMB3、SMB2 租约、持久句柄已开 | +| 共享权限 | fnvtk 对 NetBackup 可读写 | +| Mac 完全磁盘访问 | 终端已加入完全磁盘访问列表 | +| 挂载 | `/Volumes/NetBackup` 存在后再执行 tmutil | + +完成「一」后,再在 Mac 执行「二」即可正常备份。 diff --git a/02_卡人(水)/水桥_平台对接/智能纪要/脚本/cookie_minutes.txt b/02_卡人(水)/水桥_平台对接/智能纪要/脚本/cookie_minutes.txt index 861f8c78..fe971985 100644 --- a/02_卡人(水)/水桥_平台对接/智能纪要/脚本/cookie_minutes.txt +++ b/02_卡人(水)/水桥_平台对接/智能纪要/脚本/cookie_minutes.txt @@ -1,2 +1,2 @@ bv_csrf_token=8e0d42fe-edf3-4a3b-bbfd-541fa432adf6; m_e09b70=38653064343266652d656466332d346133622d626266642d353431666134333261646636b37b91f4efa89b27b410d5626626f1b2ebf3ed82d6b510030362344fb5776178; minutes_csrf_token=4619adeb-6d49-4964-8997-46d4b61cc526; m_ce8f16=34363139616465622d366434392d343936342d383939372d343664346236316363353236b37b91f4efa89b27b410d5626626f1b2ebf3ed82d6b510030362344fb5776178; passport_web_did=7514522919465811987; passport_trace_id=7514522919485292563; QXV0aHpDb250ZXh0=88883e53c92e44849a1e82932de0599b; session=XN0YXJ0-583m169b-79c6-44bf-8307-f48b160bde22-WVuZA; session_list=XN0YXJ0-583m169b-79c6-44bf-8307-f48b160bde22-WVuZA; swp_csrf_token=ba6718bb-4f76-4b86-a8d8-28c0117357e4; t_beda37=5bc818690404cb6332040fc5ed75a7e8be61177a6b1d75dd2a322245f11e63f7; msToken=ECH70c3RMEWL6kSLDGuH1CmpTYiLDVziBxfgHQlDdL8JWQgimkjy-kZQ1MQLfn2jOg1pvRhZchLDei7pMJkAz7bgniCoCiwUOYxRWQNXOeglKu41BxVhSTqkFgfX6qGN1pbwincoWE4jyxiyAAOctkQrjJGp1I9nFqKV_3ouXNJCgvk4iNwoZg== -# 自动从浏览器提取,可手动覆盖 \ No newline at end of file +# 逆向获取 \ No newline at end of file diff --git a/02_卡人(水)/水桥_平台对接/智能纪要/脚本/feishu_minutes_one_url.py b/02_卡人(水)/水桥_平台对接/智能纪要/脚本/feishu_minutes_one_url.py index 83b1c89a..6f1ef846 100644 --- a/02_卡人(水)/水桥_平台对接/智能纪要/脚本/feishu_minutes_one_url.py +++ b/02_卡人(水)/水桥_平台对接/智能纪要/脚本/feishu_minutes_one_url.py @@ -10,6 +10,7 @@ from __future__ import annotations import argparse +import json import re import sys import time @@ -87,14 +88,33 @@ def export_via_playwright_page(object_token: str, title: str = "", wait_sec: int time.sleep(wait_sec) js = f""" async () => {{ - const r = await fetch('{EXPORT_URL}?object_token={object_token}&add_speaker=true&add_timestamp=false&format=2', {{method:'POST', credentials:'include'}}); + const r = await fetch('{EXPORT_URL}', {{ + method: 'POST', + credentials: 'include', + headers: {{ 'Content-Type': 'application/x-www-form-urlencoded' }}, + body: 'object_token={object_token}&add_speaker=true&add_timestamp=false&format=2' + }}); return await r.text(); }} """ - text = pg.evaluate(js) - ctx.close() - if text and len(str(text)) > 400 and "please log in" not in str(text).lower(): - result[0] = str(text).strip() + print(" 正在页面内请求导出接口,请勿关闭窗口…") + raw = pg.evaluate(js) + text = (raw or "").strip() + if not text or "please log in" in text.lower(): + pass + elif text.startswith("{"): + try: + j = json.loads(text) + data = j.get("data") + if isinstance(data, str) and len(data) > 100: + result[0] = data + elif isinstance(data, dict): + result[0] = (data.get("content") or data.get("text") or data.get("transcript") or "") + except Exception: + if len(text) > 400: + result[0] = text + elif len(text) > 400: + result[0] = text except Exception as e: print(f" Playwright 失败: {e}", file=sys.stderr) finally: @@ -110,6 +130,7 @@ def main() -> int: ap.add_argument("-o", "--output-dir", default=str(OUT_DIR), help="输出目录") ap.add_argument("--title", help="保存文件名中的标题") ap.add_argument("--playwright-wait", type=int, default=30, help="Playwright 打开页后等待秒数") + ap.add_argument("--cookie-only", "--no-browser", action="store_true", dest="cookie_only", help="仅用 Cookie/命令行,不弹浏览器;失败时提示配置 cookie_minutes.txt") args = ap.parse_args() token = args.token or (extract_token(args.url_or_token or "") or args.url_or_token) if not token or len(token) < 20: @@ -125,7 +146,7 @@ def main() -> int: title = f"妙记_{token[:12]}" print(f"📌 object_token: {token} title: {title[:50]}…") - print(" 1) 尝试 Cookie 导出…") + print(" 1) 尝试 Cookie 导出(cookie_minutes.txt 或本机浏览器已存 Cookie)…") text = export_via_cookie(token) if text: out_dir.mkdir(parents=True, exist_ok=True) @@ -134,6 +155,9 @@ def main() -> int: path.write_text(f"标题: {title}\nobject_token: {token}\n\n文字记录:\n\n{text}", encoding="utf-8") print(f" ✅ Cookie 导出成功 -> {path}") return 0 + if args.cookie_only: + print(" ❌ Cookie 导出失败。请将妙记 list 请求的 Cookie 写入脚本同目录 cookie_minutes.txt 第一行后重试。", file=sys.stderr) + return 1 print(" 2) Cookie 失败,改用 Playwright 页面内导出…") text = export_via_playwright_page(token, title=title, wait_sec=args.playwright_wait) if text: diff --git a/02_卡人(水)/水桥_平台对接/智能纪要/脚本/下载单条妙记_仅命令行.sh b/02_卡人(水)/水桥_平台对接/智能纪要/脚本/下载单条妙记_仅命令行.sh new file mode 100644 index 00000000..7d87f762 --- /dev/null +++ b/02_卡人(水)/水桥_平台对接/智能纪要/脚本/下载单条妙记_仅命令行.sh @@ -0,0 +1,65 @@ +#!/bin/bash +# 单条妙记:仅用命令行下载文字+视频,不弹浏览器。失败时 print 打开浏览器的正确方式。 +# 用法: bash 下载单条妙记_仅命令行.sh "https://cunkebao.feishu.cn/minutes/obcn6yjg6866c3gl4ibd72vr" +# 或: bash 下载单条妙记_仅命令行.sh obcn6yjg6866c3gl4ibd72vr "soul 派对 113场 20260302" + +URL_OR_TOKEN="${1:-}" +TITLE="${2:-}" +OUT="${3:-/Users/karuo/Documents/聊天记录/soul}" +SCRIPT_DIR="$(cd "$(dirname "$0")" && pwd)" + +if [[ -z "$URL_OR_TOKEN" ]]; then + echo "用法: $0 <妙记URL或object_token> [标题] [输出目录]" + echo "示例: $0 'https://cunkebao.feishu.cn/minutes/obcn6yjg6866c3gl4ibd72vr' 'soul 派对 113场 20260302'" + exit 1 +fi + +# 提取 token +if [[ "$URL_OR_TOKEN" == *"/minutes/"* ]]; then + TOKEN=$(echo "$URL_OR_TOKEN" | sed -n 's|.*/minutes/\([a-zA-Z0-9]*\).*|\1|p') +else + TOKEN="$URL_OR_TOKEN" +fi +[[ -z "$TITLE" ]] && TITLE="妙记_${TOKEN:0:12}" + +echo "📌 object_token: $TOKEN 输出: $OUT" +echo "" + +# 1) 文字 +echo "=== 1) 文字(仅 Cookie,不弹窗)===" +if python3 "$SCRIPT_DIR/feishu_minutes_one_url.py" "$URL_OR_TOKEN" --title "$TITLE" -o "$OUT" --cookie-only 2>&1; then + echo " ✅ 文字已保存" +else + TEXT_FAIL=1 +fi +echo "" + +# 2) 视频 +echo "=== 2) 视频(仅 Cookie)===" +if python3 "$SCRIPT_DIR/feishu_minutes_download_video.py" "$URL_OR_TOKEN" -o "$OUT" 2>&1; then + echo " ✅ 视频已保存" +else + VIDEO_FAIL=1 +fi +echo "" + +if [[ -n "$TEXT_FAIL" || -n "$VIDEO_FAIL" ]]; then + echo "----------------------------------------" + echo "⚠️ 命令行未拿到有效 Cookie,需用浏览器取 Cookie 后重试:" + echo "" + echo " 1) 用浏览器打开(复制下面整行):" + echo " https://cunkebao.feishu.cn/minutes/home" + echo "" + echo " 2) 登录后 F12 → 网络 → 刷新 → 找到 list?size= 请求 → 复制请求头里的 Cookie" + echo "" + echo " 3) 粘贴到下面文件第一行并保存:" + echo " $SCRIPT_DIR/cookie_minutes.txt" + echo "" + echo " 4) 再执行本脚本:" + echo " bash $0 '$URL_OR_TOKEN' '$TITLE' '$OUT'" + echo "----------------------------------------" + exit 1 +fi + +echo "✅ 文字+视频均已保存到 $OUT" +ls -la "$OUT"/*"${TOKEN:0:8}"* "$OUT"/*113* 2>/dev/null || true diff --git a/02_卡人(水)/水桥_平台对接/智能纪要/脚本/逆向获取Cookie并下载单条.py b/02_卡人(水)/水桥_平台对接/智能纪要/脚本/逆向获取Cookie并下载单条.py new file mode 100644 index 00000000..b0196e0d --- /dev/null +++ b/02_卡人(水)/水桥_平台对接/智能纪要/脚本/逆向获取Cookie并下载单条.py @@ -0,0 +1,156 @@ +#!/usr/bin/env python3 +""" +卡若AI 逆向获取:从本机浏览器/Cookie 文件自动取 Cookie,不弹窗,直接下载单条妙记文字+视频。 +与 download_soul_minutes_101_to_103 同源(cookie_minutes.txt → 环境变量 → browser_cookie3 → Doubao)。 +用法: python3 逆向获取Cookie并下载单条.py "https://cunkebao.feishu.cn/minutes/obcn6yjg6866c3gl4ibd72vr" "soul 派对 113场 20260302" +""" +from __future__ import annotations + +import re +import sys +from pathlib import Path + +SCRIPT_DIR = Path(__file__).resolve().parent +OUT_DIR = Path("/Users/karuo/Documents/聊天记录/soul") +COOKIE_FILE = SCRIPT_DIR / "cookie_minutes.txt" + + +def get_cookie() -> str: + """与 download_soul_minutes_101_to_103 一致:cookie_minutes.txt → 环境变量 → 本机浏览器(Doubao)。""" + if COOKIE_FILE.exists(): + for line in COOKIE_FILE.read_text(encoding="utf-8", errors="ignore").strip().splitlines(): + line = line.strip() + if line and not line.startswith("#") and "PASTE_YOUR" not in line and len(line) > 100: + return line + c = __import__("os").environ.get("FEISHU_MINUTES_COOKIE", "").strip() + if c and len(c) > 100: + return c + # browser_cookie3 + try: + import browser_cookie3 + for domain in ("cunkebao.feishu.cn", "feishu.cn", ".feishu.cn"): + for loader in (browser_cookie3.safari, browser_cookie3.chrome, browser_cookie3.chromium, browser_cookie3.firefox, browser_cookie3.edge): + try: + cj = loader(domain_name=domain) + s = "; ".join(f"{c.name}={c.value}" for c in cj) + if len(s) > 100: + return s + except Exception: + continue + except ImportError: + pass + # Doubao + try: + import subprocess, shutil, tempfile, sqlite3, hashlib + for name in ("Doubao Browser Safe Storage", "Doubao Safe Storage"): + try: + key = subprocess.run(["security", "find-generic-password", "-s", name, "-w"], capture_output=True, text=True, timeout=5).stdout.strip() + if not key: + continue + except Exception: + continue + for profile in ("Default", "Profile 1", "Profile 2", "Profile 3"): + db = Path.home() / "Library/Application Support/Doubao" / profile / "Cookies" + if not db.exists(): + continue + try: + tmp = tempfile.mktemp(suffix=".db") + shutil.copy2(db, tmp) + conn = sqlite3.connect(tmp) + cur = conn.cursor() + cur.execute("SELECT host_key, name, encrypted_value FROM cookies WHERE host_key LIKE '%feishu%' OR host_key LIKE '%cunkebao%'") + rows = cur.fetchall() + conn.close() + Path(tmp).unlink(missing_ok=True) + except Exception: + continue + if not rows: + continue + from cryptography.hazmat.primitives.ciphers import Cipher, algorithms, modes + derived = hashlib.pbkdf2_hmac("sha1", key.encode("utf-8"), b"saltysalt", 1003, dklen=16) + parts = [] + for host, name, enc in rows: + if enc[:3] != b"v10": + continue + raw = enc[3:] + dec = Cipher(algorithms.AES(derived), modes.CBC(b" " * 16)).decryptor() + pt = dec.update(raw) + dec.finalize() + pad = pt[-1] + if isinstance(pad, int) and 1 <= pad <= 16: + pt = pt[:-pad] + for i in range(min(len(pt), 48)): + if i + 4 <= len(pt) and all(32 <= pt[j] < 127 for j in range(i, min(i + 8, len(pt)))): + val = pt[i:].decode("ascii", errors="ignore") + if val and "\x00" not in val: + parts.append(f"{name}={val}") + break + if len(parts) > 5: + return "; ".join(parts) + except Exception: + pass + return "" + + +def main() -> int: + url_or_token = sys.argv[1] if len(sys.argv) > 1 else "" + title = sys.argv[2] if len(sys.argv) > 2 else "" + token = (re.search(r"/minutes/([a-zA-Z0-9]+)", url_or_token).group(1) if "/minutes/" in url_or_token else url_or_token) or url_or_token + if not token or len(token) < 20: + print("用法: python3 逆向获取Cookie并下载单条.py <妙记URL或token> [标题]", file=sys.stderr) + return 1 + if not title: + title = f"妙记_{token[:12]}" + + print("🔄 逆向获取 Cookie(cookie_minutes.txt → 环境变量 → 本机浏览器/Doubao)…") + cookie = get_cookie() + if not cookie: + print("❌ 未获取到 Cookie。请确保:cookie_minutes.txt 有内容,或本机 Chrome/Safari/Doubao 已登录 cunkebao.feishu.cn", file=sys.stderr) + return 1 + print(" Cookie 长度:", len(cookie)) + # 写入以便后续脚本复用 + COOKIE_FILE.write_text(cookie + "\n# 逆向获取", encoding="utf-8") + print(" 已写入 cookie_minutes.txt") + + sys.path.insert(0, str(SCRIPT_DIR)) + from feishu_minutes_export_github import export_transcript + from feishu_minutes_download_video import get_video_url, download_video, get_cookie as get_cookie_video, make_headers + + # 1) 文字 + print("📄 下载文字…") + text = export_transcript(cookie, token) + if not text: + try: + from feishu_minutes_one_url import export_via_playwright_page + print(" Cookie 导出 401,改用 Playwright 页面内获取…") + text = export_via_playwright_page(token, title=title, wait_sec=45) + except Exception as e: + print(" Playwright 兜底失败:", e, file=sys.stderr) + if text: + OUT_DIR.mkdir(parents=True, exist_ok=True) + safe = re.sub(r'[\\/*?:"<>|]', "_", title) + path = OUT_DIR / f"{safe}.txt" + path.write_text(f"标题: {title}\nobject_token: {token}\n\n文字记录:\n\n{text}", encoding="utf-8") + print(" ✅", path.name) + else: + print(" ❌ 文字导出失败(可能 401)") + + # 2) 视频 + print("📹 下载视频…") + video_url, _title = get_video_url(cookie, token) + if video_url: + ref = "https://cunkebao.feishu.cn/minutes/" + headers = make_headers(cookie, ref) + safe = re.sub(r'[\\/*?:"<>|]', "_", title or _title or token[:12]) + out_path = OUT_DIR / f"{safe}.mp4" + if download_video(video_url, out_path, headers): + print(" ✅", out_path.name, f"({out_path.stat().st_size / (1024*1024):.1f} MB)") + else: + print(" ❌ 视频下载失败") + else: + print(" ❌ 未获取到视频链接") + + return 0 if text or video_url else 1 + + +if __name__ == "__main__": + sys.exit(main()) diff --git a/BOOTSTRAP.md b/BOOTSTRAP.md index 1026b943..d7eb94d7 100644 --- a/BOOTSTRAP.md +++ b/BOOTSTRAP.md @@ -36,8 +36,7 @@ |:---|:---|:---| | 1 | **本文件** `BOOTSTRAP.md` | 知道自己是谁、团队怎么分、怎么工作 | | 2 | **技能注册表** `SKILL_REGISTRY.md` | 查找用户需求对应的技能和路径 | -| 3 | **运行模式** `运营中枢/工作台/运行模式.md` | 若当前模式为 `max`,按 MAX 模式执行(思考更深、全栈走实施计划+TDD+两阶段评审、复盘更详);见 `运营中枢/参考资料/卡若AI运行模式说明.md` | -| 4 | **对应技能的 SKILL.md** | 拿到具体执行指令(只读匹配到的那个) | +| 3 | **对应技能的 SKILL.md** | 拿到具体执行指令(只读匹配到的那个) | **启动瘦身(按需加载)**:步骤 2 不需要全表扫描。优先只加载 `SKILL_REGISTRY.md` 中 🔴 热技能(≤8 个)的触发词+路径;未命中时再懒加载其余部分。详见 SKILL_REGISTRY 中「技能热度分级」。 @@ -49,17 +48,31 @@ --- -## 四、执行流程(强制) +## 四、MAX Mode(默认 · 卡若AI 本体) -### 第一步:先思考,并在对话中展示拆解与计划(强制) +**卡若AI 每次被调用时,均以 MAX Mode 运行。** 无需在任何平台单独开启或提问,这是卡若AI 的默认行为,写在 BOOTSTRAP 即对所有调用方生效(Cursor、Claude、API 等)。 -接到用户任务后,**必须先做深度思考与调研**,再动手执行。思考要结合团队所有成员能力(金/水/木/火/土、14 成员、53 技能),想清楚:目标是什么、该谁干、怎么干、可能卡在哪。 +- **思考**:更深度(多角度、边界情况、风险与回退);结合 SKILL_REGISTRY 热技能与相关子技能做扩展。 +- **任务拆解**:粒度更细,子步骤、依赖与顺序写清;执行计划尽量带**精确路径、命令、预期**(对齐全栈开发「实施计划标准」)。 +- **技能联动**:执行前检查是否有**联动子技能**需一并考虑(如视频切片→切片动效包装、全栈开发→需求拆解/智能追问)。 +- **验证**:至少两轮验证(结果与目标匹配、无遗漏);不通过则回溯再执行。 +- **复盘**:五块齐全且更完整,可带简要数据、引用或下一步可执行动作。 + +--- + +## 五、执行流程(强制 · 含 MAX Mode) + +### 第一步:先思考,并在对话中展示拆解与计划(强制 · MAX Mode) + +接到用户任务后,**必须先做深度思考与调研**,再动手执行。思考要结合团队所有成员能力(金/水/木/火/土、14 成员、53 技能),想清楚:目标是什么、该谁干、怎么干、可能卡在哪;**思考更深度**(多角度、边界与风险),可结合 SKILL_REGISTRY 热技能与相关子技能做扩展。 **必须在对话里先展示以下内容,再继续执行**: 1. **思考结果**:调研/分析后的结论(目标、谁干、怎么干、卡点),用简洁几句话输出 -2. **任务拆解**:把任务拆成 1、2、3… 的具体步骤 -3. **执行计划**:先写清计划,再动手 +2. **任务拆解**:把任务拆成 1、2、3… 的**细粒度**步骤(子步骤、依赖与顺序写清) +3. **执行计划**:先写清计划,尽量带**精确路径、命令、预期**,再动手 + +**执行前**:检查是否有**联动子技能**需一并考虑(如视频切片→切片动效包装、全栈开发→需求拆解/智能追问)。 **格式示例**: ``` @@ -81,23 +94,23 @@ 按思考结论:查 `SKILL_REGISTRY.md` → 读对应 SKILL.md → 按步骤执行,每步简短总结。 -### 第三步:反复验证结果(强制) +### 第三步:反复验证结果(强制 · 至少两轮) -执行完成后,**必须反复验证**:最终结果是否与用户一开始输入的命令/目标相匹配。 +执行完成后,**必须反复验证**:最终结果是否与用户一开始输入的命令/目标相匹配;**至少两轮验证**(结果与目标匹配、无遗漏)。 - **匹配** → 进入「对话结尾」。 - **不匹配** → **回溯**:回到问题点 → **搜索**(GitHub、现有 Skill、网上资料)找解决方案 → **再思考**(简洁输出)→ **再执行** → 再次验证。循环直到结果与用户目标一致或明确说明无法达成。**确保任务成功、对话执行命令成功。** -### 第四步:回复形式 = 强制复盘(卡若AI 内所有对话必守) +### 第四步:回复形式 = 强制复盘(卡若AI 内所有对话必守 · 五块更完整) -**在卡若AI 工作台内,所有对话的 AI 回复一律采用「复盘形式」。** 复盘**只有一种格式:完整复盘**;**每一轮回复、每一个步骤结束**均以完整复盘块收尾(🎯📌💡📝▶ 五块齐全),不得使用简版或省略。复盘块**必须带日期+时间**(YYYY-MM-DD HH:mm);目标·结果·达成率**整行 ≤30 字**;回复可加图标增强可读性;下一步须结合对话与项目目标、关联未完成项。复盘格式见:`运营中枢/参考资料/卡若复盘格式_固定规则.md`。 +**在卡若AI 工作台内,所有对话的 AI 回复一律采用「复盘形式」。** 复盘**只有一种格式:完整复盘**;**每一轮回复、每一个步骤结束**均以完整复盘块收尾(🎯📌💡📝▶ 五块齐全),不得使用简版或省略。**五块更完整**,可带简要数据、引用或下一步可执行动作。复盘块**必须带日期+时间**(YYYY-MM-DD HH:mm);目标·结果·达成率**整行 ≤30 字**;回复可加图标增强可读性;下一步须结合对话与项目目标、关联未完成项。复盘格式见:`运营中枢/参考资料/卡若复盘格式_固定规则.md`。 --- -### 流程小结 +### 流程小结(默认 MAX Mode) ``` -输入 → 先思考 → 在对话中展示(思考结果+任务拆解1/2/3+计划)→ 执行 → 验证 +输入 → 先思考(深度+细拆解+精确计划+技能联动)→ 在对话中展示 → 执行 → 至少两轮验证 ↑ │ └── 不匹配:回溯 → 搜索(GitHub/Skill/网上) → 再思考 → 再展示 → 再执行 ──┘ ↓ @@ -106,7 +119,7 @@ --- -## 五、标准命令(Standard Commands) +## 六、标准命令(Standard Commands) 任何平台都能用的固定动作,不依赖特定 IDE: @@ -116,14 +129,13 @@ | **复盘** | **所有对话强制(卡若AI 统一回复形式)** | 卡若AI 内**所有对话**的 AI 回复一律用复盘形式;**只用完整复盘**,每轮/每步均以完整复盘块收尾(🎯📌💡📝▶);复盘须带日期+时间、目标行≤30字、下一步关联项目目标;格式见 `运营中枢/参考资料/卡若复盘格式_固定规则.md`。不得省略、不得改格式。 | | **沉淀** | 发现有价值的经验 | 写入 `02_卡人(水)/水溪_整理归档/经验库/待沉淀/` | | **基因胶囊** | 打包技能、解包胶囊、继承能力 | 读 `05_卡土(土)/土砖_技能复制/基因胶囊/SKILL.md`;pack 时自动生成导出说明(含流程图) | -| **运行模式** | 切换 Auto / MAX | 读写 `运营中枢/工作台/运行模式.md`;用户说「开MAX」「切回Auto」「当前什么模式」时切换或查询;MAX 下思考更深、全栈走实施计划+TDD+两阶段评审,见 `运营中枢/参考资料/卡若AI运行模式说明.md` | | **Gitea 同步** | 有文件变更时 | `bash 01_卡资(金)/金仓_存储备份/Gitea管理/脚本/自动同步.sh` | | **跑 Pipeline** | 用户说「新项目上线」「内容发布」「日常运维」等 | 读 `运营中枢/参考资料/Pipeline执行清单.md` 按步骤执行 | | **对外输出** | 报告、复盘存档、执行日志、导出文件、**生成图片** | 统一写到 `/Users/karuo/Documents/卡若Ai的文件夹/` 下对应子目录;**图片** → `图片/`,并在 `图片/图片索引.md` 登记来源 Skill、生成者。经验沉淀仍写 `02_卡人(水)/水溪_整理归档/经验库/待沉淀/`。详见 `运营中枢/参考资料/输出目录规范.md`。 | --- -## 六、核心文件导航 +## 七、核心文件导航 | 文件 | 路径 | 用途 | |:---|:---|:---| @@ -140,7 +152,7 @@ --- -## 七、全局规则 +## 八、全局规则 0. **异常处理与红线(强制)**:执行时按 `运营中枢/参考资料/卡若AI异常处理与红线.md`。**红线**:① 不改变卡若AI 整体结构 ② 不导致电脑无法启动 ③ 不删除重大文件。 1. **禁止独立功能目录(强制)**:**不得再新建 `_共享模块` 或任何与五行、运营中枢并列的「功能目录」**。所有共享能力必须融入现有结构:代码/脚本归属到 `01_卡资(金)`~`05_卡土(土)` 对应成员下,参考资料/复盘/流程归属到 `运营中枢/参考资料/`,兼容层在 `运营中枢/` 下(如 `运营中枢/local_llm`、`运营中枢/memory`、`运营中枢/task_router`)。违反即视为结构违规。 @@ -153,7 +165,7 @@ --- -## 八、平台适配(可选) +## 九、平台适配(可选) 卡若AI 本身不依赖任何特定 AI 平台。以下是各平台的薄层适配: @@ -166,7 +178,7 @@ --- -## 九、SKILL.md 标准格式 +## 十、SKILL.md 标准格式 每个技能的 SKILL.md 应遵循以下结构,确保任何 AI 都能读懂并执行: @@ -205,7 +217,7 @@ updated: "YYYY-MM-DD" --- -## 十、快速开始 +## 十一、快速开始 **场景 1:你是 AI,第一次接触卡若AI** 1. 读完本文件,你就知道团队结构和工作方式了 diff --git a/运营中枢/参考资料/卡若AI运行模式说明.md b/运营中枢/参考资料/卡若AI运行模式说明.md deleted file mode 100644 index 93044382..00000000 --- a/运营中枢/参考资料/卡若AI运行模式说明.md +++ /dev/null @@ -1,45 +0,0 @@ -# 卡若AI 运行模式说明 - -> 对应「Search models / Auto / MAX Mode」类能力:通过 `运营中枢/工作台/运行模式.md` 的「当前模式」在 **Auto** 与 **MAX** 间切换,每次对话开始读取该文件并据此调整行为。 - ---- - -## 一、模式定义 - -| 模式 | 含义 | 适用场景 | -|:---|:---|:---| -| **Auto** | 平衡、效率优先;标准思考与拆解深度,按既有流程执行。 | 日常任务、快速响应、常规技能调用。 | -| **MAX** | 深度模式;思考与拆解更充分,开发类任务优先走实施计划 + TDD + 两阶段评审,复盘更完整。 | 重要需求、全栈/开发、需要最佳质量或可追溯性时。 | - ---- - -## 二、行为差异(AI 须遵守) - -### Auto 模式 - -- 先思考并在对话中展示「思考结果 + 任务拆解 + 执行计划」,再执行(与现有强制流程一致)。 -- 技能按 SKILL_REGISTRY 匹配后按 SKILL.md 执行,不额外加码。 -- 复盘按固定格式、目标行 ≤30 字,完整五块即可。 - -### MAX 模式 - -- **思考与拆解**:思考更充分,拆解更细(可多步、标出依赖与风险),计划在对话中展示更完整。 -- **全栈/开发类任务**:优先采用「实施计划」(精确路径 + 命令 + 预期)、TDD 推荐、任务/迭代两阶段评审(规格符合 → 代码质量);见 `04_卡火(火)/火炬_全栈消息/全栈开发/SKILL.md`。 -- **搜索与扩展**:可适当扩大搜索范围、多查 references,再收敛到执行方案。 -- **复盘**:复盘保持五块格式,但过程与反思可更详细,下一步可带更明确的子项或检查点。 -- **不改变**:红线、异常处理、对外输出目录、复盘格式规范、Gitea 同步等全局规则不变。 - ---- - -## 三、配置与读取 - -- **配置文件**:`运营中枢/工作台/运行模式.md`,其中「当前模式」为 `auto` 或 `max`(小写)。 -- **读取时机**:每次对话开始(在 BOOTSTRAP / 技能查找之后)读取该文件,若为 `max` 则本轮按 MAX 模式行为执行。 -- **切换**:仅当用户明确要求切换模式时,修改 `运行模式.md` 中的「当前模式」并保存,然后回复已切换;不主动建议切换。 - ---- - -## 四、「Search models」的对应关系 - -- 图片中的「Search models」在卡若AI 中对应:**按需求查技能**(查 `SKILL_REGISTRY.md`)和**按关键词匹配技能**;无需单独「搜索模型」UI,技能注册表即能力索引。 -- 若后续需要「按名字/关键词搜某类运行配置」,可在工作台增加「模式/配置」索引表,本文件作为运行模式的主说明即可。 diff --git a/运营中枢/参考资料/卡若读书笔记格式_固定规则.md b/运营中枢/参考资料/卡若读书笔记格式_固定规则.md index 8a133c80..d5fb642d 100644 --- a/运营中枢/参考资料/卡若读书笔记格式_固定规则.md +++ b/运营中枢/参考资料/卡若读书笔记格式_固定规则.md @@ -19,7 +19,7 @@ ## 二、文件与存放 - **文件名**:`作者或主题_书名或简称_读书笔记.md`(例:`曾仕强_易经_读书笔记.md`、`纳瓦尔访谈_读书笔记.md`)。 -- **存放路径**:`/Users/karuo/Documents/卡若Ai的文件夹/导出/读书笔记/`。 +- **存放路径(默认)**:`/Users/karuo/Documents/个人/2、我写的日记/读书笔记/`。**以后读书笔记一律放此目录,固定不发他处。** - **图片与流程图**:笔记内引用的图片、流程图建议与笔记**同目录**存放,用 `文件名.png` 或 `./文件名.png` 引用,避免用 `../../图片/` 等跨目录路径导致在不同预览/工作区下**不显示**。若用 Mermaid,可在同节内再插入一张导出好的流程图 PNG,保证不依赖渲染也能看到图。 - **图裂了怎么办**:若在 Cursor/VS Code 里图片不显示,可(1)用 Typora 打开该 md(以文件所在目录为基准);(2)在 Finder 中打开笔记所在文件夹,双击 md 用系统默认预览打开;(3)直接打开同目录下对应的 PNG 文件。建议在每张图下方加一句备用说明:「若图不显示,请打开本笔记所在文件夹中的 `xxx.png` 查看。」 - **记忆写入**:在 `个人/1、卡若:本人/记忆.md` 当日日期下追加 1~2 行摘要 + 本笔记文件路径;便于后续从记忆调出。 @@ -127,7 +127,7 @@ ## 五、与记忆、Skill 的衔接 - **记忆**:读书笔记写完后,在 `个人/1、卡若:本人/记忆.md` 当日下追加一条,格式: - `[HH:MM] 读书笔记·《书名》/主题:一句话摘要;全文见 卡若Ai的文件夹/导出/读书笔记/xxx.md。` + `[HH:MM] 读书笔记·《书名》/主题:一句话摘要;全文见 个人/2、我写的日记/读书笔记/xxx.md。` - **读书笔记 Skill**:`04_卡火(火)/火炬_全栈消息/读书笔记/SKILL.md` 定义五行拆书流程与 XMind 写入;本格式与之对齐,完整版即该 Skill 的 Markdown 版输出。 - **分类**:个人提升 / 人际关系 / 创业 / 商业思维 / 投资;若写 XMind 需选其一。 @@ -147,8 +147,8 @@ | 类型 | 文件 | 说明 | |:---|:---|:---| -| 完整版 | `卡若Ai的文件夹/导出/读书笔记/纳瓦尔访谈_读书笔记.md` | 五行 + 问答 + 人物 + 金句 + Mermaid + 使用规则 | -| 精简版 | `卡若Ai的文件夹/导出/读书笔记/曾仕强_易经_读书笔记.md` | 按主题分块 + 要点小结 + 整理时间 | +| 完整版 | `个人/2、我写的日记/读书笔记/纳瓦尔访谈_读书笔记.md` | 五行 + 问答 + 人物 + 金句 + Mermaid + 使用规则 | +| 精简版 | `个人/2、我写的日记/读书笔记/曾仕强_易经_读书笔记.md` | 按主题分块 + 要点小结 + 整理时间 | --- diff --git a/运营中枢/参考资料/输出目录规范.md b/运营中枢/参考资料/输出目录规范.md index 3655a661..670a0251 100644 --- a/运营中枢/参考资料/输出目录规范.md +++ b/运营中枢/参考资料/输出目录规范.md @@ -28,6 +28,7 @@ | `复盘/` | 按对话或任务存档的复盘(可选,聊天结尾已带复盘则可不另存) | `YYYY-MM-DD_主题_复盘.md` | | `报告/` | 报表、分析报告、导出结果 | 财务汇总、竞品分析、监控报告 | | `导出/` | 从系统/脚本导出的数据、配置备份等 | 导出的 CSV、配置备份 | +| **读书笔记(例外)** | **统一放** `个人/2、我写的日记/读书笔记/`,**不放** 卡若Ai的文件夹 | 曾仕强_易经、纳瓦尔访谈等;见卡若读书笔记格式_固定规则 | ### 图片子目录规范(强制) diff --git a/运营中枢/工作台/MAX_MODE说明.md b/运营中枢/工作台/MAX_MODE说明.md new file mode 100644 index 00000000..0f00ce0e --- /dev/null +++ b/运营中枢/工作台/MAX_MODE说明.md @@ -0,0 +1,23 @@ +# 卡若AI · MAX Mode 说明 + +> **规则在卡若AI 本体,不在 Cursor。** 卡若AI 每次被调用时均为 MAX Mode,定义在 `BOOTSTRAP.md`,对所有平台生效。 +> 更新:2026-02-16 + +--- + +## 一、规则放在哪里 + +- **卡若AI 本体**:`BOOTSTRAP.md` **第四节(MAX Mode)** + **第五节(执行流程)**。任何平台(Cursor、Claude、API 等)只要读 BOOTSTRAP,即按 MAX Mode 执行。 +- **Cursor**:`.cursor/rules/karuo-ai.mdc` 仅引用 BOOTSTRAP,不重复定义 MAX Mode;Cursor 内补充记忆路径、每日收集、Gitea、复盘格式等本地特有项。 + +--- + +## 二、默认行为(BOOTSTRAP 第四节) + +- 思考更深度(多角度、边界与风险) +- 任务拆解更细(子步骤、依赖与顺序;执行计划带精确路径/命令/预期) +- 执行前检查联动子技能 +- 至少两轮验证 +- 复盘五块更完整 + +无需在任何平台单独开启或提问,**每次调用卡若AI 都是 MAX Mode**。 diff --git a/运营中枢/工作台/gitea_push_log.md b/运营中枢/工作台/gitea_push_log.md index 8e649b20..c92e95e5 100644 --- a/运营中枢/工作台/gitea_push_log.md +++ b/运营中枢/工作台/gitea_push_log.md @@ -205,3 +205,4 @@ | 2026-03-02 03:22:12 | 🔄 卡若AI 同步 2026-03-02 03:22 | 更新:Cursor规则、水桥平台对接、水溪整理归档、运营中枢参考资料、运营中枢工作台 | 排除 >20MB: 14 个 | | 2026-03-02 03:27:34 | 🔄 卡若AI 同步 2026-03-02 03:27 | 更新:Cursor规则、水桥平台对接、运营中枢参考资料、运营中枢工作台 | 排除 >20MB: 14 个 | | 2026-03-02 04:34:31 | 🔄 卡若AI 同步 2026-03-02 04:34 | 更新:运营中枢参考资料、运营中枢工作台 | 排除 >20MB: 14 个 | +| 2026-03-02 04:45:41 | 🔄 卡若AI 同步 2026-03-02 04:45 | 更新:Cursor规则、总索引与入口、运营中枢参考资料、运营中枢工作台 | 排除 >20MB: 14 个 | diff --git a/运营中枢/工作台/代码管理.md b/运营中枢/工作台/代码管理.md index e9bb9a95..b7a2fad8 100644 --- a/运营中枢/工作台/代码管理.md +++ b/运营中枢/工作台/代码管理.md @@ -208,3 +208,4 @@ | 2026-03-02 03:22:12 | 成功 | 成功 | 🔄 卡若AI 同步 2026-03-02 03:22 | 更新:Cursor规则、水桥平台对接、水溪整理归档、运营中枢参考资料、运营中枢工作台 | 排除 >20MB: 14 个 | [仓库](http://open.quwanzhi.com:3000/fnvtk/karuo-ai) [百科](http://open.quwanzhi.com:3000/fnvtk/karuo-ai/wiki) | | 2026-03-02 03:27:34 | 成功 | 成功 | 🔄 卡若AI 同步 2026-03-02 03:27 | 更新:Cursor规则、水桥平台对接、运营中枢参考资料、运营中枢工作台 | 排除 >20MB: 14 个 | [仓库](http://open.quwanzhi.com:3000/fnvtk/karuo-ai) [百科](http://open.quwanzhi.com:3000/fnvtk/karuo-ai/wiki) | | 2026-03-02 04:34:31 | 成功 | 成功 | 🔄 卡若AI 同步 2026-03-02 04:34 | 更新:运营中枢参考资料、运营中枢工作台 | 排除 >20MB: 14 个 | [仓库](http://open.quwanzhi.com:3000/fnvtk/karuo-ai) [百科](http://open.quwanzhi.com:3000/fnvtk/karuo-ai/wiki) | +| 2026-03-02 04:45:41 | 成功 | 成功 | 🔄 卡若AI 同步 2026-03-02 04:45 | 更新:Cursor规则、总索引与入口、运营中枢参考资料、运营中枢工作台 | 排除 >20MB: 14 个 | [仓库](http://open.quwanzhi.com:3000/fnvtk/karuo-ai) [百科](http://open.quwanzhi.com:3000/fnvtk/karuo-ai/wiki) | diff --git a/运营中枢/工作台/运行模式.md b/运营中枢/工作台/运行模式.md deleted file mode 100644 index 564da17d..00000000 --- a/运营中枢/工作台/运行模式.md +++ /dev/null @@ -1,21 +0,0 @@ -# 卡若AI 运行模式 - -> 与「Search models / Auto / MAX Mode」类 UI 对应:用本文件切换运行模式,每次对话开始会读取此处。 - ---- - -## 当前模式 - -**当前模式:** `auto` - -(可选值:`auto` | `max`) - ---- - -## 切换方式 - -- **切到 MAX 模式**:用户说「开MAX模式」「切换MAX」「用MAX」「MAX模式」→ 将上方的 `auto` 改为 `max` 并保存,然后回复确认。 -- **切回 Auto 模式**:用户说「切回Auto」「用Auto」「自动模式」「Auto」→ 将上方的 `max` 改为 `auto` 并保存,然后回复确认。 -- **查当前模式**:用户说「当前什么模式」「运行模式」→ 读本文件,回复当前为 Auto 或 MAX。 - -行为差异见:`运营中枢/参考资料/卡若AI运行模式说明.md`。