住错了地方的段位:SoulPort 护城河前置记

住错了地方的段位:SoulPort 护城河前置记

系列回顾:从「数体积」到「读灵魂」 → 三个脑子吵出来的 Coming Soon → 本篇

一个颜色改了一半

四月十六号,我想把 Titan 段位的发光色调暖一点。

改完重启 SoulArena,上传一只灵魂包——六边形边框、段位徽章、雷达图光晕,颜色都对了。

隔天在终端跑 soulport score,还是老橙红。

愣了三秒:我改了 SoulArena 的 config.py,没改 SoulPort 的 tiers.py。

因为它们原本就是两份。

协议写在了客户端里

段位和评分最初写在 SoulArena 的 backend 里,原因很朴素——那天先做的 Web,CLI 还没有 score 命令。写完能跑,就没人逼着搬。

但标准化工具有一条隐藏铁律:

段位定义属于规范,不属于展示层。

如果 Cursor 明天想接入 SoulPort,他们能 pip install soulport 就拿到完整的五维评分和七阶段位。不该要求他们跑个 SoulArena Web 服务。SoulArena 是段位的第一个消费者——和未来任何接入方一样的身份,不应该是段位的"源"。

小龙虾在 Review 里一句话点穿:

"你把协议写在了客户端里。"

Docker 当年做对的那件事不是 docker run,是让 container image format 脱离了 Docker 引擎。格式属于公共标准之后,Kubernetes、Podman、containerd 才能接进来。

SoulPort 的类比:.bm 格式是数据标准(v0.2 就定了),评分算法和段位定义是行为标准——这一版才搬回来。两层标准都住在 pip install soulport 里,"任何下游平台接入都段位一致"才不是一句空话。

搬回来的时候翻出了什么

搬运本身很直:SoulArena 的纯统计函数搬到 soulport/scorer.py,段位字典搬到 soulport/tiers.py,SoulArena 瘦身成 thin wrapper——只留 LLM 调用和 guardrail,统计从上游 import。

733 行 → 458 行,少的 275 行搬到了它该在的地方。

但搬的过程里小龙虾翻出了五个老毛病——全都藏在"能跑"的表象下面。

独特性评分歧视非 OpenClaw 用户。 原逻辑只认 OpenClaw 的 SOUL.md,Claude Code 的 CLAUDE.md 和 Copilot 的 copilot-instructions.md 跑出来永远偏低。小龙虾的原话:"这是在惩罚用户选了别的框架。" 改成 fallback 到 identity_content,任何框架的 Identity 层都能参与。

技能目录提取写了两遍。 doctor 和 scorer 各自实现了一遍"从路径提取 skill 目录",去重逻辑还不一样。抽出来变成公共函数,一处改全局生效。

.bm 包的活跃度检测永远报 stale。 doctor 检测"最近活跃度"用的是 datetime.now()——一个三个月前导出的包,打开一看"90 天没更新"。对 workspace 合理,对快照没意义。改成用 manifest.exported_at 做参考点。

MCP 的雷达图在某些 LLM 上下文里会被吞。 Unicode 方块字符放在 Claude Desktop 里好看,但丢到别的模型的 context window 里可能变乱码。改成 ASCII bar,渲染 fallback 始终可读。

IDENTITY 扫描器只认自家格式。 score_personality_richness 扫描 Identity 层时只认 YAML 风格的 name:,不认 ## Name 这种 heading。加上 heading regex 之后,跨框架识别率立刻上来。

五个问题,共性只有一个:代码能跑,测试能过,但逻辑在跨框架场景下是错的。

护城河不在行数里

这一版没加新功能,都是基础设施的位置调整。但我觉得它是 SoulPort 路线里比较重要的一步。

护城河不在代码量里——在哪些决策必须由你的上游说了算。

段位的颜色、分数的切线、技能的去重规则,这些属于"定义什么是好灵魂",不属于"画个六边形展示它"。

v1.2.0 已上 PyPI。206 个测试,0 regression。

pip install soulport==1.2.0
soulport score your-soul.bm          # 终端渲染,或 --json 给脚本消费
soulport doctor your-soul.bm         # 直接体检 .bm 包

下次改 Titan 颜色,只改一处就够了。

Comments