关于 adversarial-swift
adversarial-swift 是面向 Swift 代码审查的技能,供需要一致通过/失败结论的团队和 Agent 使用。它由单个盲审者依据代码证据评估规则,只给出结论,不修改代码。
主要功能
- 01单个盲审者给出结论
- 02并发与任务结构检查
- 03属性与错误处理检查
- 04枚举、API 和集合检查
- 05固定目标的审查流程
适用场景
- 01合并前检查 Swift PR
- 02审查 Agent 编写的 Swift 代码
- 03检查旧版 Swift 的现代化改造
- 04将审查结论与修复工作分开
安装
复制下面的命令,在终端中运行。
npx skills add https:/ / github.com/ pproenca/ dot-skills --skill adversarial-swift安装后在 Claude Code 中输入/adversarial-swift确认已加载。
包含的文件
除 SKILL.md 外,安装时一起下载的参考资料和脚本。
gotchas.mdmetadata.jsonassets/templates/verdict.mdreferences/_sections.mdapi-autoclosure-conditional-params.mdapi-final-or-private-classes.mdapi-memberwise-init-via-extension.mdapi-never-for-nonreturning-paths.mdapi-opaque-return-over-concrete-nesting.mdapi-optionset-over-boolean-rows.mdapi-unavailable-on-fatalerror-stubs.mdcoll-count-where-over-filter-count.mdcoll-dictionary-default-subscript.mdcoll-mapvalues-value-only-transforms.mdcoll-optional-chaining-in-place-mutation.mdcoll-reduce-into-accumulators.mdconc-async-let-for-independent-awaits.mdconc-check-cancellation-in-loops.mdconc-concurrent-offload-under-mainactor-default.mdconc-resume-continuation-every-path.mdconc-taskgroup-for-dynamic-fanout.mdenum-caseiterable-over-hand-lists.mdenum-caseless-namespaces.mdenum-derived-comparable-declaration-order.mdenum-unknown-default-external-enums.mderr-callsite-location-default-args.mderr-preserve-underlying-error.mderr-result-get-over-manual-switch.mderr-rethrows-for-closure-only-throws.mderr-warning-directive-for-pending-work.md详细介绍
对抗式 Swift 门禁
Swift 语言审查门禁——通过/失败:由一个盲审子 Agent 根据本门禁的规则作出判断,并以对抗式审查为原则;只有每条规则都为 PASS 或 N/A,工作才算通过。此技能只给出裁定,绝不修复工作。
规则经过筛选,仅包含审查者能够单凭代码证据作出判断的检查项。本门禁针对 Agent 和经验丰富但尚非专家的开发者实际会造成的故障模式:导致挂起的 continuation、忽略取消的循环、串行执行的独立 await、手动同步的派生状态、被丢弃的底层错误、逐渐失效的手动维护案例列表、布尔参数行、O(n²) 集合累积,以及会在切片上导致错误的索引运算。
何时应用
- Swift diff、功能或 PR 即将合并,需要客观的 PASS/FAIL,而非建议性反馈——适用于任何目标:应用逻辑、服务端 Swift、CLI 工具、软件包。
- 代码由 Agent(Claude、Codex)编写,你希望进行独立检查,确认它没有重现典型的并发与错误处理故障模式(未恢复的 continuation 分支、伪装成取消检查的
try? await Task.sleep、抛出不含负载的领域错误的catch代码块),也没有手动实现编译器会合成的内容(CaseIterable、Comparable、成员初始化器、确定初始化检查)。 - 正在对并发前时代或 Objective-C 时代的 Swift 进行现代化改造,需要依据当前语言功能审查移植后的代码范围(
@unknown default、rethrows、canImport、reduce(into:)、count(where:)、String(validating:))。
不要应用于非 Swift 代码库(审查提示词的前置条件会中止并显示 “GATE NOT APPLICABLE”),也不要在用户想要解释和重构而非裁定时应用。SwiftUI 专项审查(状态所有权、视图标识、更新开销、任务生命周期、列表、无障碍)完全由姊妹门禁 adversarial-swift-ui 负责;本门禁的规则与框架无关,可与之同时应用。若规则的补救措施需要的工具链版本高于项目所用版本,则应标记为 N/A,而非 FAIL——审查提示词中附有版本门禁表。
审查流程
请严格遵循以下步骤——本门禁的价值在于每次审查都采用相同流程。
步骤 1 之前有两项前置条件——两者之所以存在,是因为违反它们属于本门禁系列记录在案的现场失败模式(2026 年 7 月:门禁被当作清理任务,在不断变化的目标上运行,diff 扩大到 33 个文件,却未产生任何裁定):
- 冻结目标。 只能针对固定的引用进行派发——提交 SHA、stash 或已保存的 diff,并将其记录为目标清单。如果待审代码仍在变化(工作树持续收到修改,或其他 Agent 仍在操作),则不要派发。审查进行期间目标发生变化,会使本次运行失效:以
GATE VOID — target changed替代裁定,并针对新的冻结状态重新派发。已派发的门禁必须始终以已呈现的裁定、GATE NOT APPLICABLE或已记录的作废状态结束——绝不能无声结束,因为这与“已审查”无法区分。 - 给出裁定,而非清理。 本门禁是对已完成工作的最终检查。“运行门禁并大力修复所有问题”颠倒了约定,也是已记录的范围失控路径:先完成实现,再冻结,然后运行门禁。出现 FAIL 后,调用方只在原始目标范围内应用修复;重新运行门禁时,针对同一目标清单派发新的盲审审查者——各轮之间审查范围绝不扩大;新增代码意味着必须发起新一轮门禁调用,并使用其独立的目标清单。
当其他 Agent 可能在审查期间修改工作区时,审查者应从不可变快照读取规则(例如,运行 git archive <ref> <skill-dir> | tar -x -C "$TMPDIR"),而非读取实时检出内容——技能目录属于只读基础设施,必须从所有清理或修复范围中排除。
- 确定目标。 明确指出审查对象(差异、一组文件或 PR),并记录引用和路径,确保审查针对一个明确且固定的目标。记录审查者提示词要求的技术栈事实:Swift 工具链版本(来自
Package.swift或项目设置)、目标的默认 Actor 隔离设置(默认是否为 MainActor——这决定conc-concurrent-offload-under-mainactor-default),以及任何可见的将警告视为错误设置或 TODO 检查器约定(为err-warning-directive-for-pending-work标明例外)。在目标描述中包含仓库根目录——enum-unknown-default-external-enums、prop-private-set-internal-mutation、prop-computed-over-stored-derived、enum-caseless-namespaces、api-final-or-private-classes和api-autoclosure-conditional-params需要在差异之外搜索声明模块、写入位置、实例化、子类和调用点。 - 加载规则。 阅读 references/_sections.md 和
references/中的每个规则文件(所有conc-*.md、prop-*.md、err-*.md、enum-*.md、api-*.md、coll-*.md、flow-*.md文件)。 - 编写审查者提示词。 将规则、目标和技术栈事实填入 references/reviewer-prompt.md。组合后的提示词必须完全自包含——审查者看不到对话历史,因此不得引用提示词之外的上下文。
- 派发一个盲审审查者。 启动一个 Task 子 Agent,其完整输入就是组合后的提示词——不要附带对话上下文或评论。
- 以失败关闭方式判定。 审查者的结构化输出就是裁决,不存在合并步骤。只有每条规则均为 PASS 或 N/A 时,总体裁决才是 PASS;任何一条 FAIL 都会导致门禁失败。绝不取平均、权衡严重程度或豁免规则——“轻微”的 FAIL 仍是 FAIL。如果审查者返回“GATE NOT APPLICABLE”(目标不是 Swift),则停止并报告该结果,而不是给出裁决。
- 生成裁决报告。 填写 assets/templates/verdict.md。若结果为 FAIL,将审查者提出的“满足 PASS 所缺内容”建议汇总到修复清单中,每项注明位置,并按类别重要性排序。每条最终结果为 FAIL 的规则都必须列入修复清单,并给出足够具体、可直接执行的修改——如果审查者的建议只是在复述违规内容,则在生成报告前根据规则的正确示例推导出修复方案。修复清单是用于核验的材料,证明每个 FAIL 都可判定且可翻转,而不是待办事项列表:每项修复都要指出在声明目标范围内可翻转该规则的最小修改;通过不安全的逃生手段(
@unchecked Sendable、try!、强制解包)满足规则的修复不能翻转结果。审查者在目标清单范围外发现的违规,列入裁决报告的范围外观察项——供未来门禁调用时报告,绝不能在本次调用中修复,也不能计入裁决。
如果同一规则在目标未变的多次复审中导致裁决反复翻转,或者人工阅读证据后推翻裁决,这就是规则的可判定性缺陷——将其记录到 gotchas.md 并完善规则;不要推翻门禁结果。
裁决格式
审查者须逐条规则返回:PASS | FAIL | N/A、证据(file:line 或引文——PASS 和 FAIL 都必须提供),并且对每条 FAIL,给出应用后可将该规则翻转为 PASS 的修复方案——注明具体修改及其位置,不能只是复述违规内容。最终报告遵循 assets/templates/verdict.md。
规则类别
| # | 类别 | 前缀 | 涵盖内容 |
|---|---|---|---|
| 1 | 并发与任务结构 | conc- | 确保续体在所有路径上恢复执行;在长循环中检查取消状态(用 try? 包装的休眠不算);对彼此独立的等待使用 async let;优先使用 TaskGroup,而不是为每个元素创建非结构化任务;在 MainActor 默认隔离下,对 CPU 工作使用 @concurrent |
| 2 | 属性与资源不变量 | prop- | 对派生值使用计算属性,而非存储属性;对内部修改的变量使用 private(set);使用 defer 处理会触发观察器的初始化赋值;当消耗性清理与 deinit 重复时使用 discard self |
| 3 | 错误处理与诊断 | err- | 包装错误时附上底层错误;仅在闭包抛错时使用 rethrows;优先使用 try result.get(),而非手动切换;将 #file/#line 设为默认参数;优先使用 #warning,而非随代码发布的 TODO 注释 |
| 4 | 枚举演进与穷尽性 | enum- | 对外部枚举优先使用 @unknown default;优先使用 CaseIterable,而非手动列举;优先使用合成的 Comparable,而非手写比较链;使用无用例枚举作为命名空间 |
| 5 | API 与类型表面 | api- | 通过扩展中的初始化器保留成员逐一初始化器;优先使用 OptionSet,而非布尔值数组;优先使用 some P,而非嵌套的具体类型返回值;使用 @available(*, unavailable) 占位实现;仅会触发陷阱的路径使用 -> Never;对门控参数使用 @autoclosure;使用 final/private 类进行静态派发 |
| 6 | 集合与字典 | coll- | 使用字典 default: 下标;使用可选链进行原地修改;使用 mapValues()、reduce(into:)、count(where:) |
| 7 | 控制流、字符串与条件编译 | flow- | 优先使用按分支赋值的 let,而非占位 var;优先使用 zip(indices,),而非通过 enumerated() 下标访问;对转义字符繁多的字面量使用原始字符串;对不可信字节使用 String(validating:);优先使用 canImport,而非 #if os 链;使用 Optional.take() 一次性取值 |
注意事项
派发审查者前,请先阅读 gotchas.md — 其中预先记录了源码忠实性保护规则(即源码材料认可、但社区经验认为不妥的模式,例如无类型的 throws 仍然是比类型化 throws 更推荐的默认选择),以及创建时预先标记为可判定性风险的规则,以免审查者引入外部规则,并能快速识别反复翻转的判定结果。
相关技能
adversarial-swift-ui— 负责所有 SwiftUI 架构审查(状态、标识、更新成本、任务生命周期、列表、辅助功能)的同级审查门;审查 SwiftUI 功能时请同时运行两者。ios-taste(精选)— 本审查门刻意排除的 iOS 设计判断指南;目标是审美判断而非给出判定结果时使用。search-ios26-docs/search-macos26-docs— 当版本门控问题决定某条规则是否成立时,用于核验当前 SDK 的 API 可用性。adversarial-ts-patterns/adversarial-zod/adversarial-tanstack— 面向 TypeScript 技术栈的同级审查门;协议相同,规则不同。
参考文件
| 文件 | 说明 |
|---|---|
| references/reviewer-prompt.md | 供盲审查者使用的独立提示词模板 |
| assets/templates/verdict.md | 判定报告模板 |
| references/_sections.md | 类别定义与顺序 |
| metadata.json | 版本与来源参考 |