Skip to content

Capture arrow functions and function expressions as chunks - #17

Merged
dakshcodez merged 3 commits into
mainfrom
fix-arrow-function-parsing
Aug 15, 2026
Merged

Capture arrow functions and function expressions as chunks#17
dakshcodez merged 3 commits into
mainfrom
fix-arrow-function-parsing

Conversation

@dakshcodez

Copy link
Copy Markdown
Owner

Summary

  • `JS_FAMILY_QUERY` previously only matched `function_declaration`, `class_declaration`, and `method_definition` - it silently skipped `const Foo = () => {...}` and `const Foo = function() {...}`, which are the dominant function-declaration style in modern TS/JS/React code.
  • A repo written mostly/entirely in arrow functions would parse to zero chunks and hit the "no parseable code" early return added in Always post a comment, even when there's nothing to do #16, even though the language is fully supported - this is the arrow-function gap flagged in that PR's commit message.
  • Extended the query to also capture `variable_declarator` nodes whose value is an `arrow_function` or `function_expression`, and updated `getChunkContainer` to unwrap the extra `variable_declarator -> lexical_declaration/variable_declaration` hop before checking for a wrapping `export_statement`, so exported arrow functions get correct signature/body/doc-comment text.
  • Rebuilt the Action's committed `dist/index.js` bundle so the fix is actually live in the published Action, not just in `packages/core`.

Test plan

  • `npm run lint` / `npm run typecheck` / `npm run build` all clean
  • Manual extraction (no test runner exists yet in this repo) against `.ts`, `.tsx`, and `.js` fixtures covering: plain/exported/async arrow functions, function expressions, class methods, destructuring assignments (correctly excluded), a non-function const (correctly excluded), and multiple declarators sharing one `const` (only the function-valued one becomes a chunk)
  • Confirmed the query still compiles for all three JS-family grammars (typescript, tsx, javascript)
  • Known, deliberate scope limit: class-field arrow functions (`class C { field = () => {} }`) are still not captured - same as before this change

const Foo = () => {...} and const Foo = function() {...} are the
dominant function-declaration style in modern TS/JS/React codebases,
but JS_FAMILY_QUERY only matched function_declaration/class_declaration/
method_definition - so a repo written entirely in arrow functions would
parse to zero chunks and hit the "no parseable code" early return,
even though the language is fully supported.

- queries.ts: add (variable_declarator value: (arrow_function)) and
  (variable_declarator value: (function_expression)) to JS_FAMILY_QUERY.
- extract.ts: getChunkContainer now unwraps the extra
  variable_declarator -> lexical_declaration/variable_declaration hop
  before checking for a wrapping export_statement, so exported arrow
  functions get correct signature/body/doc-comment text and the
  `export` keyword is preserved in the chunk body.

Verified via manual extraction against .ts/.tsx/.js fixtures (no test
runner exists yet in this repo): plain/exported/async arrow functions,
function expressions, class methods, and destructuring assignments all
resolve to the right kind/name; a non-function const and a destructured
assignment are correctly excluded. One known edge case: when multiple
declarators share one const/let (`const x = 1, fn = () => {}`), the
chunk's signature/body includes the whole shared declaration line -
acceptable since this pattern is uncommon for function definitions.
Class-field arrow functions (`class C { field = () => {} }`) remain
out of scope, same as before this change.
…tructuring patterns

Subagent review of the arrow-function chunk fix (this branch) found two
real issues beyond what the PR description disclosed:

1. Multi-declarator false-positive staleness + ambiguous embeddings.
   For `const a = 1, b = () => {}`, widening the container to the whole
   lexical_declaration meant every declarator on the line got an
   identical body/signature. Verified consequences: diffFileChunks
   reported byte-identical siblings as 'modified' whenever an unrelated
   sibling changed (false-positive staleness sent to the LLM), and
   chunkEmbeddingText produced indistinguishable vectors for distinct
   chunks (ambiguous doc-section linking). Fixed by only widening the
   container when the declaration has exactly one declarator
   (parent.namedChildCount === 1) - siblings now keep isolated,
   accurate bodies instead of bleeding into each other.

2. Destructuring patterns produced garbage chunk ids. `const { a, b }
   = () => {}` is syntactically legal but never meaningful in practice;
   variable_declarator's name field can be a destructuring pattern
   (unlike function_declaration/class_declaration, which never had
   this problem). Fixed with a nameNode.type !== 'identifier' guard.

Re-verified via manual extraction (no test runner in this repo yet)
against both new cases plus the full original fixture set - all still
resolve correctly, and packages/action/dist/index.js rebuilt to match.
@dakshcodez
dakshcodez merged commit 1b10072 into main Aug 15, 2026
1 of 2 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant