Feat/ts optimizer package - #8872
Open
scottweaver wants to merge 1005 commits into
Open
Conversation
…QwikDev#186) * parity(OSS-410): JSX dev-info uses source-relative lineNumber/columnNumber Production correctness fix. JSX dev-info `lineNumber:` / `columnNumber:` emitted under Inline strategy + default-strategy segment-file paths were body-relative (computed from a wrapped parser input) instead of source- relative (relative to the original module file). SWC emits source-relative positions for the same fixtures. Two call sites parse a wrapped body before walking JSX: - `rewrite/inline-body.ts` — `const __body__ = ` + body - `segment-codegen.ts` — `(` + body + `)` Without conversion the JSX walker's `lineStarts` came from the wrapper, not the source. Threaded an opt-in `sourcePosition` on `devOptions` that carries the original source string + body's byte offset + wrapper prefix length. `getDevSourceSuffix` builds `lineStarts` from the original source and converts each `nodeStart` via `bodyOriginOffset + (nodeStart - wrapperPrefixLen)` before line/column lookup. Parent-rewrite path (which already passes the original module source as the walker's `source`) is unchanged — it omits `sourcePosition` and the legacy fast-path runs. Convergence baseline preserved (203/212). The 3 dev-info-emitting fixtures using these paths (`root_level_self_referential_qrl_inline`, `example_dev_mode_inlined`, `example_dev_mode`) continue to pass via the compareAst lineNumber/columnNumber normalizer — the snap test harness feeds an extra leading newline (deliberate compensation in `snapshot-parser.ts:167` for the SWC 1-indexed-BytePos vs TS 0-indexed offset impedance on `lo:`/`hi:`), which shifts our snap output by +1 line from SWC's. Filing a follow-up to unify the impedance (snap parser strip 2 `\n`s + lo emission +1) so the normalizer can be removed cleanly. Capture-induced body mutation (`injectCapturesUnpacking` prepending `const X = _captures[N];` to the body) is also out of scope here; the documented regression tests use no-capture bodies. The mutation-aware fix would need position tracking through the unpacking step. 6 focused regression tests at `tests/optimizer/oss-410-dev-info-line- number.test.ts` exercise the new behavior via direct `transformModule` calls (bypassing the snap harness): - Inline strategy: source-relative on single-line + multi-line bodies - Default strategy: source-relative on segment files - Column on first body line uses absolute source column - Non-dev mode emits no dev-info - Multiple JSX siblings each get distinct source-relative positions Baselines: convergence 203/212 unchanged, full suite 952/980 (+6 new tests from this PR). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * refactor(OSS-410): drop nested ternaries in devOptionsForCall builders Replace `devOptions ? sourceAvail ? {...} : devOptions : undefined` nested-ternary form with `let` + procedural `if` guard at both call sites (`rewrite/inline-body.ts`, `segment-codegen.ts`). Nested ternaries are hard to read; the `if`-block reads top-to-bottom. Type-alignment side change: `InlineSegmentJsxOptions.devOptions` and `SegmentJsxOptions.devOptions` were typed as the narrow `{ relPath: string }` literal — the ternary form coerced through structural widening, the `let` form preserves the variable's inferred type. Widened both fields to the canonical `DevSuffixOptions` (from `transform/jsx.ts`) so the spread `{ ...devOptionsForCall, sourcePosition: ... }` is the canonical shape end-to-end. No behavior change. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * docs(CBP): add "No nested ternaries" rule to CODING_BEST_PRACTICES.md Captures the convention enforced in the previous commit's refactor: at most one `?:` per expression; multi-condition branching uses `let` + procedural `if` block. Uses the OSS-410 `devOptionsForCall` builder as the worked example since that's what motivated the rule. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…-445 next (QwikDev#187) OSS-410 (JSX dev-info source-relative positions) shipped. Surface-only fix per ticket scope — convergence 203/212 unchanged; full suite 946 → 952 (+6 new regression tests). Pivoted mid-PR: nested-ternary `devOptionsForCall` builder refactored to procedural `let` + `if` form after user review; new CBP rule "No nested ternaries" added under `## Functions` + saved as `feedback_no_nested_ternaries` memory. Follow-up filed: OSS-445 — refactor `transformAllJsx` (14 positional args) via `JsxTransformContext` + new `TransformAllJsxOptions`. Closes the loop on OSS-374/375/376/377's parameter-reduction sweep. STATE.md's previous "queue closed" claim was wrong by one function. OPTIMIZER.md audit: no update needed — type-internal change (new opt-in `DevInfoSourcePosition` + `DevSuffixOptions` types only). +37-line drift on `transformAllJsx` cite under the 50-line threshold; deferred to a separate doc-only refresh PR. Main head: 6eeed30. Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…kDev#188) ## What changed `transformAllJsx` (`src/optimizer/transform/jsx.ts:793`) reduced from 14 positional args to 2 via the established `JsxTransformContext` / options split pattern. New exported types: - `TransformAllJsxInput` — the 4 required inputs (source, s, program, importedNames) that the orchestrator can't sensibly default. - `TransformAllJsxOptions` — the 10 configurable knobs (skipRanges, devOptions, keyCounterStart, enableSignals=true default, qpOverrides, qrlsWithCaptures, paramNames, relPath, sharedSignalHoister, precomputedScopeBindings). All 3 production call sites (`rewrite/index.ts`, `rewrite/inline-body.ts`, `segment-codegen.ts`) and 3 test call sites (`tests/optimizer/jsx- transform.test.ts`) updated. Behavior unchanged — the function body's destructuring restores the same locals; the walk is byte-identical. ## Why beneficial in isolation - 14 positional args at the call sites were unreadable and order- fragile. Each test call site was 4 args and looked fine — the prod call sites threaded 13-14 with multiple `undefined` placeholders. - The previous PR (OSS-410) needed to thread a new `sourcePosition` through dev-info; the natural slot was inside an options object, but 14 args forced inserting it as a nested field on `devOptions` instead. The next addition fits cleanly into `TransformAllJsxOptions` with no positional shuffling. - Brings the orchestrator in line with the sibling JSX-family functions that closed OSS-374/375/376/377: `transformJsxElement` (15→3), `transformJsxFragment` (9→2), `processChildren` (8→3), `processProps` (12→3). The orchestrator was the one function that escaped the sweep. ## Why foundation for future work - Closes the loop on OSS-374/375/376/377 properly. STATE.md's previous "queue closed" claim was wrong by one function; this PR finally makes it true. - Any future addition to `transformAllJsx`'s parameter list (e.g., the deferred OSS-410 follow-up that needs to thread snap-parser/lo- emission impedance through dev-info) becomes a one-line `TransformAllJsxOptions` field addition instead of a positional-arg insertion that touches every call site. - Removes the last inconsistency a future contributor would have to navigate — every JSX-family function is now context+options shaped. ## Risk - Pure mechanical refactor; no behavior change. - Baselines verified unchanged: convergence 203/212, full suite 952/980 (26 failing — same baseline). Typecheck clean. - Refactor surface narrow (5 files, 1 prod + 3 test refactor sites, 3 prod call site rewrites). Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…ameter-reduction arc fully closed (QwikDev#189) OSS-445 (transformAllJsx 14 args → 2 via input+options) shipped. Pure mechanical refactor; baselines preserved exactly (convergence 203/212 + full suite 952/980 unchanged). Closes OSS-374/375/376/377 properly — `transformAllJsx` was the orchestrator that escaped the May 2025 sweep; STATE.md's prior "queue closed" claim is now finally accurate. OPTIMIZER.md cite refreshes folded in: `transformAllJsx` (returned at jsx.ts:741 → :997, +256 lines past 50-line threshold); `JsxKeyCounter` (:618–638 → :670–690, +52 lines past threshold); adjacent `classifyConstness` (:476–605 → :513–642, +37 lines under threshold but refreshed for section consistency). No structural change (no phase / marker / convention / migration rule / entry strategy / ExtractionResult field). Main head: ff11938. Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…el capture analysis (QwikDev#190) Three foundational fixes from the F10 Sub-B audit for example_qwik_router_client. The fixture itself doesn't flip yet — two additional unblocking issues surfaced during impl that belong to separate code paths (migration of non-marker module- level helpers; scope-aware import DCE); filed as sub-issues of OSS-446. Bug 1 — peer-tool jsx() context-stack push (extract.ts): The walker already pushed tag + q-e:<event> naming context for JSX-syntax attributes; the peer-tool form `jsx('tag', { onProp$: $() })` was missing both. Now mirrors SWC's `handle_jsx` (transform.rs:1163–1188): tag literal/identifier pushed at the JSX-runtime CallExpression, and Property keys inside the tagged props ObjectExpression route through transformEventPropName for HTML tags (strip-`$` for components). Reuses collectJsxFunctionNamesFromIterable; idle when no JSX-runtime imports. Bug 2 — parent-module jsx() rewrite (rewrite/index.ts): OSS-379's transformJsxCalls was segment-only. Now also runs in the parent path as runPeerToolJsxCallTransform — a sibling of runJsxTransform that fires independently of the JSX-syntax `enableJsx` gate (the surfacing fixture's `.mjs` extension short-circuited runJsxTransform). Extends transformJsxCalls to accept skipRanges so jsx() calls inside extraction argument trees (segment-side codegen handles those) aren't double-transformed, and to permit SpreadElement entries in props — emitted inline in source order so compareAst's mergeJsxSplitProps + mergeGetVarConstProps normalisers collapse SWC's _jsxSplit(tag, varBag, constBag) into the same shape. Bug 3 — lexical scope chain for captures (capture-analysis.ts + transform/index.ts): analyzeCaptures' `parentScopeIdentifiers` previously used the enclosing extraction's body scope (when one wrapped this one) or module top-level scope (otherwise). Both miss decls from intermediate non-marker enclosing functions — a module-level arrow holding `useVisibleTask$(() => …)` dropped both its param and its body's consts from captures (runtime crash; the qwik_router_client `usePreventNavigateQrl` pattern). New buildClosureLexicalScopes walks the program with a function-scope stack and records the union of every enclosing scope at each closure's position; analyzeCaptures consumes that union unconditionally. Mirrors SWC's flattened `decl_stack` (transform.rs:986–991). Tests: 13 new regression tests across two files (oss-446-lexical-scope-captures.test.ts × 6; oss-446-jsx-call-naming.test.ts × 7); all green. Convergence baseline 203/212 + full suite 952 unchanged. Refs: OSS-446. Follow-ups: OSS-447 (migration for non-marker module-level helpers consumed only by segments), OSS-448 (scope-aware import DCE) — both required to flip example_qwik_router_client convergence. Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…oundation landed; convergence flip gated on OSS-447 + OSS-448 (QwikDev#191) PR QwikDev#190 merged at 8aaa782. OSS-446 remains In Progress (parent of OSS-447 + OSS-448) — the audit during impl surfaced two additional causes on separate code paths that block the example_qwik_router_client convergence flip: - OSS-447: migration policy for non-marker module-level helpers consumed by exactly one segment (the useQwikMockRouter case). - OSS-448: scope-aware import DCE in filterUnusedImports (the inner-shadow const { jsx } = … defeats the regex-based test). Both filed mid-impl per feedback_parity_audit_multi_root_cause. 18th confirmed case of that pattern. STATE.md edits: - Last updated bumped to reflect PR QwikDev#190 + the foundation work + the two follow-up sub-issues + the cite refreshes folded in here. - Current measurements row: head 8aaa782; baselines preserved exactly (convergence 203/212 + full suite 952/980 unchanged; +13 regression tests now in baseline). - Branches in flight `main` row rewritten for OSS-446 context. - Most recent meaningful progress: prepended OSS-446 entry, trimmed the 11-entry-old OSS-430 bullet (back to 10). - What to do next: shifted from "no active workstream" to OSS-447/448 as the active workstream; corrected the stale F10 Sub-B 3-sub-cluster hypothesis (C2/C3 don't exist; the real causes are now mapped to OSS-446 / OSS-447 / OSS-448). - Recently closed: prepended OSS-446 foundation entry (note OSS-446 itself stays In Progress). OPTIMIZER.md cite refreshes (drift past 50-line threshold from OSS-446 + cumulative from prior PRs): - extract.ts marker-call extraction block: :863–1022 → :962–1129 - extract.ts inlinedQrl detection: :600–745 → :815–961 - extract.ts ExtractionBase block: :63–186 → :67–186 - extract.ts field-table cites (origin/name/displayName/hash/ canonicalFilename/ctxKind/ctxName/loc): all shifted ~+99 lines - extract.ts disambiguateExtractions: :1155–1196 → :1254–1295 - rewrite/index.ts preConsolidateRawPropsCaptures: :394–428 → :491–540 - rewrite/index.ts resolveNesting: :452 → :458 No structural OPTIMIZER.md changes (no phase added/removed/renumbered, no new tool-surface convention name, no migration rule change, no entry strategy change, no ExtractionResult field change). capture-analysis.ts cites drifted under threshold (analyzeCaptures, collectScopeIdentifiers, captures, captureNames, paramNames) — left as-is. Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…s; rewrite ticket-tour prose WHY-anchored (QwikDev#192) * refactor(OSS-449): strip Linear ticket refs from extract.ts comments; rewrite ticket-tour prose WHY-anchored WHAT First file of the comment-cleanup sweep (OSS-449). Removes all 32 `OSS-XXX` references from src/optimizer/extract.ts. 3 comments deleted outright (pure ticket-tour stickers with no WHY content). 21 comments rewritten — sticker stripped, prose re-anchored on the invariant or constraint the code enforces rather than the historical PR that introduced it. SWC `transform.rs:...` cross-references kept (they reference files committed in the repo, not external trackers). WHY IN ISOLATION External readers of an OSS project can't follow `linear.app/kunai/...` URLs or `OSS-XXX` identifiers — those are internal-only. Stripping them makes comments self-contained and accessible to the file's actual audience (whoever opens it). The rewrite step beyond pure deletion is the WHY-not-WHAT cleanup. Pre-fix comments were a mix of "what we did" (`Pre-fix the filter excluded X; now it includes X`) and ticket-tour ("OSS-446 Bug 1: ..."), both of which decay as code evolves. Post-fix comments state the invariant or constraint that forced the code shape, which stays accurate across refactors. Examples: - "OSS-368 — deferred; populated on leave from activeSegmentBodies.bodyIds." → "Deferred; populated on leave from activeSegmentBodies.bodyIds." - "OSS-386: `loc` is documented as [byteStart, byteEnd] in OPTIMIZER.md ... this site previously emitted [line, col] (a pre-existing semantic mismatch, hidden because convergence's strict-compare skips loc)." → "`loc` carries byte offsets, not line/col — per OPTIMIZER.md's documented [byteStart, byteEnd] contract that snap fixtures also encode." WHY FOUNDATION First step in the OSS-449 sweep (estimated 35 files, 243 total refs). extract.ts is the top offender at 32 refs; getting it cleaned validates the bucket-classification approach (3 Delete / 21 Rewrite / 0 Keep across this file) before tackling segment-generation.ts (25 refs) + rewrite/index.ts (21 refs) + the rest. The WHY-not-WHAT memory (`feedback_comments_explain_why`) is now demonstrated end-to-end on a real file — establishes the bar for future comment writing across the codebase per the project rule encoded in CBP. RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean. - `pnpm vitest convergence --run` → 203/212 unchanged. - `pnpm vitest run` → full suite passes (no baseline regressions per `ci:baseline:check`). - `grep -rE "OSS-[0-9]+" src/optimizer/extract.ts | wc -l` → 0 (was 32). - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 211 (was 243). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * refactor(OSS-449): strip Linear refs from segment-generation.ts + rewrite/index.ts; rewrite ticket-tour prose WHY-anchored WHAT Second commit in the OSS-449 sweep. Files cleaned: - src/optimizer/transform/segment-generation.ts (was 25 refs → 0) - src/optimizer/rewrite/index.ts (was 21 refs → 0) 3 comments deleted outright (`See OSS-NNN.` trailing reference-only sentences with no WHY content). 40 comments rewritten — sticker stripped, prose re-anchored on the invariant or constraint the code enforces. SWC `transform.rs:NNN` references kept (they reference files committed in the repo, not external trackers). Local cross-references (`rewrite/inline-body.ts`, `buildElementCaptureMap`, etc.) kept. WHY IN ISOLATION Same rationale as the prior extract.ts commit (this sweep is OSS-449): external readers of an OSS project can't follow `linear.app/kunai/...` URLs or `OSS-XXX` identifiers, and ticket-tour prose paraphrases the code in ways that decay across refactors. Examples from this commit: - "OSS-432 Bug C: pre-compute the per-segment JSX-key starting counter in SOURCE order... Surfaced when Bug A + Bug B exposed the segment-side comparison previously masked by the parent mismatch." → strip the sticker AND drop the "Surfaced when Bug A + Bug B..." ticket-tour tail; keep "Pre-compute the per-segment JSX-key starting counter in SOURCE order, independent of the depth-first processing order used by the main loop below..." - "OSS-438 Fix B: propagate captures... (the original upstream-built map keyed by `<`-walk byte offsets had positions 524/630 while the walker saw 221/301)." → strip sticker AND drop the debugging-detail tail; keep the invariant: "Cross-phase positions are unreliable because every intervening `parseSync` overwrites the shared buffer." WHY FOUNDATION With extract.ts (32 refs), segment-generation.ts (25), and rewrite/index.ts (21) all clean, the top-3 offenders in src/ are done (78 of the original 243 refs). The bucket-classification approach has held up across 78 individual judgement calls without surfacing any production code where a Linear ticket reference was load-bearing enough to warrant a GitHub mirror — consistent with the OSS-449 prediction that prod Keeps would be exceedingly rare. The remaining ~165 refs are spread across 32 files (smaller per-file volumes; mechanical patterns). RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean - `pnpm vitest convergence --run` → 203/212 unchanged - `pnpm ci:baseline:check` → zero regressions; all 203 + 965 baseline passing tests still pass - `grep -rE "OSS-[0-9]+" src/optimizer/transform/segment-generation.ts | wc -l` → 0 (was 25) - `grep -rE "OSS-[0-9]+" src/optimizer/rewrite/index.ts | wc -l` → 0 (was 21) - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 165 (was 243) Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…-assembly.ts + inline-body.ts (batch 2) (QwikDev#193) * refactor(OSS-449): strip Linear ticket refs from extract.ts comments; rewrite ticket-tour prose WHY-anchored WHAT First file of the comment-cleanup sweep (OSS-449). Removes all 32 `OSS-XXX` references from src/optimizer/extract.ts. 3 comments deleted outright (pure ticket-tour stickers with no WHY content). 21 comments rewritten — sticker stripped, prose re-anchored on the invariant or constraint the code enforces rather than the historical PR that introduced it. SWC `transform.rs:...` cross-references kept (they reference files committed in the repo, not external trackers). WHY IN ISOLATION External readers of an OSS project can't follow `linear.app/kunai/...` URLs or `OSS-XXX` identifiers — those are internal-only. Stripping them makes comments self-contained and accessible to the file's actual audience (whoever opens it). The rewrite step beyond pure deletion is the WHY-not-WHAT cleanup. Pre-fix comments were a mix of "what we did" (`Pre-fix the filter excluded X; now it includes X`) and ticket-tour ("OSS-446 Bug 1: ..."), both of which decay as code evolves. Post-fix comments state the invariant or constraint that forced the code shape, which stays accurate across refactors. Examples: - "OSS-368 — deferred; populated on leave from activeSegmentBodies.bodyIds." → "Deferred; populated on leave from activeSegmentBodies.bodyIds." - "OSS-386: `loc` is documented as [byteStart, byteEnd] in OPTIMIZER.md ... this site previously emitted [line, col] (a pre-existing semantic mismatch, hidden because convergence's strict-compare skips loc)." → "`loc` carries byte offsets, not line/col — per OPTIMIZER.md's documented [byteStart, byteEnd] contract that snap fixtures also encode." WHY FOUNDATION First step in the OSS-449 sweep (estimated 35 files, 243 total refs). extract.ts is the top offender at 32 refs; getting it cleaned validates the bucket-classification approach (3 Delete / 21 Rewrite / 0 Keep across this file) before tackling segment-generation.ts (25 refs) + rewrite/index.ts (21 refs) + the rest. The WHY-not-WHAT memory (`feedback_comments_explain_why`) is now demonstrated end-to-end on a real file — establishes the bar for future comment writing across the codebase per the project rule encoded in CBP. RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean. - `pnpm vitest convergence --run` → 203/212 unchanged. - `pnpm vitest run` → full suite passes (no baseline regressions per `ci:baseline:check`). - `grep -rE "OSS-[0-9]+" src/optimizer/extract.ts | wc -l` → 0 (was 32). - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 211 (was 243). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * refactor(OSS-449): strip Linear refs from segment-generation.ts + rewrite/index.ts; rewrite ticket-tour prose WHY-anchored WHAT Second commit in the OSS-449 sweep. Files cleaned: - src/optimizer/transform/segment-generation.ts (was 25 refs → 0) - src/optimizer/rewrite/index.ts (was 21 refs → 0) 3 comments deleted outright (`See OSS-NNN.` trailing reference-only sentences with no WHY content). 40 comments rewritten — sticker stripped, prose re-anchored on the invariant or constraint the code enforces. SWC `transform.rs:NNN` references kept (they reference files committed in the repo, not external trackers). Local cross-references (`rewrite/inline-body.ts`, `buildElementCaptureMap`, etc.) kept. WHY IN ISOLATION Same rationale as the prior extract.ts commit (this sweep is OSS-449): external readers of an OSS project can't follow `linear.app/kunai/...` URLs or `OSS-XXX` identifiers, and ticket-tour prose paraphrases the code in ways that decay across refactors. Examples from this commit: - "OSS-432 Bug C: pre-compute the per-segment JSX-key starting counter in SOURCE order... Surfaced when Bug A + Bug B exposed the segment-side comparison previously masked by the parent mismatch." → strip the sticker AND drop the "Surfaced when Bug A + Bug B..." ticket-tour tail; keep "Pre-compute the per-segment JSX-key starting counter in SOURCE order, independent of the depth-first processing order used by the main loop below..." - "OSS-438 Fix B: propagate captures... (the original upstream-built map keyed by `<`-walk byte offsets had positions 524/630 while the walker saw 221/301)." → strip sticker AND drop the debugging-detail tail; keep the invariant: "Cross-phase positions are unreliable because every intervening `parseSync` overwrites the shared buffer." WHY FOUNDATION With extract.ts (32 refs), segment-generation.ts (25), and rewrite/index.ts (21) all clean, the top-3 offenders in src/ are done (78 of the original 243 refs). The bucket-classification approach has held up across 78 individual judgement calls without surfacing any production code where a Linear ticket reference was load-bearing enough to warrant a GitHub mirror — consistent with the OSS-449 prediction that prod Keeps would be exceedingly rare. The remaining ~165 refs are spread across 32 files (smaller per-file volumes; mechanical patterns). RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean - `pnpm vitest convergence --run` → 203/212 unchanged - `pnpm ci:baseline:check` → zero regressions; all 203 + 965 baseline passing tests still pass - `grep -rE "OSS-[0-9]+" src/optimizer/transform/segment-generation.ts | wc -l` → 0 (was 25) - `grep -rE "OSS-[0-9]+" src/optimizer/rewrite/index.ts | wc -l` → 0 (was 21) - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 165 (was 243) Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * refactor(OSS-449): strip Linear refs from transform/index.ts + rewrite/output-assembly.ts + rewrite/inline-body.ts; rewrite ticket-tour prose WHY-anchored WHAT Second batch in the OSS-449 sweep. Files cleaned: - src/optimizer/transform/index.ts (was 19 refs → 0) - src/optimizer/rewrite/output-assembly.ts (was 18 refs → 0) - src/optimizer/rewrite/inline-body.ts (was 14 refs → 0) 2 trailing-only `See OSS-NNN.` references deleted. 46 sticker-strip rewrites — each comment's WHY-anchored prose preserved (or refined where it was tangled with ticket-tour fragments). Several brittle line references (`extract.ts:696`, `rewrite/index.ts:657`, etc.) and a few fixture-specific tail clauses (`preserves example_dev_mode_inlined etc.`, `(example_strip_client_code)`) dropped during the rewrites — those decay as code evolves and add no invariant content. WHY IN ISOLATION Same as the first OSS-449 batch (commit d1318fe + 65363b8): external readers of an OSS project can't follow `linear.app/kunai/...` URLs or `OSS-XXX` identifiers, and ticket-tour prose paraphrases the code in ways that decay across refactors. Examples from this batch: - "OSS-407 Fix A: when body is a bare identifier... (see OSS-407 Fix C in placeSCalls)." → strip both refs; keep "When body is a bare identifier referring to a module-level decl... see the forward-dep handling in `placeSCalls`." - "OSS-408 Fix A: previously skipped inlinedQrl extractions on the grounds that 'the name was set explicitly by the upstream tool'; but SWC ALSO renames them under prod..." → strip the "previously skipped" ticket-tour framing; restate as the invariant: "SWC renames inlinedQrl extractions under prod... preserving the hash suffix so runtime QRL resolution still matches." WHY FOUNDATION Combined with the first batch's top-3 offenders (PR QwikDev#192), this PR brings the OSS-449 sweep to 129 of the original 243 refs cleaned (53%). Remaining 114 refs spread across 32 smaller-volume files — mechanical patterns established by this point should make subsequent batches faster per file. RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean - `pnpm vitest convergence --run` → 203/212 unchanged - `pnpm ci:baseline:check` → zero regressions; all 203 + 965 baseline tests still pass - `grep -rE "OSS-[0-9]+" src/optimizer/transform/index.ts | wc -l` → 0 (was 19) - `grep -rE "OSS-[0-9]+" src/optimizer/rewrite/output-assembly.ts | wc -l` → 0 (was 18) - `grep -rE "OSS-[0-9]+" src/optimizer/rewrite/inline-body.ts | wc -l` → 0 (was 14) - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 114 (was 165) Stacked on top of PR QwikDev#192 (refactor/OSS-449-comment-cleanup-extract). Will rebase onto main once QwikDev#192 merges. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…-call-transform.ts + signal-analysis.ts + segment-codegen.ts + jsx-props.ts (batch 3) (QwikDev#194) * refactor(OSS-449): strip Linear ticket refs from extract.ts comments; rewrite ticket-tour prose WHY-anchored WHAT First file of the comment-cleanup sweep (OSS-449). Removes all 32 `OSS-XXX` references from src/optimizer/extract.ts. 3 comments deleted outright (pure ticket-tour stickers with no WHY content). 21 comments rewritten — sticker stripped, prose re-anchored on the invariant or constraint the code enforces rather than the historical PR that introduced it. SWC `transform.rs:...` cross-references kept (they reference files committed in the repo, not external trackers). WHY IN ISOLATION External readers of an OSS project can't follow `linear.app/kunai/...` URLs or `OSS-XXX` identifiers — those are internal-only. Stripping them makes comments self-contained and accessible to the file's actual audience (whoever opens it). The rewrite step beyond pure deletion is the WHY-not-WHAT cleanup. Pre-fix comments were a mix of "what we did" (`Pre-fix the filter excluded X; now it includes X`) and ticket-tour ("OSS-446 Bug 1: ..."), both of which decay as code evolves. Post-fix comments state the invariant or constraint that forced the code shape, which stays accurate across refactors. Examples: - "OSS-368 — deferred; populated on leave from activeSegmentBodies.bodyIds." → "Deferred; populated on leave from activeSegmentBodies.bodyIds." - "OSS-386: `loc` is documented as [byteStart, byteEnd] in OPTIMIZER.md ... this site previously emitted [line, col] (a pre-existing semantic mismatch, hidden because convergence's strict-compare skips loc)." → "`loc` carries byte offsets, not line/col — per OPTIMIZER.md's documented [byteStart, byteEnd] contract that snap fixtures also encode." WHY FOUNDATION First step in the OSS-449 sweep (estimated 35 files, 243 total refs). extract.ts is the top offender at 32 refs; getting it cleaned validates the bucket-classification approach (3 Delete / 21 Rewrite / 0 Keep across this file) before tackling segment-generation.ts (25 refs) + rewrite/index.ts (21 refs) + the rest. The WHY-not-WHAT memory (`feedback_comments_explain_why`) is now demonstrated end-to-end on a real file — establishes the bar for future comment writing across the codebase per the project rule encoded in CBP. RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean. - `pnpm vitest convergence --run` → 203/212 unchanged. - `pnpm vitest run` → full suite passes (no baseline regressions per `ci:baseline:check`). - `grep -rE "OSS-[0-9]+" src/optimizer/extract.ts | wc -l` → 0 (was 32). - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 211 (was 243). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * refactor(OSS-449): strip Linear refs from segment-generation.ts + rewrite/index.ts; rewrite ticket-tour prose WHY-anchored WHAT Second commit in the OSS-449 sweep. Files cleaned: - src/optimizer/transform/segment-generation.ts (was 25 refs → 0) - src/optimizer/rewrite/index.ts (was 21 refs → 0) 3 comments deleted outright (`See OSS-NNN.` trailing reference-only sentences with no WHY content). 40 comments rewritten — sticker stripped, prose re-anchored on the invariant or constraint the code enforces. SWC `transform.rs:NNN` references kept (they reference files committed in the repo, not external trackers). Local cross-references (`rewrite/inline-body.ts`, `buildElementCaptureMap`, etc.) kept. WHY IN ISOLATION Same rationale as the prior extract.ts commit (this sweep is OSS-449): external readers of an OSS project can't follow `linear.app/kunai/...` URLs or `OSS-XXX` identifiers, and ticket-tour prose paraphrases the code in ways that decay across refactors. Examples from this commit: - "OSS-432 Bug C: pre-compute the per-segment JSX-key starting counter in SOURCE order... Surfaced when Bug A + Bug B exposed the segment-side comparison previously masked by the parent mismatch." → strip the sticker AND drop the "Surfaced when Bug A + Bug B..." ticket-tour tail; keep "Pre-compute the per-segment JSX-key starting counter in SOURCE order, independent of the depth-first processing order used by the main loop below..." - "OSS-438 Fix B: propagate captures... (the original upstream-built map keyed by `<`-walk byte offsets had positions 524/630 while the walker saw 221/301)." → strip sticker AND drop the debugging-detail tail; keep the invariant: "Cross-phase positions are unreliable because every intervening `parseSync` overwrites the shared buffer." WHY FOUNDATION With extract.ts (32 refs), segment-generation.ts (25), and rewrite/index.ts (21) all clean, the top-3 offenders in src/ are done (78 of the original 243 refs). The bucket-classification approach has held up across 78 individual judgement calls without surfacing any production code where a Linear ticket reference was load-bearing enough to warrant a GitHub mirror — consistent with the OSS-449 prediction that prod Keeps would be exceedingly rare. The remaining ~165 refs are spread across 32 files (smaller per-file volumes; mechanical patterns). RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean - `pnpm vitest convergence --run` → 203/212 unchanged - `pnpm ci:baseline:check` → zero regressions; all 203 + 965 baseline passing tests still pass - `grep -rE "OSS-[0-9]+" src/optimizer/transform/segment-generation.ts | wc -l` → 0 (was 25) - `grep -rE "OSS-[0-9]+" src/optimizer/rewrite/index.ts | wc -l` → 0 (was 21) - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 165 (was 243) Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * refactor(OSS-449): strip Linear refs from transform/index.ts + rewrite/output-assembly.ts + rewrite/inline-body.ts; rewrite ticket-tour prose WHY-anchored WHAT Second batch in the OSS-449 sweep. Files cleaned: - src/optimizer/transform/index.ts (was 19 refs → 0) - src/optimizer/rewrite/output-assembly.ts (was 18 refs → 0) - src/optimizer/rewrite/inline-body.ts (was 14 refs → 0) 2 trailing-only `See OSS-NNN.` references deleted. 46 sticker-strip rewrites — each comment's WHY-anchored prose preserved (or refined where it was tangled with ticket-tour fragments). Several brittle line references (`extract.ts:696`, `rewrite/index.ts:657`, etc.) and a few fixture-specific tail clauses (`preserves example_dev_mode_inlined etc.`, `(example_strip_client_code)`) dropped during the rewrites — those decay as code evolves and add no invariant content. WHY IN ISOLATION Same as the first OSS-449 batch (commit d1318fe + 65363b8): external readers of an OSS project can't follow `linear.app/kunai/...` URLs or `OSS-XXX` identifiers, and ticket-tour prose paraphrases the code in ways that decay across refactors. Examples from this batch: - "OSS-407 Fix A: when body is a bare identifier... (see OSS-407 Fix C in placeSCalls)." → strip both refs; keep "When body is a bare identifier referring to a module-level decl... see the forward-dep handling in `placeSCalls`." - "OSS-408 Fix A: previously skipped inlinedQrl extractions on the grounds that 'the name was set explicitly by the upstream tool'; but SWC ALSO renames them under prod..." → strip the "previously skipped" ticket-tour framing; restate as the invariant: "SWC renames inlinedQrl extractions under prod... preserving the hash suffix so runtime QRL resolution still matches." WHY FOUNDATION Combined with the first batch's top-3 offenders (PR QwikDev#192), this PR brings the OSS-449 sweep to 129 of the original 243 refs cleaned (53%). Remaining 114 refs spread across 32 smaller-volume files — mechanical patterns established by this point should make subsequent batches faster per file. RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean - `pnpm vitest convergence --run` → 203/212 unchanged - `pnpm ci:baseline:check` → zero regressions; all 203 + 965 baseline tests still pass - `grep -rE "OSS-[0-9]+" src/optimizer/transform/index.ts | wc -l` → 0 (was 19) - `grep -rE "OSS-[0-9]+" src/optimizer/rewrite/output-assembly.ts | wc -l` → 0 (was 18) - `grep -rE "OSS-[0-9]+" src/optimizer/rewrite/inline-body.ts | wc -l` → 0 (was 14) - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 114 (was 165) Stacked on top of PR QwikDev#192 (refactor/OSS-449-comment-cleanup-extract). Will rebase onto main once QwikDev#192 merges. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * refactor(OSS-449): strip Linear refs from Tier 1 files (batch 3) WHAT Third batch in the OSS-449 sweep. Tier 1 files (≥8 refs each, 50 total): - src/optimizer/transform/jsx.ts (11 → 0) - src/optimizer/transform/jsx-call-transform.ts (11 → 0) - src/optimizer/signal-analysis.ts (11 → 0) - src/optimizer/segment-codegen.ts (9 → 0) - src/optimizer/transform/jsx-props.ts (8 → 0) 3 trailing-only `See OSS-NNN.` references deleted. 39 sticker-strip rewrites preserving the WHY-anchored prose. Several fixture-name tails (`example_strip_client_code`, `example_dev_mode`, `example_parsed_inlined_qrls`, `example_qwik_react_inline`) and brittle line refs dropped during the rewrites — those don't anchor invariants. One duplicate comment block in segment-codegen.ts:727-737 collapsed to a single comment (copy-paste artifact). WHY IN ISOLATION Same rationale as batch 1 (extract.ts, PR QwikDev#192) and batch 2 (transform/index.ts + rewrite/output-assembly.ts + rewrite/inline-body.ts, PR QwikDev#193): external readers can't follow `OSS-XXX` refs, and ticket-tour prose paraphrases code in ways that decay across refactors. Examples from this batch: - "OSS-417: root-identifier substitution and constant-subtree simplification share the orchestrator. OSS-418 dropped the OSS-414 paren-strip pass — raw-props no longer emits defensive parens at Property-value positions..." → strip all three refs; restate as the invariant: "raw-props doesn't emit defensive parens at Property-value positions — precedence-aware emission via `expressionNeedsParens` in `raw-props.ts` and `props-field-rewrite.ts` means the source slice the `_hf<n>_str` generator inherits is paren-free to begin with." - "Three semantic divergences from the pre-OSS-369 split:" → "Three semantic invariants this collector enforces:" — the divergence framing is ticket-tour (anchored to a particular code change); the bullets themselves are real invariants that survive refactors. WHY FOUNDATION Combined with PR QwikDev#192 + PR QwikDev#193, OSS-449 sweep is now at 179 of the original 243 refs cleaned (74%). Remaining 64 refs across 24 files (all ≤6 refs per file) — Tier 2 + Tier 3 batches close out the work. Pattern has been fully mechanical across 12 files now; no Keeps required for any production file (0 GH mirrors needed across 179 individual judgement calls). RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean - `pnpm vitest convergence --run` → 203/212 unchanged - `pnpm ci:baseline:check` → zero regressions; all 203 + 965 baseline tests still pass - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 64 (was 114) Stacked on top of PR QwikDev#193 (refactor/OSS-449-comment-cleanup-batch2). Will rebase onto main once QwikDev#192 + QwikDev#193 merge. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…kDev#195) * refactor(OSS-449): strip Linear ticket refs from extract.ts comments; rewrite ticket-tour prose WHY-anchored WHAT First file of the comment-cleanup sweep (OSS-449). Removes all 32 `OSS-XXX` references from src/optimizer/extract.ts. 3 comments deleted outright (pure ticket-tour stickers with no WHY content). 21 comments rewritten — sticker stripped, prose re-anchored on the invariant or constraint the code enforces rather than the historical PR that introduced it. SWC `transform.rs:...` cross-references kept (they reference files committed in the repo, not external trackers). WHY IN ISOLATION External readers of an OSS project can't follow `linear.app/kunai/...` URLs or `OSS-XXX` identifiers — those are internal-only. Stripping them makes comments self-contained and accessible to the file's actual audience (whoever opens it). The rewrite step beyond pure deletion is the WHY-not-WHAT cleanup. Pre-fix comments were a mix of "what we did" (`Pre-fix the filter excluded X; now it includes X`) and ticket-tour ("OSS-446 Bug 1: ..."), both of which decay as code evolves. Post-fix comments state the invariant or constraint that forced the code shape, which stays accurate across refactors. Examples: - "OSS-368 — deferred; populated on leave from activeSegmentBodies.bodyIds." → "Deferred; populated on leave from activeSegmentBodies.bodyIds." - "OSS-386: `loc` is documented as [byteStart, byteEnd] in OPTIMIZER.md ... this site previously emitted [line, col] (a pre-existing semantic mismatch, hidden because convergence's strict-compare skips loc)." → "`loc` carries byte offsets, not line/col — per OPTIMIZER.md's documented [byteStart, byteEnd] contract that snap fixtures also encode." WHY FOUNDATION First step in the OSS-449 sweep (estimated 35 files, 243 total refs). extract.ts is the top offender at 32 refs; getting it cleaned validates the bucket-classification approach (3 Delete / 21 Rewrite / 0 Keep across this file) before tackling segment-generation.ts (25 refs) + rewrite/index.ts (21 refs) + the rest. The WHY-not-WHAT memory (`feedback_comments_explain_why`) is now demonstrated end-to-end on a real file — establishes the bar for future comment writing across the codebase per the project rule encoded in CBP. RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean. - `pnpm vitest convergence --run` → 203/212 unchanged. - `pnpm vitest run` → full suite passes (no baseline regressions per `ci:baseline:check`). - `grep -rE "OSS-[0-9]+" src/optimizer/extract.ts | wc -l` → 0 (was 32). - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 211 (was 243). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * refactor(OSS-449): strip Linear refs from segment-generation.ts + rewrite/index.ts; rewrite ticket-tour prose WHY-anchored WHAT Second commit in the OSS-449 sweep. Files cleaned: - src/optimizer/transform/segment-generation.ts (was 25 refs → 0) - src/optimizer/rewrite/index.ts (was 21 refs → 0) 3 comments deleted outright (`See OSS-NNN.` trailing reference-only sentences with no WHY content). 40 comments rewritten — sticker stripped, prose re-anchored on the invariant or constraint the code enforces. SWC `transform.rs:NNN` references kept (they reference files committed in the repo, not external trackers). Local cross-references (`rewrite/inline-body.ts`, `buildElementCaptureMap`, etc.) kept. WHY IN ISOLATION Same rationale as the prior extract.ts commit (this sweep is OSS-449): external readers of an OSS project can't follow `linear.app/kunai/...` URLs or `OSS-XXX` identifiers, and ticket-tour prose paraphrases the code in ways that decay across refactors. Examples from this commit: - "OSS-432 Bug C: pre-compute the per-segment JSX-key starting counter in SOURCE order... Surfaced when Bug A + Bug B exposed the segment-side comparison previously masked by the parent mismatch." → strip the sticker AND drop the "Surfaced when Bug A + Bug B..." ticket-tour tail; keep "Pre-compute the per-segment JSX-key starting counter in SOURCE order, independent of the depth-first processing order used by the main loop below..." - "OSS-438 Fix B: propagate captures... (the original upstream-built map keyed by `<`-walk byte offsets had positions 524/630 while the walker saw 221/301)." → strip sticker AND drop the debugging-detail tail; keep the invariant: "Cross-phase positions are unreliable because every intervening `parseSync` overwrites the shared buffer." WHY FOUNDATION With extract.ts (32 refs), segment-generation.ts (25), and rewrite/index.ts (21) all clean, the top-3 offenders in src/ are done (78 of the original 243 refs). The bucket-classification approach has held up across 78 individual judgement calls without surfacing any production code where a Linear ticket reference was load-bearing enough to warrant a GitHub mirror — consistent with the OSS-449 prediction that prod Keeps would be exceedingly rare. The remaining ~165 refs are spread across 32 files (smaller per-file volumes; mechanical patterns). RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean - `pnpm vitest convergence --run` → 203/212 unchanged - `pnpm ci:baseline:check` → zero regressions; all 203 + 965 baseline passing tests still pass - `grep -rE "OSS-[0-9]+" src/optimizer/transform/segment-generation.ts | wc -l` → 0 (was 25) - `grep -rE "OSS-[0-9]+" src/optimizer/rewrite/index.ts | wc -l` → 0 (was 21) - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 165 (was 243) Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * refactor(OSS-449): strip Linear refs from transform/index.ts + rewrite/output-assembly.ts + rewrite/inline-body.ts; rewrite ticket-tour prose WHY-anchored WHAT Second batch in the OSS-449 sweep. Files cleaned: - src/optimizer/transform/index.ts (was 19 refs → 0) - src/optimizer/rewrite/output-assembly.ts (was 18 refs → 0) - src/optimizer/rewrite/inline-body.ts (was 14 refs → 0) 2 trailing-only `See OSS-NNN.` references deleted. 46 sticker-strip rewrites — each comment's WHY-anchored prose preserved (or refined where it was tangled with ticket-tour fragments). Several brittle line references (`extract.ts:696`, `rewrite/index.ts:657`, etc.) and a few fixture-specific tail clauses (`preserves example_dev_mode_inlined etc.`, `(example_strip_client_code)`) dropped during the rewrites — those decay as code evolves and add no invariant content. WHY IN ISOLATION Same as the first OSS-449 batch (commit d1318fe + 65363b8): external readers of an OSS project can't follow `linear.app/kunai/...` URLs or `OSS-XXX` identifiers, and ticket-tour prose paraphrases the code in ways that decay across refactors. Examples from this batch: - "OSS-407 Fix A: when body is a bare identifier... (see OSS-407 Fix C in placeSCalls)." → strip both refs; keep "When body is a bare identifier referring to a module-level decl... see the forward-dep handling in `placeSCalls`." - "OSS-408 Fix A: previously skipped inlinedQrl extractions on the grounds that 'the name was set explicitly by the upstream tool'; but SWC ALSO renames them under prod..." → strip the "previously skipped" ticket-tour framing; restate as the invariant: "SWC renames inlinedQrl extractions under prod... preserving the hash suffix so runtime QRL resolution still matches." WHY FOUNDATION Combined with the first batch's top-3 offenders (PR QwikDev#192), this PR brings the OSS-449 sweep to 129 of the original 243 refs cleaned (53%). Remaining 114 refs spread across 32 smaller-volume files — mechanical patterns established by this point should make subsequent batches faster per file. RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean - `pnpm vitest convergence --run` → 203/212 unchanged - `pnpm ci:baseline:check` → zero regressions; all 203 + 965 baseline tests still pass - `grep -rE "OSS-[0-9]+" src/optimizer/transform/index.ts | wc -l` → 0 (was 19) - `grep -rE "OSS-[0-9]+" src/optimizer/rewrite/output-assembly.ts | wc -l` → 0 (was 18) - `grep -rE "OSS-[0-9]+" src/optimizer/rewrite/inline-body.ts | wc -l` → 0 (was 14) - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 114 (was 165) Stacked on top of PR QwikDev#192 (refactor/OSS-449-comment-cleanup-extract). Will rebase onto main once QwikDev#192 merges. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * refactor(OSS-449): strip Linear refs from Tier 1 files (batch 3) WHAT Third batch in the OSS-449 sweep. Tier 1 files (≥8 refs each, 50 total): - src/optimizer/transform/jsx.ts (11 → 0) - src/optimizer/transform/jsx-call-transform.ts (11 → 0) - src/optimizer/signal-analysis.ts (11 → 0) - src/optimizer/segment-codegen.ts (9 → 0) - src/optimizer/transform/jsx-props.ts (8 → 0) 3 trailing-only `See OSS-NNN.` references deleted. 39 sticker-strip rewrites preserving the WHY-anchored prose. Several fixture-name tails (`example_strip_client_code`, `example_dev_mode`, `example_parsed_inlined_qrls`, `example_qwik_react_inline`) and brittle line refs dropped during the rewrites — those don't anchor invariants. One duplicate comment block in segment-codegen.ts:727-737 collapsed to a single comment (copy-paste artifact). WHY IN ISOLATION Same rationale as batch 1 (extract.ts, PR QwikDev#192) and batch 2 (transform/index.ts + rewrite/output-assembly.ts + rewrite/inline-body.ts, PR QwikDev#193): external readers can't follow `OSS-XXX` refs, and ticket-tour prose paraphrases code in ways that decay across refactors. Examples from this batch: - "OSS-417: root-identifier substitution and constant-subtree simplification share the orchestrator. OSS-418 dropped the OSS-414 paren-strip pass — raw-props no longer emits defensive parens at Property-value positions..." → strip all three refs; restate as the invariant: "raw-props doesn't emit defensive parens at Property-value positions — precedence-aware emission via `expressionNeedsParens` in `raw-props.ts` and `props-field-rewrite.ts` means the source slice the `_hf<n>_str` generator inherits is paren-free to begin with." - "Three semantic divergences from the pre-OSS-369 split:" → "Three semantic invariants this collector enforces:" — the divergence framing is ticket-tour (anchored to a particular code change); the bullets themselves are real invariants that survive refactors. WHY FOUNDATION Combined with PR QwikDev#192 + PR QwikDev#193, OSS-449 sweep is now at 179 of the original 243 refs cleaned (74%). Remaining 64 refs across 24 files (all ≤6 refs per file) — Tier 2 + Tier 3 batches close out the work. Pattern has been fully mechanical across 12 files now; no Keeps required for any production file (0 GH mirrors needed across 179 individual judgement calls). RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean - `pnpm vitest convergence --run` → 203/212 unchanged - `pnpm ci:baseline:check` → zero regressions; all 203 + 965 baseline tests still pass - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 64 (was 114) Stacked on top of PR QwikDev#193 (refactor/OSS-449-comment-cleanup-batch2). Will rebase onto main once QwikDev#192 + QwikDev#193 merge. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * refactor(OSS-449): strip Linear refs from Tier 2 files (batch 4) WHAT Fourth batch in the OSS-449 sweep. Tier 2 files (4–6 refs each, 37 total): - src/optimizer/transform/event-capture-promotion.ts (6 → 0) - src/optimizer/transform/jsx-elements-core.ts (5 → 0) - src/optimizer/transform/diagnostic-detection.ts (5 → 0) - src/optimizer/rewrite/raw-props.ts (5 → 0) - src/optimizer/utils/range-replace.ts (4 → 0) - src/optimizer/types/brands.ts (4 → 0) - src/optimizer/rewrite/symbol-collision.ts (4 → 0) - src/optimizer/rewrite/rewrite-context.ts (4 → 0) All sticker-strips with WHY-anchored prose preserved. Several fixture-name tails (`example_strip_client_code`, `issue_7216_add_test`, `example_props_optimization`, `example_spread_jsx`) and ticket-tour fragments ("validated against...", "the case we hit during OSS-384's call-site sweep", "tracked as a follow-up") dropped — those don't anchor invariants. Comparison tables and historical context were preserved where they're genuinely load-bearing (e.g. `range-replace.ts`'s caller table, the `brands.ts` HASH_SHAPE rationale). WHY IN ISOLATION Same rationale as the prior three batches (PRs QwikDev#192, QwikDev#193, QwikDev#194): external readers can't follow `OSS-XXX` refs, and ticket-tour prose paraphrases code in ways that decay across refactors. WHY FOUNDATION With this batch, the OSS-449 sweep is at 216 of the original 243 refs cleaned (89%). Remaining 27 refs across 16 small-volume files (Tier 3, mostly 1–3 refs each) — one more PR closes out the sweep. RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean - `pnpm vitest convergence --run` → 203/212 unchanged - `pnpm ci:baseline:check` → zero regressions; all 203 + 965 baseline tests still pass - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 27 (was 64) Stacked on PRs QwikDev#192 + QwikDev#193 + QwikDev#194. Will rebase onto main once the stack merges. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…oses OSS-449 (QwikDev#196) * refactor(OSS-449): strip Linear ticket refs from extract.ts comments; rewrite ticket-tour prose WHY-anchored WHAT First file of the comment-cleanup sweep (OSS-449). Removes all 32 `OSS-XXX` references from src/optimizer/extract.ts. 3 comments deleted outright (pure ticket-tour stickers with no WHY content). 21 comments rewritten — sticker stripped, prose re-anchored on the invariant or constraint the code enforces rather than the historical PR that introduced it. SWC `transform.rs:...` cross-references kept (they reference files committed in the repo, not external trackers). WHY IN ISOLATION External readers of an OSS project can't follow `linear.app/kunai/...` URLs or `OSS-XXX` identifiers — those are internal-only. Stripping them makes comments self-contained and accessible to the file's actual audience (whoever opens it). The rewrite step beyond pure deletion is the WHY-not-WHAT cleanup. Pre-fix comments were a mix of "what we did" (`Pre-fix the filter excluded X; now it includes X`) and ticket-tour ("OSS-446 Bug 1: ..."), both of which decay as code evolves. Post-fix comments state the invariant or constraint that forced the code shape, which stays accurate across refactors. Examples: - "OSS-368 — deferred; populated on leave from activeSegmentBodies.bodyIds." → "Deferred; populated on leave from activeSegmentBodies.bodyIds." - "OSS-386: `loc` is documented as [byteStart, byteEnd] in OPTIMIZER.md ... this site previously emitted [line, col] (a pre-existing semantic mismatch, hidden because convergence's strict-compare skips loc)." → "`loc` carries byte offsets, not line/col — per OPTIMIZER.md's documented [byteStart, byteEnd] contract that snap fixtures also encode." WHY FOUNDATION First step in the OSS-449 sweep (estimated 35 files, 243 total refs). extract.ts is the top offender at 32 refs; getting it cleaned validates the bucket-classification approach (3 Delete / 21 Rewrite / 0 Keep across this file) before tackling segment-generation.ts (25 refs) + rewrite/index.ts (21 refs) + the rest. The WHY-not-WHAT memory (`feedback_comments_explain_why`) is now demonstrated end-to-end on a real file — establishes the bar for future comment writing across the codebase per the project rule encoded in CBP. RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean. - `pnpm vitest convergence --run` → 203/212 unchanged. - `pnpm vitest run` → full suite passes (no baseline regressions per `ci:baseline:check`). - `grep -rE "OSS-[0-9]+" src/optimizer/extract.ts | wc -l` → 0 (was 32). - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 211 (was 243). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * refactor(OSS-449): strip Linear refs from segment-generation.ts + rewrite/index.ts; rewrite ticket-tour prose WHY-anchored WHAT Second commit in the OSS-449 sweep. Files cleaned: - src/optimizer/transform/segment-generation.ts (was 25 refs → 0) - src/optimizer/rewrite/index.ts (was 21 refs → 0) 3 comments deleted outright (`See OSS-NNN.` trailing reference-only sentences with no WHY content). 40 comments rewritten — sticker stripped, prose re-anchored on the invariant or constraint the code enforces. SWC `transform.rs:NNN` references kept (they reference files committed in the repo, not external trackers). Local cross-references (`rewrite/inline-body.ts`, `buildElementCaptureMap`, etc.) kept. WHY IN ISOLATION Same rationale as the prior extract.ts commit (this sweep is OSS-449): external readers of an OSS project can't follow `linear.app/kunai/...` URLs or `OSS-XXX` identifiers, and ticket-tour prose paraphrases the code in ways that decay across refactors. Examples from this commit: - "OSS-432 Bug C: pre-compute the per-segment JSX-key starting counter in SOURCE order... Surfaced when Bug A + Bug B exposed the segment-side comparison previously masked by the parent mismatch." → strip the sticker AND drop the "Surfaced when Bug A + Bug B..." ticket-tour tail; keep "Pre-compute the per-segment JSX-key starting counter in SOURCE order, independent of the depth-first processing order used by the main loop below..." - "OSS-438 Fix B: propagate captures... (the original upstream-built map keyed by `<`-walk byte offsets had positions 524/630 while the walker saw 221/301)." → strip sticker AND drop the debugging-detail tail; keep the invariant: "Cross-phase positions are unreliable because every intervening `parseSync` overwrites the shared buffer." WHY FOUNDATION With extract.ts (32 refs), segment-generation.ts (25), and rewrite/index.ts (21) all clean, the top-3 offenders in src/ are done (78 of the original 243 refs). The bucket-classification approach has held up across 78 individual judgement calls without surfacing any production code where a Linear ticket reference was load-bearing enough to warrant a GitHub mirror — consistent with the OSS-449 prediction that prod Keeps would be exceedingly rare. The remaining ~165 refs are spread across 32 files (smaller per-file volumes; mechanical patterns). RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean - `pnpm vitest convergence --run` → 203/212 unchanged - `pnpm ci:baseline:check` → zero regressions; all 203 + 965 baseline passing tests still pass - `grep -rE "OSS-[0-9]+" src/optimizer/transform/segment-generation.ts | wc -l` → 0 (was 25) - `grep -rE "OSS-[0-9]+" src/optimizer/rewrite/index.ts | wc -l` → 0 (was 21) - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 165 (was 243) Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * refactor(OSS-449): strip Linear refs from transform/index.ts + rewrite/output-assembly.ts + rewrite/inline-body.ts; rewrite ticket-tour prose WHY-anchored WHAT Second batch in the OSS-449 sweep. Files cleaned: - src/optimizer/transform/index.ts (was 19 refs → 0) - src/optimizer/rewrite/output-assembly.ts (was 18 refs → 0) - src/optimizer/rewrite/inline-body.ts (was 14 refs → 0) 2 trailing-only `See OSS-NNN.` references deleted. 46 sticker-strip rewrites — each comment's WHY-anchored prose preserved (or refined where it was tangled with ticket-tour fragments). Several brittle line references (`extract.ts:696`, `rewrite/index.ts:657`, etc.) and a few fixture-specific tail clauses (`preserves example_dev_mode_inlined etc.`, `(example_strip_client_code)`) dropped during the rewrites — those decay as code evolves and add no invariant content. WHY IN ISOLATION Same as the first OSS-449 batch (commit d1318fe + 65363b8): external readers of an OSS project can't follow `linear.app/kunai/...` URLs or `OSS-XXX` identifiers, and ticket-tour prose paraphrases the code in ways that decay across refactors. Examples from this batch: - "OSS-407 Fix A: when body is a bare identifier... (see OSS-407 Fix C in placeSCalls)." → strip both refs; keep "When body is a bare identifier referring to a module-level decl... see the forward-dep handling in `placeSCalls`." - "OSS-408 Fix A: previously skipped inlinedQrl extractions on the grounds that 'the name was set explicitly by the upstream tool'; but SWC ALSO renames them under prod..." → strip the "previously skipped" ticket-tour framing; restate as the invariant: "SWC renames inlinedQrl extractions under prod... preserving the hash suffix so runtime QRL resolution still matches." WHY FOUNDATION Combined with the first batch's top-3 offenders (PR QwikDev#192), this PR brings the OSS-449 sweep to 129 of the original 243 refs cleaned (53%). Remaining 114 refs spread across 32 smaller-volume files — mechanical patterns established by this point should make subsequent batches faster per file. RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean - `pnpm vitest convergence --run` → 203/212 unchanged - `pnpm ci:baseline:check` → zero regressions; all 203 + 965 baseline tests still pass - `grep -rE "OSS-[0-9]+" src/optimizer/transform/index.ts | wc -l` → 0 (was 19) - `grep -rE "OSS-[0-9]+" src/optimizer/rewrite/output-assembly.ts | wc -l` → 0 (was 18) - `grep -rE "OSS-[0-9]+" src/optimizer/rewrite/inline-body.ts | wc -l` → 0 (was 14) - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 114 (was 165) Stacked on top of PR QwikDev#192 (refactor/OSS-449-comment-cleanup-extract). Will rebase onto main once QwikDev#192 merges. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * refactor(OSS-449): strip Linear refs from Tier 1 files (batch 3) WHAT Third batch in the OSS-449 sweep. Tier 1 files (≥8 refs each, 50 total): - src/optimizer/transform/jsx.ts (11 → 0) - src/optimizer/transform/jsx-call-transform.ts (11 → 0) - src/optimizer/signal-analysis.ts (11 → 0) - src/optimizer/segment-codegen.ts (9 → 0) - src/optimizer/transform/jsx-props.ts (8 → 0) 3 trailing-only `See OSS-NNN.` references deleted. 39 sticker-strip rewrites preserving the WHY-anchored prose. Several fixture-name tails (`example_strip_client_code`, `example_dev_mode`, `example_parsed_inlined_qrls`, `example_qwik_react_inline`) and brittle line refs dropped during the rewrites — those don't anchor invariants. One duplicate comment block in segment-codegen.ts:727-737 collapsed to a single comment (copy-paste artifact). WHY IN ISOLATION Same rationale as batch 1 (extract.ts, PR QwikDev#192) and batch 2 (transform/index.ts + rewrite/output-assembly.ts + rewrite/inline-body.ts, PR QwikDev#193): external readers can't follow `OSS-XXX` refs, and ticket-tour prose paraphrases code in ways that decay across refactors. Examples from this batch: - "OSS-417: root-identifier substitution and constant-subtree simplification share the orchestrator. OSS-418 dropped the OSS-414 paren-strip pass — raw-props no longer emits defensive parens at Property-value positions..." → strip all three refs; restate as the invariant: "raw-props doesn't emit defensive parens at Property-value positions — precedence-aware emission via `expressionNeedsParens` in `raw-props.ts` and `props-field-rewrite.ts` means the source slice the `_hf<n>_str` generator inherits is paren-free to begin with." - "Three semantic divergences from the pre-OSS-369 split:" → "Three semantic invariants this collector enforces:" — the divergence framing is ticket-tour (anchored to a particular code change); the bullets themselves are real invariants that survive refactors. WHY FOUNDATION Combined with PR QwikDev#192 + PR QwikDev#193, OSS-449 sweep is now at 179 of the original 243 refs cleaned (74%). Remaining 64 refs across 24 files (all ≤6 refs per file) — Tier 2 + Tier 3 batches close out the work. Pattern has been fully mechanical across 12 files now; no Keeps required for any production file (0 GH mirrors needed across 179 individual judgement calls). RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean - `pnpm vitest convergence --run` → 203/212 unchanged - `pnpm ci:baseline:check` → zero regressions; all 203 + 965 baseline tests still pass - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 64 (was 114) Stacked on top of PR QwikDev#193 (refactor/OSS-449-comment-cleanup-batch2). Will rebase onto main once QwikDev#192 + QwikDev#193 merge. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * refactor(OSS-449): strip Linear refs from Tier 2 files (batch 4) WHAT Fourth batch in the OSS-449 sweep. Tier 2 files (4–6 refs each, 37 total): - src/optimizer/transform/event-capture-promotion.ts (6 → 0) - src/optimizer/transform/jsx-elements-core.ts (5 → 0) - src/optimizer/transform/diagnostic-detection.ts (5 → 0) - src/optimizer/rewrite/raw-props.ts (5 → 0) - src/optimizer/utils/range-replace.ts (4 → 0) - src/optimizer/types/brands.ts (4 → 0) - src/optimizer/rewrite/symbol-collision.ts (4 → 0) - src/optimizer/rewrite/rewrite-context.ts (4 → 0) All sticker-strips with WHY-anchored prose preserved. Several fixture-name tails (`example_strip_client_code`, `issue_7216_add_test`, `example_props_optimization`, `example_spread_jsx`) and ticket-tour fragments ("validated against...", "the case we hit during OSS-384's call-site sweep", "tracked as a follow-up") dropped — those don't anchor invariants. Comparison tables and historical context were preserved where they're genuinely load-bearing (e.g. `range-replace.ts`'s caller table, the `brands.ts` HASH_SHAPE rationale). WHY IN ISOLATION Same rationale as the prior three batches (PRs QwikDev#192, QwikDev#193, QwikDev#194): external readers can't follow `OSS-XXX` refs, and ticket-tour prose paraphrases code in ways that decay across refactors. WHY FOUNDATION With this batch, the OSS-449 sweep is at 216 of the original 243 refs cleaned (89%). Remaining 27 refs across 16 small-volume files (Tier 3, mostly 1–3 refs each) — one more PR closes out the sweep. RISK Comment-only edits — no behaviour change. Verified: - `pnpm typecheck` clean - `pnpm vitest convergence --run` → 203/212 unchanged - `pnpm ci:baseline:check` → zero regressions; all 203 + 965 baseline tests still pass - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 27 (was 64) Stacked on PRs QwikDev#192 + QwikDev#193 + QwikDev#194. Will rebase onto main once the stack merges. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * refactor(OSS-449): strip remaining Linear refs from Tier 3 files — closes OSS-449 WHAT Fifth and final batch in the OSS-449 sweep. Tier 3 files (1–3 refs each, 27 total): - src/hashing/siphash.ts (1 → 0) - src/optimizer/capture-analysis.ts (1 → 0) - src/optimizer/dev-mode.ts (1 → 0) - src/optimizer/path-utils.ts (3 → 0) - src/optimizer/rewrite/const-propagation.ts (1 → 0) - src/optimizer/rewrite/lib-mode-collapse.ts (1 → 0) - src/optimizer/rewrite/predicates.ts (1 → 0) - src/optimizer/segment-codegen/body-transforms.ts (2 → 0) - src/optimizer/segment-codegen/import-collection.ts (1 → 0) - src/optimizer/transform/module-cleanup.ts (1 → 0) - src/optimizer/transform/post-process.ts (3 → 0) - src/optimizer/types.ts (3 → 0) - src/optimizer/utils/jsx-import-source.ts (1 → 0) - src/optimizer/utils/props-field-rewrite.ts (2 → 0) - src/optimizer/utils/simplify.ts (3 → 0) - src/testing/ast-compare.ts (2 → 0) All sticker-strips. The Linear references in these files were mostly introducing prose with `OSS-NNN:` followed by load-bearing WHY content, or trailing parenthetical "(per OSS-NNN)" attribution. OSS-449 SWEEP CLOSED With this batch, the sweep has cleaned ALL 243 originally-found Linear references across the codebase: - PR QwikDev#192 (batch 1, top-3): extract.ts (32), segment-generation.ts (25), rewrite/index.ts (21) → 78 refs cleaned - PR QwikDev#193 (batch 2): transform/index.ts (19), output-assembly.ts (18), inline-body.ts (14) → 51 refs cleaned - PR QwikDev#194 (batch 3, Tier 1): jsx.ts (11), jsx-call-transform.ts (11), signal-analysis.ts (11), segment-codegen.ts (9), jsx-props.ts (8) → 50 refs cleaned - PR QwikDev#195 (batch 4, Tier 2): 8 files × 4–6 refs → 37 refs cleaned - This PR (batch 5, Tier 3): 16 files × 1–3 refs → 27 refs cleaned Total: 78 + 51 + 50 + 37 + 27 = 243 refs cleaned across 36 files. KEEP COUNT 243 individual judgement calls across the sweep. Zero production-code Keeps required — i.e. zero GH issue mirrors needed. The OSS-449 ticket predicted "exceedingly rare for prod" and the prediction held perfectly end-to-end. The Keep+mirror process is documented in the ticket and ready for any future case that arises but didn't fire here. VERIFIED CLEAN - `grep -rE "OSS-[0-9]+" src/ --include="*.ts" | wc -l` → 0 (was 243) - `grep -rE "linear\.app" src/ --include="*.ts" | wc -l` → 0 - `pnpm typecheck` clean - `pnpm vitest convergence --run` → 203/212 unchanged - `pnpm ci:baseline:check` → zero regressions OSS-449 acceptance criteria all met. Ready to close. Stacked on PRs QwikDev#192 + QwikDev#193 + QwikDev#194 + QwikDev#195. Will rebase onto main once the stack merges. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…stripped from src/ (QwikDev#197) Five OSS-449 PRs (QwikDev#192/QwikDev#193/QwikDev#194/QwikDev#195/QwikDev#196) merged in sequence today. Main at ce58ac2. Comment-only sweep across 36 files; convergence 203/212 + full suite 965/980 unchanged. STATE.md edits: - Last updated bumped to reflect the OSS-449 sweep + the OSS-446 follow-up context that carries over. - Current measurements row: head ce58ac2; baselines exact preservation; OSS-449 closed note. - Branches in flight `main` row rewritten for OSS-449 context + OSS-447/OSS-448 as the active workstream pickup. - Most recent meaningful progress: prepended OSS-449 entry (covers all 5 PRs as one logical sweep); trimmed the oldest OSS-431 bullet to keep the log at 10. - Recently closed: prepended OSS-449 entry. OPTIMIZER.md audit verdict: no update needed. The OSS-449 sweep touched many trigger-checklist files but the changes were strictly comment- text edits — no phase added/removed/renumbered, no new tool-surface convention, no migration rule change, no entry strategy change, no ExtractionResult field change. The cite refreshes are also unnecessary because none of the rewrites moved cited line numbers past the 50-line drift threshold. Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
QwikDev#198) Filed 2026-06-04 alongside the existing OSS-447 + OSS-448 follow-ups from the OSS-446 stack. Adds a second candidate workstream for any session picking up the project cold; the parity vs integration trade-off is explicit in the "What to do next" section. Tickets created: - OSS-450 (umbrella) — TS optimizer drop-in for qwik-bundler - OSS-451 (Sub-A) — Public API surface (src/index.ts + exports) - OSS-452 (Sub-B) — createOptimizer-compatible factory - OSS-453 (Sub-C) — preParsedProgram thread-through audit - OSS-454 (Sub-D) — Bundler-side opt-in adapter (qwik-bundler repo PR) - OSS-455 (Sub-E) — Parity smoke fixture Design choices locked at scoping time (per user direction): 1. Adapter lives in this repo (TS optimizer side) — API parity is the rewrite's responsibility, not the bundler's. 2. Reuse Rolldown's meta.ast — passes the bundler's OXC Program into the optimizer to skip the internal parse. Foundation in Sub-C, consumed in Sub-D. Also saved a project memory entry (project_qwik_bundler_integration) so future sessions surface the sub-goal before they hit STATE.md. Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…ev#199) Forward-looking architectural constraint: Yuku (https://github.com/yuku-toolchain/yuku) is a planned future drop-in alternative to OXC for the bundler's parser. Yuku promises ESTree/TS-ESTree output matching OXC's shape, so the swap should be transparent — but only if the optimizer's external AST input contract stays parser-agnostic. Captured as the third locked design choice on the OSS-450 umbrella ("parser-agnostic AST input contract"); also pinned via: - Inline comment on the OSS-450 Linear issue - Project memory project_qwik_bundler_integration.md update Practical: Sub-C (OSS-453, preParsedProgram thread-through) must accept any structurally-compatible ESTree Program, not just OXC's specific type. Internal parses (parseWithRawTransfer, body re-parses for JSX walks) can stay OXC-specific for now — those are an optimizer implementation detail, not the public contract. Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…ev#200) Sub-A of the OSS-450 qwik-bundler integration umbrella. Establishes the package's importable surface as a one-time foundation step; no behaviour changes in src/optimizer/. What landed: - New src/index.ts barrels the public API: transformModule, the TransformModulesOptions / TransformOutput / TransformModule(Parent| Segment) / SegmentAnalysis / EntryStrategy / Diagnostic / EmitMode / MinifyMode / DiagnosticHighlightFlat / WithManualEntryMap types, the hasManualEntryMap predicate, and the full brand-types surface (FilePath, SourceText, RelativePath, etc.) with their smart constructors so consumers can satisfy the branded input types without casting at every call site. - New tsconfig.build.json extends the root tsconfig with rootDir:"src", noEmit:false, and excludes tests + src/testing/ so dist/ ships only the production surface. - package.json adds the build script, main/types/exports/files entries. Stays private:true; publishing is out of scope for Sub-A. Smoke-tested: pnpm build emits dist/index.{js,d.ts}; external import('dist/index.js') resolves all 15 runtime exports; transformModule round-trips a minimal $() input through the dist. Baselines preserved: convergence 203/212 + full suite 965/980 unchanged (this is packaging only — no src/optimizer/ changes). Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…T.md (QwikDev#201) Adds the optional agent_sync block (schema: bootstrap-project skill) so the portable ~/.claude/skills/agent-sync skill resolves the rules-sync script without auto-detection, plus a prose section documenting the .claude/rules → .cursor/rules mirroring contract. Co-authored-by: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…ler integration shipped (QwikDev#200) (QwikDev#202) PR QwikDev#200 (1296e97) shipped the public API surface foundation step for the OSS-450 qwik-bundler integration umbrella: src/index.ts barrel + tsconfig.build.json + package.json main/types/exports/build script. Packaging-only — baselines preserved exactly (convergence 203/212 + full suite 965/980 unchanged). OPTIMIZER.md audit: non-trigger-touching, skipped (PR only touched package.json, src/index.ts, tsconfig.build.json — none on the trigger checklist). OSS-450 umbrella status: Sub-A Done; Sub-B (OSS-452 createOptimizer factory) is the next pickup. Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…ape (QwikDev#203) Sub-B of the OSS-450 qwik-bundler integration umbrella. Bridges the API shape gap between the TS optimizer's sync `transformModule` and SWC's stateful-async `createOptimizer(opts): Promise<Optimizer>` so the bundler call site (qwik-bundler/src/rolldown.ts:354) reads through unchanged when swapping providers: const result = await (await getOptimizer()).transformModules(opts); What landed: - New `src/create-optimizer.ts` (top-level facade, sibling of index.ts) defines `QwikOptimizer`, `OptimizerOptions`, `OptimizerSystem`, `SystemEnvironment`, and `Path` interfaces mirroring SWC's public surface (from `@qwik.dev/optimizer/dist/index.d.ts`). `createOptimizer` is async (`Promise<QwikOptimizer>`) to match SWC even though nothing is genuinely async — `Promise.resolve(instance)` satisfies the contract. The instance's `transformModules` wraps the synchronous `transformModule` and returns `Promise.resolve(result)`. - Default `sys` stub satisfies the full SWC `OptimizerSystem` interface (cwd via process.cwd, env: 'node', os: process.platform, dynamicImport/strictDynamicImport via native import(), path delegating to pathe). `options.sys` overrides if provided. SWC parity at the field level so consumers swapping providers get an identical type surface; the TS pipeline never reads `sys` itself. - Passthrough OptimizerOptions fields (binding / inlineStylesUpToBytes / sourcemap / _optimizer) accepted for type-compat with existing SWC integration options objects but not consumed. - src/index.ts re-exports `createOptimizer` + the 5 new public types. - New `tests/optimizer/create-optimizer.test.ts` with 6 unit tests pinning the factory shape, the async round-trip through `.transformModules`, custom-sys pass-through, passthrough-fields acceptance, pathe delegation, and the bundler's double-await call pattern. Baselines preserved: convergence 203/212 + full suite 965/980 unchanged (+6 new unit tests will be absorbed into baseline on merge). Typecheck clean. `pnpm build` emits `dist/create-optimizer.{js,d.ts}` alongside `dist/index.{js,d.ts}`; external `import('dist/index.js')` resolves `createOptimizer` and round-trips through it end-to-end. Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…ler integration shipped (QwikDev#203) (QwikDev#204) PR QwikDev#203 (c26732d) shipped the createOptimizer factory matching SWC's stateful-async shape: src/create-optimizer.ts top-level facade + QwikOptimizer / OptimizerOptions / OptimizerSystem / SystemEnvironment / Path interfaces + 6 focused unit tests. Baselines preserved exactly (convergence 203/212 + full suite 965/980 unchanged; +6 unit tests absorbed into baseline on merge). OPTIMIZER.md audit: non-trigger-touching, skipped (PR only touched new facade files + barrel re-exports + a new unit test; no pipeline files). OSS-450 umbrella status: Sub-A ✅ Done (PR QwikDev#200), Sub-B ✅ Done (PR QwikDev#203). Sub-C (OSS-453 preParsedProgram thread-through audit) is the next pickup — verifies the existing OSS-350 parameter is wired end-to-end from public entry through every phase so Sub-D's bundler-side adapter can hand in Rolldown's meta.ast without an internal re-parse. State-file edits: Last updated + Last verified + Branches in flight `main` row (head c26732d, OSS-452 closure summary, Sub-C as next active workstream) + new dated entry prepended to "Most recent meaningful progress" + trimmed oldest entry (OSS-432 from 2026-05-23) per Maintenance "~10 entries" rule. Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…ev#205) * feat(OSS-453): thread preParsedProgram through public boundary Sub-C of the OSS-450 qwik-bundler integration umbrella. Wires the existing `extractSegments(preParsedProgram)` parameter (added in OSS-350) all the way out to the public `transformModule` entry so Sub-D's bundler adapter can hand in Rolldown's `meta.ast` and avoid the double-parse (host parses for `meta.ast`; optimizer used to parse again internally via `repairInput`). Audit found one gap: `repairInput` always called `parseWithRawTransfer` internally to detect whether repair was needed, even though `transformModule` already deduplicated its own parse against that result. So the bundler-host parse was the third one in the chain. What landed: - `repairInput(source, filename, preParsedProgram?, preParsedModule?)` now short-circuits its internal parse when a Program is supplied, trusting the caller's AST (callers like Rolldown wouldn't hand us broken source). Existing behavior unchanged when the param is omitted. - `TransformModuleInput` gains optional `program?: AstProgram` and `module?: AstEcmaScriptModule` fields. Documented as opt-in: omit and the optimizer parses internally as before; supply and the optimizer skips both internal parses (the one in `repairInput` and the legacy fallback at `transform/index.ts:118`). - `transformModule` forwards `input.program` / `input.module` into `repairInput`. No other phase changes — Phase 0.5 flatten-destructures and downstream body re-parses are out of scope per ticket (they don't have access to the parent's `meta.ast` and operate on rewritten source anyway). - `src/index.ts` re-exports `AstProgram` as `Program` and `AstEcmaScriptModule` as `EcmaScriptModule` so consumers can type their input. Per locked design choice, the contract is structural: any ESTree/TS-ESTree-compatible Program satisfies the type at runtime — OXC today, Yuku in the future. - `@oxc-project/types` promoted from devDependency to dependency (was already reachable via runtime; needed to be reachable via consumer type-resolution after the re-export). - 5 focused regression tests at `tests/optimizer/preparsed-program.test.ts` pin: pre-parsed Program acceptance, structural identity vs no-program path on every emitted module + segment metadata field, legacy parse-internally path preservation, module-optional-when-program-supplied, and end-to-end round-trip through `createOptimizer().transformModules()`. Baselines preserved: convergence 203/212 + full suite 971/980 unchanged (+5 new unit tests will be absorbed into baseline on merge). Typecheck clean. `pnpm build` emits the updated public types. Runtime exports unchanged (16; Program/EcmaScriptModule are type-only). Independent of Sub-D — ships as foundation. The bundler-side adapter (OSS-454) will pass `meta.ast` into this field; Sub-E's parity smoke fixture exercises the end-to-end path. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * fix(OSS-453): sync pnpm-lock.yaml with @oxc-project/types dep promotion CI failed on `pnpm install --frozen-lockfile` because the previous commit moved `@oxc-project/types` from devDependencies to dependencies in package.json without updating the lockfile. Pure mechanical sync — same package version, just moved between buckets in the lockfile's importer manifest. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…ler integration shipped (QwikDev#205) (QwikDev#206) PR QwikDev#205 (058839b) wired the preParsedProgram thread-through from the public boundary down to extract. repairInput short-circuits when caller supplies a Program; TransformModuleInput gains optional program? + module? fields; src/index.ts re-exports Program + EcmaScriptModule with structural-ESTree contract per locked design. @oxc-project/types promoted to dep; lockfile sync caught by CI install-step failure on initial push, fixed in follow-up commit + saved as feedback_lockfile_sync_on_dep_changes memory. Baselines preserved: convergence 203/212 + full suite 971/980 unchanged (+5 new unit tests absorbed into baseline on merge). OPTIMIZER.md audit: no update needed — Phase 0 opt-in plumbing only, not structural. Individual cite drift on Phase 1-5 markers now +17 to +34 lines, under the 50-line threshold; cumulative-drift sweep deferred per PROJECT.md convention. OSS-450 umbrella status: Sub-A ✅ Done, Sub-B ✅ Done, Sub-C ✅ Done. Sub-D (OSS-454 cross-repo bundler-side adapter) is the next pickup — lives in qwik-bundler, not this repo. Foundation in this repo now complete end-to-end: Sub-A barrel exposes createOptimizer + transformModule + types; Sub-B mirrors SWC's async shape; Sub-C accepts pre-parsed Program. State-file edits: Last updated + Last verified + Branches in flight `main` row (head 058839b, OSS-453 closure, Sub-D as next active workstream) + new dated entry prepended to "Most recent meaningful progress" + trimmed oldest entry (OSS-435 from 2026-05-24) per Maintenance "~10 entries" rule. Line-48 markdown table cell contains a TypeScript union (`'swc' \| 'ts'`) escaped per markdown table rules so the pipe is rendered as a literal character rather than a cell separator. Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…t paths) (QwikDev#208) * fix: promote oxc-parser/oxc-walker/oxc-transform to runtime dependencies The Sub-A packaging step left `oxc-parser`, `oxc-walker`, and `oxc-transform` in devDependencies, but all three are imported at runtime by src/ code (parse.ts, extract.ts, capture-analysis.ts, const-replacement.ts, variable-migration.ts, rewrite/inline-body.ts, rewrite/index.ts, rewrite/output-assembly.ts, utils/walk-with-protocol.ts). When a consumer (qwik-bundler) installs qwik-optimizer-ts and tries to use it via `optimizer: 'ts'`, the dynamic import resolves but the optimizer's first internal `import { parseSync } from 'oxc-parser'` crashes with "Cannot find package 'oxc-parser'" — pnpm's strict hoisting doesn't surface devDeps to consumers. Same class of bug as QwikDev#205's `@oxc-project/types` promotion: a runtime dep that escaped the original Sub-A audit. Cross-checked the entire `from 'oxc-*'` / `from 'fast-deep-equal'` import surface: - oxc-parser, oxc-walker, oxc-transform → all 9 src/ files use them → MOVED to deps. - fast-deep-equal → only used by src/testing/ast-compare.ts (test oracle) → stays in devDeps. Caught by attempting the rolldown-h3 fixture build under `qwik({ optimizer: 'ts' })`. Pre-fix: "Cannot find package 'oxc-parser'". Post-fix: the package resolves and the optimizer pipeline runs end-to-end. (A separate parent/segment path-resolution divergence surfaces past this fix; tracked as a follow-up — out of scope here.) No functional change. typecheck + build clean. Convergence + full-suite baselines preserved (this is packaging only — zero src/ edits). Lockfile re-synced per `feedback_lockfile_sync_on_dep_changes` memory. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * fix: emit segment module.path in the input.path namespace When a consumer passes absolute `input.path` values (which is what bundlers do — Rolldown hands plugins absolute file paths), SWC emits `module.path` as absolute too. Consumers like qwik-bundler rely on this: their `resolveId` hook joins `dirname(importer)` with the parent's relative import string, and matches the result against segment-map keys built from `module.path`. If `module.path` is srcDir-relative while the importer is absolute, every parent-to-segment lookup misses and the build fails with "Module not found". This was caught running `pnpm --dir fixtures/rolldown-h3 build` under `qwik({ optimizer: 'ts' })` in qwik-bundler — every segment file was emitted but unreachable from the parent module. What landed: - New `inputPath` field on `SegmentGenerationContext`, populated from `input.path` directly in transform/index.ts (next to the existing `relPath`, which stays srcDir-relative for hashing/naming use). - Both segment-emit sites in segment-generation.ts now compute `module.path` as `join(getDirectory(ctx.inputPath), canonical + ext)`. Snapshot fixtures use root-level paths like "test.tsx" where getDirectory returns "" — output unchanged. Bundler integrations passing absolute paths get absolute outputs back. - `mkRelativePath` brand validation relaxed to only reject empty strings. The leading-slash ban was an over-specification — SWC's `TransformModule.path` legitimately holds absolute paths in bundler-supplied scenarios. The brand still distinguishes from `FilePath` at the type level; the runtime check shrinks to the invariant we can actually rely on. Documented inline. - One brand test renamed + behaviour flipped from "rejects absolute" to "accepts absolute (only empty rejected)". Baseline absorbs the rename per the existing REGRESSION.md "renamed tests count as missing" convention. End-to-end validation: - pnpm typecheck clean. - Convergence 203/212 unchanged. Full suite 976/1004 unchanged (snapshot fixtures all use root-level paths so getDirectory("") = "" and segment.path is byte-identical to before). - qwik-bundler's full test suite 167/167 passes against this dist. - rolldown-h3 fixture builds clean under qwik({ optimizer: 'ts' }). - The h3 server starts, serves the HTML, and the QRL wiring is intact (`<button q:p="0" q-e:click="q-D4Y6RLLt.js#_run#1">`). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * fix(ci): align baseline total with CI environment The local baseline regen captured `full.total = 1004`, but CI's Linux environment runs 1002 — two tests run on macOS that don't run on Linux (probably platform-conditional). The regression check correctly flagged this as a possible silent test deletion when comparing the PR's run (1002) against the committed baseline (1004). Solution: revert the `.ci/baseline.json` totals to the 4f85b3c version that CI already accepts, then apply only the brand-test rename on top (`mkRelativePath rejects empty and absolute paths` → `mkRelativePath rejects only empty strings ...`). This keeps the renamed test tracked correctly without inflating totals beyond what CI sees. Net effect on the baseline file: one entry's name changed in the `full.passing` set; `total` counts unchanged (1002 / 212). The auto-baseline-update workflow on main will re-derive everything from CI's actual run after merge. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
* chore: strip Linear ticket refs from source code comments Per the project convention (feedback_comments_explain_why memory, strengthened 2026-06-04): ticket refs belong in PR titles + commit messages + tracker only. Never in source code, test file headers, or test descriptions — the audience of source comments doesn't have access to the tracker and doesn't need to. OSS-454's Sub-D PR review surfaced this; cleaning up the four sites introduced by the OSS-450 umbrella's TS-Optimizer-side sub-issues: - src/optimizer/input-repair.ts (from QwikDev#205): dropped `OSS-453:` prefix from the preParsedProgram comment; kept the WHY (eliminates the double-parse when integrating with a host that already has the AST). - src/optimizer/transform/index.ts (from QwikDev#205): dropped `(OSS-453, ...)` from the Phase 0 repair comment. - src/index.ts (from QwikDev#205): dropped `(OSS-453)` from the Program / EcmaScriptModule re-export comment. - src/create-optimizer.ts (from QwikDev#203): rewrote the header comment to describe the shape it mirrors (`@qwik.dev/optimizer`'s public surface) rather than ticket-tour the sub-issue lineage. - tests/optimizer/preparsed-program.test.ts (from QwikDev#205): dropped `OSS-453 — ` prefix from the describe block. The OSS-449 sweep cleaned 243 src/ refs in May; OSS-454 introduced 4 new ones in the Sub-A/B/C series that escaped review. The memory is now hardened with explicit `NEVER` framing + worked examples from both the Sub-C and Sub-D violations so future agents can't misread it. Baseline regenerated to absorb the describe-block rename per REGRESSION.md "renamed tests count as missing" caveat. No functional change. Convergence 203/212 + full suite 976/1004 unchanged from the prior measurement (965 → 976 reflects newly-baselined unit tests from QwikDev#203/QwikDev#205, not new behaviour). Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> * fix(ci): align baseline total with CI environment Same fix as f/oxc-runtime-deps c2a7e75 applied to this branch's baseline: the local regen captured `full.total = 1004` but CI's Linux env runs 1002 (two tests run on macOS that don't run on Linux). The regression check correctly flagged the 1004 → 1002 drop as possible silent test deletion. Solution: revert `.ci/baseline.json` totals to the e0520c4 version (post-OSS-453 / pre-this-branch state that CI accepts) and apply only the five `OSS-453 — preParsedProgram thread-through ...` → `preParsedProgram thread-through ...` describe-block renames that this PR makes. Totals (1002 full / 212 convergence) match CI. The auto-baseline-update workflow on main will re-derive everything from CI's actual run after merge. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com> --------- Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…#207 + QwikDev#208 merged (QwikDev#209) Two same-day same-track merges (bundler-integration packaging) batched into one progress entry per the wrap-up convention for tightly-related merges. PR QwikDev#208 (6ff151e parent commit 850386b): fixed two packaging blockers caught by attempting the README's rolldown-h3 fixture under the TS optimizer — three runtime deps mis-bucketed in devDependencies (oxc- parser, oxc-walker, oxc-transform → all imported by 9 src/ files); segment module.path namespace divergence (TS emitted srcDir-relative, SWC emits in input.path namespace, bundlers' resolveId expected SWC's). Fix threaded input.path through to SegmentGenerationContext as new inputPath field; loosened mkRelativePath brand validation. PR QwikDev#207 (6ff151e): stripped Linear ticket refs from src/ + tests/ comments per the feedback_comments_explain_why memory; strengthened the memory with explicit "NEVER ticket refs in code" framing + worked-example entries for both the Sub-C (PR QwikDev#205) and Sub-D (qwik-bundler PR QwikDev#12) violations. End-to-end demo working: rolldown-h3 fixture builds + runs under qwik({ experimental: ['tsOptimizer'] }); h3 server boots; HTML response carries full Qwik QRL wiring intact. OPTIMIZER.md audit: no update needed — two trigger-checklist files touched (transform/index.ts, segment-generation.ts) but no structural-change criterion fires. New inputPath field is type- internal; module.path namespace switch is at the output-emission boundary, not the pipeline shape. OSS-450 umbrella status: Sub-A/B/C all Done; TS-Optimizer-side packaging blockers resolved. Sub-D (OSS-454) in qwik-bundler PR QwikDev#12 is in its final shape with optimizer selection driven from EXPERIMENTAL_FEATURES (`tsOptimizer` flag), validated end-to-end against rolldown-h3, ready to merge. State-file edits: Last updated + Last verified + Branches in flight `main` row (head 6ff151e, batched closure summary) + new dated entry prepended to "Most recent meaningful progress" + trimmed oldest entry (OSS-437 from 2026-05-24) per Maintenance "~10 entries" rule. Co-authored-by: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
…/535 Done, OSS-532 parked (QwikDev#353) Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
…ect crash cleared (QwikDev#354) Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
…mode) (QwikDev#355) * fix(OSS-536): inject _useHmr into inline/hoist component bodies (hmr mode) In hmr mode the optimizer injected `_useHmr(devFile)` into `component$` bodies only on the segment (client) strategy path (post-process.ts). The inline/hoist strategy — which the dev SSR render uses — emitted the body with no HMR hook. `_useHmr` is a Qwik hook: its presence changes a component's serialized hook/vnode layout. The SSR render (inline/hoist, no hook) serialized ref offsets one way; the client (segment, with hook) re-rendered differently under interaction, so vnode ref offsets desynced → an intermittent `Missing refElement` assert under DOM churn on every ref-bound component (carousel, checkbox, checklist, collapsible, tree in qwik-design-system). TS-only; the SWC reference injects the hook in both paths and stays consistent. Inject `_useHmr` in the inline/hoist emission path (output-assembly.ts), gated identically to the segment path: `mode === 'hmr' && devFilePath && isAnyComponentCtx(ctxName)`. Extracted the block/expression body-injection core out of `injectUseHmr` and added `injectUseHmrIntoInlineBody` for the bare-body shape the inline/hoist path carries. Browser head-to-head (qwik-design-system dev SSR, TS :5200 vs SWC :5201): the refElement assert is gone across all 5 routes (carousel 3/3→0, checklist 4/4→0, checkbox 2/15→0, collapsible 3/3→0, tree 1/8→0); TS SSR HTML now emits q-d:q-hmr markers + q:template projection elements matching SWC. Convergence unchanged (203/9 — no inline/hoist fixture runs in hmr mode). Full baseline green. +5 regression tests. OPTIMIZER.md useHmr emission-site note updated. Closes OSS-536. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * docs(state): record OSS-536 root-cause + fix Server/client HMR-hook desync fixed; refElement assert gone on all 5 ref-bound qds routes. Branch entry + measurements + progress log updated. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * refactor(OSS-536): drop what-comments from useHmr inline-injection path Remove the inline WHY comment on the inline/hoist _useHmr gate plus the two doc comments on injectHmrCallIntoFunctionBody / injectUseHmrIntoInlineBody added by the fix. The gate mirrors the uncommented segment-path gate; the function names state intent and the behavior is guarded by inline-hoist-usehmr.test.ts. The serialized-layout desync rationale stays in the fix commit message where it can't rot. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * docs(state): record OSS-536 full post-fix qds re-sweep (clean) Full 29-route head-to-head re-sweep post-fix: 0 TS-only divergences across all 23 rendering routes; all 5 fixed routes crash->0; 9 prior-MATCH routes no regression; modal symmetric, 6 identical 404s. Refresh header, progress log (trim to 10), and the what-to-do-next section. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v --------- Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
…v#356) PR QwikDev#355 (OSS-536: inject _useHmr into inline/hoist component bodies in hmr mode) merged to main (c4091ea; baseline 2bdf578). Post-merge wrap-up: branch fix/oss-536-inline-hoist-usehmr deleted local+remote, qds dist rebuilt + re-synced, OSS-536 flipped to Done. STATE refresh: header PR-status + tail, branches table (main head SHA 2bdf578, OSS-536 row removed), measurements (main baseline 203/9 convergence + 1192 full, +5 absorbed), progress-log prepend + trim to 10, what-to-do-next OSS-536 marked Done. OPTIMIZER.md useHmr emission-site note already updated in the fix PR — no further audit. Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
…ves, wireMigration split (QwikDev#357) * refactor: remove dead code + an exact-dup helper (hygiene batch A) What: pure deletions + one import repoint across 7 files. - applyRawPropsTransformDetailed + RawPropsTransformResult — zero callers. - collectIdentifiersFromExpr — orphaned (collectSignalDeps uses the inlined fallbackCollectIdents); fixed its one stale doc reference. - findArrowIndex — whole chain dead: canonical in text-scanning.ts, its lone import + re-export in body-transforms.ts, no consumers repo-wide. - addBindingNamesToSet — one-line passthrough; call the already-imported addBindingNamesFromPatternToSet directly at all 4 sites. - partsHaveImport — import-collection.ts kept a byte-identical private clone of the body-transforms.ts export it already imports from. Isolation: removes silently-dead surface area and one duplicate that could drift from its source. No behavior change. Foundation: clears the "free wins" tranche ahead of the shared-primitive consolidation (batch B). Risk: deletions + one import repoint. typecheck clean; convergence 203/203 and full 1192/1192 baseline-passing tests unchanged. Net -91 LOC. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * refactor: share edit/AST primitives across passes (hygiene batch B) What: replace hand-rolled duplicates with shared primitives. - 6 reverse-splice apply loops (dead-code, module-cleanup, const-propagation) → the existing applyReplacements; ranges are disjoint by construction at every site. - resolveConstLiterals / resolveConstLiteralsInClosure: extract the shared inner walk as collectConstLiteralValues(root, source, offset, …); the two now differ only by wrapper-offset vs source-absolute. - containsJsx / containsUnknownCall / containsImportedReference: fold the three deep-existential walks onto a new someAstDescendant primitive in ast/guards (sibling of someAstChild); drop containsJsx's vestigial array-input branch (no caller passes an array). - getPropertyName / staticPropName → shared memberStaticPropName; the two q_<sym>.w() capture-wrap arms (jsx.ts, jsx-props.ts) → shared isCaptureWrappingQrlCall. - inlineConstCaptures guard + isRealRef → the canonical isReplaceableIdentifierPosition (adds a params-position exclusion the hand-rolled copies lacked; params shadow, so it can only be more correct). Isolation: one home per operation instead of 2-6 drifting copies; the divergent-guard risk (each reverse-splice/position-guard copy could rot independently) is removed. Foundation: someAstDescendant + memberStaticPropName + the shared predicates are reused by later hygiene batches (C/D). Risk: behavior-preserving. typecheck clean; convergence 203/203 and full 1192/1192 baseline-passing tests unchanged. Net -97 LOC. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * refactor: dedupe _noopQrl builders + dev-meta literal (hygiene batch C) What: the inline/hoist strategy had four near-identical _noopQrl string builders differing only in the LHS var name (q_<sym> vs sentinel q_qrl_<counter>), and the {file,lo,hi,displayName} dev-meta object literal was hand-emitted three times (twice here, once in dev-mode.ts). - Two private core builders buildNoopQrl(varName, symbolName) / buildNoopQrlDev(varName, symbolName, devMeta); the four public builders become one-line delegations. - NoopQrlDevMeta type + formatDevMeta() in dev-mode.ts, now the single source of the dev-meta literal for both _noopQrlDEV and qrlDEV. - Trimmed the redundant format-example doc blocks the delegations no longer need. Isolation: one place each defines the noop-QRL template and the dev-meta literal; output is byte-identical (snapshot-pinned). Foundation: formatDevMeta is the reuse point if a third dev-meta emitter appears. Risk: string builders are snapshot-pinned; convergence 203/203 and full 1192/1192 baseline-passing tests unchanged (byte-identical). Net -34 LOC. Deferred (NOT behavior-preserving as pure refactors — the "duplicates" have diverged): - Import-before-separator idiom (5 sites): guards genuinely differ (substring vs partsHaveImport-structured vs startsWith-import) and the canonical helper unshifts where these skip when no separator exists. - Same-file import ladder (2 sites): different data sources (reexportedNames set vs migrationDecisions lookup), skip conditions, and default-vs-reexport ordering. Unifying either would normalize behavior in edge cases the fixtures may not cover. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * refactor: extract lib-mode marker predicate (hygiene batch D) What: the identical `name.length > 1 && name.endsWith('$')` lib-mode marker test appeared at 3 sites (rewrite/index, output-assembly, module-cleanup), each behind a paragraph-long comment explaining the same rationale. Extract isLibModePreservedMarker() in qwik/qrl-naming; the rationale now lives once on the predicate's doc, and the three site comments (which also referenced the reference implementation, against the comment convention) are gone. Isolation: one named predicate for "a $-suffixed marker other than the bare $"; the intent is stated once instead of re-explained per site. Foundation: the marker-name predicate is the reuse point if a fourth lib-mode gate appears. Risk: identical boolean, surrounding conditions unchanged — behavior provably preserved. convergence 203/203 and full 1192/1192 unchanged. Deferred (NOT behavior-preserving as pure refactors): - isHtmlTagName (4 copies): three genuinely different rules — any-lowercasing char vs strict ASCII a-z vs not-uppercase-letter. They disagree on digit/non-ASCII-initial tags; unifying normalizes behavior. - signal-result const/var classification (2 sites): diverge on param/in-loop handling — sharing would close a parity gap = change output. - createTransformSession adoption (5 sites): a parse-mechanism swap with wrapper prefix/suffix offset math to verify per site; too much risk layered on batch B's const-propagation changes for a boilerplate win. - marker->Qrl slice dup: the diagnostic caller may not want getQrlCalleeName's $/sync$ special-casing; needs verification, not a blind swap. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * refactor: split wireMigration into a helper sequencer (hygiene batch E) What: wireMigration was a ~200-line function interleaving five concerns. Extract three named helpers, mirroring the generateAllSegmentModules sequencer pattern (OSS-343): - resolveMovedDeclImportDeps — a moved decl's import dependencies. - emitMovedDeclaration — marker-QRL vs plain-decl emission. - filterMigratedCaptures — drop migrated names from captures + reconcile the captures flag against paramNames. wireMigration is now a ~40-line orchestrator: auto-imports, pre-scan sets, the move loop (calling the two per-decl helpers), then the capture filter. Also folded the move-loop's reexport guard to an early-continue. Isolation: each concern is independently readable and named; the move loop reads as "resolve deps, emit" instead of 100 lines inline. The shared-mutation surface (captureInfo, movedQrlSymbols) is now threaded explicitly through helper parameters rather than closed over. Foundation: the per-decl helpers are the natural extension points for the deferred SWC transitive-ordering work (topological emit) noted in OPTIMIZER.md's migration deep dive. Risk: pure code motion. typecheck clean; convergence 203/203 and full 1192/1192 baseline-passing tests unchanged. Net -5 LOC. Also updates the OPTIMIZER.md line refs this move invalidated (wireMigration/buildDefaultStrategySegment/generateAllSegmentModules). The doc's other segment-generation.ts refs carry pre-existing cumulative drift and are left for a dedicated line-ref refresh. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * refactor: drop self-evident docs on two batch-B helpers collectConstLiteralValues and isCaptureWrappingQrlCall each carried a doc block that only restated what the name + logic already say (the offset parameter's two modes are shown by its two call sites; the q_<sym>.w shape is exactly what the predicate checks, and the const-classification rationale belongs at the call site, not on the shape detector). Comment- only; no behavior change. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v --------- Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
Deletions (assert nothing / exact duplicate):
- extract.test.ts: two disambiguateExtractions stubs — one had zero
expect() calls, the other only asserted length on an input that by
construction produces no disambiguation. Both superseded by the working
"disambiguates multiple extractions with same display name" test.
- fnsignal-nonreactive-map.test.ts: a byte-identical duplicate of
fnsignal-computed-key.test.ts's computed-key test.
- segment-only-debug.test.ts: a debug harness ending in
expect(true).toBe(true) that ran a full-corpus transform each CI run to
console.log a report — an investigation artifact, not a test, and not
referenced by any doc.
Strengthened in place (kept the test IDs; each now fails on real
regression instead of passing vacuously):
- failure-families.test.ts: had zero assertions (a categorize-and-log
harness). Added corpus-present + complete-partition guards so a missing
or dropped snapshot surfaces. Kept as a test since docs reference it as
a secondary signal.
- transform.test.ts: two ctxKind tests asserted inside `if (seg)` guards
that vanish if extraction stops emitting the segment — now assert the
segment is found first. The const-vs-var test only checked a
`_jsxSorted("div"` call existed — now also asserts both prop values
survive. Dropped a reference-implementation comment.
- rewrite-parent.test.ts Test 9: named "parent-child relationship" but
only asserted extraction count — now asserts a nested extraction's
parent resolves to another extraction's symbol.
Baseline: the four deletions drop four passing IDs and the total. Mapped
.ci/baseline.json from the stored (CI-true) baseline — removed exactly
those four IDs, decremented full.total 1217 -> 1213 — rather than
regenerating locally (local totals carry +2 from the QWIK_HOME benchmark
skips). Verified: convergence 203/203, full 1188/1188, 1:1 with zero
unaccounted adds/removes.
Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v
Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
* refactor(OSS-540): extract plainQrlName primitive (finding QwikDev#6) What: extract the special-case-free `$`→`Qrl` slice into `plainQrlName`; `getQrlCalleeName` now layers its bare-`$`/`sync$` cases on top of it, and the C05 diagnostic export-name check uses `plainQrlName` directly instead of its own inline `slice(0,-1)+'Qrl'`. Why: removes the duplicated slice while preserving the diagnostic's exact current behavior — it intentionally does NOT want getQrlCalleeName's marker special-casing (a user `sync$`/`$` export must still be checked against `syncQrl`/`Qrl`, not `_qrlSync`/``). Naively sharing getQrlCalleeName would have changed that; the primitive avoids the change. Foundation: resolves the OSS-540 "marker→Qrl slice dup" finding as a safe extraction rather than a behavior-changing merge. Risk: none — pure extraction. Typecheck clean; +3 plainQrlName pins; 42/42 in rewrite-calls + diagnostics suites, unchanged. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * refactor(OSS-540): unify raw-name HTML predicate on isHtmlElement (finding QwikDev#3) What: point segment-generation's local `isHtmlElementName` at the canonical `isHtmlElement`, and drop the redundant a-z re-check in jsx-elements-core's `tagIsHtml` (its `tag.startsWith('"')` already encodes processJsxTag's isHtmlElement decision). Left jsx-children's `isComponent` alone — it is a distinct uppercase check; expressing it as `!isHtmlElement` would flip member-expression children (empty tagStr → HTML). Why: the audit flagged "4 copies" of the HTML-tag test, but only one was a divergent copy of the raw-name predicate. segment-generation used a strict ASCII a-z rule while the rest of the pipeline uses Rule L (first char equals its lowercase); they disagreed on digit/non-ASCII-initial tags. Unifying removes the latent inconsistency and leaves one canonical predicate. Foundation: resolves the OSS-540 isHtmlTagName finding — single source of truth for "is this raw tag name an HTML element". Risk: none on real input. The two rules agree on every valid tag (a-z lowercase → HTML, A-Z → component); they diverge only on digit/non-ASCII initials, which are invalid/absent in the fixture corpus. Convergence 203/9 unchanged; +4 edge-case pins (hyphenated, caseless-initial, empty). The 3 unrelated failures in segment/jsx dirs are pre-existing on main. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * refactor(OSS-540): adopt createTransformSession in 4 body-reparse sites (finding QwikDev#5) What: replace hand-rolled wrapper-prefix + parseSync + offset-math in four body-text reparse sites with the canonical `createTransformSession`: - const-propagation.ts ×3 (resolveConstLiterals, inlineConstCaptures, propagateConstLiteralsInBody) — read AST positions, edit the unwrapped body via applyReplacements; now use session.program + session.offset. - lib-mode-collapse.ts substituteInnerQVarsInText — edits a MagicString on the wrapped source; now uses session.edits + session.toSource(), which also removes the fragile manual `.slice(offset, len-1)` suffix trimming. Why: every one of these reimplemented the same wrap/parse/offset idiom with its own prefix (`__rl__`/`__ic__`/`__pb__`/`__body__`) and its own filename, so their wrapped-source strings never matched the canonical session's — no shared parse memo, and four subtly different offset computations to keep correct. Routing them through createTransformSession gives one wrapper idiom and lets repeated parses of the same body version share a cached parse. Foundation: resolves the OSS-540 createTransformSession-adoption finding for the clean-swap sites; single canonical body-reparse path. Deferred (documented): inline-body.ts's JSX-in-inline-body reparse keeps its hand-rolled wrapper — its prefix length escapes into the JSX transform's dev-info `sourcePosition.wrapperPrefixLen`, so adopting the session would have to thread session.wrapperPrefix.length through source-map positioning; bounded benefit, real source-map risk, left for a dedicated pass. Risk: none. parseWithRawTransfer (the session's parse) is exactly the parseSync(RAW_TRANSFER_PARSER_OPTIONS) these sites used; the offset shift (15/17 → 16) is applied consistently within each session. Typecheck clean; const-propagation + lib-mode suites 23/23; convergence 203/9 unchanged. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * refactor(OSS-540): unify ensureCoreImports onto canonical import helpers (finding QwikDev#1) What: ensureCoreImports now uses `partsHaveImport` for its already-imported guard and `insertImportBeforeSeparator` for the insert, replacing its loose `startsWith('import') && includes(sym)` guard and inline `splice(sepIdx, 0, ...)`. The dead no-separator early-return is dropped. Why: the audit flagged three divergent guards for "is this symbol already imported"; ensureCoreImports carried the loosest (substring-on-import-line), the one most prone to false positives. The single caller guarantees a `//` separator right before the call, so the early-return branch was unreachable and the guard's precision was the only real difference. partsHaveImport is behavior-identical here because the core symbol set has no substring collisions. Foundation: resolves the OSS-540 import-before-separator finding for the provably-safe site; ensureCoreImports now shares one insert idiom with the rest of import-collection/segment-codegen. Deferred (documented): the segment-codegen raw-splice sites keep their own no-separator fallbacks (append-import-then-separator / append-import / skip), which are genuinely distinct from the canonical unshift and can't collapse without changing behavior. One of them also has a `, sym`-substring guard that false-positives on _noopQrl vs _noopQrlDEV; correcting it is a real behavior change, left out of this behavior-preserving pass. Risk: none on real input. Guard is identical for the core symbols; no-sep branch was dead; the insert switch flips core-import order from reverse to forward, which is not semantically checked (imports are order-independent) and regresses nothing. Convergence 203/9, full 1188 baseline all pass; +4 ensureCoreImports contract pins. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * refactor(OSS-540): share the same-file import ladder (finding QwikDev#2) What: extract `resolveSameFileImportName` (+ `formatSameFileImport`) as the single same-file-symbol import resolver, and route both prior copies through it: import-collection's `addSameFileImport` (which emitted import strings) and segment-generation's `resolveMovedDeclImportDeps` (which builds MovedImportDep objects). Why: the audit flagged these two ladders as divergent — different data sources (a migration-decision lookup vs a precomputed reexportedNames set) and opposite reexport-vs-default evaluation order. On inspection they encode the same decision: the reexport predicate is identical (`reexport && !isExported` at both sites), and the reexport/default arms are mutually exclusive (a default export is always isExported, so it can never enter the reexport arm), which makes the order difference unobservable. Unifying makes that equivalence explicit and removes the drift risk of two ladders that must stay in lockstep by hand. Foundation: one canonical same-file import resolution; the two callers now differ only in how they format the shared result (string vs dep object). Risk: none. The resolver reproduces every arm of both ladders; the order switch is unobservable by the mutual-exclusivity argument above. Typecheck clean; convergence 203/9, full 1188 baseline all pass; +8 resolver/formatter pins covering all four arms. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * fix(OSS-540): share _fnSignal deps-const classifier, close _jsxDEV param gap (finding QwikDev#4) What: extract `fnSignalDepsAllConst` (jsx.ts) as the single deps-const predicate for _fnSignal prop classification, and route both classifiers through it — the raw-JSX path (jsx-props `processProps`, two call sites) and the pre-transformed `_jsxDEV` path (jsx-call-transform `classifyProp`). Why (behavior change): `classifyProp` was missing the raw path's component-parameter arm — a dep that's a closure parameter counts as const-eligible on a *component* element (not on HTML). So on the `_jsxDEV` path a param-dependent _fnSignal prop on a component element was wrongly placed in the var-props bag instead of the const bag. Confirmed by byte-level probe: before: _jsxSorted(Inner, { title: _fnSignal(_hf0, [props], …) }, null, null, …) after: _jsxSorted(Inner, null, { title: _fnSignal(_hf0, [props], …) }, null, …) Now the `_jsxDEV` path classifies identically to the raw-JSX path. The raw path's other arm (`!inLoop`) is not portable — the `_jsxDEV` path has no loop tracking — so classifyProp gains only the param arm. Scope: convergence is unaffected (every fixture is raw JSX; the `_jsxDEV` path is never exercised there). This path is covered by the jsxdev unit tier and real bundler builds (qds/router). A qds head-to-head is the definitive validation — recommended follow-up before relying on the qds output shift. Also: dropped the SWC-reference comments from the edited processProps block (the param/component rationale now lives once on fnSignalDepsAllConst's doc). Risk: full suite + convergence green (203/9, 1188 baseline all pass); no existing test regressed. +2 jsxdev pins: component element → const bag (the fix), HTML element → var bag (param arm correctly HTML-gated, unchanged). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * refactor(OSS-540): drop what-comments on small helpers (PR QwikDev#359 review) Remove WHAT-comments that restated what the name and body already say: - plainQrlName: doc deleted — name + the getQrlCalleeName body below are self-evident, and a test pins the special-case-free contract. - fnSignalDepsAllConst: trimmed to the one non-obvious WHY (params are const-eligible only on component elements). - ensureCoreImports: doc deleted — name + body say it. Also restructured processProps's _fnSignal block: the two empty guard branches (each carrying a fall-through comment) collapse into named `isRawWhenNonConst` / `excludedFromHoist` booleans, so the code speaks for itself with no comments. Behavior-preserving: typecheck clean; convergence 203/9, full 1188 baseline all pass; no test changed. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v --------- Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
…SS-537 hygiene sweep complete (QwikDev#360) - main → 36417d2; OSS-538/539/540 Done (PRs QwikDev#357/QwikDev#358/QwikDev#359 merged). - Header rewritten to the current state: OSS-540's six consolidations, with QwikDev#4 flagged as a `_jsxDEV`-path parity change (not a convergence flip) whose definitive validation is a still-pending qds head-to-head. - Measurements: 203/9 convergence, 1188 baseline all pass (+20 absorbed). - Branches: main head bumped; merged OSS-540 branch removed. - Progress log: prepend QwikDev#359 + QwikDev#357/QwikDev#358 entries, trim oldest 2. - Regenerated .cursor/rules mirrors (STATE.mdc; OPTIMIZER.mdc drift corrected). Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
…Dev#361) * refactor: de-any jsx-transform.test.ts AST-extraction helpers What: replace the two `any`-returning parse helpers (`parseExpr` plus its dead byte-identical twin `parseJsx`) with four typed helpers — `parseExpr`, `parseExprStatement`, `parseJsxElement`, `parseJsxFragment` — and collapse the 18 inline `(program.body[0] as any).expression` node extractions into single typed-helper calls. Drop the `collectScopeAwareBindings(program as any)` cast (assignable directly). 20 `any`s and one dead helper removed. Why (isolation): the helpers now return `Expression` / `JSXElement` / `JSXFragment` and assert node structure, so a malformed parse throws a named error instead of silently propagating `undefined` into the assertion — a strictly stronger test. Upholds the hard "no `any`" type-discipline rule. Why (foundation): the typed-extraction pattern is the reusable template for the deferred `tests/optimizer` de-any effort (STATE.md "Held / deferred") — the same `(body[0] as any).expression` idiom recurs across sibling specs (capture-analysis, jsx-arrow-prop-value, …) and adopts these helpers next. Risk: test-only, one file, touches no src. Verified behavior-identical — 62 pass / 2 fail before and after (the 2 are pre-existing SWC-parity known-failures, not in the baseline passing set, untouched). typecheck clean; local gate green: convergence 203/203, full 1208/1208 baseline- passing, zero regressions. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * refactor: extract shared typed AST-parse helpers for tests What: promote the four typed parse helpers (`parseExpr`, `parseExprWithSource`, `parseJsxElement`, `parseJsxFragment`) from jsx-transform.test.ts into a shared `tests/optimizer/helpers/parse-nodes.ts` module, and adopt them in signal-analysis.test.ts — removing its last two `any`s (its own `{ node, source }` parse helper duplicated the pattern). Why (isolation): a second consumer appeared, so the helpers move to one home instead of being copied. One typed definition of "parse a string into an AST node", asserting structure at the boundary, now serves both specs. Why (foundation): this is the reusable surface the deferred `tests/optimizer` de-any effort (STATE.md "Held / deferred") builds on — sibling specs that share the `(body[0] as any).expression` idiom adopt these helpers next instead of re-deriving them. Risk: test-only, touches no src; the new module is a non-test `.ts` (adds no tests). Verified behavior-identical — jsx-transform 62/2, signal-analysis 25/1, unchanged before/after (the 3 fails are pre-existing SWC-parity known-failures outside the baseline passing set). typecheck clean; gate green: convergence 203/203, full 1208/1208, zero regressions. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v --------- Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
…lla filed (QwikDev#362) PR QwikDev#361 (test-infrastructure de-any) merged to main (d30c4ab): jsx-transform.test.ts + signal-analysis.test.ts de-anied, shared tests/optimizer/helpers/parse-nodes.ts extracted. Test-only; gate green (convergence 203/9 unchanged, full 1208 baseline all pass). - Bump Last updated + main head SHA (36417d2 -> d30c4ab) + measurements. - Prepend progress entry; trim oldest (Stranded-QwikDev#348). - Correct the "Held / deferred" de-any note: now tracked as umbrella OSS-541 + subs OSS-542 (tests/optimizer + oxc-walker) / OSS-543 (ast-compare oracle narrowing -- NOT mechanical as previously billed). - Regenerate .cursor/rules/STATE.mdc mirror. OPTIMIZER.md audit: PR touched only tests/ -- no trigger-checklist file, no update needed. Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
De-any the low-risk test-spec track of the OSS-541 umbrella (test-only). What changed: - Typed the oxc-walker pattern in capture-analysis.test.ts (~19 sites) and loop-hoisting.test.ts: AstNode/AstFunction callbacks, this.skip() via the walker's contextual this, dropped every `program as any`. - capture-analysis.test.ts: unified the two near-identical dollar-arg helpers behind typed collectors (asClosureArg/collectDollarArgs/collectParentScopeIds/ collectImportedNames/buildDollarArgFacts), removing the duplication. - Extracted the duplicated AST position-stripping normalizer from convergence-breakdown + failure-families into tests/optimizer/helpers/ ast-normalize.ts (unknown + isRecord narrowing, no casts). - Typed findFirstCall/findFirstNode to return CallExpression/AstNode and throw on absence (the parse-nodes.ts convention); every callsite supplies valid input. - transform.test.ts: `as any` -> `as SegmentMetadataInternal`, the sanctioned test idiom already used in stripped-qrl-cleanup.test.ts for reaching the internal captureNames field. Beneficial in isolation: removes the actionable `any` from tests/optimizer, upholding the "any is never the right answer" rule; kills two duplicated `strip` normalizers; typed walker callbacks surface AST-shape mistakes at compile time. Foundation: extends the parse-nodes.ts typed-helper pattern (PR QwikDev#361); ast-normalize.ts becomes the shared normalizer for breakdown-style tests. Completes Sub A of OSS-541, leaving OSS-543 (ast-compare.ts oracle) as the only remaining de-any. Risk: test-only, behavior-preserving. Casts are erased at runtime; refactored helpers are semantically identical. Convergence 203/9 and full 1208 baseline all pass, 0 regressions; the 6 pre-existing transform.test.ts failures are unchanged (verified against main). Refs: OSS-542 (sub of OSS-541). Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
…subs landed (QwikDev#365) OSS-542 (QwikDev#363) merged to main (0e56468); OSS-543 (QwikDev#364) In Review. Bumped main SHA + Last verified; prepended the umbrella progress entry and trimmed the log to ~10. Regenerated the .cursor/rules/STATE.mdc mirror. Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
…v#364) * refactor(OSS-543): de-any the ast-compare differential oracle De-any the higher-risk track of the OSS-541 umbrella: the AST differential-comparison oracle (`src/testing/ast-compare.ts`, ~164 `any` sites across 71 normalizer functions), consumed by both the convergence suite and production `output-assembly.ts`. What changed: - Every code-level `any` replaced with typed narrowing. Node params -> `AstCompatNode`; recursive-clone/walk params + returns -> `unknown`; local accumulators -> `Record<string, unknown>` / `unknown[]`. - Three shared narrowing primitives carry the per-site work: reused `isAstNode` from `optimizer/ast/guards.ts`, plus local `isRecord` and `asArray` (returns the SAME array reference so in-place push/splice/ sort/index-assign still mutate the real tree) and `asString`. - Strict-oxc-typed helpers that actually receive the loose post-strip tree were retyped to `AstCompatNode`/`unknown` (`isReorderableDeclaration`, `stripFrameworkHelperImports` + its closures); the now-unused `Directive`/`ImportDeclaration`/ `ModuleExportName`/`Program`/`Statement` imports were dropped. - Removed a provably-dead `=== 'AssignmentPattern'` check in `inlineDestructuredBindings` (the preceding `!== 'Identifier'` break already covers it) rather than keep a type-defeating `: unknown` dodge. No `as` casts introduced (the sanctioned one-cast-at-the-boundary lives inside `guards.ts`'s `isAstNode`); narrowing is guard-based throughout. Beneficial in isolation: closes the last `any` hole in the test infrastructure and makes the oracle's dynamic AST access compile-time checked. Foundation: completes OSS-541. Risk: this is the differential oracle — a weakened comparison would silently mask convergence regressions. Verified BIT-IDENTICAL: the full pass/fail set is unchanged (before pass=1208 fail=25, after pass=1208 fail=25; 0 regressed, 0 newly-passing, 0 gained-fail, 0 lost-fail), confirmed by re-running the whole suite and diffing test-id sets. `pnpm typecheck` clean. Closes OSS-543 (sub of OSS-541). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * refactor(OSS-543): drop doc comments on trivial asArray/asString helpers Per review: the one-line JSDoc on `asArray`/`asString` only restated the name + body (WHAT-narration). The names and one-line bodies are self-evident. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v --------- Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
…lla closed (QwikDev#366) OSS-543 (QwikDev#364) merged to main (b7fa34c); OSS-541/542/543 all Done. Bumped main SHA + Last verified; prepended the close-out entry and trimmed the log to ~10. Regenerated the .cursor/rules/STATE.mdc mirror. Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
…SWC parity) (QwikDev#367) * fix(OSS-471): MOVE single-consumer server$ binding into its segment (SWC parity) A module-level `const testServer$ = server$(…)` referenced only inside one nested `onClick$` was re-exported (`_auto_`) instead of moved into its single consumer, diverging from the reference optimizer. Four coupled fixes, each verified byte-for-byte against the reference on the canonical route shape: - Capture over-attribution: a parent extraction dropped module-level captures whose every occurrence falls inside a nested child's byte range. Gated to file-emitting strategies — under inline/hoist the child body stays inline (`q_X.s(IDENT)`), so the parent still references the name and the reexport must survive (e.g. `useStyle$(STYLES)`). - Escaped-name match in `tryBuildMarkerDeclMove` and the parallel `movedMarkerSymbols` detection: a `$`-suffixed decl's displayName is escaped (`testServer$` → `…_testServer_server`), so a raw match missed it — leaving a broken raw-text move and an un-demoted parent QRL binding. - Marker-QRL callee imports from the marker's real source (`@qwik.dev/router`), not hardcoded core. - PURE annotation on the moved wrap is per-callee (`componentQrl` pure, `serverQrl` not), via `needsPureAnnotation`. Reachable (non-stripped) output now matches the reference: parent emits a bare QRL registration, the handler segment is a self-contained `serverQrl(qrl(…))` move. The stripped variant registers via `_noopQrl` (a `qrl(()=>import(strippedChunk))` would resolve to the chunk's `null` export); its local var name is a known cosmetic divergence on an unreachable path. Three baseline tests that pinned the reexport behavior updated to the MOVE (IDs kept for the name-based gate); one focused strip-aware test added. Convergence-neutral (203/203); full suite 1208 pass, 0 regressions, +1 new. Refs: OSS-471 (sub of OSS-456). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * chore(OSS-471): trim inline docs per review Apply the comment ladder to the OSS-471 diff: delete WHAT-narration, lean on self-documenting locals (`moduleLevelCaptures`, `usedOutsideAnyChild`) and `expect(...)` message args, and drop comments the tests already guard (the inline/hoist exclusion gate is pinned by the hoist-regctxname STYLES test). Only genuinely-irrecoverable one-line WHYs remain (the module-level capture invariant, the escapeSymbol match, the retained test-ID note). No behavior change — typecheck clean, affected tests + convergence unchanged. Refs: OSS-471 (sub of OSS-456). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v * chore(OSS-471): drop remaining inline comments; rename tests to match contract Remove every inline `//` comment from the OSS-471 diff — the code, the self-documenting locals, and the `expect(...)` messages carry the intent, and the rationale lives in the commit/PR/Linear. The two router-integration tests whose names described the old reexport behavior are renamed to state the MOVE contract directly (no explanatory comment needed); the two baseline IDs are mapped through in `.ci/baseline.json` (REGRESSION.md deliberate-migration). No behavior change — typecheck clean, convergence 203/203, full 1208 pass, 0 regressions (verified against the mapped baseline). Refs: OSS-471 (sub of OSS-456). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v --------- Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
… landed (QwikDev#368) OSS-471 (single-consumer server$ binding MOVE, SWC parity) merged via PR QwikDev#367 → main (02b2610); OSS-471 Done, closing an OSS-456 sub (OSS-473 is the last open one). Bump Last-updated + measurements (convergence 203/9 unchanged; full 1209 after baseline auto-update), main-row head SHA, drop OSS-471 from the Backlog list, prepend the progress entry + trim to 10. OPTIMIZER.md audited — no update (bug-fix/type-internal; cited refs <50-line drift). Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
…migration hygiene) (QwikDev#369) Prepares the tree for migration into the Qwik core monorepo, where the SWC optimizer ships as a sibling package and "matches SWC" comments become actively misleading. Comment-only across 163 files (plus 5 test-name rewordings); no behavior change. - Comment volume 9,918 -> 2,617 lines (-74%): deleted WHAT-narration, section banners, numbered step markers, JSDoc that restated signatures, and test preambles (tests self-document via describe/it names). Kept only irrecoverable one-line WHYs (invariants, external-tool workarounds). - Scrubbed every reference-optimizer mention from comments AND test descriptions (~300 across 73 files): SWC, *.rs file:line refs, Rust fn names, @qwik.dev/optimizer, "matches SWC"/"SWC parity". Behavioral notes reworded as this optimizer's own contract. NAPI retained only where it names the native-binding ABI the public types conform to. The benchmark's functional SWC references (it loads and times the native optimizer) stay. - Renamed 7 test names that editorialized "matches SWC"/"NAPI parity"; the 7 IDs are mapped 1:1 in .ci/baseline.json (deliberate migration). Verification: oxc-based skeleton proof shows 163/168 changed files code-identical and the other 5 differ only in the intentional test-name strings; full suite 1234/1209/25 unchanged from the pre-sweep baseline; typecheck clean; baseline gate green (203 convergence, 1209 full). Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v Co-authored-by: Claude Opus 4.8 <noreply@anthropic.com>
Remove TS-Optimizer-repo-specific infrastructure that is redundant inside the Qwik monorepo (which provides its own): the .ci baseline-regression system and its scripts/, the .github workflows, .claude/.cursor agent rules, .planning docs, the agent-sync tooling, the root-only pnpm-lock.yaml, and the swc-reference-only pinned copy of the optimizer (packages/optimizer is the source of truth here). Also drop the agent-facing AGENTS.md/CLAUDE.md and the point-in-time RCA writeup. Package build/test stays self-contained (tsdown + vitest). History for every removed file is preserved in the grafted commits. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v
Reconcile package.json for its new home: drop the baseline/CI scripts (whose files were removed with the standalone infra), repoint repository/homepage/bugs to QwikDev/qwik with a `directory` field, and remove the package-level `packageManager` pin (the root owns it; its version differed from root). Add the package's dependencies to the workspace lockfile via pnpm install. Verified in-tree: typecheck clean, `tsdown` build emits dist, and the full vitest suite runs with a byte-identical pass/fail set to standalone (1209/1234 passing; the 25 failures are the pre-existing convergence/parity gaps, unchanged by the move). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v
…timizer Match the monorepo convention (packages/optimizer -> @qwik.dev/optimizer): drop the now-redundant `qwik-` prefix and scope the package under @qwik.dev. Moves the directory to packages/ts-optimizer (history preserved via git rename detection), updates package name + repository/homepage/directory metadata, the README, and the index.ts header, and regenerates the workspace lockfile. Verified in the new location: typecheck clean, build emits dist, full suite 1209/1234 passing (25 pre-existing convergence/parity failures unchanged). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CJEPKkGz766mEd1Y7pHi8v
|
Member
|
hey @scottweaver, please change target branch to main, v2 is now on main |
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.
This set of changes sees the experimental Typescript optimizer from https://github.com/thejackshelton/TS-Optimizer to a Qwik sub-package project.