Expand description
The java CodeGenerator target.
Consumes the exact same validated EtlDocument + resolved fault-tree
probabilities + AsyncApiRegistry that etdl_compiler::RustCodeGenerator
consumes — nothing in this crate re-parses .etdl, re-validates ECEL
conditions, or re-evaluates fault trees. Only the code-generation layer
differs. See docs/architecture/targets.md for the full picture.
Building this crate never requires a JDK — it only emits Java source text. A JDK is needed solely to compile the generated output, which is entirely the concern of whoever consumes the generated files.
§Output shape
etdl/runtime/*.java— a small, fixed, read-only Java runtime (WorkflowError,Publisher,BranchMonitor,RetryPolicy,BackoffStrategy,Condition) mirroring the pieces ofetdl-coreevery generated Rust file already depends on. Not document-specific; identical across every--target javainvocation.<package>/<Type>.java— one record file per distinct AsyncAPI message referenced anywhere in the document (both External and Internal References resolve throughAsyncApiRegistry::resolve_message, so — unlike the Rust target — Java never assumes a pre-existing{alias}::messages-equivalent package exists for an External Reference; it generates the record either way).<package>/<Stem>Workflow.java— onepublic final classholding the fault-tree-probability constants and onepublic staticorchestration method per event tree — the stable, read-only, autogenerated orchestration logic (branches, retries, SLA/branch monitoring, sends), structurally the same thingRustCodeGenerator::generate_event_tree_handleremits, translated to Java control flow.<package>/<Tree>Handlers.java— onepublic interfaceper event tree, one method per distincthandler:id used in that tree. This is the user-editable/application-specific boundary: the orchestration class calls through this interface, never the other way around, so a developer implements it in their own (never regenerated) class without ever touching the generated orchestration or runtime code — the same role Rust’s naming-conventionasync fn <handler>(...)functions play, made explicit as a generated contract because Java has no equivalent free-function-by-convention mechanism.
§Known scope limits (see the crate-level deliverables report)
Generated Java carries no JSON library dependency (unlike the Rust
target, which bakes in serde/serde_json): message records are plain
data carriers and Publisher.publish takes Object. (De)serialization
across the wire is left to the integration layer the developer wires up,
so the generated output — and this crate’s own compile-check test —
never require a JSON library to be on the classpath, only a JDK.