尧图精选

eslint-plugin-unicorn 规则详解:no-array-from-fill——用 `Array.from` 映射参数取代链式 `.fill()`

🕒 发布时间:2026/9/18 6:51:20 📁 来源:尧图网络
eslint-plugin-unicorn 规则详解no-array-from-fill——用Array.from映射参数取代链式.fill()【免费下载链接】eslint-plugin-unicornMore than 300 powerful ESLint rules项目地址: https://gitcode.com/GitHub_Trending/es/eslint-plugin-unicorn导读本文围绕 eslint-plugin-unicorn 中的no-array-from-fill规则展开结合规则文档 docs/rules/no-array-from-fill.md、规则实现 rules/no-array-from-fill.js、测试用例 test/no-array-from-fill.js 及其 AVA 快照报告 test/snapshots/no-array-from-fill.js.md系统梳理该规则禁止在Array.from({length: …})之后链式调用.fill()的完整判定逻辑、触发与放行边界、修复手法以及快照测试的运行机制。读完本文你将能准确理解该规则的底层实现知道哪些代码会被标记、哪些写法是安全的并能在自己的项目中正确配置与使用这条规则。规则速览报什么错、在哪启用no-array-from-fill的核心主张是用Array.from({length: …}, mapFunction)的第二个参数直接生成元素而不是先Array.from({length: …})再链式调用.fill()。规则元信息rules/no-array-from-fill.js声明如下元数据项值规则类型meta.typesuggestion规则描述Disallow.fill()afterArray.from({length: …})推荐级别docs.recommendedunopinionated支持语言meta.languagesjs/js仅 JavaScript消息 IDMESSAGE_IDno-array-from-fill报告消息Use the Array.from(…, mapFunction) argument instead of chaining .fill().规则文档头部docs/rules/no-array-from-fill.md说明该规则在recommended与unopinionated两个预设配置中启用规则本身在 rules/index.js 中被统一导出。为什么值得禁止.fill()之后的冗余与共享对象陷阱文档明确指出两条核心动机映射场景下.fill()纯属冗余。Array.from({length: 3}).fill().map((_, index) index)中.fill()只是先把数组填一遍随后map又把每个元素重新计算一遍等于做了无用功——Array.from的映射参数可以直接产出最终值。// ❌ 先 fill 再 mapfill 结果被完全覆盖 Array.from({length: 3}).fill().map((_, index) index); // ✅ 直接利用 Array.from 的 mapFunction 参数 Array.from({length: 3}, (_, index) index);.fill({})存在共享对象陷阱。Array.from({length: 3}).fill({})只会创建一个对象然后让数组的 3 个元素全部引用同一个实例如果后续修改了其中任一元素其他元素会同步受影响。若希望每个元素都是独立对象必须用工厂式的映射函数// ❌ 三个元素共享同一个对象 Array.from({length: 3}).fill({}); // ✅ 每个元素各自创建一个新对象 Array.from({length: 3}, () ({}));快照揭示的 12 个违规模式规则到底抓什么快照报告 test/snapshots/no-array-from-fill.js.md 由 AVA 测试框架为 test/no-array-from-fill.js 自动生成记录了全部 12 个 invalid 用例的输入与报告详情。所有用例的报告消息完全一致Use the Array.from(…, mapFunction) argument instead of chaining .fill().区别仅在错误定位报告节点是callExpression.callee.property见 rules/no-array-from-fill.js即.fill中的fill标识符本身因此下划线^^^^总是精确标注在fill上多行场景下则标注在换行后的.fill那一行。#输入invalid 用例错误定位1Array.from({length: 3}).fill(0).fill的fill2Array.from({length: 3}).fill().fill的fill3Array.from({length}).fill(null).fill的filllength简写属性4Array.from({length: 3}).fill(0).fill的fill字符串键5Array.from({length: 3}).fill({}).fill的fill6Array.from({length: 3}).fill(0).map((_, index) index).fill的fill链式后续调用不影响判定7Array.from({length: 3}).fill().map((value, index) index).fill的fill8Array.from({length: 3}).fill(0).flatMap((_, index) [index]).fill的fill9Array.from({length: 3}).fill().flatMap(value [value]).fill的fill10Array.from({length: 3}).fill(0).filter(Boolean).fill的fill11Array.from({length: 3})\n\t.fill(0)\n\t.map((_, index) index);第 2 行.fill的fill多行链式12Array.from(\n\t{length: 3}\n)\n\t.fill(0)\n\t.map((_, index) index);第 4 行.fill的fillArray.from内部也换行从快照可以提炼两个关键观察.fill()的参数多少不影响判定fill(0)、fill()、fill(null)、fill({})一律命中只要不超过 1 个实参见下文条件分析.fill()之后是否还有.map()/.flatMap()/.filter()链式调用也不影响判定规则只看是否在Array.from({length})的结果上直接调用.fill()一旦命中就报告快照用例 610、1112 均验证了这一点。源码级判定逻辑五个严格条件缺一不可规则实现rules/no-array-from-fill.js由两个判定函数 一个入口组成。第一步isArrayFromLengthCall——确认是数组字面量长度形式的Array.from该函数rules/no-array-from-fill.js要求同时满足是一个方法调用且为Array.from(...)对象名Array、方法名from复用插件最常用的 AST 工具 rules/ast/is-method-call.js该工具先按方法名快速过滤再做CallExpression与MemberExpression的形状校验实参数量恰为 1argumentsLength: 1不允许可选调用/可选成员optionalCall: false、optionalMember: falseArray必须是全局引用通过context.sourceCode.isGlobalReference(node.callee.object)校验确保没有被局部变量、形参遮蔽对照实现 rules/utils/is-global-identifier.js插件还提供isUnresolvedVariable作为隐式全局的补充判断唯一的实参必须是ObjectExpression且恰好只含 1 个属性该属性满足isLengthPropertyrules/no-array-from-fill.js非计算属性!property.computed非方法定义!property.methodkind init键名必须是length——可以是标识符length也可以是字符串字面量length。也就是说Array.from({length: 3})的语义是创建一个长度固定为 3、元素初始为undefined的数组这正是规则针对的固定长度数组模式。第二步isArrayFromFillCall——确认紧跟.fill()调用该函数rules/no-array-from-fill.js要求外层是方法调用方法名为fillfill的实参数量最多为 1maximumArguments: 1——因为fill(value, start, end)一旦传入起始/结束下标fill的行为就从整体填充变成了局部填充语义不再与Array.from的映射参数等价因此Array.from({length: 3}).fill(0, 1)会被放行同样不允许可选调用/可选成员其调用对象node.callee.object必须通过isArrayFromLengthCall的校验即.fill()必须直接挂在Array.from({length})的返回值上。第三步在CallExpression上报告入口函数rules/no-array-from-fill.js使用现代 ESLint 扁平规则 API 的context.on(CallExpression, …)监听所有函数调用命中isArrayFromFillCall后将报告节点指向callExpression.callee.property即fill标识符并携带messageId: no-array-from-fill。放行场景18 个 valid 用例揭示的边界快照对应的测试文件 test/no-array-from-fill.js 还提供了 18 个合法用例它们精确划定了规则的安全区。对照上述判定条件可归为几类类别合法用例示例放行原因根本没有.fill()Array.from({length: 3})无违规调用已经使用映射参数Array.from({length: 3}, (_, index) index)本身就是推荐写法只map不fillArray.from({length: 3}).map(...)无.fill()对象实参不是仅一个 length 属性Array.from({length: 3, 0: value}).fill(0)属性数 1不满足isLengthProperty约束对象实参不是普通字面量属性Array.from({...length}).fill(0)、Array.from({[length]: 3}).fill(0)展开语法/计算属性均被排除fill参数超过 1 个Array.from({length: 3}).fill(0, 1)、fill(0, 1, 2)maximumArguments: 1限制fill使用展开参数Array.from({length: 3}).fill(...value)参数数量无法静态确定存在可选链Array.from?.({length: 3}).fill(0)、Array.from({length: 3})?.fill(0)、Array.from({length: 3}).fill?.(0)optionalCall/optionalMember: false名称不匹配NotArray.from({length: 3}).fill(0)、Array.notFrom({length: 3}).fill(0)对象名/方法名不符.fill()未直接挂接Array.from({length: 3}).slice().fill(0)调用对象不是Array.from调用本身Array被局部遮蔽const Array {from() {...}}; Array.from(...).fill()...function unicorn(Array) { return Array.from({length: 3}).fill(0); }isGlobalReference校验失败最后一类尤其重要规则通过全局引用检查确保不会误伤那些自定义对象上恰好叫Array.from的方法——即便语法上完全匹配Array.from({length: 3}).fill(0)只要Array被局部变量、函数形参或导入遮蔽规则就保持沉默。测试与快照机制如何验证与更新该规则的测试采用 AVA 快照模式。在 test/no-array-from-fill.js 中通过getTester(import.meta)取得测试器然后调用test.snapshot({valid: [...], invalid: [...]})valid 数组内的代码要求零报错invalid 数组内的代码要求按预期报告而预期本身不手写而是由 AVA 首次运行时生成并保存。快照的产物有两个test/snapshots/no-array-from-fill.js.snapAVA 实际保存的快照数据含转义字符的原始文本test/snapshots/no-array-from-fill.js.md人类可读的 Markdown 版快照报告顶部标注Snapshot report fortest/no-array-from-fill.js、The actual snapshot is saved inno-array-from-fill.js.snap以及Generated by AVA。快照机制的价值在于报告消息文本、错误定位哪个节点、第几行、哪几列被下划线标注的任何细微变动都会被 AVA 捕捉并提示差异防止规则行为在重构中悄然漂移。若规则实现有意变更了报告内容开发者需要通过 AVA 的快照更新能力重新生成快照并人工审查 diff 后提交从而保证测试预期与实际行为永远一致。小结no-array-from-fill是一个典型的写法简化型规则它精准识别Array.from({length: …})之后直接链式.fill()的代码——判定条件严格到实参数量、属性形状、全局引用、可选链、直接挂接关系五重校验——并用Array.from(…, mapFunction)的映射参数给出等价且更优的替代写法。通过阅读规则源码rules/no-array-from-fill.js、规则文档docs/rules/no-array-from-fill.md与 AVA 快照test/snapshots/no-array-from-fill.js.md开发者可以完整掌握该规则的判定边界、放行策略与测试方法从而在实际工程中放心地启用它减少冗余调用并规避fill({})的共享对象陷阱。【免费下载链接】eslint-plugin-unicornMore than 300 powerful ESLint rules项目地址: https://gitcode.com/GitHub_Trending/es/eslint-plugin-unicorn创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
上一篇/下一篇内容由系统自动关联 返回资讯列表 →