Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
94 changes: 94 additions & 0 deletions AGENTS.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,94 @@
<!--
GENERATED FILE - DO NOT EDIT.
Template: fusion-build-internal/src/main/resources/agents/root.md
Refresh with: mvn install -pl fusion-build-internal (any full build does it too).
-->
# Yupiik Fusion - agent guide

Fusion is a reflectionless, self-contained Java framework designed to be GraalVM-native friendly.
Business code never depends on jakarta/spring/guice. Everything heavy (bean/model discovery, DI wiring,
JSON codecs, configuration binding, persistence models, proxies) is generated at COMPILE TIME by an
annotation processor; only bean resolution happens at runtime.

- Documentation site: https://yupiik.github.io/fusion/
- Example applications: https://github.com/yupiik/fusion-examples

## Requirements and build commands

Requires Java >= 17 and Maven >= 3.8 (no wrapper is committed, use your own Maven).

| Command | Purpose |
|---|---|
| `mvn install` | Full build with tests (also regenerates all AGENTS.md/CLAUDE.md files). |
| `mvn install -pl <module> -am` | Build one module and its dependencies. |
| `mvn test -pl <module> -Dtest=MyTest` | Run a single test class. |
| `mvn license:format` | Add/fix the mandatory Apache-2.0 Yupiik license headers. |
| `mvn install -DskipTests ossindex:audit` | Dependency security audit. |
| `mvn compile yupiik-tools:serve-minisite -e` | Preview the documentation site (run in `fusion-documentation`). |

## Module map

Each module has its own `AGENTS.md` with entry points and module specific rules.

| Module | Description |
|---|---|
| [fusion-api](fusion-api/AGENTS.md) | Fusion runtime API: IoC container, scopes, lifecycle, events and configuration. |
| [fusion-processor](fusion-processor/AGENTS.md) | Fusion annotation processor generating beans, JSON codecs, configuration binding and persistence models at build time. |
| [fusion-build-api](fusion-build-api/AGENTS.md) | API which is used by the annotation processor but not the runtime. |
| [fusion-json](fusion-json/AGENTS.md) | Reflectionless JSON mapping with compile time generated codecs, JSON-Patch/Pointer/diff utilities. |
| [fusion-http-server](fusion-http-server/AGENTS.md) | HTTP server based on Apache Tomcat with a light request/response API and endpoint matchers. |
| [fusion-testing](fusion-testing/AGENTS.md) | JUnit 5 integration to test Fusion applications (container lifecycle, injection, CLI launcher). |
| [fusion-jsonrpc](fusion-jsonrpc/AGENTS.md) | JSON-RPC 2.0 server on top of the Fusion HTTP server with OpenRPC support. |
| [fusion-cli](fusion-cli/AGENTS.md) | Command line application support with compile time generated commands. |
| [fusion-httpclient-parent](fusion-httpclient-parent/AGENTS.md) | Parent of the Fusion HTTP client extensions. |
| [fusion-httpclient](fusion-httpclient-parent/fusion-httpclient/AGENTS.md) | Extended java.net.http client: routing, throttling, retries, logging listeners. |
| [fusion-kubernetes-client](fusion-httpclient-parent/fusion-kubernetes-client/AGENTS.md) | Lightweight Kubernetes client based on the JDK HTTP client (in-cluster and kubeconfig support). |
| [fusion-tracing](fusion-tracing/AGENTS.md) | Zipkin oriented tracing for the Fusion HTTP server and clients. |
| [fusion-observability](fusion-observability/AGENTS.md) | Observability HTTP server exposing health checks and OpenMetrics metrics. |
| [fusion-persistence](fusion-persistence/AGENTS.md) | Lightweight reflectionless JDBC persistence with compile time generated entity models. |
| [fusion-documentation](fusion-documentation/AGENTS.md) | AsciiDoc minisite of the project and documentation generators (configuration, OpenRPC converters). |
| [fusion-handlebars](fusion-handlebars/AGENTS.md) | Handlebars templating engine implementation without any dependency. |
| [fusion-jwt](fusion-jwt/AGENTS.md) | JWT signing and validation based on JDK cryptography. |
| [fusion-kubernetes-operator-base](fusion-kubernetes-operator-base/AGENTS.md) | Base to build Kubernetes operators with Fusion (watch/reconcile runtime, CRD support). |
| [fusion-build-internal](fusion-build-internal/AGENTS.md) | Internal build tooling keeping repository agent files (AGENTS.md/CLAUDE.md) in sync. Never published. |

How consumers use Fusion (the "triad"): applications depend on `fusion-build-api` + `fusion-processor`
in `provided` scope (compile time only) and `fusion-api` in `compile` scope (runtime). Opt-in modules
(json, http-server, jsonrpc, cli, persistence, ...) are added as needed.

## Design rules (do not break these)

