Summary
An arrow function's destructured parameter keeps its default values:
export const dirGlob = ({ cwd, patterns, gitignore = true }: GlobOptions) => ...emits ({ cwd, patterns, gitignore = true }: GlobOptions) => ..., and TypeScript rejects an initializer in a declaration (TS2371); knip's util/glob does not parse for this reason. #3093 removed a parameter's own default and #3095 fixed destructured parameters of function declarations; an arrow function const goes through cleanParameterDefaults, which only looked for a default at the top level of a parameter.
Changes
A destructuring pattern with a type annotation now loses its defaults, as tsc writes it: { cwd, patterns, gitignore }: GlobOptions.
- Reading the pattern.
stripPatternDefaultsparses the pattern with a small grammar: names, string and number keys, nested patterns and rest elements, with defaults that are each a name, a number, a string,[]or{}. - What is left alone. Any other pattern (a default with an operator or a call, a computed key) is left as written. So is a pattern without a type, whose defaults are what give it its type.
- Lists without their own defaults. When no parameter has a default of its own, only such patterns are rewritten and the rest of the parameter list is kept as written; a list holding a
/or a template literal is left alone.
Testing
New test/arrow-destructuring-defaults.test.ts. Each of these is type-checked through a consumer with the existing runTsc helper; main fails these 6 cases:
- object and array patterns;
- a nested pattern with its own default;
- a pattern beside a parameter default;
- defaults that are names, numbers, strings,
[],{}and a member path, with a rest element; - two patterns around a generic type.
Fifteen more cases check that patterns it does not handle stay exactly as main writes them: comments, a regex, type arguments, a computed key, comparisons, nested templates, unannotated patterns, a sibling parameter with a comment or a template literal type.
bun test (Zig library built with the pinned Zig, so its tests run too), typecheck, lint and zig build test pass. Over 4,192 files from vue-core, vue-router, pinia and knip (LF and CRLF), the only output that changes is knip's util/glob, which now parses. Over 11,774 more from tailwindcss, stacks, eslint-plugin-vue and home, nothing changes.