@@ -11,14 +11,12 @@ iteration**. Stop conditions are at the bottom.
1111## Current state
1212
1313- ** Ported operators:** 14 / 14 — all operators iterated
14- - ** Last completed:** Join-alias refactor (` processJoin ` builds ON after
15- requalify; ` requalifyTableSpec ` rewrites ` on ` predicates;
16- ` buildSelectQualifier ` looks up attr qualifiers in select list)
17- - ** Totals:** 89 cases · ** 72 ported** (5 divergent, 0 known-bug, 17
14+ - ** Last completed:** LEFT JOIN defaults (COALESCE) across core + bmg-sql
15+ - ** Totals:** 89 cases · ** 80 ported** (4 divergent, 0 known-bug, 9
1816 blocked via ` it.todo ` )
19- - ** Stopped?** yes — loop paused. Remaining 17 blocked cases need new
20- capabilities (prefix/suffix/constants push-down, CROSS JOIN, LEFT JOIN
21- defaults, LIKE predicate, transform type-tokens, UNION ALL option ).
17+ - ** Stopped?** yes — loop paused. Remaining 9 blocked cases need new
18+ capabilities (LIKE predicate, transform type-tokens, UNION ALL option,
19+ constants push-down ).
2220
2321Update the four bullets above at the end of every iteration.
2422
@@ -85,30 +83,41 @@ vs. bmg-rb's INNER-before-LEFT reordering optimization).
8583
8684---
8785
86+ ## Unblocker pass 2 — completed 2026-04-24
87+
88+ After the join-alias refactor landed (72/89), a second scoped
89+ unblocker pass took the three next-smallest items:
90+
91+ | # | Unblocker | Cases unblocked |
92+ | ---| -----------------------------------------| ----------------------------------------------|
93+ | 1 | prefix / suffix push-down (+ rename-aware ON/WHERE qualifier lookup) | prefix.01, suffix.01, join.02, join.10, restrict.07 (already ported but divergent; now correct), left_join.02 (corrected) |
94+ | 2 | CROSS JOIN push-down | join.08, join.09 |
95+ | 3 | LEFT JOIN defaults / COALESCE | left_join.03, left_join.08 |
96+
97+ Net: +8 ported cases (72 → 80/89). restrict.07 no longer divergent
98+ (was snapshotting broken SQL).
99+
100+ Side effect of item 1: JOIN ON and WHERE now resolve attr names to
101+ their underlying column (via the select list), not the alias name —
102+ which is required for correct SQL after rename/prefix/suffix.
103+
104+ ---
105+
88106## Next up (if resumed)
89107
90108Sorted by estimated effort × value. See INDEX.md "Blockers summary"
91109for the ground truth.
92110
93- 1 . ** prefix / suffix push-down** — unblocks prefix.01, suffix.01,
94- join.02, join.10, left_join.02-form cases. Medium processor
95- addition; a prefix is essentially a bulk rename.
96- 2 . ** CROSS JOIN push-down** — 2 cases (join.08, join.09). Small
97- processor (` processCrossJoin ` ) + expose on ` SqlRelation.cross_join ` .
98- 3 . ** LEFT JOIN defaults / COALESCE** — 2 cases (left_join.03,
99- left_join.08). Needs ` defaults ` arg on ` left_join ` in bmg core and
100- ` coalesce ` emission in bmg-sql.
101- 4 . ** LIKE predicate** (` rxmatch.01-02 ` , ` restrict.08-09 ` ) — 4 cases.
111+ 1 . ** LIKE predicate** (` rxmatch.01-02 ` , ` restrict.08-09 ` ) — 4 cases.
102112 Add a ` match ` predicate kind to ` @enspirit/predicate ` and wire it
103113 through bmg-sql (with dialect hook for ` ESCAPE ` ).
104- 5 . ** Transform type-token API** — 4 cases; needs declarative marker
114+ 2 . ** Transform type-token API** — 4 cases; needs declarative marker
105115 in ` Transformation ` plus a ` processTransform ` with CAST emission.
106- 6 . ** UNION ALL option** — 1 case (union.03). Needs a cross-package
116+ 3 . ** UNION ALL option** — 1 case (union.03). Needs a cross-package
107117 API change to ` Relation.union() ` options.
108- 7 . ** constants push-down** — 1 case (constants.01). Localized.
109- 8 . ** Alias-in-WHERE-after-rename** (restrict.07) and ** union
110- push-down into branches** (restrict.10/.11) — localized bmg-sql
111- processor improvements; currently divergent.
118+ 4 . ** constants push-down** — 1 case (constants.01). Localized.
119+ 5 . ** Union push-down into branches** (restrict.10/.11) — localized
120+ bmg-sql processor improvements; currently divergent.
112121
113122---
114123
@@ -259,23 +268,26 @@ Only operators supported by bmg-sql today. Port in this order.
259268- [x] ** not_matching** (4/4) — .04 ported via unblocker D
260269- [x] ** matching** (7/7) — all ported (.06 unblocked by join-alias
261270 fix, .07 via unblocker D)
262- - [x] ** left_join** (6/8) — .03/.08 blocked on defaults/COALESCE API;
263- .06 divergent on source-order join emission
264- - [x] ** restrict** (9/11) — unblocker A ported .03/.04/.05. Remaining:
265- .07 divergent (alias-in-WHERE-after-rename), .10/.11 divergent (no
266- UNION push-down), .08/.09 blocked (LIKE predicate missing)
271+ - [x] ** left_join** (8/8) — all ported via the join-alias fix +
272+ LEFT JOIN defaults; .06 divergent on source-order join emission
273+ - [x] ** restrict** (9/11) — unblocker A ported .03/.04/.05;
274+ the rename-aware qualifier lookup (unblocker pass 2 item 1) ported
275+ .07. Remaining: .10/.11 divergent (no UNION push-down), .08/.09
276+ blocked (LIKE predicate missing)
267277- [x] ** summarize** (10/10) — all ported (.05/.07 unblocked by
268278 join-alias + WHERE-qualifier fix; .09/.10 by unblocker B)
269- - [x] ** join** (10 /14) — .02/.10 blocked (prefix push-down);
270- .08/.09 blocked ( CROSS JOIN push-down); .06 divergent on bracketed
271- join shape
279+ - [x] ** join** (14 /14) — all ported via join-alias fix + prefix
280+ push-down (item 1) + CROSS JOIN push-down (item 2 ); .06/.09 divergent
281+ on join shape / FROM reorder
272282- [x] ** transform** (0/4) — all blocked: bmg core ` Transformation `
273283 is JS-function-only; bmg-sql has no ` processTransform ` / CAST
274284 emission. Test file kept as ` it.todo ` s so the blocker stays visible.
275285
276- ### Operators added outside the original 14 (by unblocker pass )
286+ ### Operators added outside the original 14 (by unblocker passes )
277287
278288- [x] ** page** (5/5) — operator added to core + bmg-sql by unblocker C.
289+ - [x] ** prefix** (1/1) — push-down added in unblocker pass 2 item 1.
290+ - [x] ** suffix** (1/1) — push-down added in unblocker pass 2 item 1.
279291
280292---
281293
@@ -290,11 +302,14 @@ loop.
290302** Still blocked:**
291303- ** rxmatch** — operator missing in bmg core and bmg-sql.
292304- ** constants** — SQL push-down missing; falls back to in-memory.
293- - ** prefix** — SQL push-down missing; falls back to in-memory (also
294- blocks join.02, join.10).
295- - ** suffix** — SQL push-down missing; falls back to in-memory.
296- - ** CROSS JOIN push-down** — blocks join.08, join.09.
297- - ** LEFT JOIN defaults / COALESCE** — blocks left_join.03, left_join.08.
305+ - ** UNION ALL** — ` Relation.union() ` has no options arg (1 case).
306+ - ** transform** — cross-package: needs type-token channel and
307+ ` processTransform ` / CAST emission (4 cases).
308+
309+ ** Resolved by unblocker pass 2:**
310+ - ~~ ** prefix** ~~ , ~~ ** suffix** ~~ — push-down added (item 1).
311+ - ~~ ** CROSS JOIN push-down** ~~ — added (item 2).
312+ - ~~ ** LEFT JOIN defaults / COALESCE** ~~ — added (item 3).
298313
299314** Resolved by the unblocker pass (A→D):**
300315- ~~ ** page** ~~ — ` Relation.page() ` surfaced by ** unblocker C** .
0 commit comments