Introspection & Observability
A core philosophy that emerges from Happen's design is the principle of radical observability. Traditional testing often involves writing example-based scripts to verify behavior before deployment. Happen enables a complementary approach: making the system so transparent and interactive that its correctness can be verified by observing it in real time.
This is the idea of a system that is "testable through usage." It shifts the focus from post-mortem debugging of logs to live, interactive exploration. Because Happen's
Causal Event Web produces a complete, verifiable audit trail of all system activity by default, you have all the raw material needed to build a deeply intuitive and observable application. The following techniques are not built-in features, but rather patterns that the framework's raw primitives make possible.
Visualizing Event Flows
The Causal Event Web is, fundamentally, a graph. Every event is a node in this graph, linked by its causationId and grouped by its correlationId. While this data is powerful, it becomes truly transformative when visualized.
By building a simple diagnostic tool that consumes the event stream, you can render the lifecycle of any transaction as a directed graph. Instead of reading logs, you can visually trace how an initial event flowed through the system, which nodes it touched, and what new events it triggered.
This provides an unparalleled, intuitive view of your system's behavior, making it immediately obvious if a workflow is behaving as expected.
A REPL for Your System
You can create a special "admin" or "diagnostic" node that allows you to interact with your live application. This is similar to the Read-Eval-Print-Loop (REPL) found in languages like Elixir or Lisp and is a powerful tool for live debugging and exploration.
Querying a Live Node's State
Your diagnostic node could send a direct request to any other node to inspect its current state.
// In your diagnostic tool's code
const apiGatewayState = await diagnosticNode.send(apiGatewayNode, {
type: 'introspect-get-state'
}).return();
// The apiGatewayNode would have a handler for this event
apiGatewayNode.on('introspect-get-state', (event, context) => {
// Return a copy of the current state
return apiGatewayNode.state.get();
});Injecting Events
The REPL could also allow you to manually inject an event into the system to trigger a flow and observe the outcome in your visualizer. This is a powerful way to test edge cases or reproduce bugs in a controlled manner.
// In your diagnostic tool's code
diagnosticNode.broadcast({
type: 'create-order',
payload: {
// Manually crafted payload to test a specific scenario
customerId: 'cust-123',
items: [{ id: 'prod-edge-case', quantity: 1 }]
}
});The Power of Observation
By embracing these patterns, you can create a development experience where observing the "usage" of your live system is the most effective and intuitive way to verify its correctness. This approach embodies the Happen philosophy: providing simple, powerful primitives that can be composed into sophisticated, transparent, and resilient systems.
Last updated