Marwa Framework is intentionally small. The architecture is built around a few core responsibilities:
Application: boots the container, environment, and core shared servicesHttpKernel: coordinates HTTP boot flow and request handlingConsoleKernel: builds the Symfony Console application and registers commandsProviderBootstrapper: registers configured service providersModuleBootstrapper: loadsmarwa-moduleservices, boots module providers, and integrates module routes, views, and console discoveryMenuRegistry: collects application and module menu items and exposes the built main navigation treeMiddlewareBootstrapper: resolves and pushes middleware into the pipelineCommandRegistry: stores commands from config, code, and package integrationsCommandDiscovery: resolves command classes from configured namespaces or PSR-4-mapped directories- Adapters: connect the framework to router, logger, events, views, and error handling
Applicationis created with the host app base path.- The container is initialized with reflection-based autowiring.
.envis loaded and core singletons are bound.HttpKernelloads app config and delegates provider, module, and middleware setup to dedicated bootstrappers.- Module providers are booted, menu contributions are collected, module routes are loaded, and module view namespaces are registered when enabled.
- The request enters
RelayPipelineAdapter. RouterMiddlewaredispatches tomarwa-router.HttpKernel::terminate()emits the final response.
Applicationloads the environment and binds shared services.ConsoleKernelloadsconfig/app.phpandconfig/console.php.ProviderBootstrapperregisters application service providers andModuleBootstrapperbinds the module registry/runtime.CommandRegistrycollects built-in commands, configured commands, discovered commands, module commands, and optional package commands such asmarwa-db.ConsoleApplicationboots the Symfony Console runtime and runs the selected command.
- Add service providers through
config/app.phpunderproviders - Add global middleware through
config/app.phpundermiddlewares - Register routes in
routes/web.phporroutes/api.php - Add modules through
config/module.phpand module manifests under your configured module paths - Register CLI commands through
config/console.phporApplication::registerCommand() - Resolve loaded modules through
Application::modules(),Application::hasModule(), andApplication::module() - Build shared navigation through
Marwa\Framework\Navigation\MenuRegistryor themenu()helper - Configure custom not-found handling with
HttpKernel::setNotFound() - Extend view, logger, and event behavior with their corresponding config files
- Internal framework code now prefers constructor-injected
Config,Application, and contracts over facade access where practical - Facades and global helpers remain available as consumer-facing convenience APIs
- Config contracts are formalized in
src/Config/so defaults and expected keys are centralized