noirapi / framework
Small PHP 8.4 web framework: FastRoute routing, Latte views, noirapi/database models, Tracy debugging.
Requires
- php: ^8.4
- ext-fileinfo: *
- ext-json: *
- ext-mbstring: *
- ext-pdo: *
- ext-posix: *
- bacon/bacon-qr-code: ^2.0.8 || ^3.0
- html2text/html2text: ^4.3
- laminas/laminas-permissions-acl: ^2.10
- latte/latte: ^3.1
- nette/neon: ^3.4 || ^4.0
- nette/schema: ^1.3
- nette/utils: ^4.0
- nikic/fast-route: ^1.3
- nikic/php-parser: ^5.0
- nikolaposa/rate-limit: ^3.3
- noirapi/database: ^5.0
- php-curl-class/php-curl-class: ^9.1 || ^10.0 || ^11.0 || ^12.0 || ^13.0
- robthree/twofactorauth: ^2.0 || ^3.0
- symfony/mailer: ^7.0 || ^8.0
- tracy/tracy: ^2.10
Requires (Dev)
- pdepend/pdepend: 3.x-dev@dev
- phpmd/phpmd: 3.x-dev@dev
- phpstan/phpstan: ^2.1
- phpunit/phpunit: ^12.0
- rector/rector: ^2.2
- squizlabs/php_codesniffer: ^4.0
- vimeo/psalm: ^7.0.0-beta19
Suggests
- ext-memcached: Memcached session handler (session.driver: memcached)
- ext-pdo_mysql: MySQL / MariaDB models and the MySQL session handler
- ext-pdo_sqlite: SQLite models and the SQLite session handler
- ext-swoole: Serving the app with swoole.php and Lib\Tasks
- digitickets/lalit: XML responses (Response::TYPE_XML)
- rector/rector: Automated upgrades with Rector/config/*.php (see UPGRADE.md)
Provides
None
Conflicts
None
Replaces
None
README
Small PHP 8.4 web framework: FastRoute routing, Latte views, noirapi/database models, Tracy debugging, NEON config, and pluggable auth (password, magic link, TOTP, GitHub/Google OAuth).
Package: noirapi/framework, namespace Noirapi\, PHP ^8.4, MIT.
Installation
There are two supported layouts, and they run the same code (Noirapi\Lib\Kernel).
Composer (new projects)
composer require noirapi/framework
Project layout. Every path is relative to the project root, which the kernel is given:
myapp/
app/
Route.php App\Route: process($method, $uri) -> FastRoute dispatch result
controllers/ models/ views/ layouts/
config/default.neon picked by the CONFIG env var, else the virtual host name, else "default"
htdocs/index.php web root
temp/ logs/ must exist and be writable (Latte/config cache, Tracy logs)
data/ SQLite databases with relative DSNs
vendor/
composer.json "autoload": {"classmap": ["app/"]}
htdocs/index.php:
<?php declare(strict_types=1); require dirname(__DIR__) . '/vendor/autoload.php'; Noirapi\Lib\Kernel::run(dirname(__DIR__));
CLI scripts only boot (config, timezone, sessions, Tracy):
require __DIR__ . '/../../vendor/autoload.php'; Noirapi\Lib\Kernel::boot(__DIR__ . '/../..');
Tools are exposed as one Composer binary (see docs/cli.md):
vendor/bin/noirapi dev-server start [--port 8000] [--host localhost] [--config NAME] vendor/bin/noirapi dev-server stop|restart|status vendor/bin/noirapi latte-lint app/views vendor/bin/noirapi latte-check [--strict] [--no-controller-check] vendor/bin/noirapi latte-format [--check] [paths] # tidy templates vendor/bin/noirapi crawl crawl.json [--start] # see docs/crawl.md vendor/bin/noirapi cache:clear | config:check | routes:list | key:generate vendor/bin/noirapi make:controller Name | make:model Name | db:migrate
git submodule (existing projects)
Existing apps keep the framework checked out at <root>/noirapi/ and use the legacy entry points,
which are thin shims over the same kernel:
require dirname(__DIR__) . '/noirapi/kernel.php'; // htdocs/index.php and CLI scripts require dirname(__DIR__) . '/noirapi/include.php'; // bootstrap only
noirapi/bin/dev-server start noirapi/bin/latte-lint app/views php noirapi/bin/latte-check.php
See UPGRADE.md for what a submodule app needs when it updates to 1.x, and for moving it to the Composer layout.
How the application root is found
Noirapi\Config::getRoot() resolves, in order:
- the root passed to
Kernel::run()/Kernel::boot(); - the
NOIRAPI_ROOTenvironment variable (vendor/bin/noirapianddev-serverset it); - the submodule layout: the framework's parent directory, when it contains
app/; - the Composer layout: the root of the Composer install that contains
noirapi/framework.
The framework's own files (bundled templates, bin scripts) are found with Config::getFrameworkDir().
Documentation
- Routing, Controllers, Views, Layouts
- Database, Sessions, Mail
- Command line, Security (trusted proxies, CSRF, headers/CSP, rate limits), Authentication
- Configuration reference, Validation, Swoole
Development
composer install composer test # PHPUnit composer phpstan # PHPStan (level 5) composer psalm # Psalm 7 (level 4, purity annotations required) composer phpmd # PHPMD 3 composer phpcs # PSR-12 composer coverage # coverage summary (needs pcov or Xdebug)
Releases are tagged vX.Y.Z on master. CI (.github/workflows/ci.yml) runs the tests and
then notifies Packagist; it needs the PACKAGIST_USERNAME and PACKAGIST_TOKEN repository secrets.