R380 In Review -> Done: approve @reference join-subquery filter conditions - #503
Closed
alf wants to merge 3438 commits into
Closed
R380 In Review -> Done: approve @reference join-subquery filter conditions#503alf wants to merge 3438 commits into
alf wants to merge 3438 commits into
Conversation
…tions
Independent-session review (reviewer session != implementer session
session_01Xhs2BcPVDn18MRfAngVovm). Verdict: approve.
- Spec -> diff alignment: both filter surfaces fixed (input-object filter
fields + direct scalar arguments) via the shared RemoteColumnPredicate
model + TypeConditionsGenerator EXISTS emitter spine; Design A honored
(EXISTS inside the generated method, call sites unchanged). All v1
deferrals (ConditionJoin rejection, composite-emitter-only, @splitQuery
no-op) recorded in the implementation commit as the spec required.
- Architecture: sealed wrapper keeps local-vs-remote off the
operator/value-arity ColumnPredicate axis; local emitter output is
byte-for-byte unchanged; the load-bearing Direct-vs-NodeIdDecodeKeys
discriminator is implemented and documented; helpers reused
(resolveColumnForReference, parsePath, JoinPathEmitter, buildInnerSelect
shape); validator mirrors at both sites.
- Tests: pipeline tier asserts model-level (both surfaces, single/multi-hop,
{key:}/{table:}, list In, nodeId-stays-local guard, ConditionJoin
rejection); execution tier proves real rows incl. the motivating bug and
absent-arg-returns-all.
- Build: full reactor green under -Plocal-db.
Carried debt (non-blocking): the new TypeConditionsGeneratorTest cases pin
the EXISTS body with code().toString() contains(...) assertions, matching
that file's pre-existing convention (R375/R79/R50) but contrary to the
"no code-string assertions on generated method bodies" principle. Behavior
is independently proven at the execution + compilation tiers, so the cases
are redundant rather than wrong. Whole-file migration filed as R387
(Backlog).
Approve actions: spec file deleted, changelog entry added (R380 @ 745c0cd),
README regenerated, R387 Backlog item filed.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01Cbz49UaK7pjQ4ap11ptvVW
…V in DevMojoTest fork) Independent In Review gate on R385 (docs.search). The slice is mostly sound, but the build is red: DevMojo.bindServer unconditionally starts the real ONNX embedder warm, so DevMojoTest's execute()-driven bind-failure test loads the bge model on a daemon thread inside the maven-plugin surefire fork, which SIGSEGVs libonnxruntime.so and aborts the build (reproduced twice). The MCP bind-failure catch arm also leaks the just-started warms (only server.close() runs, not warm cleanup). Feedback captured in the spec body; status returned to Ready for the next pass. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01EBUiBFG685scFBerUDsMem
…nery The faceted-search spec was written against a connection pipeline that has since been refactored away (ConnectionSynthesis -> ConnectionPromoter, field-first synthesis) and predates R316's (source, operation, target) model and R333's data-model framing. Phases 2-4 referenced retired seams. Rewrite Current State, Desired End State, Key Discoveries, and Phases 2-4 onto the current architecture, choosing the contained route: - FacetSpec rides GraphitronType.ConnectionType (per-type), not the slimmed FieldWrapper.Connection (per-site); new FacetsType / FacetValueType arms. - ConnectionPromoter grows the facet arm; facet types ride additionalType. - The connection fetcher carries a facet plan on ConnectionResult and a new ConnectionHelper.facets resolver issues the UNION ALL aggregate, exactly as totalCount carries (table, condition) and runs its own count today. - Operation.Facet stays unpopulated behind the ConnectionType quarantine; R314 folds the contained emit into general dispatch, as it will for Operation.Count. Adds a Contained approach section making this explicit. Phase 1 (SQL spike), Phase 5 (execution tests), Phase 6 (hierarchical), and the SQL-strategy / design-decision sections are unchanged in substance. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_017WnHmQSh6TihaiKV5NvvEz
Flesh out R99 with an implementation plan, test plan, and user-doc draft, and record the walk-up-vs-JAR-scanning design decision. Chosen approach (Option A): when graphitron:dev runs from inside a single-module reactor, walk up to the parent pom, parse <modules> in document order, and widen both the classpath scan and the source walk over the same sibling set so R351/R369 scan/walk parity is preserved. Rejected Option B (scan dependency JARs) as crossing the scanner's parse-only boundary and promoting the warned-about scanned-but-unwalked residue into the common path; consulted principles-architect. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01F3ibCAD4z6bQoFMNMkkctP
… unwind Addresses the two coupled DevMojo defects the In Review gate failed on; the build was red because DevMojoTest paid a real BgeEmbedder ONNX load that SIGSEGV'd the surefire fork. 1. Seam for the warms. DevMojo.bindServer no longer constructs DocsRag.embedderWarm() / docsWarm() directly; it goes through package-private warm factories defaulting to the DocsRag factories. DevMojoTest swaps in ONNX-free fakes (and mojoFor defaults to structured-only null warms), so the fast suite never loads the real ONNX model. Mirrors the GraphitronMcpServer structured-only / injected-warm seam. 2. Warm cleanup on the bind-failure path. The MCP-bind-failure catch arm previously closed only the LSP socket; warm cleanup lived in cleanup() (the normal Ctrl+C stop), which the exception path never reaches. A failed bind returns into a still-live JVM, so a warm left mid-load kept running on its daemon thread after execute() returned (the SIGSEGV's proximate cause). awaitAndCloseWarms() now joins each warm to its terminal state and closes the warmed docs store before rethrowing. DevMojoTest asserts the failed bind leaves no live warm and freed the docs store, paralleling the existing LSP-socket-closed assertion. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01TsvurVyFkyHFFtRis6C9pt
…d-failure cleanup) Records the two gate-blocking DevMojo defects as fixed at bba3251 and moves the item back to In Review; mvn install -Plocal-db is green. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01TsvurVyFkyHFFtRis6C9pt
… Phase 2/3, generated facet predicates Folds in the three Spec-review findings: 1. *FacetValue.value nullability is derived from the annotated filter field's element type (same scalar AND same nullability), resolving the non-null-vs-nullable contradiction. Non-null element keeps value non-null and scrubs its NULL group (IS NOT NULL); nullable element preserves the NULL bucket and round-trips. FacetSpec gains a valueNullable flag; FacetNaming keys on (scalar, nullability) to avoid type-name collisions. 2. FacetSpec record + ConnectionType.facets() land with Phase 2 in a single commit, so the "each phase build-green" invariant holds; Phase 3 owns only the rejection/validation logic. 3. Per-facet filter-minus-self predicates are generated as QueryConditions fragments (<field>Facet_<g>Condition), not reconstructed inline in the fetcher from raw env values. Keeps value binding inside the typed adapter boundary (Column value binding convention) and the resolver only composes pre-built Condition objects. Status stays Spec; reviewer for the next Spec -> Ready pass must be a different session. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CpGU7GXxCKKDwpfkgGJahj
…abel Spec-review revision (status stays Spec). Two findings from the Spec -> Ready pass: 1. The sibling-widening adds scan + walk roots over a sibling set, but unwalkedScannedModules() (the R369 scan/walk parity WARN) is a fourth reader of the reactor set that the dir-based helper cannot feed. R369 pins that diagnostic and resolveCompileSourceRoots() to one project set "so resolver and diagnostic cannot drift", so the spec must state the decision rather than leave it implicit. Added a bullet: the WARN stays reactor-scoped by design, justified by standard-layout sibling parity holding by construction (target/classes implies a co-located src/main/java); the only scanned-but-unwalked sibling case is a non-standard <build><sourceDirectory>, already out of scope, and is documented residue analogous to R369's published-JAR residue. The scan side (completion, @service/@condition resolution, unknown-class diagnostics) is unaffected in every case. 2. Re-labelled the primary test from "Pipeline-tier" to "Mojo-tier": it simulates a Maven session and asserts classpath/source assembly, the surface R351/R369 tested via AbstractRewriteMojoTest/DevMojoTest, not the SDL -> TypeSpec pipeline tier rewrite-design-principles defines. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_015X8gnp6RRyzLbEj5DJQUDR
Independent-session In Review -> Done review of R385 (MCP docs.search: build-time .adoc chunking + pre-embedded bundled index, async-loaded semantic retrieval over the documentation, R118 slice 9). Approved: spec->diff alignment complete (chunker, build-time generator, bundle-tuples divergence, dimension guard, deep link, server + DevMojo warm wiring); the dependency quarantine holds (Base64 payload avoids widening the RAG dep surface); all named test tiers present with structured-content assertions (no code-string assertions on generated bodies). The rework landed both gate-blocking DevMojo defects in the reviewer's prescribed shape: the package-private warm-factory seam keeps the real BgeEmbedder ONNX load out of the fast suite, and awaitAndCloseWarms() joins + closes the warms on the bind-failure unwind, with parallel DevMojoTest assertions. Full reactor green under -Plocal-db, no SIGSEGV. Delete the spec file; record the milestone in changelog.md (landing b0afcf8/6cb322a/d751110, rework df7525a->ee71c81). README regenerated. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_011CQv6STcAMjrUZBE3YEiGw
Independent Spec -> Ready review of R13 (faceted search on @asConnection). Plan is architecturally sound against the rewrite-design-principles, code anchors verify, test coverage spans the relevant tiers, and the open decisions left to the implementer are bounded with stated trade-offs. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01RmCwcRM6ofXU42WXytvvgB
Add the second semantic MCP tool, catalog.search: fuzzy discovery over the
database catalog by table/column names and comments, so an agent can find a
table it can only describe in natural language and hand the schema-qualified
SQL id straight to catalog.describe.
- CatalogDescriptors: pure descriptor composer (raw SQL token + normalized
words; comment-aware degradation) and snake_case/camelCase/acronym name
splitter (R118 OQ3), plus the corpus hash computed over the exact strings
embedded so the hashed and embedded artifacts cannot drift.
- CatalogSearchIndex: warm-managed, self-observing index mirroring R374's
Cache. Two gates (reference identity, content hash) over the live
catalogFacts; a changed hash re-embeds on an AsyncWarm daemon, persisting a
content-hash-keyed Lucene FSDirectory under RagConfig.cacheDir with an
embedder-identity manifest that closes the cross-model load trap, and reaps
stale sibling dirs keeping current + one prior.
- RagConfig: dev-environment cache-dir glue, room to grow.
- GraphitronMcpServer: widen the constructor with a RagConfig overload (eager
warm) and a back-compat overload (temp dir, cold warm, no ONNX); register
catalog.search returning ranked {id, schema, name, comment?, score} or the
WarmState degradation while warming/failed.
- DevMojo: supply ${project.build.directory}/graphitron-mcp-rag.
- Tests across the unit / handler / ONNX tiers; getting-started.adoc note.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01H4uSAsvUiDiSXinnvthWZC
…vMojo line cites Independent Spec -> Ready review. Plan is architecturally sound: widens at the shared reactorProjects()/collectExistingDirs seam to preserve the R351/R369 scan/walk parity invariant, and the Option A vs B rejection is principle-grounded (parse-only ClasspathScanner boundary, parity residue). Test plan asserts both parity sides at the correct mojo tier; scope/non-goals are honest. Corrected the two DevMojo line citations that drifted ~17 lines after R385's DevMojo work landed (startup line ~153->~170; WARN render DevMojo.java:171->180). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01CgDUATqTYaXTL483otUqRQ
…e failure Discriminator column emitted unqualified in cross-table join ON-clause and SELECT (ambiguous SQL when a participant's composite FK re-declares the discriminator column), plus a discriminator-column field carrying @reference misclassified as a cross-table participant field (fetcher reads a join-only alias the interface-level projection never produces). Captures the two defects and the missing execution fixture. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01FFykVoanhsujZWYC4kVhPL
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01FFykVoanhsujZWYC4kVhPL
The @table(subjekt)+@reference contortion is forced, not chosen: $fields projects each participant against the shared interface table (param typed to the participant's own jOOQ table class), so a participant on its own detail table won't compile. Captures why, narrows the defect-2 validation guard to base-table-column overlap (navn's @reference stays valid), and flags first-class discriminated joined-table inheritance as a separate larger item. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01FFykVoanhsujZWYC4kVhPL
R388 Spec: three-part fix — (A) qualify the discriminator column to the base table at all three emission sites in TypeFetcherGenerator (SELECT projection, LEFT JOIN ON-clause, WHERE IN filter); (B) reject a discriminator/base-column field carrying @reference at validation, with the predicate computed once in the classifier and mirrored by the validator; (C) add the load-bearing execution fixture (composite FK re-declaring the discriminator column) plus a validation regression test. Reviewed by principles-architect. R389 (Backlog): first-class discriminated joined-table inheritance, the deeper gap that removes the need for the @table(base)+@reference workaround. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01FFykVoanhsujZWYC4kVhPL
Spec → Ready guard satisfied: reviewer session ≠ last spec committer (disqualified session_01FFykVoanhsujZWYC4kVhPL). Verified all cited code/test references are live (TypeFetcherGenerator emission sites, TypeBuilder.extractCrossTableFields self-join skip, validateTableInterfaceType, GraphQLQueryTest FilmContent.rating coverage gap). Plan is sound: defect-1 qualification fix correctly identified as having no compile-tier guard (execution fixture load-bearing), defect-2 validator gate mandatory per validator-mirrors-classifier. One minor note for the implementer: the Workstream-B "carry the fact" anti-drift goal is best met with a shared build-time predicate helper, since the classifier-skip discards the contradiction field rather than carrying it on the model. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01KLL9hsbdAC1pbnv4UzhqkH
…with R316 The 2026-05-20 draft layered tenant routing by widening the sealed GraphitronContext (getTenantId(env)/getDslContext(T)) and stashing the routing function under a marker key. Its own Q4 flagged this as a likely revision target; a 2026-06-26 principles pass confirmed two of the three findings (thunk method, trans-axis null return) and cleared the third (byTenant rides the same typed-key mechanism R190 uses for defaultDsl, so it is not a wire-format leak). Resolved direction, reconciled with R316's (source, operation, target) model: - GraphitronContext stays at R190's three-method shape; no widening. - New per-field sealed TenantIdSource overlay (sibling to source/operation/ target, computed only when <tenantColumn> is configured) with a structural RequestScoped/SourceScoped scope split so the loader-name prefix consumer accepts only RequestScoped|Untenanted at compile time. - byTenant travels on GraphQLContext like defaultDsl; dispatch reads it inline. Five DataLoader sites and HandleMethodBody grouping consume the classified axis, not a method. - Adds a tenantColumnAbsentOnParent rejection for the SourceScoped axis alongside the three directive rejections. Also: fixed the Motivation's getContextArgument signature (R190 dropped the Class<T> param), re-anchored drifted code sites on symbols, corrected the R85 cross-reference (now independent, no method widening), and reframed Open questions (Q4 resolved; Q3 no longer dissolves; added scope-split and SourceScoped-carrier forks). Regenerated roadmap README. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01MqUb5cYzZpsMBNBQK4HPiW
Two review findings that hold against the reworked spec: - The "Depends on" prose linked single-tenant-execution-input-factory.md, which no longer exists (R190 is Done; its file was deleted). De-linked and noted that depends-on: [] is correct for a completed dependency, with the record now pointed at changelog.md. - Re-anchored the five DataLoader loader-name cites on verified current-code lines: TypeFetcherGenerator ~:5832 (was unnumbered) and MultiTablePolymorphicEmitter ~:1113/~:1182 (the second was wrongly :1201). The reviewer's other findings (Q4 open, GraphitronContext-widening sections present) were against the pre-rework spec on trunk; the reworked spec on this branch already resolved Q4 onto TenantIdSource and deleted those sections. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01MqUb5cYzZpsMBNBQK4HPiW
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01RmCwcRM6ofXU42WXytvvgB
…bled schema A @table type reachable only through a directive-driven @asConnection carrier field lost its schema-class emission: generated GraphitronSchema.java named a <Type>Type class that was never written and javac failed (regression seen on RC20). Two-level shape from the report: a @splitQuery @asConnection @reference list whose element type exposes a nested @reference list to a third type; the nested type's record and fetcher emitted but its schema class did not. Root cause is in ConnectionPromoter.rebuildAssembledForConnections. Once the carrier rewrite retypes the bare-list carrier to name its synthesised Connection, the element type is referenced only through the Connection's nodes / Edge's node type references. SchemaTransformer rebuilds its type map from the concretely-traversed graph (type references are leaves), so an element type reachable in the original schema only through that one carrier, together with its whole transitive @reference subgraph, was pruned. Surfaces either as a silent drop (missing <Type>Type schema class) or, when a surviving typeRef still points at the pruned type, an NPE in GraphQLTypeResolvingVisitor. Because the element type is never traversed, SchemaTransformer also skips a nested carrier's own @asConnection rewrite, leaving that field a bare list while its fetcher is connection-shaped (the report's variant 3 mismatch). Fix: pin each rewritten carrier's element type as a GraphQLSchema.additionalType before the transform, so the element and its subgraph stay concretely reachable and every nested carrier rewrite applies. Adds a pipeline-tier regression test covering both the nested @reference retention and the nested @asConnection retype. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01X1TJsBx3285cZcFyy7Fep2
Code, regression test, and root-cause writeup already landed on trunk (5485578). Moving the item straight to In Review (manual edit; the tool rejects the Backlog -> In Review jump) so an independent session can run the In Review -> Done workflow-gate review. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01X1TJsBx3285cZcFyy7Fep2
…or bullet Spec line 172 cited a `@LoadBearingClassifierCheck` / `@DependsOnClassifierCheck` annotation pairing "following the R190 / R204 precedent" as the classifier/emitter no-drift mechanism. Neither annotation exists in the rewrite tree, and there is no R204 roadmap item; this is the false-precedent the "Documentation names only live tests/code" principle prohibits. R190's actual no-drift mechanism is a single cached producer (`ContextArgumentClassifier`'s output on `GraphitronSchema.contextArguments`) read by both validator and emitter, plus the validator-mirror already described in the same bullet. Rephrased to that real mechanism. Spec stays in Spec; this is the only blocker found in the Spec -> Ready review. The final flip needs a reviewer session different from this one (now last committer). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_013uvi6DQGzdXQmE8xZ5tBoc
File a Backlog item for a Graphitron facade convenience that collapses the buildSchema + GraphQL.newGraphQL boilerplate into Graphitron.newGraphQL() for the no-extra-wiring default case. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01YbXsM6xY7egY65SLS4XgcR
Write the spec body for the Graphitron.newGraphQL() convenience: design (returns GraphQL.Builder, delegates to single-arg buildSchema, federation-safe), call-site sweep scoped to load-bearing vs cleanup, and structural-only unit coverage plus execution/federation assertions (no banned body-string matching). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01YbXsM6xY7egY65SLS4XgcR
…etention Independent-session In Review -> Done review of R390. The fix pins each rewritten carrier's element type as a GraphQLSchema.additionalType before the connection rebuild transform, so an element reachable only through the synthesised Connection's node typeRefs (and its transitive subgraph) stays concretely reachable instead of being pruned by SchemaTransformer. Verified: - Spec -> diff alignment: delivers exactly the pinning approach the spec named; nothing in scope unshipped, nothing out-of-scope landed. - Architectural soundness: "pinning direct carrier elements suffices" holds for deeper nesting (every carrier at every depth is in the rewrite set, so each element is pinned), multiple carriers sharing an element (deduped by name via putIfAbsent), and structural SDL-declared connections (no typeRef introduced, element stays concretely referenced, so not at risk). carrierElementType null-degrades cleanly. - Test coverage: NestedConnectionElementRetentionPipelineTest present, asserts nested @reference retention and nested @asConnection retype on schema structure; no code-string assertions on generated bodies. Both cases pass. - Build green: full reactor passes under mvn install -Plocal-db. Deleted the spec file; recorded the milestone in changelog.md; regenerated the roadmap README. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01Mk7pdF1ah1ZvmimY5PYsD5
…tems + a code straggler
R237 retired the @LoadBearingClassifierCheck / @DependsOnClassifierCheck
annotation pair and swept most references, but a few live ones survived:
- R239 (column-field-parent-table-record-component) and R240
(tablemethod-return-type-token-threading), the two structural-lift follow-ups
R237 spawned, still described their origin via the retired annotation keys
("candidate keyed `...`", "the annotation `...` retires with R237", "rubrics
no longer push the annotation pattern"). Rephrased to keep the R237 Phase 2
origin lineage and the technical substance while dropping the dead
annotation/key framing; R237 has shipped, so the Phase-1/Phase-4 timing
preconditions are dropped as satisfied. README roll-up regenerated.
- FieldBuilder.requireDmlDataTableMatchesInputTable javadoc opened with
"Load-bearing classifier check (R75 Phase 1)"; reworded to describe the
invariant the method actually validates.
The changelog is deliberately untouched: its references are the accurate
historical record of the annotations' use and their R237 retirement.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_013uvi6DQGzdXQmE8xZ5tBoc
…reference-on-base-column Fixes two runtime defects in the discriminated-interface (@table + @discriminate) fetcher path, both invisible to compile-time checks and uncaught by any test. Defect 1 (TypeFetcherGenerator): the discriminator column was emitted as a bare DSL.field(DSL.name(col)) at all three sites (SELECT projection, LEFT JOIN ON-clause, WHERE filter). When a participant's FK-target detail table re-declares the discriminator column via a composite FK, that bare reference is ambiguous and PostgreSQL rejects the query once the join fires. Now qualified to the base table via a two-part DSL.name(baseTableSqlName, col) — renders "base"."col" and preserves the Field<Object> the .eq(String)/.in(String...) predicates need (a table-instance reference would type as Field<?> and fail to compile). The three helpers thread the base table's SQL name. Defect 2 (TypeBuilder.extractCrossTableFields): a participant @reference field whose resolved column already exists on the interface/base table is a contradiction. Detected once with the catalog in scope: the field is skipped from the cross-table set (classifier narrowing) and a build diagnostic is registered, surfaced through the validator's existing drainBuildDiagnostics as an INVALID_SCHEMA author error with file:line and a detail-column candidate hint. (The spec called for validator-side emission, but validateTableInterfaceType has no catalog access; the diagnostic-drain is the faithful realisation of "resolve once, validator reads rather than recomputes".) A participant-only @reference field stays valid. Fixture (Workstream C): jti_subject + jti_app_account + jti_person joined-inheritance tables in init.sql (detail tables re-declare the discriminator via composite FK), the corresponding corrected-shape SDL in the example schema, execution-tier regression tests (GraphQLQueryTest.allSubjects_*), and validation pipeline tests (DiscriminatorReferenceContradictionPipelineTest). Bumped jooq.codegen.schema.version to force catalog regeneration. mvn install -Plocal-db green end-to-end. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01KLL9hsbdAC1pbnv4UzhqkH
Independent Spec -> Ready review. All cited references verified accurate:
GraphitronFacadeGenerator.generate(...), GraphqlEngine.java:16-17,
GraphQLQueryTest:80-81, FederationBuildSmokeTest (_service { sdl } precedent +
the line-62 single-arg-delegates-to-two-arg proof), the facade unit test at
lines 35-39, and the example README pattern. Design mirrors the newExecutionInput
builder-return convention, keeps buildSchema the single schema producer, honors
the code-string-assertion ban, and pins the one silent-failure risk (federation
wrap) with an execution assertion rather than prose. No material findings.
Reviewer (session_013uvi6DQGzdXQmE8xZ5tBoc) != last spec committer
(session_01YbXsM6xY7egY65SLS4XgcR).
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_013uvi6DQGzdXQmE8xZ5tBoc
Facets are a best-effort aggregate, not a structural guarantee. Relax the per-facet fields on the Facets object from [XFacetValue!]! to [XFacetValue!] (nullable list, non-null elements) and document the failure semantics: a facet query failure or timeout degrades to null rather than bubbling through GraphQL non-null propagation to abort the connection or request. Each per-facet field being nullable also keeps the wire contract stable for a future split into one query per facet field that can succeed or fail individually. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01RmCwcRM6ofXU42WXytvvgB
…return Reworked the first implementation pass (1b6971d) onto current trunk, which now carries R405's shared read-side re-projection helper. R406 consumes that helper instead of re-extracting it, per this item's "whichever lands first extracts; the second consumes" contract (R405 landed first). A DML @mutation(typeName: INSERT|UPDATE) returning a single-table discriminated interface (@table @discriminate, implementers pinned by @Discriminator, all sharing one jOOQ table, e.g. Content over content) was silently mis-accepted and emitted non-compiling code. The write half is a plain single-@table write; the fix is entirely on the return half. - Model: add DmlReturnExpression.DiscriminatedSingle/List carrying the read-side discrimination data (interfaceName, discriminatorColumn, knownDiscriminatorValues, participants). dmlDomainReturnType / dmlTarget map both to the Record/Table shape, like Projected*. - Classify: buildDmlField (the single DML chokepoint) resolves the return's look-ahead verdict once; a TableInterfaceType return builds the Discriminated* arm instead of Projected*. No new MutationField leaf. - Validate: dispatchPerformsReFetch recognises the Discriminated* arms as re-fetching, keeping the emitter and requiresReFetch in agreement. DELETE and Connection floors already fire for the interface case. - Emit: emitDiscriminated reuses the PK-only RETURNING transaction verbatim and re-projects through R405's buildTableInterfaceReprojection (List.of() for its alwaysProject param) keyed by a PK-IN condition off the RETURNING keys. Deleted the duplicate buildDiscriminatedReprojection. emitKeysTransaction and the composite-safe buildPkKeysCondition stay R406-owned (the DML write half R405 has no equivalent of), shared only between emitProjected and emitDiscriminated; they do not duplicate R405's records-keyed buildPkInCondition. Tests: classification + regression + DELETE-floor pins in GraphitronSchemaBuilderTest; INSERT/UPDATE pipeline shape assertions in FetcherPipelineTest; execution proof in DmlTableInterfaceReturnExecutionTest (per-__typename routing off the live discriminator, cross-table rating join, same-table description isolation, unknown-discriminator write/read asymmetry) plus a ContentInput / createContent / updateContent sakila fixture. Full reactor green under -Plocal-db. R406 -> In Review. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01MiQszkiLd3mJR6VcaxRV8y
…us spike Per feedback while in Ready (safe in-place refinements): - Reframe the motivation: the primary driver for owning compilation is that the graphitron:dev MCP server should execute GraphQL queries against the generated resolvers in-process (no Quarkus/app server), which needs the generated code as loaded, runnable .class. Incremental compile is the mechanism that keeps that viable at scale; framework reload is demoted to a secondary, framework-scoped benefit. - State that dev startup generates AND compiles the whole tree, so the graphitron-exclusive dir holds a complete runnable image before any edit (required for MCP execution; also closes the classpath-shadowing gap for consumers who exclude generated-sources). - Stop crying wolf in the compile-diagnostics taxonomy: add the benign, self-resolving third source (transient consumer-ABI inconsistency from a mid-refactor consumer surfaced via the classpath watcher); default tone is no-defect-asserted. - Resolve the output-ownership open question with a source-level Quarkus spike: quarkus:dev (RuntimeUpdatesProcessor, 3.34.5) watches its own source roots / classesPath and recompiles generated sources itself; it does not consume an external target/graphitron-classes, and front-loading it is a no-op-to-shadowing-hazard. Conclusion documented: do not front-load for Quarkus (value routed to MCP execution); the co-run consume benefit survives only for Spring DevTools and plain java/IDE runs. First-client doc and slice 6 updated accordingly. Status stays Ready. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01XFAKeBjm21AmprZLUs92E7
Split/reference batch fetchers correlate the target table to a VALUES (idx, parent_key…) derived table whose cells are typed from ColumnRef.columnClass() (the Java type) instead of the column's jOOQ DataType. A converter-backed key column (e.g. kode_numerisk_domain = BIGINT + Long⇄String converter) then renders as varchar, and the join throws "operator does not exist: <domain> = character varying". Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
…ning in-hand @service-path sites Second rework pass. Swaps the two in-hand bestGuess-over-binary-fqClassName sites the In Review -> Ready review flagged, mirroring the query-side fixes already landed, and adds a witness for each. - TypeFetcherGenerator.computeMutationServiceRecordReturnType: collapse the class-backed arm to serviceMethodCall().javaReturnType() (the mutation twin of computeServiceRecordReturnType), and correct the now-true "Identical policy" javadoc. Compile-witnessed by a nested mutation @service record payload (NestedFilmReviewPayload / NestedFilmReviewPayloadHolder.Payload) in graphitron-sakila-service/-example: mvn install -Plocal-db emits DataFetcherResult<Outcome<NestedFilmReviewPayloadHolder.Payload>> and compiles; reverting the swap reproduces the Outer$Nested javac break. - FieldBuilder.resolveErrorChannel: swap bestGuess(fqClassName) -> ClassName.get(payloadCls) (payloadCls is already loaded). Correcting the review's premise: after the R244 Outcome flip, root @service outcome fields classify to ErrorChannel.Mapped (new Outcome.ErrorList<>), so no developer payload class is emitted on the @service path and the payloadClass ClassName is never emitted there (reverting the swap leaves sakila-example output byte-identical). resolveErrorChannel's PayloadClass arm is reached by a child @service field, so the swap is witnessed at the classification tier: ErrorChannelClassificationTest.childServiceRecordField_nestedPayloadBacking_payloadClassIsStructurallyResolved asserts (object-equality on the resolved TypeName) the PayloadClass.payloadClass() is the structural Outer.Nested, not Outer$Nested. Reverting the swap fails it. The FetcherEmitter data-field cast sites (propertyOrRecordBinding / inlineSuccessRead) remain R412 (no reflected Class at the site); the error-channel witness is errors-only so it does not depend on them. Moves R370 to In Review. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01XcmnoNvZaeQDmxowznShNp
…face return Independent-session In Review -> Done review of R406 (support a single-table discriminated interface as a DML @mutation INSERT/UPDATE return type, landed at e72eb02). Go decision. Verified: - Spec -> diff alignment: all five rework items delivered. buildDiscriminatedReprojection is gone; emitDiscriminated consumes R405's shared buildTableInterfaceReprojection with List.of() for alwaysProject; the R406-owned emitKeysTransaction / buildPkKeysCondition key off the RETURNING keys and are shared cleanly between emitProjected and emitDiscriminated, distinct from R405's records-keyed buildPkInCondition. - Architecture: the new DiscriminatedSingle/List arm (over a per-verb leaf) is well-grounded in "lift the fork into the model"; the classify chokepoint resolves the interface verdict once; the dispatchPerformsReFetch validator mirror is updated in lockstep with OutputField.dmlTarget under the build-time drift guard. - Tests: unit classification + regression + DELETE-floor pins, pipeline shape assertions, and a behavior-focused execution test (per-__typename routing, cross-table join, same-table isolation, unknown-discriminator write/read asymmetry). - Build green: full reactor passes under -Plocal-db. The graphitron-core Query.allParties / JoinedTableInheritancePipelineTest red was the flagged stale-DB artifact (missing jti_* composite PKs); resolved by re-seeding rewrite_test and a clean catalog regen, orthogonal to R406. Deleted the spec file, added a changelog entry citing e72eb02 and R405 (whose buildTableInterfaceReprojection R406 consumes), regenerated the roadmap README. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_011xZ4ase6WmQEvVBHnip131
A reviewer found the KeyNodeSynthesiser half of the R407 spec rested on a false premise. KeyNodeSynthesiser.apply does not inject new null-source federation nodes; it decorates author-written @node object types in place (registry.remove + registry.add) with a @key directive. Those types are author-owned with real source locations, and no lint rule fires on the added @key. An implementer following "return the names of the nodes it synthesises" literally would union author @node type names into the exclusion set and suppress legitimate findings, violating acceptance criterion 2. Revise the spec so FederationLinkApplier / loadFederationImportedDefinitions is the sole contributor of injected names throughout (Problem, Decision, Implementation, Tests, Acceptance). KeyNodeSynthesiser.apply keeps its void signature; no second injector is threaded into loadAttributedRegistry. Strengthen the pipeline fixture to make the non-compliant author type a @node type so it doubles as a regression guard for the exclusion set. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01VRy6qDy2yYaemVFSsCbxee
…ter.Nested Independent-session In Review -> Done review. The implementation delivers the spec contract: both AccessorRef producers and the four @service-path in-hand bestGuess-over-binary-fqClassName sites now build ClassNames structurally (ClassName.get(Class) / captured javaReturnType), so a nested backing class emits the JLS-legal Outer.Nested rather than the non-compiling Outer$Nested. The two in-hand sites the prior review flagged (computeMutationServiceRecordReturnType, resolveErrorChannel) are fixed with witnesses; the no-Class-in-hand emit sites are correctly deferred to R412. Delete the spec file, record the milestone in changelog.md (landing a13523e, 4e22ee4), and regenerate the roadmap README. Full reactor green under mvn -f graphitron-rewrite/pom.xml install -Plocal-db. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01YXADrG3nSgSjetK1K65tsy
The excludedTypes name-pattern filter sits at LintEngine.run's skip points, which only see the engine's AST walk. Classifier advisories arrive pre-formed on schema.warnings() and never pass through that walk, so an excluded type would still show its classifier advisory, yet the user doc promised exclusion "silences the warning everywhere it would fire." Pick a side in prose: scope excludedTypes to engine findings only (the flat BuildWarning list has a SourceLocation but no owning-type handle to glob against; reverse-mapping it is the fragile-anchor trap option C already rejects), state classifier advisories are suppressible by rule id only, soften the doc sentence, and add a pipeline test pinning that an excluded type still shows its classifier advisory. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01DfK8XtbazhvCJZgSwpRhkb
…om linting Independent Spec review. The KeyNodeSynthesiser finding raised in the first pass was resolved by the author's revision (4eacff0): it now correctly documents KeyNodeSynthesiser as an in-place decorator (no injected names), and the pipeline fixture uses an author @node type to guard against folding decorated names into the exclusion set. FederationLinkApplier provenance is the sole injected-names contributor; all cited paths/line numbers verified. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_019g1ow9ggLM4nRvLyN29Keo
…tion bugs Two connection/pagination defects found probing Graphitron 10 output against the utdanningsregisteret consumer schema (siblings to R413): - R414: split/DataLoader connections build ConnectionResult without (table, condition), so ConnectionHelper.totalCount always returns null on nested connections though the SDL advertises totalCount: Int. - R415: ConnectionHelper.pageRequest never clamps first/last >= 0, so a negative page size reaches SQL LIMIT and throws a redacted 500. Co-Authored-By: Claude Opus 4.8 (1M context) <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01KoNNBn6Tw6cSoKooNaTXt2
R19's rebase-and-squash approach is not the path R182 takes; R182 unnests the rewrite in three ordinary commits without rewriting history. Delete the R19 item file, note the discard in changelog.md, regenerate the roadmap README. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01KoNNBn6Tw6cSoKooNaTXt2
Remove the six legacy modules (graphitron-codegen-parent, graphitron-common, graphitron-example, graphitron-maven-plugin, graphitron-servlet-parent, graphitron-schema-transform) and the root reactor pom.xml. The rewrite reactor is standalone (graphitron-rewrite/pom.xml has no parent and no dependency on any legacy module) and continues to build via -f graphitron-rewrite/pom.xml; docs/ parents to graphitron-rewrite-parent and is unaffected. Also delete .github/workflows/maven-build.yml, which ran 'mvn --file pom.xml' against the legacy root reactor on every push/PR to main and would fail the required build check the moment the root POM is gone (rewrite-build.yml already covers the rewrite reactor). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01KoNNBn6Tw6cSoKooNaTXt2
git mv every graphitron-rewrite/ entry up to the repo root except docs/ (handled in commit 3): the eleven reactor modules, graphitron-tree-sitter-natives, scripts/, roadmap/, roadmap-tool/, and the aggregator pom.xml, which becomes the root POM. graphitron-rewrite-parent is now the sole parent; child modules use the default ../pom.xml relativePath, which still resolves since parent and children moved up together. POM/path fixes required by the move: - root pom.xml <modules>: ../docs -> docs; two comment paths de-prefixed. - docs/pom.xml parent relativePath ../graphitron-rewrite/pom.xml -> ../pom.xml; render-roadmap-adoc scan dir ../graphitron-rewrite/roadmap -> ../roadmap. - roadmap-tool/pom.xml check-adoc-tables: a single repo-root scan now covers docs/ too, so the second (now out-of-repo) root is dropped. docs/ still points at graphitron-rewrite/docs/ for the architecture tree; that move and its reference repoints land in commit 3. The only test red at this boundary is ClassifiedDocTest (locates code-generation-triggers.adoc, not yet moved), fixed in commit 3. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01KoNNBn6Tw6cSoKooNaTXt2
…tecture/
Reshape the flat graphitron-rewrite/docs/ tree into a Diataxis-shaped
docs/architecture/{explanation,reference,how-to}/ folded into the site module,
and move roadmap-internal workflow.adoc out of the site.
Moves:
- explanation/: rewrite-design-principles, dispatch-axes, typed-rejection
- reference/: code-generation-triggers, argument-resolution, runtime-extension-points
- how-to/: testing, release-natives (was tree-sitter-natives-release)
- README.adoc split into index.adoc (quadrant picker + publishing policy),
reference/modules.adoc (module table), explanation/pipeline-overview.adoc
(pipeline narrative); added the three quadrant index pages.
- getting-started.adoc dissolved: its consumer content is already covered by the
manual (runtime-api reference, custom-scalars, apollo-federation, tenant-scoping,
dev-loop, tutorial), so only genuinely-new contributor internals move, into the
new how-to/dev-loop-internals.adoc (5-component breakdown, both mermaid diagrams,
federation-internals) carrying the #dev-loop-detail and #native-runtime-dependency
anchors. workflow.adoc leaves the site entirely -> roadmap/workflow.adoc.
Reference repoints:
- Intra-tree quadrant xrefs; ~11 inbound docs/** xrefs (faq, quick-start,
security, footer nav, index row, and the manual explanation/how-to/reference
pages) repointed to the new quadrant paths / manual homes; manual->architecture
refs corrected from ../../../ to ../../ now that architecture is local under docs/.
- roadmap-tool Main.java: README header, quadrant-aware mapAdocTarget (+ workflow
arm + ARCH_QUADRANT table), and the status-board header.
- docs/pom.xml: architecture/** folded into stage-adoc; stage-architecture + the
README->index copy hack removed; per-quadrant css + docinfo copy targets added.
- graphitron-mcp docs.source.dir ../../docs -> ../docs (module moved up in commit 2).
Test fixups for moved paths: ClassifiedDocTest and SealedHierarchyDocCoverageTest
doc paths; ManualXrefIntegrityTest drops the obsolete graphitron-rewrite/docs
staging remap (architecture is now first-class local content).
Full reactor green under mvn install -Plocal-db (docs profile renders); the
rendered /architecture/ Diataxis tree and /roadmap/ verified, workflow absent
from the site as intended.
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_01KoNNBn6Tw6cSoKooNaTXt2
Drop the -f graphitron-rewrite/pom.xml flag and graphitron-rewrite/ path prefixes now that the reactor root is the repo root: - rewrite-build.yml: init.sql path, mvn verify, the roadmap-tool leaf-coverage invocation (scan root graphitron-rewrite -> .), and the two artifact paths (roadmap/inference-axis-coverage.adoc); docs-build mvn -pl :graphitron-docs. - preview-docs.yml: paths filter collapses (graphitron-rewrite/docs/** folds into the existing docs/**; roadmap/** and pom.xml de-prefixed) and the docs mvn drops -f. - maven-publish.yml: init.sql path, versions:set, and deploy drop -f (the RC-aware tag regex is already in place, so the release-event path now builds the single root reactor rather than the deleted legacy one). - .gitlab-ci.yml: init.sql path, versions:set, and deploy drop -f. - tree-sitter-natives-release.yml: NATIVES_MODULE / GRAMMAR_DIR env vars de-prefixed. LeafCoverageReport: with the scan root now the repo root, the migration-mode output path changes from root.resolveSibling(docs/...) to root.resolve(docs/...) (docs is a child of root, no longer a sibling of graphitron-rewrite), and the regenerate hint drops -f and uses 'leaf-coverage .'. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01KoNNBn6Tw6cSoKooNaTXt2
De-prefix graphitron-rewrite/ from paths and drop the -f graphitron-rewrite/pom.xml flag across the docs and tooling that survived the move, and repoint the retired docs into their new homes. - CLAUDE.md: drop the legacy-out-of-scope Scope rule (whole repo is in scope now), fix the module list, common commands, doc links (architecture quadrants, roadmap/workflow.adoc), and the roadmap-tool commands. - .claude/web-environment.md: root-pom build commands, testing.adoc link, and drop the now-moot standalone-build-verify section. - .claude/skills/* and .claude/agents: roadmap/, capabilities/, module source paths, workflow.adoc -> roadmap/, architecture doc links, and mvn commands. - .claude/scripts/session-start-web-env.sh: init.sql path. - README.md: replace dead legacy-module links + legacy Building section with the rewrite manual/tutorial links and the single-reactor build. - docs/README.adoc, docs/manual/**, docs/architecture/** body text: de-prefixed paths, mvn commands, and the sakila-example / init.sql references. - rewrite-design-principles.adoc: rewrite the 'builds independently of legacy' section (no legacy tree remains) and retire verify-standalone-build.sh. - roadmap/workflow.adoc + roadmap/inference-axis-coverage.adoc: paths and the leaf-coverage regen command. - roadmap-tool (LeafCoverageReport, pom description): report-header command, migration output path (root.resolve, not resolveSibling), and description. - Emitted build diagnostics + their paired test assertions: the deferred-rejection 'see roadmap/<slug>.md' hint (Rejection, GraphitronSchemaValidator, BuildContext, FieldBuilder) and the federation-recipe message (-> docs/manual/how-to/apollo-federation.adoc), plus diagnostics-glossary.adoc and the javadoc references. - Delete .mise.toml (legacy example workflow; to be rebuilt for the rewrite later). Full reactor green under mvn install -Plocal-db (docs profile renders). Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01KoNNBn6Tw6cSoKooNaTXt2
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01KoNNBn6Tw6cSoKooNaTXt2
The R182 unwrap moved the reactor pom to repo root; R407's acceptance criteria still cited `mvn -f graphitron-rewrite/pom.xml install -Plocal-db`. Match the canonical post-unwrap form in CLAUDE.md (`mvn install -Plocal-db`). Tooling-path correction only; the design and all code/line citations remain correct post-unwrap (verified). Item stays Ready. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_019g1ow9ggLM4nRvLyN29Keo
…mojo-configuration.adoc R182 dissolved getting-started.adoc; the R408 first-client doc block named it as its home. Repoint to the live docs/manual/reference/mojo-configuration.adoc plugin-config reference (the spec's own hedged alternative), which already documents every <configuration> parameter the new <lint> block would join. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01BujyXUx4FRC3hSbMnRJTUv
…repo root Independent-session In Review -> Done review of R182 (spec: unnest-rewrite-aggregator.md). Every spec deliverable shipped across the five-commit sequence (657dd71 delete, a505cab unwrap, aad2f61 docs, cbaeb64 CI, 31750bf paths): legacy graphitron-parent reactor and maven-build.yml gone, rewrite aggregator promoted to root POM with its modules + docs at top level, docs restructured into Diataxis docs/architecture/, workflow.adoc moved to roadmap/ and absent from the site, maven-publish.yml de-prefixed with the RC-aware tag regex, roadmap-tool mapAdocTarget made quadrant-aware, R19 discarded, verify-standalone-build.sh retired, CLAUDE.md scope rule removed. Full reactor green under mvn install -Plocal-db (2406 tests in graphitron; docs site renders the /architecture/ Diataxis tree). The graphitron-core red first seen in the review sandbox (Query.allParties -> UnclassifiedField) was the known stale-rewrite_test-DB artifact (DB predated the R389 party fixture, jOOQ skipped codegen); re-seed + clean catalog regen produced a fully green reactor, orthogonal to the R182 diff. Delete the spec file, record the milestone in changelog.md, regenerate README. Also repoint changelog.md's header workflow.adoc link (../docs/workflow.adoc -> workflow.adoc) missed by the workflow.adoc relocation. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01KFwPVAeukggLNLYZjmX5Kc
Independent Spec-review sign-off. Design verified sound against the build-is-single-evaluator spine and the typed-not-stringly config guard; the excludedTypes/classifier-advisory scope asymmetry is settled in prose with a pinning test, and every named code symbol resolves at post-unnest paths. The only stale reference the R182 unwrap introduced (the dissolved getting-started.adoc doc home) was repointed to mojo-configuration.adoc in the prior commit. User confirmed the trivial doc-path edit does not disqualify this session from the reviewer-rule guard. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01BujyXUx4FRC3hSbMnRJTUv
… linting Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_019g1ow9ggLM4nRvLyN29Keo
…ting The R398 lint engine warned on federation @link import definitions (federation__FieldSet, link__Import, ...) that FederationLinkApplier injects into the registry. The author never wrote them, cannot rename them (the names are dictated by the federation spec) and cannot document them (descriptions are owned by federation-graphql-java-support), so type-names-pascal-case and types-and-fields-have-descriptions firing on them was pure noise. Identify the injected definitions by provenance from the injector, not a name heuristic: FederationLinkApplier.apply now returns the Set of names it injected (collected in its existing defs.forEach loop) instead of a bare boolean. AttributedRegistry carries that set as injectedNames() and derives the federationLink() flag from it (injected anything), collapsing the two facts into one component. LintEngine.run gains an overload taking the injected-name set and unions it with the existing BUNDLED_TYPE_NAMES exclusion at the two skip points it already has; no new skip mechanism, no new rule, no new node kind. KeyNodeSynthesiser is untouched: it decorates author @node types in place and injects no new definitions, so folding its names in would wrongly silence real author violations. Pipeline test carries a federation @link plus an author "type lowercase @node" (the exact type KeyNodeSynthesiser decorates): the injected names stay silent while the author type's pascal-case violation still fires, guarding both halves. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_019g1ow9ggLM4nRvLyN29Keo
…n implemented Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_019g1ow9ggLM4nRvLyN29Keo
… retirement main's #499 (null guard for listed enum filters) added integration-test fixtures and a record under graphitron-example/, the legacy example module. R182 retired that whole module, but its deletion set predated #499, so these seven files survived the rebase as orphans referencing a module that no longer has a pom or build. Remove them so the rebased trunk tree matches the rewrite's intended final state. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01WZA9xDNjKE6WpUK53PGnG7
Collaborator
Author
|
Fikser dette fra cli. |
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.
Independent-session review (reviewer session != implementer session
session_01Xhs2BcPVDn18MRfAngVovm). Verdict: approve.
fields + direct scalar arguments) via the shared RemoteColumnPredicate
model + TypeConditionsGenerator EXISTS emitter spine; Design A honored
(EXISTS inside the generated method, call sites unchanged). All v1
deferrals (ConditionJoin rejection, composite-emitter-only, @splitQuery
no-op) recorded in the implementation commit as the spec required.
operator/value-arity ColumnPredicate axis; local emitter output is
byte-for-byte unchanged; the load-bearing Direct-vs-NodeIdDecodeKeys
discriminator is implemented and documented; helpers reused
(resolveColumnForReference, parsePath, JoinPathEmitter, buildInnerSelect
shape); validator mirrors at both sites.
{key:}/{table:}, list In, nodeId-stays-local guard, ConditionJoin
rejection); execution tier proves real rows incl. the motivating bug and
absent-arg-returns-all.
Carried debt (non-blocking): the new TypeConditionsGeneratorTest cases pin
the EXISTS body with code().toString() contains(...) assertions, matching
that file's pre-existing convention (R375/R79/R50) but contrary to the
"no code-string assertions on generated method bodies" principle. Behavior
is independently proven at the execution + compilation tiers, so the cases
are redundant rather than wrong. Whole-file migration filed as R387
(Backlog).
Approve actions: spec file deleted, changelog entry added (R380 @ 745c0cd),
README regenerated, R387 Backlog item filed.
Co-Authored-By: Claude Opus 4.8 noreply@anthropic.com
Claude-Session: https://claude.ai/code/session_01Cbz49UaK7pjQ4ap11ptvVW