
caveman-shrink压缩 MCP/OpenAI 工具目录的 Token 工程——caveman 项目中 fail-open 与可逆压缩的设计拆解【免费下载链接】caveman why use many token when few token do trick — Claude Code skill that cuts 65% of tokens by talking like caveman项目地址: https://gitcode.com/GitHub_Trending/caveman1/cavemancaveman-shrink 是 caveman 仓库中专用于压缩 MCP/OpenAI 工具定义目录tool catalog的产品它在工具清单撑满上下文窗口之前删掉注解类元数据、把冗长描述缩减为引导句 全部约束句同时保证名称、参数、枚举、required以及default/const等参数构造值逐字节存活。读完本文你将掌握它的 CLI 与 npm 启动器用法、基于 enginetoolschema压缩器的底层压缩规则以及结构选择面不变量 有界 CCR 可逆恢复这两条正确性边界的实现与测试证据。定位toolschema 压缩器的专用产品面caveman-shrink 本身不是一套独立的压缩算法。根据 shrink/CLAUDE.md它是对 engine 中toolschema压缩器的一个薄 Go 封装thin wrapper结构压缩器本体位于 engine/compressors/toolschema.goshrink 只复用、绝不 fork。这一分工在 shrink/CLAUDE.md 的 Conventions 一节中是明确约定构建/测试make product-build PRODUCTshrink/make product-test PRODUCTshrinkshrink 是toolschema压缩器的专用产品面。engine 的 API/CLI 调用方也可以本地强制走该压缩器通过engine.Options.Type toolschema但在 caveman 的受管网关managed-gateway路径中工具数组被保留在冻结的 prompt-cache 前缀里从不交给它处理网关上另一条 S2 的 tool-search/deferral 路径也不是压缩。本地缩减的统计口径一律记为inferred文档同时给出一条未来的商业化前提如果将来要为这个变换开辟计费路由必须先有 cache-vs-schema 的成本证明、稳定的逐字节前缀输出以及一个 eval 门禁。压缩行为本身分三层均来自 shrink/CLAUDE.md 首段与 engine/compressors/toolschema.go 的类型注释丢弃注解元数据——examples、example、title、$comment、$schema这类对工具选择没有信息量、却最占字节的 JSON-Schema 注解键缩减自由文本描述——只保留引导句和所有携带约束的句子规则见后文两条正确性边界逐字节保留两类 token——选择 token工具名、参数名、类型、enum、required和参数构造值default、const、内部$ref目标。它在 engine 的安全分级里属于 S4lossy、模型可见的字节会被改变。这一点可以从 engine/safety/safety.go#L48 的注册表看到S4: {Class: S4, ByteSafe: false, RequiresCCR: true, Reversible: false}——S4 类要求依赖 CCR上下文压缩恢复存储作为安全网。目录布局与三种入口形态shrink/CLAUDE.md 的 Layout 一节列出了 shrink 的三块组成对应仓库中的实际路径组成路径职责库shrink/shrink.goShrink目录 → 压缩fail-open 的 S4 变换持久化 CCR 支撑、Recoverhandle → 原始字节、Lint逐工具的 inferred token 缩减报告、SelectionProfile结构选择面——即必须存活的东西CLIshrink/cmd/caveman-shrink/main.gocaveman-shrink/shrinkstdin→stdout、lint file、recover handlenpm 启动器shrink/bin/caveman-shrink.mjs shrink/package.jsonnpx caveman-shrink的 MIT 启动器围绕预构建二进制工作库入口 shrink/shrink.go 的核心 API 值得逐一说明Shrink(input []byte, opts ...Option) (Result, error)——以Type: toolschema强制路由到工具的 schema 压缩器shrink/shrink.go#L117-L124。它是 fail-open 的任何解析问题、或结果不更小都原样返回输入Ratio为 0、无 handle。Result——Output、TokensBefore、TokensAfter、Ratio、Basis恒为inferred、ContentType、RecoveryHandle仅当真正压缩时非空。Recover(handle, opts...)——从与Shrink相同的持久化 store 读取原始字节未知 handle 返回ccr.ErrNotFoundengine/ccr/store.go#L27-L29恢复过程从不猜测。WithStore(s *ccr.Store)/WithStorePath(path string)——两个 Option 用于指定恢复存储前者由调用方持有生命周期后者打开指定路径:memory:仅在一次调用内有意义。不提供 Option 时使用默认的共享持久化 storeCAVEMAN_CCR_DB环境变量否则~/.caveman/ccr.db。Lint(input) (Report, error)——只测量、不提交对每个工具用 engine 的默认离线 counter 计数并刻意取压缩前后较小者若压缩结果不更小就保留原值保证 Lint 的数字不会虚报。SelectionProfile(input) (map[string]ToolProfile, error)——提取每个工具的选择面参数名列表、每参数的enum值、required列表description被刻意排除因为那正是 shrink 要压缩的对象。它支持三种目录形态shrink/shrink.go#L240-L284 的extractToolsMCP 的{tools:[…]}、OpenAI 的{functions:[…]}或扁平数组含{function: …}嵌套以及单个裸工具对象schema 字段则兼容 MCP 的inputSchema与 OpenAI 的parameters。默认存储路径的解析在 shrink/shrink.go#L79-L95依次尝试CAVEMAN_CCR_DB→CAVEMAN_HOME/ccr.db→~/.caveman/ccr.db并会自动创建父目录0o700使一台机器上的第一次 shrink 就能成功。CLI 实操shrink、lint、recover 三个子命令CLI 入口在 shrink/cmd/caveman-shrink/main.go。子命令分派逻辑是显式shrink、lint、recoverhelp/-h打印用法不带子命令时把整个调用当作对 stdin 的 shrink——这使得它可以直接插进管道。基本用法# 压缩目录stdin → stdoutinferred 的 ratio 报告写到 stderr cat tools.json | caveman-shrink tools.min.json # 从 shrink stderr 报告里打印的 handle 恢复精确的原始字节 caveman-shrink recover ccr_... tools.original.json # 不承诺压缩、只查看逐工具的缩减量 caveman-shrink lint tools.json以上三条即 shrink/README.md 的 Use 一节。仓库自带一个可直接拿来试手的示例目录 shrink/testdata/catalog.json两个工具search_files、run_command带title、$schema、examples、enum、default等注解正好覆盖压缩器会处理的所有注解类型caveman-shrink lint shrink/testdata/catalog.json cat shrink/testdata/catalog.json | caveman-shrink有界输入32 MiB 上限CLI 对 stdin 有硬性上限。shrink/cmd/caveman-shrink/main.go#L23 定义maxStdinBytes int64 32 20readBoundedInput用io.LimitReader(r, maxBytes1)读取超限即返回cave_input_too_large错误——更大的目录直接失败而不是无界缓冲shrink/README.md 将其列为 Bounded input 保证之一。fail-open 的字节安全语义shrink/cmd/caveman-shrink/main.go#L46-L63 的runShrink体现了失败也不改字节的原则Shrink返回错误时CLI把原始输入原样写到 stdout并在 stderr 输出{ratio:0,basis:informed…,note:passed through: …}成功时 stdout 是压缩后的目录stderr 是Result的 JSON其中recovery_handle字段是后续recover的凭据。测试侧 shrink/shrink_test.go#L174-L186 的TestShrinkByteSafeOnMalformed锁死了库层行为喂入{not a valid catalog这样的坏 JSONShrink不返回 error输出与输入逐字节相等且ratio0、无 handle。npm 启动器无需 Go 工具链shrink/package.json 声明包名caveman-shrink、bin: {caveman-shrink: bin/caveman-shrink.mjs}、Node18、MIT 许可。shrink/bin/caveman-shrink.mjs 是一个 shim通过ensureBinary定位预构建的 Go 二进制支持CAVEMAN_SHRINK_BIN环境变量覆盖stdio: inherit地 exec 它并透传退出码找不到二进制时以退出码 127 失败。按 shrink/README.mdMIT 启动器首次运行会下载匹配的 BSL-1.1 许可二进制校验密钥签名的 checksum 清单与工件 SHA-256并缓存在~/.caveman/bin——因此不需要 Go 工具链也不需要全局安装 Cavemannpx -y caveman-shrink lint tools.json许可是拆开的npm 启动器本身是 MITshrink/LICENSE.launcher 对应LICENSE.launcher文件下载到的二进制受 shrink/BINARY_LICENSE.md 中注明的 BSL-1.1 条款约束。shrink/CLAUDE.md 标题中的 commercial Go core MIT launcher 指的就是这个结构。引擎侧压缩规则哪些字节会掉哪些字节必活shrink 的全部压缩决策发生在 engine/compressors/toolschema.go 的toolSchemaCompressor中。理解四个键集合和描述缩减算法就理解了 shrink 的完整行为面。元数据丢弃集与必保留集engine/compressors/toolschema.go#L28-L45 定义了两张核心表// 直接丢弃schema 注解元数据可经 CCR 恢复 var schemaMetaDrop map[string]bool{ examples: true, example: true, $comment: true, title: true, $schema: true, } // 逐字节保留承载参数构造语义的键不递归、不截断 var keepSchemaKeys map[string]bool{ enum: true, required: true, default: true, const: true, }源码注释里有一个值得注意的设计动机default被刻意排除在丢弃集之外因为它是agent 省略参数时所依赖的值——丢掉default会静默改变调用行为const同理它钉死了唯一合法值。第三张表 userDefinedKeysproperties、$defs、definitions、patternProperties、dependentSchemas、dependentRequired、dependencies标记了键名本身由用户控制的位置一个叫title的属性名是用户命名不是 schema 元数据必须逐字存活压缩器只递归压缩这些键下面的 schema 值。compressSchemaengine/compressors/toolschema.go#L191-L230用一个inUserKeys布尔位区分这两种语境。描述缩减小额预算整体保留 约束句全保留compressDescriptionengine/compressors/toolschema.go#L269-L289的规则是小额预算整体保留。常量maxDescLen 80L18smallDescBudget maxDescLen * 2 160字节L260。描述若 ≤160 字节整句保留、一个句子都不剪——源码注释解释了为什么短描述是常见情形为一个省不了多少字节的小描述冒漏掉无标记约束的风险不值得。大描述 引导句 全部约束句。对超过预算的描述先按句号切句splitSentences然后遍历带约束标记的句子永不丢弃、永不截断第一个非约束句作为引导句保留按 rune 边界截到 80 字节capRunes保证不拆 UTF-8 字符、尽量退回词边界其余非约束句丢弃可经 CCR 找回。约束标记是一个刻意写得宽的正则 constraintRe匹配整词/短语涵盖四类语义义务/禁止must、must not、cannot、cant、shall、require*、reject*、disallow*、forbidden合法性判断invalid、not allowed、not permitted数量/互斥/边界exactly one、only one of、one of、at least、at most、mutually exclusive、only、unique、case-sensitive、max、min、maximum、minimum、range、between、greater/less/more/fewer than、no more/less than、over、above、below、under、beyond、exceed*格式锚点format*、iso[- ]?数字*、rfc[- ]?数字*、absolute后两者允许尾随数字串以便RFC3339、ISO8601命中。源码注释明确给出了取舍原则匹配宁多勿少over-keep——多留一句只损失一点 ratio而丢掉一个约束句会造出非法工具调用和重试循环代价远超 shrink 省下的字节。句子切分splitSentencesengine/compressors/toolschema.go#L296-L330专门处理了英文缩写陷阱只有当句号后跟空白大写字母、且句号不是某个缩写e.g、i.e、etc、vs等见 abbrevSet的结尾时才切句。这保证 e.g. /srv/x 不会被截成 e.——shrink/CLAUDE.md 里把这一反例写得很直白把 Target path, e.g. /srv… 截成 Target path, e. 会产生非法调用而结构 profile 根本看不见这类错误。信封与 schema 的分流压缩器还区分provider 工具信封与裸 JSON SchemacompressDocumentengine/compressors/toolschema.go#L112-L133识别tools数组、function嵌套、单工具对象compressToolEnvelope对工具级description走描述缩减对声明为 schema 值的字段才进入compressSchema。MCP 注解里模型可见的title等信封字段不受 schema 元数据规则影响。两条正确性边界结构选择面与参数有效性shrink/CLAUDE.md 用Two correctness boundaries一节划定了这个产品能证明什么、不能证明什么这是全文最核心的诚实性声明。边界一结构选择面不变量不变量是SelectionProfile(input)SelectionProfile(Shrink(input).Output)恒成立。这证明了工具名、参数名、enum值、required列表逐字节存活。但它不能证明模型会选中同一个工具——因为描述是模型可见的而长描述的缩减是有损的。行为等价需要模型 eval 固件当前结果因此保持inferred。库级测试TestStructuralSelectionSurfaceInvariantshrink/shrink_test.go#L105-L127就是这条不变量的执行体对压缩前后分别取SelectionProfile并reflect.DeepEqual同时验证mode参数的 3 个 enum 值一个不少。边界二参数有效性偏向 over-keepAgent 是从描述里构造工具参数的所以选择面存活并不等于参数合法。shrink 的保证偏保守地多留是两条一个已经装得下小额预算≤maxDescLen * 2字节的描述整体保留——不剪任何句子因此即便约束句没有使用任何被识别的标记词它也活下来对真正大的描述保留引导句 每个带约束标记的句子完整保留见上一节的标记清单。丢default、RFC3339 或边界规则会产生结构 profile 看不见的非法调用为此 engine 侧有 call-validity 一致性测试golden fixture 复现的 under-keep 用例位于engine/compressors测试中把已识别的约束 token 钉死在行为里。shrink 产品层的对应测试是TestShrinkPreservesArgumentConstraintsshrink/shrink_test.go#L134-L172断言压缩输出必须仍然包含must be an absolute path绝对路径规则exactly one of body互斥约束format must be RFC3339时间戳格式e.g. /srv/x缩写不被截成 e.并且长描述里的填充散文This trailing clause is filler…应当被丢弃。shrink/CLAUDE.md 的总结语是产品的行为准则Over-keep is the rule — never knowingly under-keep.Reversible for real持久化 CCR 恢复存储shrink/CLAUDE.md 的 Gotchas 第三条reversible for real描述了一次真实的缺陷修复早先的实现在返回时关闭的内存store 里铸造 handle导致Shrink 一返回handle 就永远无法解析——可逆性声明在每次调用上都是假的。现在的设计是先提交、后发布。一次真正压缩的 shrink 会把精确的原始字节写入持久化store——engine 的Compress在发布变换后的字节之前提交恢复行shrink/shrink.go#L112-L116 的注释。因此任何非空的RecoveryHandle都能稍后、跨进程、经Recover/caveman-shrink recover解析。默认 store 是共享的CAVEMAN_CCR_DB/~/.caveman/ccr.db与 engine CLI、MCP server、网关使用同一个。store 打不开则不承诺可逆。若持久 store 无法打开库的Shrink返回 errorCLI 捕获后转发原始字节没有 handle也就没有可逆性声明。两条测试锁死这个语义。TestShrinkRoundTripsThroughAFreshStoreshrink/shrink_test.go#L76-L99是可逆性门禁第一次Shrink用WithStorePath(dbPath)然后用同一路径全新打开一个 store 实例模拟一个recover进程看到的状态取回字节与原始 catalog 逐字节比较——注释特别指出旧实现下handle ! 的自证检查恰好掩盖了这个 bug。TestShrinkReturnsPassThroughResultWhenCCRIsUnavailableshrink/shrink_test.go#L188-L203则验证store 已关闭时Shrink返回 error且附带一个完整记账的原始字节直通结果Ratio0、无 handle、TokensAfter TokensBefore让库调用方既能安全转发又能感知操作失败。恢复端同样有边界测试TestRecoverUnknownHandleFailsshrink/shrink_test.go#L205-L209断言未知 handle 必须失败——recovery never guesses。诚实性不变量与统计口径shrink/CLAUDE.md 最后三条 Gotchas 汇总成产品的诚实性不变量值得逐条对照源码验证S4 lossy、fail-open成功压缩会改变模型可见的字节S4 在 engine/safety/safety.go 中ByteSafe: false畸形/不可压缩的目录原样直通ratio:0、无 handle。直通语义在库层由TestShrinkByteSafeOnMalformed、CLI 层由runShrink的 error 分支共同保证。inferred-onlytoken 数来自 engine 的离线 counter是估计值永远是inferred从不verified也从不二次投影。Lint的Report.Basis硬编码为engine.BasisInferredshrink/shrink.go#L183TestLintReportsInferredReductionsshrink/shrink_test.go#L211-L230验证两个工具各自有名、总量确有下降。reversible for real如上节所述持久 store、先提交后发布、跨进程可解析store 不可用时宁可报 error 也不发 handle。ratio 的计算口径也值得说明ratio(before, after) (before-after)/before且当after before时直接记 0shrink/shrink.go#L326-L331——ratio 永远不会是负数压不动与没压在报告里是同一个信号0。小结caveman-shrink 用很小的表面一个库文件 一个 CLI 一个 npm shim实现了工具目录压缩的完整产品语义压缩决策全部委托给 engine 的toolschema压缩器产品层负责存储寻址CAVEMAN_CCR_DB/~/.caveman/ccr.db、有界输入32 MiB、fail-open 直通和跨进程可逆恢复。它的两条正确性边界——结构选择面不变量与偏向 over-keep 的参数构造保真——分别由SelectionProfile对比测试和约束句保留测试钉死而全部数字都是 inferred的口径则避免了结构检查被误读为行为等价。相关深入阅读路径shrink/CLAUDE.md、shrink/README.md、engine/CLAUDE.md、engine/compressors/toolschema.go、shrink/shrink_test.go。【免费下载链接】caveman why use many token when few token do trick — Claude Code skill that cuts 65% of tokens by talking like caveman项目地址: https://gitcode.com/GitHub_Trending/caveman1/caveman创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考