fix(elixir): populate first_string_arg for Elixir calls - #1721
Conversation
tree-sitter-elixir attaches no field name to a call's arguments node. Its whole field set is key, left, operand, operator, quoted_start, quoted_end, right, target and value, so ts_node_child_by_field_name(node, "arguments") is always null for Elixir and call.first_string_arg was never populated for any Elixir call. Every downstream signal that keys off a call's string argument was therefore dead for Elixir: Phoenix route paths, HTTP/async service URLs, and config keys. Nothing reported an error — the field was simply always NULL. The definition side already knows this: extract_defs.c carries elixir_call_args() with a positional second-child fallback for exactly this reason. This adds the same fallback on the call side, gated to `call` nodes, since Elixir's other call kinds (`dot`, the `|>` binary_operator) carry no arguments node in that position. The new test pins the field directly rather than a downstream effect. Signed-off-by: Henry Hazan <henry@teramine.io>
|
Thanks for opening this — it has been seen, and it is queued. This note is automated, but it is not a brush-off: it exists so you know where your PR stands instead of having to guess from silence. Current review status: working through a backlog. What that means for this PR, concretely:
Things that will genuinely speed it up whenever review does happen:
If this fixes a bug, a reproduction we can run is worth more than a description of the symptom. Thanks for contributing, and sorry in advance for the wait. |
|
The build step succeeded; the guard script failed:
Five independent subprocess/daemon startups failing in one Windows job reads like a sick runner rather than a code defect. Why it should not be reachable from this diff:
Everything else on the PR is green: DCO, I do not have rerun rights on this repo — could a maintainer re-run that single job? Happy to push an empty commit to re-trigger instead if you would rather not spend the click, and equally happy to dig further if you have seen this guard fail for a real reason before. |
|
Reran the Windows guard job for you — and you were right that it is not your diff, so let me give you the mechanism rather than just agreeing.
The change itself is right, and the test is the good kind. What I want to credit specifically is I verified your premise too: Two things before I merge:
On your ordering question: yes, #1721 first. Nothing forces it, but your unopened defect 3 (Phoenix router macros minting no One heads-up that affects all three. Your production files are genuinely disjoint — Thank you for the tracking issue and for splitting this into four reviewable pieces instead of one large one — that is exactly how I would want a language's defects to arrive. |
|
Closing the loop: the Windows startup-coordination fix has merged as Notably it merged with |
The bug
tree-sitter-elixirattaches no field name to a call's arguments node. Its entire field set is:There is no
argumentsfield. Buthandle_calls()ininternal/cbm/extract_calls.creads exactly that:For Elixir this is always null, so
call.first_string_argwas never populated for any Elixir call — not once, in any file. Nothing errored; the field was simply alwaysNULL.Why it matters
Everything downstream that keys off a call's string argument was silently dead for Elixir:
get "/wallets", WalletController, :indexnever yielded a pathCBM_SVC_HTTP/CBM_SVC_ASYNCclassification needs the URL or topic literalApplication.get_env("...")is matched asCBM_SVC_CONFIG, which reads the same fieldThe fix
The definition side has always known about this.
extract_defs.ccarrieselixir_call_args()with a positional second-child fallback for precisely this reason:This adds the same fallback on the call side. It is gated to
callnodes, because Elixir's other call kinds —dot, and the|>binary_operator— carry no arguments node in that position and would otherwise pick up the operator token.Test
elixir_call_string_argumentpinsfirst_string_argdirectly rather than asserting a downstream effect, so it stays meaningful independently of route or service classification.Verification
make -f Makefile.cbm test-focused TEST_SUITES="extraction registry lang_contract grammar_regression grammar_labels repro_language_registry repro_call_node_manifest"→ 388 passed, 0 failedCBM_LANG_ELIXIRclang-format --dry-run --Werrorclean on the changed source.tests/was deliberately left unformatted, per the note that it is not inLINT_SRCSelixir-plug/plugand an 829-file Phoenix applicationScope
Submitted as a bug fix under the CONTRIBUTING exception for focused bug fixes and test additions, so there is no prior issue. Additions only — 54 lines, no deletions, no reformatting.
This is the first of four independent Elixir fixes found while auditing Elixir extraction against a real Phoenix codebase. The other three are prepared and gated separately, and I will open them one at a time rather than as a bundle:
first_string_argnever populatedargumentsfield again, plus a dispatch on adefnode type the grammar does not have)Routenodes (everyroute_reg_suffixesentry is prefixed.or::, but the macros are bare) — depends on this PR for the path argumentHappy to reorder, split further, or drop any of them if you would rather discuss the approach in an issue first.
🤖 Generated with Claude Code
https://claude.ai/code/session_01DpDDX9sFC16mQ9U9wQ3WNd