Diagnostic code registry
Explanations and repairs from the bundled diagnostic registry.
Diagnostic catalogue
| Code | Title | Default severity |
|---|---|---|
| EFFX0001 | Analysis and project TypeScript versions differ | info |
| EFFX0010 | Diagnostic registry contract violated | error |
| EFFX1001 | Stable identity has conflicting content | error |
| EFFX1002 | Graph edge references an absent node | error |
| EFFX1003 | Extension node has no owner | error |
| EFFX1101 | No interpreter for annotation | error |
| EFFX1102 | Malformed or unlowerable annotation arguments | error |
| EFFX1103 | Annotation needs an operation | error |
| EFFX1104 | Unsupported declaration syntax | error |
| EFFX1105 | Handler return type is not Effect | error |
| EFFX1106 | Runtime resolution or handler binding mismatch | error |
| EFFX1107 | External binding cannot implement an executable projection | error |
| EFFX1301 | Schema argument cannot be lowered from source | error |
| EFFX1302 | Annotation name invalid or declared twice | error |
| EFFX1303 | Annotation target does not fit syntax | error |
| EFFX1304 | Annotation effect key identity collision | error |
| EFFX1306 | Definition module reaches application code | error |
| EFFX2201 | Inferred error missing from assertion | error |
| EFFX2202 | Declared error no longer inferred | error |
| EFFX2203 | Inferred error lacks a Schema address | error |
| EFFX2204 | Boundary has no inferred addressable errors | warning |
| EFFX2205 | Problem mapping does not cover operation errors | error |
| EFFX2206 | Problem mapping points outside declared codes | error |
| EFFX2302 | Inferred requirement missing from assertion | error |
| EFFX2303 | Declared requirement no longer inferred | error |
| EFFX2304 | Requirement has no stable identity | error |
| EFFX2401 | Query uses a mutating HTTP verb | error |
| EFFX2402 | Invalid HTTP contract or group | error |
| EFFX2403 | Invalid external HTTP binding | error |
| EFFX2404 | Invalid HTTP group association | error |
| EFFX2405 | Conflicting HTTP group defaults | error |
| EFFX2406 | Generated HTTP export collision | error |
| EFFX2410 | Ambiguous or conflicting request channels | error |
| EFFX2411 | Unknown request input field keys | error |
| EFFX2412 | Invalid problem identifier naming pattern | error |
| EFFX2413 | Derived problem identifiers collide | error |
| EFFX2414 | Access decision time cannot be inferred | error |
| EFFX2415 | Concrete HTTP endpoint inventory unavailable | error |
| EFFX2420 | Invalid binding group | error |
| EFFX2421 | Invalid binding function | error |
| EFFX2422 | Duplicate group binding | error |
| EFFX2423 | Invalid binding choices | error |
| EFFX2424 | Invalid binding ownership | error |
| EFFX2500 | Malformed or duplicate access contract | error |
| EFFX2501 | Command access decides in a read snapshot | error |
| EFFX2502 | Query declares a transaction decision | warning |
| EFFX2503 | Protected access lacks security middleware | error |
| EFFX2504 | HTTP exposure lacks access declaration | warning |
| EFFX2505 | HTTP root mixes visibility modes | error |
| EFFX2506 | Invalid command snapshot decision claim | error |
| EFFX2601 | Foldkit command or tagged Message contract invalid | error |
| EFFX2701 | Project target or Effect installation unsupported | error |
| EFFX2801 | Deployment entry does not reach a Worker | error |
| EFFX2802 | Required generated wiring is not referenced | error |
| EFFX2803 | Deployment references obsolete generated wiring | error |
| EFFX2804 | Surface comparison entry cannot be read | error |
| EFFX2805 | Persisted surface differs from current IR | warning |
| EFFX2806 | Wiring cannot be decided statically | warning |
| EFFX2807 | Emit mode has no wiring to check | info |
| EFFX2901 | Example operation is deprecated | warning |
| EFFX2902 | Example deprecated annotation is malformed | error |
| EFFX3001 | Unsupported Effect construct | error |
| EFFX3002 | Channel schema must be an exported named schema | error |
| EFFX3003 | Response header schema must be an exported named schema | error |
| EFFX3004 | Problem codes must be an exported const tuple | error |
| EFFX3005 | Access annotation is not a registered builder call with literal arguments | error |
| EFFX3006 | No lifter rule for callee | error |
| EFFX3007 | Success has no schema | error |
| EFFX3008 | Group not found, or not in exactly one root | error |
| EFFX3009 | No request channel to serve as operation input | error |
| EFFX3010 | Lift decision requires review | warning |
| EFFX3011 | Annotation lift could not run | error |
| EFFX3012 | Effect key is not statically resolvable | error |
| EFFX3101 | Wire contracts differ | error |
| EFFX3102 | Check passed | info |
| EFFX3103 | Check could not run | error |
| EFFX3201 | Binding keys differ from the group's endpoint keys | error |
| EFFX3202 | Binding needs hand adaptation | error |
| EFFX3401 | Persistence method must be declaration-only | error |
| EFFX3402 | Persistence port method has transport exposure | error |
| EFFX3403 | Persistence port shape or identity invalid | error |
| EFFX3404 | Query-only port has vacuous transaction laws | warning |
| EFFX4101 | Cedar projection identity invalid or ambiguous | error |
| EFFX4102 | Application Cedar policy validation error | error |
| EFFX4103 | Parameterized requirement projected by id only | warning |
| EFFX4104 | All capabilities cannot be one Cedar request | warning |
| EFFX4105 | Capability uses generic Cedar principal | info |
| EFFX4106 | Application Cedar policy validation warning | warning |
| EFFX4107 | No authorization facts to project | info |
| EFFX9001 | Example Command lacks Audit annotation | warning |
| EFFX9002 | Example Audit annotation needs an operation | error |
| EFFX9101 | Example RateLimit requires HTTP exposure | error |
| EFFX9102 | Example rate limit is effectively unlimited | warning |
EFFX0001 — Analysis and project TypeScript versions differ
Owner: frontend
Default severity: info
Severity policy: typescript-major-skew — Same-major skew is info; different-major skew is warning.
Allowed severities: info, warning
The frontend analyses with its bundled TypeScript version while the project pins another. tsc/tsgo remains authoritative. Same-major skew is informational; different-major skew warns. A package range is compared using its first numeric major, not by resolving that range.
Example 1
Before:
effx TypeScript 6.0.2; project typescript 7.0.2After:
effx TypeScript 6.0.2; project typescript 6.0.2Align the project's pin with the analysis version when practical, and always run the project's type gate.
EFFX0010 — Diagnostic registry contract violated
Owner: registry
Default severity: error
Severity policy: Fixed
Registry data must decode as DiagnosticEntry, codes must be unique across owners, and reported diagnostics (including related diagnostics) must have a registered code and a permitted severity. Invalid registry data, duplicate codes, undeclared emissions and severity-policy mismatches stop generation; they are user or extension contract diagnostics, not CompilerFault.
Example 1
Before:
extensions: [firstCopy, secondCopy]After:
extensions: [firstCopy]Load each owner once, declare every emitted code, and emit severity using its named policy.
EFFX1001 — Stable identity has conflicting content
Owner: kernel
Default severity: error
Severity policy: Fixed
Two nodes with the same StableId have different semantic content. Equivalent duplicate contributions can normalize together, but differing nodes cannot share an identity.
Example 1
Before:
Operation.query({ name: "User.Get", input: A, success: A }); Operation.query({ name: "User.Get", input: B, success: B });After:
Operation.query({ name: "User.GetA", input: A, success: A }); Operation.query({ name: "User.GetB", input: B, success: B });Give distinct operations distinct names, or make duplicate contributions identical.
EFFX1002 — Graph edge references an absent node
Owner: kernel
Default severity: error
Severity policy: Fixed
An IR edge names a source or target that is absent from the node set. This covers either or both endpoints and every edge kind.
Example 1
Before:
{ nodes: [operation], edges: [{ kind: "Requires", from: operation.id, to: missingService.id }] }After:
{ nodes: [operation, service], edges: [{ kind: "Requires", from: operation.id, to: service.id }] }Contribute each referenced node, or remove the edge when removing its node.
EFFX1003 — Extension node has no owner
Owner: kernel
Default severity: error
Severity policy: Fixed
Every Extension node needs an outgoing ExtensionOf edge to its semantic owner. An orphan extension cannot be safely interpreted or generated.
Example 1
Before:
Contribution.make([extensionNode], [])After:
Contribution.make([extensionNode], [{ kind: "ExtensionOf", from: extensionNode.id, to: operationId }])Contribute the owner edge with the extension node.
EFFX1101 — No interpreter for annotation
Owner: annotation
Default severity: error
Severity policy: Fixed
The frontend collected an annotation name, but no selected extension owns an interpreter for it. This includes generic Annotate and extension-defined spellings.
Example 1
Before:
@Annotate("Audit", { level: "sensitive" })After:
extensions: [...builtin, auditExtension]Register the interpreter through the selected config, and check the exact case-sensitive annotation name.
EFFX1102 — Malformed or unlowerable annotation arguments
Owner: annotation
Default severity: error
Severity policy: Fixed
An annotation argument does not decode against its definition, cannot be represented by source lowering, or cannot be printed for an effect clause. Source lowering accepts supported literals, object properties and exported Schema/service/runtime references, not arbitrary evaluation. It rejects computed keys, unsupported expressions and runtime calls, unresolved or unexported symbols, invalid capability/focus construction, invalid Schema/HTTP root shapes and tuple spreads whose readonly const runtime initializers disagree with their types, cycle or contain non-string elements. Definition-specific symbol checks retain the declared expectation; Schema issue text retains the decoder detail. Effect clauses additionally reject lambdas and non-finite numbers that the writer cannot print.
Example 1
Before:
@RateLimit({ perMinute: "many" })After:
@RateLimit({ perMinute: 60 })Match the argument Schema, use literal source data and exported references, repair readonly tuple initializers, and replace unprintable effect-clause arguments.
EFFX1103 — Annotation needs an operation
Owner: annotation
Default severity: error
Severity policy: Fixed
An operation-target built-in annotation was applied to a declaration without Query or Command. There is no operation node to own the contribution.
Example 1
Before:
@Http.Get("/users") static get() { return handler(); }After:
@Query({ input: Input, success: User }) @Http.Get("/users") static get() { return handler(); }Add the operation declaration, or remove the operation-target annotation.
EFFX1104 — Unsupported declaration syntax
Owner: annotation
Default severity: error
Severity policy: Fixed
Source collection requires called decorators on static methods in exported classes, exported group/model classes and exported builder values. Persistent models need one options object; group/model builders need their defined constructor forms. Operation chains must terminate with handler(fn) or declare(), with a callable handler and recognized steps. with(...) accepts one applied annotation call. Class-only decorators cannot decorate methods and operation decorators cannot decorate arbitrary class members.
Example 1
Before:
class UserOps { @Query(options) get() { return handler(); } }After:
export class UserOps { @Query(options) static get() { return handler(); } }Export the declaration, use the supported decorator target and call shape, and terminate the builder chain correctly.
EFFX1105 — Handler return type is not Effect
Owner: annotation
Default severity: error
Severity policy: Fixed
Handler signature inference requires Effect.Effect<A, E, R>. Promise, plain values and other return types do not expose the required success/error/service channels.
Example 1
Before:
handler: () => Promise.resolve(user)After:
handler: () => Effect.succeed(user)Return an Effect with the intended channels.
EFFX1106 — Runtime resolution or handler binding mismatch
Owner: annotation
Default severity: error
Severity policy: frontend-resolution-versus-core-contract — Frontend runtime resolution is warning; source and IR binding contract violations are error.
Allowed severities: error, warning
Frontend resolution warns when @effx/runtime cannot be resolved, because no effx declarations can be recognized. Core interpretation rejects an external operation carrying a local handler or signature, or a local operation lacking an authored typed handler. IR analysis also rejects either invalid binding/handler pair. These are phase-specific policies under one legacy code, not interchangeable severities.
Example 1
Before:
Operation.query(options).declare() /* local handler intended */After:
Operation.query(options).handler(handler)Install and resolve @effx/runtime for frontend warnings; use declare() for external bindings and a typed handler for local operations.
EFFX1107 — External binding cannot implement an executable projection
Owner: annotation
Default severity: error
Severity policy: Fixed
An external HTTP operation has no local implementation for RPC, CLI or Foldkit.Command. Each unsupported transport and Foldkit contribution is diagnosed separately.
Example 1
Before:
Operation.query(options).rpc.expose().declare()After:
Operation.query(options).rpc.expose().handler(handler)Supply a local typed handler for executable projections, or keep the declaration HTTP-only.
EFFX1301 — Schema argument cannot be lowered from source
Owner: annotation
Default severity: error
Severity policy: Fixed
A.fromSchema encountered an unsupported Schema AST node. Each invalid leaf is reported with its path in the annotation argument list, including object fields, arrays, records and union cases. Definition construction remains total; the compiler reports these recorded problems before interpreting uses. Replace the unsupported node with an argument-algebra description or a Schema shape the frontend can lower; a runtime transformation cannot be evaluated during source collection.
Example 1
Before:
args: { value: A.fromSchema(Schema.DateTimeUtcFromString) }After:
args: { value: A.string }Keep the source argument a string and perform the date conversion in the interpreter, rather than asking source lowering to run a Schema transformation.
EFFX1302 — Annotation name invalid or declared twice
Owner: annotation
Default severity: error
Severity policy: Fixed
Annotation names must match [A-Za-z][A-Za-z0-9._-]* and have exactly one selected definition owner. Both invalid grammar and duplicate definitions share this code.
Example 1
Before:
Annotation.define({ name: "bad name", target: "operation", args: {} })After:
Annotation.define({ name: "app.Valid", target: "operation", args: {} })Choose a valid namespaced name and register only one definition for it.
EFFX1303 — Annotation target does not fit syntax
Owner: annotation
Default severity: error
Severity policy: Fixed
An operation-target user annotation cannot decorate a class. A builder with(...) application must also target operation, not another declared target. This guard is based on the definition, not the spelling of the use.
Example 1
Before:
@RateLimit({ perMinute: 60 }) export class UserOps {}After:
export class UserOps { @Query(options) @RateLimit({ perMinute: 60 }) static get() { return handler(); } }Apply the annotation to an operation, or declare the target that fits the intended syntax.
EFFX1304 — Annotation effect key identity collision
Owner: annotation
Default severity: error
Severity policy: Fixed
Two selected annotation definitions use the same effect.key id. That id is the runtime identity, so one contribution would overwrite another on an endpoint. Key ids must be literal source identities; the currently emitted form reports duplicate owners.
Example 1
Before:
const first = Context.Reference("app/key", { defaultValue: () => 0 }); const second = Context.Reference("app/key", { defaultValue: () => 0 });After:
const first = Context.Reference("app/first", { defaultValue: () => 0 }); const second = Context.Reference("app/second", { defaultValue: () => 0 });Give each distinct annotation a unique literal key id, or share one annotation definition instead of duplicating it.
EFFX1306 — Definition module reaches application code
Owner: annotation
Default severity: error
Severity policy: Fixed
Config evaluation loads definition modules, so their runtime import closure must not reach a module declaring application operations or groups. Transitive imports count; external Effect/@effx modules and definition modules form the safe boundary.
Example 1
Before:
// rate-limit.ts
import { UserOperations } from "./users.ts";After:
// rate-limit.ts
import { A, Annotation } from "@effx/runtime";Move shared argument definitions into a leaf module without application imports, and keep operation modules downstream.
EFFX2201 — Inferred error missing from assertion
Owner: contracts
Default severity: error
Severity policy: Fixed
A local handler can fail with an inferred Schema error absent from @Errors. The assertion must exactly match the handler error channel.
Example 1
Before:
@Errors(NotFound) // handler also fails with ConflictAfter:
@Errors(NotFound, Conflict)Add the inferred error Schema or remove that handler failure.
EFFX2202 — Declared error no longer inferred
Owner: contracts
Default severity: error
Severity policy: Fixed
@Errors declares a Schema that the local handler cannot fail with. It is an exact assertion, not permission to expose extra errors.
Example 1
Before:
@Errors(NotFound, Conflict) // handler fails only with NotFoundAfter:
@Errors(NotFound)Remove the stale declaration or restore the intentional typed handler failure.
EFFX2203 — Inferred error lacks a Schema address
Owner: contracts
Default severity: error
Severity policy: Fixed
An inferred opaque error cannot become a stable exported Schema reference for generation. This is not the same as a missing @Errors member.
Example 1
Before:
handler: (): Effect.Effect<User, string> => effectAfter:
@Errors(NotFound) // map the handler error to the exported SchemaMap the opaque error to an exported Schema and declare it with @Errors.
EFFX2204 — Boundary has no inferred addressable errors
Owner: contracts
Default severity: warning
Severity policy: Fixed
The operation uses inferred errors, but no Schema-addressable errors survived inference. The generated boundary exposes none; this warning does not invent a response contract.
Example 1
Before:
Operation.query(options).handler(opaqueErrorHandler)After:
Operation.query(options).errors(NotFound).handler(schemaErrorHandler)Use an exported error Schema when the boundary must expose a failure, or accept that it exposes none.
EFFX2205 — Problem mapping does not cover operation errors
Owner: contracts
Default severity: error
Severity policy: Fixed
Http.Problems either maps a tag that is not an operation error, or leaves an operation error without a mapping or sourced HTTP status. Tags use the sourced _tag where available, not necessarily the Schema export name.
Example 1
Before:
@Http.Problems({ registry: Problems, codes: ["user.not-found"], map: {} })After:
@Http.Problems({ registry: Problems, codes: ["user.not-found"], map: { UserNotFound: "user.not-found" } })Remove map keys outside the error set and map every unsourced-status error tag.
EFFX2206 — Problem mapping points outside declared codes
Owner: contracts
Default severity: error
Severity policy: Fixed
A Http.Problems map value is absent from its codes list. The map associates an operation error tag with a code already declared by that contract.
Example 1
Before:
codes: ["user.not-found"], map: { Conflict: "user.conflict" }After:
codes: ["user.not-found", "user.conflict"], map: { Conflict: "user.conflict" }Add the mapped code to codes or point the tag at an existing declared code.
EFFX2302 — Inferred requirement missing from assertion
Owner: contracts
Default severity: error
Severity policy: Fixed
A local handler requires a service absent from @Requirements. The assertion must exactly match its inferred requirement channel.
Example 1
Before:
@Requirements(Store) // handler also requires ClockServiceAfter:
@Requirements(Store, ClockService)Add the required service or remove its use from the handler.
EFFX2303 — Declared requirement no longer inferred
Owner: contracts
Default severity: error
Severity policy: Fixed
@Requirements names a service the local handler no longer requires. External declarations have different semantics; this is a local exact-assertion mismatch.
Example 1
Before:
@Requirements(Store, ClockService) // handler only uses StoreAfter:
@Requirements(Store)Remove the stale assertion or restore the intended service use.
EFFX2304 — Requirement has no stable identity
Owner: contracts
Default severity: error
Severity policy: Fixed
An opaque inferred requirement cannot be assigned a stable effx service identity. Declare or register an exported service so the graph can address it.
Example 1
Before:
handler: (): Effect.Effect<User, never, AnonymousRequirement> => effectAfter:
export class Store extends Context.Service<Store, StoreApi>()("app/Store") {}Use or register an exported service with a stable key and source reference.
EFFX2401 — Query uses a mutating HTTP verb
Owner: http
Default severity: error
Severity policy: Fixed
A Query normally uses GET. A Query over POST needs the explicit payloadIsQuery contract; other verbs require a Command.
Example 1
Before:
@Query(...)
@Http.Put("/users")After:
@Query(...)
@Http.Get("/users")Use GET for reads, or declare a Command for mutation.
EFFX2402 — Invalid HTTP contract or group
Owner: http
Default severity: error
Severity policy: Fixed
This umbrella covers annotation target/cardinality, malformed contract data or ownership edges, missing or repeated exposures, unsafe group/root identifiers, conflicting group definitions, repeated contracts on one operation, colliding root exports, missing external group/root declarations, request and response channel constraints, status bounds, and command identity headers. Match path parameters exactly; GET cannot carry payload. conditional requires GET and responseHeaders; mediaType requires payload. payloadIsQuery requires a POST Query with explicit payload. commandIdentity belongs to a Command and requires idempotency-key and if-match headers. Http.Problems variants cover duplicate contracts, missing HTTP exposure, malformed ProblemContract data with validator detail, unsafe or empty identifier overrides, and repeated problem codes.
Example 1
Before:
@Http.Get("/users/:id")
@Http.Contract({ group: "users", success: User })After:
@Http.Get("/users/:id")
@Http.Contract({ group: "users", params: UserId, success: User })Declare params with exactly the id field. For other variants, correct the named contract constraint; attach a single contract to one operation, export one valid group and supply its concrete root when external.
Example 2
Before:
@Http.Problems({ registry: Problems, codes: ["NotFound", "NotFound"] })After:
@Http.Problems({ registry: Problems, codes: ["NotFound"] })Keep one Problems contract on an HTTP-exposed operation. Remove duplicate codes, use a nonempty identifier-safe identifier when overriding schema identity, and correct fields named by the ProblemContract validator.
EFFX2403 — Invalid external HTTP binding
Owner: http
Default severity: error
Severity policy: Fixed
Externally bound operations need a contract and metadata.operationId of the form group.endpointKey. Endpoint keys are identifier-safe and unique. A root/group cannot mix local and external bindings.
Example 1
Before:
metadata: { operationId: "get-user" }After:
metadata: { operationId: "users.getUser" }Use the declared group prefix and a unique identifier-safe endpoint key; keep every binding in a group consistently local or external.
EFFX2404 — Invalid HTTP group association
Owner: http
Default severity: error
Severity policy: Fixed
Group associations require an operation and exactly one exported Http.group value or @Http.Group class. Multiple group declarations, repeated .in(Group), unresolved references and malformed associations are rejected.
Example 1
Before:
Operation.query({ input: Input, output: Output }).in(Users).in(Users)After:
Operation.query({ input: Input, output: Output }).in(Users)Associate the operation once with one exported group; remove duplicate decorators and ensure the reference resolves to the group itself.
EFFX2405 — Conflicting HTTP group defaults
Owner: http
Default severity: error
Severity policy: Fixed
An associated HTTP operation still requires an explicit Http.Contract. Its explicit root/group must agree with its group. query: true only derives a GET Query input not already assigned to another channel.
Example 1
Before:
@Http.Contract({ root: "other", group: "users", success: User })After:
@Http.Contract({ root: "api", group: "users", success: User })Align the contract with the associated group whose root is api; remove an invalid query default or specify its channel explicitly.
EFFX2406 — Generated HTTP export collision
Owner: http
Default severity: error
Severity policy: Fixed
Different root/group identities can normalize to the same generated class, API or handler export. Empty groups are checked too.
Example 1
Before:
Http.group({ root: "api", group: "user-list" })
Http.group({ root: "api", group: "user_list" })After:
Http.group({ root: "api", group: "user-list" })
Http.group({ root: "api", group: "accounts" })Rename one group so its generated export names no longer collide.
EFFX2410 — Ambiguous or conflicting request channels
Owner: http
Default severity: error
Severity policy: Fixed
An input marked Http.headers cannot also be a body or compete with another headers schema. When input fields mix route parameters and other fields, the compiler will not invent split schemas: explicitly declare params and query or payload.
Example 1
Before:
@Http.Get("/users/:id")
@Http.Contract({ group: "users", success: User })After:
@Http.Get("/users/:id")
@Http.Contract({ group: "users", params: UserId, query: Search, success: User })Split id into UserId and search fields into Search; for mutating verbs declare payload instead of query. A headers-marked input must use the same headers channel.
EFFX2411 — Unknown request input field keys
Owner: http
Default severity: error
Severity policy: Fixed
GET or DELETE with path parameters and input keys unavailable to static analysis cannot distinguish params from query. Either explicit channel resolves this ambiguity.
Example 1
Before:
@Http.Get("/users/:id")
@Http.Contract({ group: "users", success: User })After:
@Http.Get("/users/:id")
@Http.Contract({ group: "users", params: UserId, query: Search, success: User })Declare the request channels explicitly rather than relying on inaccessible input keys.
EFFX2412 — Invalid problem identifier naming pattern
Owner: http
Default severity: error
Severity policy: Fixed
naming.problemIdentifier is data, not a function. Only {Group}, {Key}, {group} and {key} are allowed, at least one Key/key placeholder is required, and each expansion must be a safe identifier. Explicit problem identifiers still override a valid naming policy.
Example 1
Before:
defineConfig({ naming: { problemIdentifier: "{Group}Problem" } })After:
defineConfig({ naming: { problemIdentifier: "{Group}{Key}Problem" } })Include the endpoint key and use only supported placeholders and identifier characters.
EFFX2413 — Derived problem identifiers collide
Owner: http
Default severity: error
Severity policy: Fixed
Two operations derive the same problem identifier but declare different problem code lists. Equal code lists may share a name. Explicit identifier overrides are not derived collisions and remain caller-owned.
Example 1
Before:
defineConfig({ naming: { problemIdentifier: "{Key}Problem" } })After:
defineConfig({ naming: { problemIdentifier: "{Group}{Key}Problem" } })Disambiguate the pattern or explicitly name a deliberately shared problem union.
EFFX2414 — Access decision time cannot be inferred
Owner: http
Default severity: error
Severity policy: Fixed
Http.Access omits decisionTime, but its declaration has no single Query or Command from which to infer SnapshotRead or Transaction.
Example 1
Before:
@Http.Access({ ...accessOptions })After:
@Http.Access({ ...accessOptions, decisionTime: "Transaction" })Write decisionTime explicitly, or attach access to exactly one operation of the intended kind.
EFFX2415 — Concrete HTTP endpoint inventory unavailable
Owner: http
Default severity: error
Severity policy: Fixed
Endpoint inventory is a handler-factory generation precondition, never a declaration-lowering check: contract-only emission never reports EFFX2415. A concrete HttpApi root must prove finite required group and endpoint keys with matching literal identifiers; only groups whose handler factories are being emitted need their declared endpoints checked. An unresolved root leaf rejects the whole root because its unknown identifier may replace a healthy group. Report one root-level diagnostic naming the unresolved leaf, not cascading group diagnostics, and emit no factory using that root. Earlier fatal diagnostics defer inventory proof. Generate every contract imported by the authored root before handler generation, including groups outside the current invocation. Cold --emit=all is atomic and writes nothing, including no contract or manifest: contract-first is required. A failed build preserves previously owned handler outputs and publishes no partial ownership record.
Example 1
Before:
effx build --emit=all // cold: authored root imports missing generated contractsAfter:
effx build --emit=contract // every group imported by the root
effx build --emit=handlersBootstrap every imported group contract before proving handlers. Full-root contracts support full-root or healthy-only handlers; healthy-only contracts cannot bootstrap a missing unrelated group. Fix the unresolved leaf named by the root diagnostic before emitting any factory for that root.
EFFX2420 — Invalid binding group
Owner: http
Default severity: error
Severity policy: Fixed
The first argument must resolve to an exported Http.group value or @Http.Group class.
Example 1
Before:
Binding.group(value, options)After:
Binding.group(Group, { handlers, guards })Bind an exported group declaration.
EFFX2421 — Invalid binding function
Owner: http
Default severity: error
Severity policy: Fixed
Handlers, guards and guardFor must resolve to exported functions. Inline callbacks and unexported values cannot be imported by generated code.
Example 1
Before:
Binding.group(value, options)After:
Binding.group(Group, { handlers, guards })Export the function and reference its symbol.
EFFX2422 — Duplicate group binding
Owner: http
Default severity: error
Severity policy: Fixed
A canonical group symbol may have only one backend binding.
Example 1
Before:
Binding.group(value, options)After:
Binding.group(Group, { handlers, guards })Keep one binding for this group.
EFFX2423 — Invalid binding choices
Owner: http
Default severity: error
Severity policy: Fixed
A binding requires handlers and exactly one of guards or guardFor.
Example 1
Before:
Binding.group(value, options)After:
Binding.group(Group, { handlers, guards })Supply handlers and one guard factory.
EFFX2424 — Invalid binding ownership
Owner: http
Default severity: error
Severity policy: Fixed
A bound group must own at least one external operation and no locally implemented operation. Native endpoints outside effx remain supported by native mixed completion.
Example 1
Before:
Binding.group(value, options)After:
Binding.group(Group, { handlers, guards })Bind a wholly external effx group.
EFFX2500 — Malformed or duplicate access contract
Owner: access
Default severity: error
Severity policy: Fixed
Access annotations and semantic contracts must be singular. Malformed AccessContract data includes the Schema validator detail after the stable prefix.
Example 1
Before:
@Http.Access(accessOptions)
@Http.Access(accessOptions)After:
@Http.Access(accessOptions)Remove the duplicate. For malformed data, correct the fields named by the validator; extension producers must conform to AccessContractData.
EFFX2501 — Command access decides in a read snapshot
Owner: access
Default severity: error
Severity policy: Fixed
A Command cannot authorize from a read snapshot unless it makes the constrained snapshotDecisionForCommand claim. Ordinary command decisions belong in its transaction.
Example 1
Before:
decisionTime: "SnapshotRead"After:
decisionTime: "Transaction"Decide access inside the mutation transaction, so the decision and write share the relevant state.
EFFX2502 — Query declares a transaction decision
Owner: access
Default severity: warning
Severity policy: Fixed
A Query with decisionTime Transaction is accepted with a warning: the usual read-only access decision uses SnapshotRead.
Example 1
Before:
decisionTime: "Transaction"After:
decisionTime: "SnapshotRead"Use a snapshot read decision unless the query intentionally needs transactional decision semantics.
EFFX2503 — Protected access lacks security middleware
Owner: access
Default severity: error
Severity policy: Fixed
Protected HTTP access needs a security middleware marker in Http.Contract. Declaring capabilities alone does not authenticate requests.
Example 1
Before:
@Http.Contract({ group: "users", success: User })After:
@Http.Contract({ group: "users", success: User, middleware: [Security] })Include the exported middleware marker declared with security: true, whose application implementation authenticates the accepted credentials.
EFFX2504 — HTTP exposure lacks access declaration
Owner: access
Default severity: warning
Severity policy: strictAccess — Warning by default; error when strictAccess is true.
Allowed severities: error, warning
HTTP exposure requires an explicit @Http.Access contract. This is a warning by default and an error under strictAccess (including --strict-access). Declare public access explicitly too; absence is not a public-access contract.
Example 1
Before:
@Query(...)
@Http.Get("/users")After:
@Query(...)
@Http.Get("/users")
@Http.Access(accessOptions)Declare an access contract with the intended credentials, principal kinds, capabilities, scope resolver and decision time. Do not disable strict mode to hide missing access.
EFFX2505 — HTTP root mixes visibility modes
Owner: access
Default severity: error
Severity policy: Fixed
A generated ForApi client exposes its entire root. Internal and External operations cannot share a root; visibility must be uniform.
Example 1
Before:
root: "api", exposure: "Internal"
root: "api", exposure: "External"After:
root: "internalApi", exposure: "Internal"
root: "api", exposure: "External"Separate internal and external operations into different roots, or align their intended visibility.
EFFX2506 — Invalid command snapshot decision claim
Owner: access
Default severity: error
Severity policy: Fixed
snapshotDecisionForCommand requires a Command, SnapshotRead decision time, no requirements, exactly ObjectCapability credentials and exactly CapabilityHolder principals. All violated conditions are reported in their original order. An accepted shape is a reviewable assertion, not proof of resolver or guard behavior.
Example 1
Before:
snapshotDecisionForCommand: true, decisionTime: "Transaction"After:
snapshotDecisionForCommand: false, decisionTime: "Transaction"Remove the claim and use transactional command authorization. Only retain a snapshot claim when every narrow capability-only condition holds and the resolver/guard have been reviewed.
EFFX2601 — Foldkit command or tagged Message contract invalid
Owner: foldkit
Default severity: error
Severity policy: Fixed
This legacy code covers both Foldkit IR validation and frontend Message-schema lowering. Foldkit.Command needs valid UiCommand data, exactly one qualified owner edge to an operation, one command contribution, exactly one HTTP exposure and an external (not Internal) HTTP root. The interpreter also rejects duplicate annotations. Independently, frontend success/failure Message fields must reference exported tagged Schemas whose Type has a literal-union _tag. Preserve both meanings; this number is not a new target-only diagnostic.
Example 1
Before:
@Foldkit.Command({ success: Schema.String, failure: Schema.String })After:
@Foldkit.Command({ success: Saved, failure: SaveFailed }) // exported tagged Message SchemasUse exported tagged Messages, attach one command to one operation and one external HTTP exposure, and repair malformed IR ownership/data.
EFFX2701 — Project target or Effect installation unsupported
Owner: project
Default severity: error
Severity policy: Fixed
The tsconfig effx settings may be invalid, effect/package.json may be unresolved or invalid, the installed Effect version may not select a supported target, or a generated source module may be unsupported for the selected target. These are configuration/target diagnostics, not arbitrary generator failures.
Example 1
Before:
"effx": { "target": "unknown" }After:
"effx": { "target": "effect-4.0" }Select a supported target, install a supported Effect cohort, resolve its package from the project and use source modules available in that target.
EFFX2801 — Deployment entry does not reach a Worker
Owner: surface
Default severity: error
Severity policy: Fixed
The against entry neither is nor reaches a recognized Alchemy Worker program: recognition is a call of Cloudflare.Worker imported from alchemy/Cloudflare. Arbitrary similarly named functions do not count.
Example 1
Before:
effx surface check --against src/schema.tsAfter:
effx surface check --against alchemy.run.tsPoint --against at the deployment program that reaches the recognized Worker call.
EFFX2802 — Required generated wiring is not referenced
Owner: surface
Default severity: error
Severity policy: Fixed
The current surface requires a generated wiring export, but the selected deployment entry never references that export. A type-only import does not wire runtime behavior. The message uses the generated file basename.
Example 1
Before:
import type { AppRoutes } from "./.effx/generated/http.ts";After:
import { AppRoutes } from "./.effx/generated/http.ts"; // use in Worker wiringReference the generated runtime wiring from the deployment entry.
EFFX2803 — Deployment references obsolete generated wiring
Owner: surface
Default severity: error
Severity policy: Fixed
The deployment references a generated wiring export that the current build does not produce. This includes removed groups and stale modules. The message uses the generated file basename.
Example 1
Before:
import { RemovedApiHandlers } from "./.effx/generated/removed.ts";After:
import { UsersApiHandlers } from "./.effx/generated/users.ts";Remove obsolete wiring or replace it with the current generated export.
EFFX2804 — Surface comparison entry cannot be read
Owner: surface
Default severity: error
Severity policy: Fixed
The file selected with --against does not exist at the resolved path. This data diagnostic covers the existence check; other filesystem failures retain their existing failure taxonomy.
Example 1
Before:
effx surface check --against missing.tsAfter:
effx surface check --against alchemy.run.tsSupply an existing deployment entry and resolve its path from the command directory.
EFFX2805 — Persisted surface differs from current IR
Owner: surface
Default severity: warning
Severity policy: Fixed
The existing .effx/surface.json contents differ from the current normalized IR projection. Surface checking does not write or repair that file itself.
Example 1
Before:
// .effx/surface.json from before operation changesAfter:
effx buildRegenerate the persisted surface with effx build and review the updated wiring.
EFFX2806 — Wiring cannot be decided statically
Owner: surface
Default severity: warning
Severity policy: Fixed
A dynamic import with a non-literal specifier or computed namespace access into a generated module prevents static wiring analysis. The source location belongs to the undecidable expression; the warning does not claim the wiring is absent.
Example 1
Before:
const routes = generated[key];After:
const routes = generated.AppRoutes;Use a literal module specifier and a statically named export so the checker can follow runtime references.
EFFX2807 — Emit mode has no wiring to check
Owner: surface
Default severity: info
Severity policy: Fixed
The selected emit mode generates no AppRoutes or group ApiHandlers exports. Surface checking has nothing to compare for wiring in this mode.
Example 1
Before:
effx surface check --emit contractAfter:
effx surface check --emit allUse a wiring-producing emit mode when deployment wiring verification is intended.
EFFX2901 — Example operation is deprecated
Owner: example.deprecated
Default severity: warning
Severity policy: Fixed
The shipped example.deprecated extension found a deprecated annotation and reports its authored reason for each operation owner. This numeric code is a grandfathered example reservation, not a general third-party range.
Example 1
Before:
@Annotate("example.deprecated", { reason: "Use User.GetV2" })After:
// switch callers to User.GetV2 and remove the obsolete operationFollow the authored replacement reason before removing the deprecated operation.
EFFX2902 — Example deprecated annotation is malformed
Owner: example.deprecated
Default severity: error
Severity policy: Fixed
The deprecated example requires one argument shaped { reason: string } and an operation declaration to own it. Both malformed arguments and missing operation ownership are diagnosed.
Example 1
Before:
@Annotate("example.deprecated", { reason: 42 })After:
@Query(options) @Annotate("example.deprecated", { reason: "Use User.GetV2" })Supply a string reason and apply the annotation to a Query or Command.
EFFX3001 — Unsupported Effect construct
Owner: lift
Default severity: error
Severity policy: Fixed
Lift reads only the exact declaration grammar of the spec: literal keys, paths and option objects; registered application wrappers; registered metadata calls with literal arguments; registered annotation keys. A computed key, path or option object, a spread, an unknown endpoint step, an unknown pipe step, an unregistered annotation key, a form-encoded inline payload, a group prefix, group middleware or group addError, and a registered metadata call with a non-literal argument are all reported with the construct named. The endpoint is omitted from every suggestion: lift never guesses and never evaluates source.
Example 1
Before:
HttpApiEndpoint.get("list", "/items", { success: ItemsResponse }).setHeaders(CustomHeaders)After:
HttpApiEndpoint.get("list", "/items", { success: ItemsResponse })Remove the unsupported step or move the behavior into a registered wrapper; lift reports the construct instead of dropping it.
EFFX3002 — Channel schema must be an exported named schema
Owner: lift
Default severity: error
Severity policy: Fixed
A request channel or the success of an endpoint is written as inline fields, as the bare fields of another schema, or as an inline Schema expression, so it has no exported name. An effx declaration references schemas by exported name, so lift suggests a wire-preserving refactor that exports a named schema and points the channel at it. The diagnostic carries the source edits; it blocks --check unless the overlay applies it.
Example 1
Before:
query: ScopeQuery.fieldsAfter:
export const ScopeQuerySchema = Schema.Struct(ScopeQuery.fields);
// query: ScopeQuerySchemaThe bare fields are not the schema itself, because the named schema carries an identifier annotation that would add an OpenAPI component.
EFFX3003 — Response header schema must be an exported named schema
Owner: lift
Default severity: error
Severity policy: Fixed
A registered success wrapper builds its response headers inline, so no exported schema names them. Lift suggests exporting the header schema from the wrapper's module and making the wrapper use it, a wire-preserving refactor that the overlay check proves. The diagnostic carries the source edits.
Example 1
Before:
export const privateRead = (success) => HttpApiSchema.WithHeaders(success, { cache: Cache })After:
export const PrivateReadHeaders = Schema.Struct({ cache: Cache });
export const privateRead = (success) => HttpApiSchema.WithHeaders(success, PrivateReadHeaders)Export the headers once and reference the export from the wrapper.
EFFX3004 — Problem codes must be an exported const tuple
Owner: lift
Default severity: error
Severity policy: Fixed
The code list of a problem union is written inline, so the effx declaration would duplicate it. Lift suggests extracting the list into an exported const tuple that both the union and the declaration reference. A list that is not a literal array of string literals cannot be read without evaluating source and is unliftable until it is named.
Example 1
Before:
problemUnion("ReadProblem", ["not-found", "forbidden"])After:
export const ReadProblemCodes = ["not-found", "forbidden"] as const;
problemUnion("ReadProblem", ReadProblemCodes)One exported tuple is the single source of truth for the codes.
EFFX3005 — Access annotation is not a registered builder call with literal arguments
Owner: lift
Default severity: error
Severity policy: Fixed
Access is lifted only from a registered access builder called with literal arguments. A local closure, a named constant, a spread or a non-literal builder argument would require partial evaluation, which lift never performs. The endpoint is omitted from every suggestion.
Example 1
Before:
.pipe((endpoint) => annotateAccessSpec(endpoint, access(true)))After:
.pipe((endpoint) => annotateAccessSpec(endpoint, personNativeAccess({ capability: "profile.read-self", canonicalScopeResolver: "profile.current-person", decisionTime: "SnapshotRead" })))Write the access with a registered builder and literal arguments.
EFFX3006 — No lifter rule for callee
Owner: lift
Default severity: error
Severity policy: Fixed
An application helper is used as a success wrapper, metadata, access or problem helper, but no lifter rule registers it. Rules are data supplied through the definition-owned lift hook; lift never guesses a helper's meaning and never unfolds its body as authority.
Example 1
Before:
success: customResponse(UserResponse)After:
// register customResponse as a SuccessWrapper rule, or write the schema directly
success: UserResponseRegister the helper with a lift rule so lift can map it.
EFFX3007 — Success has no schema
Owner: lift
Default severity: error
Severity policy: Fixed
The success of the endpoint is a document body of a runtime content type, or another construct with no Schema. effx declares a success only by a schema, so the endpoint is not liftable. A body-less success such as HttpApiSchema.NoContent is liftable and does not produce this diagnostic.
Example 1
Before:
success: documentMutationResponse("application/pdf")After:
success: ReceiptResponseDeclare the response with a schema, or keep the endpoint as handwritten Effect.
EFFX3008 — Group not found, or not in exactly one root
Owner: lift
Default severity: error
Severity policy: Fixed
The requested group id matches no HttpApiGroup.make declaration, or the group is not added to exactly one HttpApi root. The root is the unique HttpApi.make value whose .add contains the group; zero or several roots cannot select a unique root identity.
Example 1
Before:
effx lift --group profile // the group is added to two rootsAfter:
effx lift --group profile // the group is added to one rootAdd the group to exactly one root declaration.
EFFX3009 — No request channel to serve as operation input
Owner: lift
Default severity: error
Severity policy: Fixed
An effx operation requires a fully resolved input. The endpoint declares no params, query, headers or payload schema, and no emptyInput schema is configured, so lift cannot choose an input without inventing one. Configure a real exported emptyInput schema.
Example 1
Before:
HttpApiEndpoint.get("health", "/health", { success: Health })After:
// configure emptyInput: an exported Schema for no inputName a real exported schema as the lifter's emptyInput.
EFFX3010 — Lift decision requires review
Owner: lift
Default severity: warning
Severity policy: Fixed
The effx IR contains facts with no Effect twin: the operation kind, the operation input and the real names of new exports. They cannot be validated by comparing wire contracts, so lift prints them as decisions to review and never reports them as verified.
Example 1
Before:
POST /search // lifted as a CommandAfter:
// review: the read-only POST may be a Query with payloadIsQueryReview each decision before accepting the suggestion.
EFFX3011 — Annotation lift could not run
Owner: lift
Default severity: error
Severity policy: Fixed
A registered annotation definition's compiler lift failed at one .annotate site: the definition-owned recognizer rejected the site, threw, returned a non-Result value, produced arguments that do not satisfy the definition's own lowered-args schema, or named a reference the analyzed project does not record. The diagnostic carries a closed reason and, where the recognizer's own schema-defined failure named one, the construct text; it never carries the thrown value, a message, a cause or argument payload. The site is blocked: no annotation, refactor or code plan is produced for it, and no fallback recognition runs after the hook claimed the key.
Example 1
Before:
.annotate(RateLimit.effect.key, { perMinute: -1 })After:
.annotate(RateLimit.effect.key, { perMinute: 60 })The recognizer returned its own Unsupported construct; lift blocks the site with the reason named instead of guessing.
EFFX3012 — Effect key is not statically resolvable
Owner: lift
Default severity: error
Severity policy: Fixed
An .annotate effect key is not a statically resolvable registered definition key: the source names a key-shaped reference (a .key or .effect.key chain, or a definition whose recorded key id differs from the runtime definition's own key id) and the analyzed source provides no literal key identity for it. Lift never evaluates application code, so such a key cannot become an annotation. It is distinct from EFFX3001 (a registered key that no selected definition claims, reported as today) and does not reuse the two-owners EFFX1304 entry or the check-only EFFX3103.
Example 1
Before:
.annotate(keyOfSomeService.id, { perMinute: 60 })After:
.annotate(RateLimit.effect.key, { perMinute: 60 })Write the Context key of a registered definition's effect clause through its literal key identity; lift never evaluates a key supplier.
EFFX3101 — Wire contracts differ
Owner: lift
Default severity: error
Severity policy: Fixed
The check built the Reflection of the untouched original group and of the generated group and found a difference outside the closed set of tolerated deltas. The difference is the payload of the report.
Example 1
Before:
original summary: Read own profileAfter:
generated summary: Read my profileAny difference in a wire-visible field fails the check.
EFFX3102 — Check passed
Owner: lift
Default severity: info
Severity policy: Fixed
The Reflections of the original and the generated group are equal after the closed set of delta normalizers. The applied delta classes are listed.
Example 1
Before:
effx lift --check --group profileAfter:
PASS(ref-suffix)The only tolerated differences were the named deltas.
EFFX3103 — Check could not run
Owner: lift
Default severity: error
Severity policy: Fixed
The overlay does not compile, a root cannot be built, or a registered projection hook threw. Lift stays total: a check-time exception becomes this diagnostic and never an exit by exception. It is not a pass. The definition-owned output-recognizer exceptions of the compiler lift are EFFX3011, not this entry: the 0019 check and the recognition paths report through separate closed reasons.
Example 1
Before:
effx lift --check // the overlay has a type errorAfter:
effx lift --check // the overlay compilesFix the overlay or the hook, then run the check again.
EFFX3201 — Binding keys differ from the group's endpoint keys
Owner: lift
Default severity: error
Severity policy: Fixed
The handler keys registered by the application's HttpApiBuilder.group call are not exactly the endpoint keys of the group. The key sets are compared statically without executing source.
Example 1
Before:
h.handleRaw("read", fn) // the group also declares updateAfter:
h.handleRaw("read", fn).handleRaw("update", fn)Register exactly the group's endpoint keys.
EFFX3202 — Binding needs hand adaptation
Owner: lift
Default severity: error
Severity policy: Fixed
A handler calls the application's authorization function directly, decodes the payload itself, or registers with .handle instead of .handleRaw. Moving an authorization call behind the lazy authorize callback cannot be mechanical. Lift lists each site and never invents handler code.
Example 1
Before:
yield* authorize(request) // inside the handlerAfter:
(input, authorize) => ... // lazy authorize callbackAdapt the site by hand; the binding report stays unverified until then.
EFFX3401 — Persistence method must be declaration-only
Owner: persistence
Default severity: error
Severity policy: Fixed
A persistence port method has a local handler or local binding. Ports describe an adapter capability and must not embed an application implementation.
Example 1
Before:
Operation.query({ name: "Store.Get", input: Input, success: User }).with(Port({ port: "Store" })).handler(handler)After:
Operation.query({ name: "Store.Get", input: Input, success: User }).with(Port({ port: "Store" })).declare()Use declare() and place implementation in the adapter, not the port definition.
EFFX3402 — Persistence port method has transport exposure
Owner: persistence
Default severity: error
Severity policy: Fixed
Persistence port methods cannot have HTTP, RPC or CLI exposures. They are an internal adapter interface, not an application transport boundary.
Example 1
Before:
Operation.query(options).with(Port({ port: "Store" })).http.get("/users").declare()After:
Operation.query(options).with(Port({ port: "Store" })).declare()Expose a separate application operation that calls the port.
EFFX3403 — Persistence port shape or identity invalid
Owner: persistence
Default severity: error
Severity policy: Fixed
A Port contribution needs one operation owner and { port: string }. Methods must have the port-name prefix and a nonempty method name, without duplicates. Different port names cannot collapse to the same generated filename. Duplicate Port annotations on a declaration are also rejected under this code.
Example 1
Before:
Operation.query({ ...options, name: "Get" }).with(Port({ port: "Store" })).declare()After:
Operation.query({ ...options, name: "Store.Get" }).with(Port({ port: "Store" })).declare()Repair ownership/data, use PortName.method naming, declare each method once and choose port names whose escaped lowercase filenames differ.
EFFX3404 — Query-only port has vacuous transaction laws
Owner: persistence
Default severity: warning
Severity policy: Fixed
The port declares only Queries. Generated rollback and atomicity properties are vacuous because no Command mutation exists to exercise them. This is not evidence that an adapter supports transactional writes.
Example 1
Before:
Store: { Get: Query }After:
Store: { Get: Query, Put: Command }Add a real Command if transactional write conformance is required; otherwise accept the query-only limitation.
EFFX4101 — Cedar projection identity invalid or ambiguous
Owner: cedar
Default severity: error
Severity policy: Fixed
The namespace must consist of unreserved Cedar identifiers joined by ::. Entity type names must be valid, nonreserved and not Action, and cannot merge distinct source identities into one name. Generated policy ids must also be unique. Each variant blocks projection rather than silently renaming or dropping a source.
Example 1
Before:
effx cedar --namespace 1badAfter:
effx cedar --namespace App::AuthzUse valid unreserved namespace/entity names, disambiguate source exports and ensure distinct policy identities.
EFFX4102 — Application Cedar policy validation error
Owner: cedar
Default severity: error
Severity policy: Fixed
The Cedar validator rejected an application-authored --policies file against the emitted schema. Findings retain the file, optional policy id, exact validator message and optional help. Generated Cedar validation failures remain CompilerFault invariant failures, not this diagnostic.
Example 1
Before:
permit(principal, action == Effx::Action::"operation/User.Gett", resource);After:
permit(principal, action == Effx::Action::"operation/User.Get", resource);Repair the policy using the emitted actions/entity types and the validator help, then validate again.
EFFX4103 — Parameterized requirement projected by id only
Owner: cedar
Default severity: warning
Severity policy: Fixed
An AccessContract requirement has parameters. The Cedar projection records its id but does not enforce parameter constraints. Do not mistake successful projection for full authorization equivalence.
Example 1
Before:
requirements: [{ id: "workspace.member", parameters: { role: "admin" } }]After:
// enforce role parameters in the application authorization decisionKeep parameter enforcement in the application or an explicitly authored policy; the emitted id-only model is insufficient.
EFFX4104 — All capabilities cannot be one Cedar request
Owner: cedar
Default severity: warning
Severity policy: Fixed
An AccessContract capabilities All expression, or several linked capabilities without a contract, requires all capabilities at once. One Cedar request cannot represent that conjunction, so the operation action has no capability-group parent. The legacy no-contract form reports the capability count.
Example 1
Before:
capabilities: Capability.all("read", "write")After:
// authorize the required conjunction explicitly in application policy/decision logicRetain the conjunction in application authorization; do not change All to Any just to silence the warning.
EFFX4105 — Capability uses generic Cedar principal
Owner: cedar
Default severity: info
Severity policy: Fixed
An operation declares a capability without an AccessContract. The projection falls back to the generic Principal entity type because no principalKinds contract exists. This is informational, not a statement that credentials have been checked.
Example 1
Before:
@Authorize(ReadCapability) // no Http.AccessAfter:
@Http.Access({ ...accessContract, principalKinds: ["User"] })Declare an AccessContract when the Cedar model needs the actual principal kinds.
EFFX4106 — Application Cedar policy validation warning
Owner: cedar
Default severity: warning
Severity policy: Fixed
The Cedar validator warned about an application-authored --policies file. Findings preserve file, optional policy id, exact validator message and optional help. Warnings do not block by default, but --deny-warnings makes the command fail without changing diagnostic severity.
Example 1
Before:
permit(principal, action == Effx::Action::"operation/User.Get", resource) when { false };After:
permit(principal, action == Effx::Action::"operation/User.Get", resource);Review and repair the validator finding; use --deny-warnings when policy warnings must fail the command.
EFFX4107 — No authorization facts to project
Owner: cedar
Default severity: info
Severity policy: Fixed
No operation has a capability or AccessContract. Cedar writes nothing because there is no authorization model to project, rather than emitting an empty misleading schema.
Example 1
Before:
@Query(options) static get() { return handler(); }After:
@Query(options) @Authorize(ReadCapability) static get() { return handler(); }Declare the intended capability/access facts before requesting a Cedar projection, or accept that nothing is written.
EFFX9001 — Example Command lacks Audit annotation
Owner: ai-docs
Default severity: warning
Severity policy: Fixed
The shipped handwritten Audit extension warns for each Command without its Audit ExtensionOf contribution. Queries do not trigger this rule. This is an example-owned numeric reservation only.
Example 1
Before:
Operation.command(options).handler(handler)After:
Operation.command(options).annotate("Audit", { level: "sensitive" }).handler(handler)Attach an Audit annotation and select auditExtension if the example audit policy is intended.
EFFX9002 — Example Audit annotation needs an operation
Owner: ai-docs
Default severity: error
Severity policy: Fixed
The shipped handwritten Audit interpreter cannot attach an Audit contribution when no operation id exists. This reservation is specific to the authoring example.
Example 1
Before:
@Annotate("Audit", { level: "standard" }) static get() { return handler(); }After:
@Query(options) @Annotate("Audit", { level: "standard" }) static get() { return handler(); }Add Query or Command so the Audit node has an operation owner.
EFFX9101 — Example RateLimit requires HTTP exposure
Owner: ai-docs
Default severity: error
Severity policy: Fixed
The shipped implement(RateLimit) example checks for an HTTP exposure on the annotated operation. RPC-only and unexposed operations cannot use that example rate-limit policy.
Example 1
Before:
Operation.query(options).with(RateLimit({ perMinute: 60 })).handler(handler)After:
Operation.query(options).http.get("/users").with(RateLimit({ perMinute: 60 })).handler(handler)Expose the operation through HTTP or remove this HTTP-specific example annotation.
EFFX9102 — Example rate limit is effectively unlimited
Owner: ai-docs
Default severity: warning
Severity policy: Fixed
The shipped RateLimit example warns when perMinute exceeds 10,000. At or below that threshold this analysis emits nothing; the warning does not itself enforce requests.
Example 1
Before:
@RateLimit({ perMinute: 20000 })After:
@RateLimit({ perMinute: 60 })Choose the intended finite policy value and enforce it in the relevant runtime boundary.