 到 onSelect():HumanLayer Skills 移除可选回调的完整实战指南)
从 onSelect?.() 到 onSelect()HumanLayer Skills 移除可选回调的完整实战指南【免费下载链接】skills项目地址: https://gitcode.com/GitHub_Trending/skills53/skillsHumanLayer Skillsskills53/skills是 HumanLayer 开源的 Claude Code 技能合集其中narrow-react-prop-types 技能专攻一个高频痛点把 React 组件中形如onSelect?.(...)的可选回调收窄为必须提供的onSelect(...)让 TypeScript 类型只描述真实运行代码的状态。本文将带你一步步了解这套移除可选回调的方法论。为什么onSelect?.()是类型腐化的信号在 React 项目中组件的 props 往往会随着 Storybook 故事、测试 mock、演示代码不断变宽。最典型的征兆就是组件接口里塞满了可选字段onSelect?、onArchive?、onRename?内部用onSelect?.(item)防御式调用生怕回调没传用items ?? []、count ?? 0兜底那些运行时代码里其实总是有值的 prop问题在于每一个可选回调都意味着组件必须额外处理一条分支。菜单项明明永远渲染点击却可能点了没反应——这就是可选回调制造出的死区状态。HumanLayer Skills 的核心理念是以真实业务调用方live code paths为唯一事实来源让类型尽可能严格把不可能表达的状态挡在类型系统之外。安装 narrow-react-prop-types 技能一键上手步骤安装非常简单在你的项目目录中执行npx skills add humanlayer/skills --skill narrow-react-prop-types然后在 Claude Code 中直接输入/narrow-react-prop-types即可启动技能。完整安装说明见 README.md。如果想 clone 整个仓库研究源码可使用git clone https://gitcode.com/GitHub_Trending/skills53/skills移除可选回调的 11 步工作流该技能的完整方法论定义在 SKILL.md共 11 个步骤可以概括为找 → 查 → 改 → 验四阶段1️⃣ 识别嫌疑组件技能列出了 5 类高危信号其中最核心的就是可选回调调用onSelect?.(...)、onArchive?.(...)和兜底状态处理items ?? []。 注意不要仅凭一个 story 或测试就锁定目标——故事和测试只能证明类型被放宽了不能证明某个状态是真实存在的。2️⃣ 穷举所有调用方并分类搜索组件及其导出类型的所有引用然后分成两类类别包含内容作用真实代码路径应用路由、providers、hooks、生产包导出✅ 决定 props 契约的唯一依据支撑代码Storybook、测试、fixtures、mock⚠️ 只作辅助证据3️⃣ 逐个 prop 判定必填、可选还是删除这是移除可选回调的关键判据必填所有非测试、非 Storybook 调用方都传了这个 prop可选至少一个真实调用方没传且不传本身是有意义的运行时状态删除没有任何真实调用方使用它往往只是当年为 Storybook 加的一个容易混淆的细节可空 ≠ 可选。如果真实代码总是传值但值可能为空应写成必填的可空 propfocusedItem: FocusedItem | null而不是focusedItem?: FocusedItem | null。4️⃣ 收紧类型并由外向内传播这是本技能最精华的部分收紧不能只停在导出的组件上。如果父组件的 props 收窄后传给子组件的 handler 也总是有了那么子组件内部的onRename?.(id, name)就应直接改为必须调用onRename(id, name)技能还强调了一条铁律如果组件总是渲染一个可交互元素按钮、菜单项就必须要求对应的 handler 为必填——绝不允许出现看得见的按钮点了没反应的死区状态。5️⃣ 删除只为宽类型服务的兜底逻辑可选回调移除后一堆防御式代码会失去存在意义// 之前 new Set(expandedIds ?? defaultExpandedIds ?? []) // 之后 new Set(expandedIds)// 之前 items items.length 0 // 之后 items.length 06️⃣ 让测试和故事去适应真实代码收窄 props 后story 或测试报错了怎么办反向修复给故事补上真实合理的 handler 和状态而不是为了让测试省事把 prop 重新改成可选。如果测试配置变得啰嗦应创建测试辅助函数fixture来满足严格契约并把它留在支撑代码一侧。7️⃣ 类型检查验证最后对改动的包和所有消费方跑类型检查本技能在 monorepo 中推荐bun --bun run typecheck --filter package确保共享包与消费应用都通过编译。CI 自动化让 AI Agent 定时执行类型收窄这套技能不只用于手动执行HumanLayer 还把它做成了GitHub Actions 定时 Agent 工作流的模板位于 agent-narrow-component-props.yml。其运行机制非常巧妙⏰定时/手动模式cron 每天触发示例为0 13 * * *Agent 自动挑选一批高置信度的收窄改动开 PR/iterate迭代模式维护者在 Agent PR 下评论/iterate 反馈意见工作流会自动拉取 PR 上下文、评论与 Agent 记忆文件把反馈合并进提示词继续迭代实现人反馈 → AI 修正的闭环标准化 PR 报告每次运行按 response-template.md 输出结构化 PR 正文包含变更表格、支撑收窄的真实调用方清单、验证结果和风险评级其中 narrow-component-props-memory.md 是一个Agent 记忆文件沉淀历次运行中维护者给出的长期约束例如只改apps/riptide-ui不动apps/riptide-cloud让 AI 越跑越懂你的项目。避坑清单这些反模式千万别做SKILL.md 结尾整理了一份反模式清单建议收藏❌ 为了让 story 可以省略 handler把回调改成可选❌ 渲染一个调用onAction?.(...)的菜单项❌ 在真实代码是受控模式时为 Storybook 加default*props❌ 用?? []、?? 0掩盖本应由调用方保证的必填状态❌ 真实代码只用一种形态却兼容多种 API 形状配套的 Review Checklist 还有 10 项逐条核对项例如被删除的 prop 确实没有任何真实调用方使用空值语义只保留给真实状态如当前无焦点项。写在最后从onSelect?.()到onSelect()表面上只是删掉一个?背后却是完整的类型治理方法论以真实代码路径为准绳、类型尽量严格、兜底逻辑随宽类型一起删除、测试反向适配契约。这套技能对新手同样友好——你不需要先成为 TypeScript 类型专家只要跟随 SKILL.md 的 11 步工作流配合 marketplace.json 中声明的技能市场安装方式就能让项目的 React 组件契约一天天变得更干净。仓库里还有 improve-claude-md、show-me、design-control-loop 等技能值得一并探索。【免费下载链接】skills项目地址: https://gitcode.com/GitHub_Trending/skills53/skills创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考