Chaos engineering extension for Quarkus -- inject latency, exceptions, HTTP failures, and dependency degradation into your running application without touching a single line of source code.
Quarkus has excellent resilience primitives (MicroProfile Fault Tolerance, Mutiny reactive timeouts, health probes), but no built-in way to trigger the failures these mechanisms are supposed to handle. Goblin fills that gap.
- Latency injection -- Artificial delay before processing (configurable min/max ms)
- Exception injection -- Throw configurable exceptions before method execution
- HTTP status forcing -- Return specific HTTP status codes (503, 500, etc.)
- Dependency degradation -- Simulate downstream service failures
- Response body injection -- Truncate or inflate the response entity (
TRUNCATEkeeps the first N%,INFLATEpads it) to break strict JSON clients and length-validating consumers - Response header injection -- Set or remove headers on emitted responses (
SETforces the value, replacing an existing header or adding it when absent;REMOVEdeletes it when present) - Client-side assaults -- Inject latency and exceptions into outgoing MicroProfile / Quarkus REST Client calls (
quarkus-rest-client) and Vert.xWebClientcalls (GoblinWebClient.enable(...), opt-in at client creation) - Multiple types simultaneously -- Enable latency + exception together for slow failure simulation
- Targeting -- By package, by annotation, by percentage of requests
- Dev UI -- Toggle assaults, edit config, view history -- all in real time
- State persistence -- Dev UI config changes survive restarts automatically (
.goblin-state.json) - Markdown report export -- Generate a factual report of config + assault history, ready to hand to an LLM for resilience review
- Dev mode only -- Chaos artifacts are physically absent from production builds
Add the dependency:
<dependency>
<groupId>io.quarkiverse.goblin</groupId>
<artifactId>quarkus-goblin</artifactId>
<version>${goblin.version}</version>
</dependency>Start in dev mode:
./mvnw quarkus:devOpen the Dev UI at http://localhost:8080/q/dev and look for the Goblin card.
# Enable/disable (default: true, only active in dev mode)
quarkus.goblin.enabled=true
# Assault type enabled at startup (can be changed at runtime via Dev UI)
quarkus.goblin.assault.type=LATENCY
# Predefined composite assault mode: NONE, SLOW_FAILURE, INTERMITTENT, TIMEOUT
# Overrides assault.type when not NONE. Individual assaults stay user-overridable.
# At startup, a non-NONE profile takes precedence over the static assault toggles/params above.
quarkus.goblin.assault.profile=NONE
# Latency settings
quarkus.goblin.assault.latency.min-milliseconds=100
quarkus.goblin.assault.latency.max-milliseconds=5000
# Exception settings
quarkus.goblin.assault.exception.type=java.lang.RuntimeException
quarkus.goblin.assault.exception.message=Goblin chaos: simulated exception
# HTTP status settings
quarkus.goblin.assault.http-status.code=503
quarkus.goblin.assault.http-status.message=Service Unavailable (Goblin chaos)
# Response body settings
quarkus.goblin.assault.body.mode=truncate
quarkus.goblin.assault.body.percentage=50
# Response header rules (actions: set, remove)
# SET forces the header with the value (replacing an existing one or adding it when absent)
# REMOVE deletes the header when present (value ignored)
quarkus.goblin.assault.headers.X-Chaos.action=set
quarkus.goblin.assault.headers.X-Chaos.value=goblin
quarkus.goblin.assault.headers.Cache-Control.action=set
quarkus.goblin.assault.headers.Cache-Control.value=no-store
# Target level (0-100% of requests affected)
quarkus.goblin.target.level=100
# Optional: include/exclude packages
# quarkus.goblin.target.include-packages=com.example.api
# quarkus.goblin.target.exclude-packages=com.example.health
# Optional: exclude annotated methods
# quarkus.goblin.target.exclude-annotations=org.eclipse.microprofile.faulttolerance.TimeoutThe Chaos Dashboard provides:
- Master toggle -- Activate/deactivate all chaos
- Profile selector -- Switch a whole assault setup (
NONE,SLOW_FAILURE,INTERMITTENT,TIMEOUT) in one click; individual toggles stay overridable - Assault type toggles -- Independent on/off for Latency, Exception, HTTP Status, Dependency Degradation, Response Body, and Response Header
- Client-side assault toggles --
client latencyandclient exceptionfor outgoing REST Client and Vert.x WebClient calls - Config sections -- Edit parameters per type (disabled with placeholders when type is off)
- Target level -- Adjust percentage of affected requests
- History -- Live chaos-testing console: 2-second auto-refresh, newest-first ordering, filters (assault type, method, time period), a summary band with totals and average injected latency, and expandable Active Config cells
- Markdown report -- "Export Markdown" button in the History panel generates a factual report of the current configuration and assault history (copy or download it), handy for pasting into an LLM assistant (e.g. Claude) for a resilience review
All changes apply instantly with WARN logs in the console and are persisted to .goblin-state.json across restarts. Invalid values are never applied: Goblin logs a clear message and applies a safe fallback -- inverted latency ranges are swapped, out-of-range HTTP status codes (100-599) fall back to 503, unknown exception classes fall back to RuntimeException, the response body percentage is clamped to its mode's valid range (0-100 for TRUNCATE, 101-1000 for INFLATE), unknown header actions are skipped, and the target level is clamped to 0-100. In the dashboard, a warning toast explains the applied correction.
- Dev mode only -- Chaos only exists in
quarkus:dev. Physically absent in production. - Zero code modification -- No annotations needed. Fully automatic instrumentation.
- Explicit logging -- WARN log emitted when chaos is active.
Each module carries its own README for contributors:
- runtime -- the assault abstraction and how to add a new assault (the extension SPI)
- runtime-dev -- the Dev UI JSON-RPC backend (dev mode only)
- deployment -- build steps, bean registration, and Dev UI wiring
- integration-tests -- the
@QuarkusTestsuite and how to extend it - docs -- the Antora documentation sources
The full AsciiDoc guide lives in docs/modules/ROOT/pages/ (index.adoc), covering assault types, targeting, configuration validation, the Dev UI (with screenshots), an end-to-end example, a JSON-RPC reference, and a FAQ.
Screenshots of the Dev UI are stored in docs/modules/ROOT/assets/images/.
Test coverage is aggregated by JaCoCo (report-aggregate on integration-tests). On every push to main, the coverage CI job recomputes the instruction coverage and publishes coverage.json to the badges branch, which feeds the badge above through a shields.io endpoint.
To inspect the full HTML report locally:
./mvnw clean install -Dno-format
open integration-tests/target/site/jacoco-aggregate/index.htmlThe badge color follows the coverage: brightgreen >= 90%, green >= 80%, yellowgreen >= 70%, yellow >= 60%, red < 60%.
- Java 25+
- Quarkus 3.38+
Apache License 2.0