- NO REFLECTION in runtime code paths: user code is bound through processor-generated classes, never
`java.lang.reflect` lookups on business classes. This is the core promise of the framework.
- New user-facing annotations go in `fusion-build-api` (package `io.yupiik.fusion.framework.build.api.*`)
and MUST be handled in `fusion-processor` (they are compile-time only, `provided` scope for consumers).
- Package conventions: public API in `...api`, extension points in `...spi`, implementation details in
`...internal` or `...impl` (never referenced from user documentation or other modules' public API).
- There is deliberately NO declarative interceptor support - this is a documented design choice, do not add one.
- Keep modules dependency-light: no new third party runtime dependency without strong justification
(Tomcat in `fusion-http-server` is the notable exception).

## Coding conventions

- Every `.java`, `.xml`, `.properties` and `.yaml` file starts with the Apache-2.0 Yupiik header
(checked at `validate` phase, fix with `mvn license:format`).
- Java 17 level: records, switch expressions, `var` are idiomatic here; parameters and locals are
typically `final`.
- ASCII-only content in sources and documentation.

## Testing conventions

- JUnit Jupiter, test classes are package-private, named `*Test`, mirroring the main package layout.
- Surefire runs tests IN PARALLEL (classes and methods, `junit.jupiter.execution.parallel.enabled=true`):
tests must not rely on shared mutable global state, fixed network ports or the working directory.
- Use `fusion-testing` helpers: `@FusionSupport`/`@MonoFusionSupport` (container lifecycle), `@Fusion`
(injection in tests), `@FusionCLITest` with `Stdout`/`Stderr` for CLI, `TestClient` for HTTP.

## Documentation workflow

- The site is AsciiDoc, sources in `fusion-documentation/src/main/minisite/content/fusion/*.adoc`.
- `fusion-documentation/src/main/minisite/content/_partials/generated/**` is GENERATED from the
annotation metadata - never edit by hand.
- User-facing feature changes need a matching `.adoc` update.
- All `AGENTS.md` files and `CLAUDE.md` are GENERATED by `fusion-build-internal`: edit the templates in
`fusion-build-internal/src/main/resources/agents/` then run `mvn install -pl fusion-build-internal`.
11 changes: 11 additions & 0 deletions CLAUDE.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
<!--
GENERATED FILE - DO NOT EDIT.
Template: fusion-build-internal/src/main/resources/agents/claude.md
Refresh with: mvn install -pl fusion-build-internal (any full build does it too).
-->
@AGENTS.md

Per-module guides live in each module directory (`<module>/AGENTS.md`), read the one matching the module you work on.

Note: this file and all `AGENTS.md` files are generated by `fusion-build-internal`. To change them, edit the
templates in `fusion-build-internal/src/main/resources/agents/` and run `mvn install -pl fusion-build-internal`.
58 changes: 58 additions & 0 deletions fusion-api/AGENTS.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,58 @@
<!--
GENERATED FILE - DO NOT EDIT.
Template: fusion-build-internal/src/main/resources/agents/module/fusion-api.md
Refresh with: mvn install -pl fusion-build-internal (any full build does it too).
-->
# Fusion :: API (`fusion-api`)

Fusion runtime API: IoC container, scopes, lifecycle, events and configuration.

Runtime side of the framework: the IoC container consumers embed in their application.

## Entry points

- `io.yupiik.fusion.framework.api.ConfiguringContainer`: bootstrap API (`ConfiguringContainer.of().start()`).
- `io.yupiik.fusion.framework.api.RuntimeContainer` / `Instance`: running container and bean instance handles.
- `io.yupiik.fusion.framework.api.scope`: `@ApplicationScoped` (lazy singleton) and `@DefaultScoped` (instance per lookup).
- `io.yupiik.fusion.framework.api.event`: event bus (`Emitter`), container lifecycle events `Start`/`Stop`.
- `io.yupiik.fusion.framework.api.configuration.Configuration`: runtime configuration lookup abstraction.
- `io.yupiik.fusion.framework.api.main.Launcher`: default `main` entry point for applications
(`CliLauncher` variant for CLI applications - it skips the command name argument, prefer it with `fusion-cli`).
- `io.yupiik.fusion.framework.api.spi.FusionModule`: SPI the generated code implements to register beans/listeners.

## Declaring and consuming beans

```java
@ApplicationScoped
public class MyService {
@Injection
OtherBean dependency; // or constructor injection; wired by generated code, no reflection

@Init
public void start() { /* post-construct */ }

@Destroy
public void stop() { /* pre-destroy */ }

public void onStart(@OnEvent final Start start) { /* container started */ }
}

// embedding the container manually (Launcher does it for you):
try (final var container = ConfiguringContainer.of().start();
final var lookup = container.lookup(MyService.class)) {
lookup.instance().doSomething();
}
```

## Module rules

- This is the API consumers code against at runtime: any signature change is a breaking change, be conservative.
- No reflection: bean registration flows through `FusionModule` implementations generated by `fusion-processor`.



## Working in this module

- Build it: `mvn install -pl fusion-api -am` (from the repository root).
- The root [AGENTS.md](/AGENTS.md) holds the global rules: reflectionless design, license headers, parallel JUnit 5 tests, ASCII-only.

1 change: 1 addition & 0 deletions fusion-api/pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@

<artifactId>fusion-api</artifactId>
<name>Fusion :: API</name>
<description>Fusion runtime API: IoC container, scopes, lifecycle, events and configuration.</description>

<dependencies>
<dependency>
Expand Down
44 changes: 44 additions & 0 deletions fusion-build-api/AGENTS.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
<!--
GENERATED FILE - DO NOT EDIT.
Template: fusion-build-internal/src/main/resources/agents/module/fusion-build-api.md
Refresh with: mvn install -pl fusion-build-internal (any full build does it too).
-->
# Fusion :: Build API (`fusion-build-api`)

API which is used by the annotation processor but not the runtime.

All user-facing annotations live here, under `io.yupiik.fusion.framework.build.api.*`. Consumers declare this
module in `provided` scope: it is only needed at compile time, the annotation processor (`fusion-processor`)
translates the annotations into generated code.

## API catalog (generated from the classpath)

- `cli`: `@Command`
- `configuration`: `@ConfigurationModel`, `@Property`, `@RootConfiguration`
- `container`: `@DetectableContext`, `@LazyContext`
- `event`: `@OnEvent`
- `http`: `@HttpJavaMatcher`, `@HttpMatcher`
- `json`: `@JsonModel`, `@JsonOthers`, `@JsonProperty`
- `jsonrpc`: `@JsonRpc`, `@JsonRpcError`, `@JsonRpcParam`
- `kubernetes.crd`: `@CustomResourceDefinition`
- `lifecycle`: `@Destroy`, `@Init`
- `metadata`: `@BeanMetadata`, `@BeanMetadataAlias`
- `metadata.spi`: `MetadataContributor`
- `order`: `@Order`
- `persistence`: `@Column`, `@Id`, `@OnDelete`, `@OnInsert`, `@OnLoad`, `@OnUpdate`, `@Table`
- `scanning`: `@Bean`, `@Injection`

## Module rules

- Compile-time only: NEVER make runtime code require this jar.
- Adding a type here without handling it in `fusion-processor` ships a no-op API: both always change together
(plus documentation in `fusion-documentation`).
- Annotations must stay dependency-free (JDK only).



## Working in this module

- Build it: `mvn install -pl fusion-build-api -am` (from the repository root).
- The root [AGENTS.md](/AGENTS.md) holds the global rules: reflectionless design, license headers, parallel JUnit 5 tests, ASCII-only.

37 changes: 37 additions & 0 deletions fusion-build-internal/AGENTS.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,37 @@
<!--
GENERATED FILE - DO NOT EDIT.
Template: fusion-build-internal/src/main/resources/agents/module/fusion-build-internal.md
Refresh with: mvn install -pl fusion-build-internal (any full build does it too).
-->
# Fusion :: Build Internal (`fusion-build-internal`)

Internal build tooling keeping repository agent files (AGENTS.md/CLAUDE.md) in sync. Never published.

This module generates the file you are reading: all `AGENTS.md` files and the root `CLAUDE.md` are rendered
from handlebars templates at `process-classes` phase (exec-maven-plugin) and committed to git.

## Layout and entry points

- `io.yupiik.fusion.build.internal.agent.AgentsFileSynchronizer`: the generator (also a plain `main`).
- `src/main/resources/agents/root.md` and `agents/claude.md`: root `AGENTS.md`/`CLAUDE.md` templates.
- `src/main/resources/agents/module/<artifactId>.md`: per-module templates (`_default.md` fallback,
`_footer.md` shared tail).
- Data available in templates: pom data (module list, names, descriptions, java release), per-module
configuration tables from `META-INF/fusion/configuration/documentation.json`, and the `fusion-build-api`
annotation catalog.

## Module rules

- To change any AGENTS.md/CLAUDE.md: edit the template, then run `mvn install -pl fusion-build-internal`
and commit both the template and the regenerated files.
- `-Dfusion.build-internal.agents.mode=check` makes the build fail on stale files instead of rewriting them (CI friendly).
- This module is never published (deploy and central publishing are skipped).
- When a module is added to the reactor, add its template here (the build warns and falls back to `_default.md`).



## Working in this module

- Build it: `mvn install -pl fusion-build-internal -am` (from the repository root).
- The root [AGENTS.md](/AGENTS.md) holds the global rules: reflectionless design, license headers, parallel JUnit 5 tests, ASCII-only.

Loading
Loading