fix(ingestion): parse tsconfig.json as JSONC, not JSON - #2156
Closed
nickbrus wants to merge 1 commit into
Closed
Conversation
tsconfig.json is JSONC: tsc accepts // and /* */ and real configs carry
them. _parse_json_lenient tolerated trailing commas only, so a commented
root config raised, the error was swallowed at debug level, and the
resolver came up with zero path aliases.
Downstream that is silent and expensive. Every aliased import
("@/components/Button", "~/lib/x") is minted as an external: node instead
of an edge to the real file; the real file's in-degree stays 0; and the
dead-code analyzer, which credits a symbol or file only on an inbound
edge, reports it unreachable. On one TS monorepo with a single // comment
at line 76 of the root tsconfig, dead-code findings went from 618 to
1,288 -- 670 false rows, and 11 aliases (~/*, @/*, @assets/*, @styles/*,
@ui/* and friends) silently lost. Same symptom as #648, reached through
the config loader rather than the rebuild wiring.
The stripper is a hand-written scanner, not a regex: a regex cannot tell
a // inside a string literal ("url": "https://example.com") from a real
comment, and tsconfig files carry both. Candidates are tried
cheapest-first, so a plain JSON file still costs one json.loads and no
scanning, and an unparseable file now logs a clear reason instead of a
JSONDecodeError offset.
Tests: 10 cases in TestJsoncComments -- the four shapes tsc accepts, the
two traps a regex-based stripper falls into, two negatives, and one
end-to-end resolve through a commented config. Four of them fail on main.
7 tasks
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
tsconfig.jsonis JSONC —tscaccepts//and/* */, and real configs carry them.TsconfigResolver._parse_json_lenienttolerated trailing commas only, so a commented root config raised, the error was swallowed atlog.debug, and the resolver came up with zero path aliases.@/components/Button,~/lib/x) is minted as anexternal:node instead of an edge to the real file, the real file's in-degree stays 0, and the dead-code analyzer reports it unreachable.//inside a string literal ("url": "https://example.com") from a real comment, and tsconfig files carry both.What it looked like in the field
One TypeScript monorepo, one
//comment at line 76 of the roottsconfig.json:670 false rows from one comment. Eleven aliases were being silently lost —
~/*,@/*,@assets/*,@styles/*,@ui/*, two package roots and their wildcards, and two macro paths. Nothing surfaced: the only trace was onelog.debug("tsconfig_parse_failed", …).tsconfig_resolver.pyis byte-identical in 0.48.0, 0.49.0 andmain, so this is live onmaintoday.Related Issues
Same symptom as #648, reached through the config loader rather than the rebuild wiring. Not a duplicate — #648's path is fixed; this one is not.
Notes on the implementation
text→ trailing-comma strip → comment strip → both), so a plain JSON file still costs onejson.loadsand no scanning.JSONDecodeErrorbyte offset.Test Plan
TestJsoncCommentsintests/unit/ingestion/test_tsconfig_resolver.py— 10 cases:tscaccepts: plain JSON, trailing comma,//,/* */, and comment + trailing comma together;"https://example.com"and an escaped quote"a\"//b";None;resolve("@/components/Button", …)through a config with comments in it.Four of the ten fail on
mainbefore the change. Full file: 39 passed.pytest tests/unit/ingestion tests/unit/dead_code) — failure set identical tomainon the same machine, and +10 passingruff check,ruff format --checkon both touched files)Checklist