Documentation
¶
Overview ¶
Package kernel boots the application.
It is the equivalent of Laravel's bootstrap/app.php: the single place where an application is composed. One difference matters: the Kernel boots ONCE, at process start, not per request, so nothing here may assume request scope.
Index ¶
- func FormatRoutes(routes []httpx.Route) string
- type Bootable
- type Closable
- type Health
- type Kernel
- func (k *Kernel) Boot(ctx context.Context) error
- func (k *Kernel) Config() config.Config
- func (k *Kernel) Handler() http.Handler
- func (k *Kernel) Logger() *slog.Logger
- func (k *Kernel) Migrations() []Migration
- func (k *Kernel) Register(mods ...Module) *Kernel
- func (k *Kernel) Routes() []httpx.Route
- func (k *Kernel) Run(ctx context.Context) error
- func (k *Kernel) Shutdown() error
- func (k *Kernel) Use(mw ...httpx.Middleware) *Kernel
- type Migratable
- type Migration
- type Module
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
func FormatRoutes ¶
FormatRoutes renders the route table for the terminal, grouped by module and sorted by pattern. It is here, and not in the CLI, so that every project prints the same table.
Types ¶
type Bootable ¶
Bootable is optional: implement it when the module needs to prepare state at boot -- open a pool, warm a cache, register codecs.
type Kernel ¶
type Kernel struct {
// contains filtered or unexported fields
}
Kernel holds the composed application: configuration, modules, the global middleware pipeline and the router.
func New ¶
New assembles the kernel. It opens no connection and listens on no port -- that is Boot and Run.
func (*Kernel) Boot ¶
Boot initializes modules and registers routes. It fails fast: if any module fails to boot the process does not come up. There is no silent degraded mode.
func (*Kernel) Handler ¶
Handler returns the composed handler: the router wrapped in the global pipeline, with the application logger installed above everything else. Useful for tests, which drive the whole stack without a socket.
The logger has to be outermost. Without it, every Log(ctx) call in a request would fall back to slog.Default() and ignore the configured handler and level, which in production means request logs in the wrong format.
func (*Kernel) Logger ¶
Logger returns the root logger. Request handlers must use observability.Log(ctx) instead, which carries the request id.
func (*Kernel) Migrations ¶
Migrations collects the migrations of every module, in registration order. Hand the result to data.Migrate.
func (*Kernel) Register ¶
Register adds modules in the order they will be booted. Order matters: a module may depend on another one already being up.
func (*Kernel) Routes ¶
Routes returns the registered routes. It is empty before Boot, because a module only registers its routes when it boots.
func (*Kernel) Run ¶
Run starts the server and blocks until SIGINT or SIGTERM, then shuts down gracefully.
type Migratable ¶
type Migratable interface {
Migrations() []Migration
}
Migratable is optional: the module declares its migrations, and the Kernel collects them from every registered module in registration order.
type Migration ¶
Migration is a versioned, immutable-once-published schema change.
It is an alias, not a copy: the migration runner lives in the data package, and a module must be able to hand its migrations straight to it.
type Module ¶
type Module interface {
// Name is the stable identifier of the module: a lowercase slug, no spaces.
Name() string
// Routes registers the module's HTTP routes.
Routes(r *httpx.Router)
}
Module is the only unit of composition in the framework.
A module is a directory. It registers its own routes, its own migrations and its own dependency graph. There is no injection container and no reflection based resolution: the wiring is explicit, and the CLI generates the file that instantiates everything.
Every third-party module implements this interface and nothing else. It is the public contract of the framework -- change it and the whole ecosystem breaks, so change it with great care.