This Go library provides an event bus mechanism to manage event handlers, middleware, and command execution. It supports registering handlers for specific events, applying middleware, and executing commands while dispatching the resulting events to the appropriate handlers.
- Event Registration: Register handlers for specific event types.
- Middleware Support: Add middleware to modify or enhance handler behavior.
- Command Execution: Execute commands that generate events, which are then dispatched to their respective handlers.
- Concurrent Event Handling: Supports concurrent handling of events.
- Error Handling: Propagates and aggregates errors from handlers and commands for a single event.
To install mbus, you can use the following command:
go get github.com/treenoder/mbusImport mbus into your Go project:
import "github.com/treenoder/mbus/mbus"To create a new instance of the event bus, call the NewBus function:
logFunc := func(values ...any) {
fmt.Println(values...)
}
bus := mbus.NewBus(logFunc)You can pass a custom logging function, or if logFunc is set to nil, the library initializes a default empty logger.
To register a handler for a specific event type:
bus.RegisterHandler("UserRegistered", func(ctx context.Context, event mbus.Event) ([]mbus.Event, []mbus.Command, error) {
// Handle the event
return nil, nil, nil
})Middleware can be used to wrap event handlers for additional logic before and after the handler executes:
bus.UseMiddleware(func(next mbus.HandlerFunc) mbus.HandlerFunc {
return func(ctx context.Context, event mbus.Event) ([]mbus.Event, []mbus.Command, error) {
// Before handler
events, commands, err := next(ctx, event)
// After handler
return events, commands, err
}
})Commands execute logic and can generate events that are then dispatched to their registered handlers:
cmd := &MyCommand{
// Command details
}
err := bus.ExecuteCommand(context.Background(), cmd)
if err != nil {
log.Println("Error executing command:", err)
}A command must implement the Command interface:
type MyCommand struct {}
func (c *MyCommand) GetName() string {
return "MyCommand"
}
func (c *MyCommand) Execute(ctx context.Context) ([]mbus.Event, error) {
// Execute the command logic
return []mbus.Event{&MyEvent{}}, nil
}An event should implement the Event interface:
type MyEvent struct {}
func (e *MyEvent) GetType() mbus.EventType {
return "MyEvent"
}The library includes comprehensive tests to cover the main functionalities. To run the tests:
go test -v ./mbus/...The repository includes a Makefile to help automate testing and code coverage:
-
Run all tests:
make test -
Generate and display code coverage:
make cover
-
Clean up coverage files:
make clean
This project is licensed under the MIT License. See the LICENSE file for more details.