@ -1,12 +1,27 @@
![](https://user-images.githubusercontent.com/104888/50957476-9c4acb80-14be-11e9-88ce-6447364dc1bb.png)
![](https://img.shields.io/badge/PHPStan-level%206-brightgreen.svg?style=flat)
![](https://img.shields.io/matrix/flight-php-framework%3Amatrix.org?server_fqdn=matrix.org& style=social& logo=matrix)
[![HitCount ](https://hits.dwyl.com/flightphp/core.svg?style=flat-square&show=unique )](http://hits.dwyl.com/flightphp/core)
# What the fork?
This is a fork of the original project [https://github.com/mikecao/flight ](https://github.com/mikecao/flight ). That project hasn't seen updates in quite some time, so this fork is to help maintain the project going forward.
# What is Flight?
# What is Flight?
Flight is a fast, simple, extensible framework for PHP. Flight enables you to
Flight is a fast, simple, extensible framework for PHP. Flight enables you to
quickly and easily build RESTful web applications.
quickly and easily build RESTful web applications.
Chat with us on Matrix IRC [#flight-php-framework:matrix.org ](https://matrix.to/#/#flight-php-framework:matrix.org )
# Basic Usage
```php
```php
require 'flight/Flight.php';
Flight::route('/', function(){
// if installed with composer
require 'vendor/autoload.php';
// or if installed manually by zip file
//require 'flight/Flight.php';
Flight::route('/', function() {
echo 'hello world!';
echo 'hello world!';
});
});
@ -27,14 +42,15 @@ Flight is released under the [MIT](http://flightphp.com/license) license.
1\. Download the files.
1\. Download the files.
If you're using [Composer ](https://getcomposer.org/ ), you can run the following command:
If you're using [Composer ](https://getcomposer.org/ ), you can run the following
command:
```
```bash
composer require mikecao /flight
composer require n0nag0n /flight
```
```
OR you can [download ](https://github.com/ mikecao/flight/archive/master.zip) them directly
OR you can [download ](https://github.com/ n0nag0n/flight/archive/master.zip)
and extract them to your web directory.
them directly and extract them to your web directory.
2\. Configure your webserver.
2\. Configure your webserver.
@ -47,7 +63,8 @@ RewriteCond %{REQUEST_FILENAME} !-d
RewriteRule ^(.*)$ index.php [QSA,L]
RewriteRule ^(.*)$ index.php [QSA,L]
```
```
**Note**: If you need to use flight in a subdirectory add the line `RewriteBase /subdir/` just after `RewriteEngine On` .
**Note**: If you need to use flight in a subdirectory add the line
`RewriteBase /subdir/` just after `RewriteEngine On` .
For *Nginx* , add the following to your server declaration:
For *Nginx* , add the following to your server declaration:
@ -75,7 +92,7 @@ require 'vendor/autoload.php';
Then define a route and assign a function to handle the request.
Then define a route and assign a function to handle the request.
```php
```php
Flight::route('/', function(){
Flight::route('/', function () {
echo 'hello world!';
echo 'hello world!';
});
});
```
```
@ -91,7 +108,7 @@ Flight::start();
Routing in Flight is done by matching a URL pattern with a callback function.
Routing in Flight is done by matching a URL pattern with a callback function.
```php
```php
Flight::route('/', function(){
Flight::route('/', function () {
echo 'hello world!';
echo 'hello world!';
});
});
```
```
@ -99,7 +116,7 @@ Flight::route('/', function(){
The callback can be any object that is callable. So you can use a regular function:
The callback can be any object that is callable. So you can use a regular function:
```php
```php
function hello(){
function hello() {
echo 'hello world!';
echo 'hello world!';
}
}
@ -146,11 +163,11 @@ By default, route patterns are matched against all request methods. You can resp
to specific methods by placing an identifier before the URL.
to specific methods by placing an identifier before the URL.
```php
```php
Flight::route('GET /', function(){
Flight::route('GET /', function () {
echo 'I received a GET request.';
echo 'I received a GET request.';
});
});
Flight::route('POST /', function(){
Flight::route('POST /', function () {
echo 'I received a POST request.';
echo 'I received a POST request.';
});
});
```
```
@ -158,7 +175,7 @@ Flight::route('POST /', function(){
You can also map multiple methods to a single callback by using a `|` delimiter:
You can also map multiple methods to a single callback by using a `|` delimiter:
```php
```php
Flight::route('GET|POST /', function(){
Flight::route('GET|POST /', function () {
echo 'I received either a GET or a POST request.';
echo 'I received either a GET or a POST request.';
});
});
```
```
@ -168,7 +185,7 @@ Flight::route('GET|POST /', function(){
You can use regular expressions in your routes:
You can use regular expressions in your routes:
```php
```php
Flight::route('/user/[0-9]+', function(){
Flight::route('/user/[0-9]+', function () {
// This will match /user/1234
// This will match /user/1234
});
});
```
```
@ -179,7 +196,7 @@ You can specify named parameters in your routes which will be passed along to
your callback function.
your callback function.
```php
```php
Flight::route('/@name/@id', function($name, $id){
Flight::route('/@name/@id', function(string $name, string $id) {
echo "hello, $name ($id)!";
echo "hello, $name ($id)!";
});
});
```
```
@ -188,7 +205,7 @@ You can also include regular expressions with your named parameters by using
the `:` delimiter:
the `:` delimiter:
```php
```php
Flight::route('/@name/@id:[0-9]{3}', function($name, $id){
Flight::route('/@name/@id:[0-9]{3}', function(string $name, string $id) {
// This will match /bob/123
// This will match /bob/123
// But will not match /bob/12345
// But will not match /bob/12345
});
});
@ -202,13 +219,16 @@ You can specify named parameters that are optional for matching by wrapping
segments in parentheses.
segments in parentheses.
```php
```php
Flight::route('/blog(/@year(/@month(/@day)))', function($year, $month, $day){
Flight::route(
'/blog(/@year(/@month(/@day)))',
function(?string $year, ?string $month, ?string $day) {
// This will match the following URLS:
// This will match the following URLS:
// /blog/2012/12/10
// /blog/2012/12/10
// /blog/2012/12
// /blog/2012/12
// /blog/2012
// /blog/2012
// /blog
// /blog
});
}
);
```
```
Any optional parameters that are not matched will be passed in as NULL.
Any optional parameters that are not matched will be passed in as NULL.
@ -219,7 +239,7 @@ Matching is only done on individual URL segments. If you want to match multiple
segments you can use the `*` wildcard.
segments you can use the `*` wildcard.
```php
```php
Flight::route('/blog/*', function(){
Flight::route('/blog/*', function () {
// This will match /blog/2000/02/01
// This will match /blog/2000/02/01
});
});
```
```
@ -227,7 +247,7 @@ Flight::route('/blog/*', function(){
To route all requests to a single callback, you can do:
To route all requests to a single callback, you can do:
```php
```php
Flight::route('*', function(){
Flight::route('*', function () {
// Do something
// Do something
});
});
```
```
@ -238,7 +258,7 @@ You can pass execution on to the next matching route by returning `true` from
your callback function.
your callback function.
```php
```php
Flight::route('/user/@name', function($name){
Flight::route('/user/@name', function (string $name) {
// Check some condition
// Check some condition
if ($name != "Bob") {
if ($name != "Bob") {
// Continue to next route
// Continue to next route
@ -246,7 +266,7 @@ Flight::route('/user/@name', function($name){
}
}
});
});
Flight::route('/user/*', function(){
Flight::route('/user/*', function () {
// This will get called
// This will get called
});
});
```
```
@ -259,7 +279,7 @@ the route method. The route object will always be the last parameter passed to y
callback function.
callback function.
```php
```php
Flight::route('/', function($route){
Flight::route('/', function(\flight\net\Route $route) {
// Array of HTTP methods matched against
// Array of HTTP methods matched against
$route->methods;
$route->methods;
@ -286,7 +306,7 @@ To map your own custom method, you use the `map` function:
```php
```php
// Map your method
// Map your method
Flight::map('hello', function($name){
Flight::map('hello', function ($name) {
echo "hello $name!";
echo "hello $name!";
});
});
@ -329,7 +349,7 @@ new object. The callback function takes one parameter, an instance of the new ob
```php
```php
// The callback will be passed the object that was constructed
// The callback will be passed the object that was constructed
Flight::register('db', 'PDO', array('mysql:host=localhost;dbname=test','user','pass'), function($db){
Flight::register('db', 'PDO', array('mysql:host=localhost;dbname=test','user','pass'), function (PDO $db): void {
$db->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
$db->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
});
});
```
```
@ -387,7 +407,7 @@ methods as well as any custom methods that you've mapped.
A filter function looks like this:
A filter function looks like this:
```php
```php
function(& $params, & $output) {
function (array & $params, string & $output) {
// Filter code
// Filter code
}
}
```
```
@ -397,7 +417,7 @@ Using the passed in variables you can manipulate the input parameters and/or the
You can have a filter run before a method by doing:
You can have a filter run before a method by doing:
```php
```php
Flight::before('start', function(& $params, & $output){
Flight::before('start', function (array & $params, string & $output) {
// Do something
// Do something
});
});
```
```
@ -405,7 +425,7 @@ Flight::before('start', function(&$params, &$output){
You can have a filter run after a method by doing:
You can have a filter run after a method by doing:
```php
```php
Flight::after('start', function(& $params, & $output){
Flight::after('start', function (array & $params, string & $output) {
// Do something
// Do something
});
});
```
```
@ -417,18 +437,18 @@ Here's an example of the filtering process:
```php
```php
// Map a custom method
// Map a custom method
Flight::map('hello', function($name){
Flight::map('hello', function ($name) {
return "Hello, $name!";
return "Hello, $name!";
});
});
// Add a before filter
// Add a before filter
Flight::before('hello', function(& $params, & $output){
Flight::before('hello', function (array & $params, string & $output) {
// Manipulate the parameter
// Manipulate the parameter
$params[0] = 'Fred';
$params[0] = 'Fred';
});
});
// Add an after filter
// Add an after filter
Flight::after('hello', function(& $params, & $output){
Flight::after('hello', function (array & $params, string & $output) {
// Manipulate the output
// Manipulate the output
$output .= " Have a nice day!";
$output .= " Have a nice day!";
});
});
@ -439,17 +459,19 @@ echo Flight::hello('Bob');
This should display:
This should display:
Hello Fred! Have a nice day!
```
Hello Fred! Have a nice day!
```
If you have defined multiple filters, you can break the chain by returning `false`
If you have defined multiple filters, you can break the chain by returning `false`
in any of your filter functions:
in any of your filter functions:
```php
```php
Flight::before('start', function(& $params, & $output){
Flight::before('start', function (array & $params, string & $output){
echo 'one';
echo 'one';
});
});
Flight::before('start', function(& $params, & $output){
Flight::before('start', function (array & $params, string & $output): bool {
echo 'two';
echo 'two';
// This will end the chain
// This will end the chain
@ -457,7 +479,7 @@ Flight::before('start', function(&$params, &$output){
});
});
// This will not get called
// This will not get called
Flight::before('start', function(& $params, & $output){
Flight::before('start', function (array & $params, string & $output){
echo 'three';
echo 'three';
});
});
```
```
@ -515,12 +537,14 @@ be reference like a local variable. Template files are simply PHP files. If the
content of the `hello.php` template file is:
content of the `hello.php` template file is:
```php
```php
Hello, ' <?php echo $name; ?> ' !
Hello, <?php echo $name; ?> !
```
```
The output would be:
The output would be:
Hello, Bob!
```
Hello, Bob!
```
You can also manually set view variables by using the set method:
You can also manually set view variables by using the set method:
@ -580,26 +604,26 @@ If the template files looks like this:
```php
```php
< html >
< html >
< head >
< head >
< title > <?php echo $title; ?> < / title >
< title > <?php echo $title; ?> < / title >
< / head >
< / head >
< body >
< body >
<?php echo $header_content; ?>
<?php echo $header_content; ?>
<?php echo $body_content; ?>
<?php echo $body_content; ?>
< / body >
< / body >
< / html >
< / html >
```
```
The output would be:
The output would be:
```html
```html
< html >
< html >
< head >
< head >
< title > Home Page< / title >
< title > Home Page< / title >
< / head >
< / head >
< body >
< body >
< h1 > Hello< / h1 >
< h1 > Hello< / h1 >
< div > World< / div >
< div > World< / div >
< / body >
< / body >
< / html >
< / html >
```
```
@ -615,11 +639,11 @@ require './Smarty/libs/Smarty.class.php';
// Register Smarty as the view class
// Register Smarty as the view class
// Also pass a callback function to configure Smarty on load
// Also pass a callback function to configure Smarty on load
Flight::register('view', 'Smarty', array(), function($smarty){
Flight::register('view', 'Smarty', array(), function (Smarty $smarty) {
$smarty->template_dir = './templates/';
$smarty->setTemplateDir() = './templates/';
$smarty->compile_dir = './templates_c/';
$smarty->setCompileDir() = './templates_c/';
$smarty->config_dir = './config/';
$smarty->setConfigDir() = './config/';
$smarty->cache_dir = './cache/';
$smarty->setCacheDir() = './cache/';
});
});
// Assign template data
// Assign template data
@ -648,7 +672,7 @@ response with some error information.
You can override this behavior for your own needs:
You can override this behavior for your own needs:
```php
```php
Flight::map('error', function(Exception $ex){
Flight::map('error', function(Throwable $ex){
// Handle error
// Handle error
echo $ex->getTraceAsString();
echo $ex->getTraceAsString();
});
});
@ -669,7 +693,7 @@ behavior is to send an `HTTP 404 Not Found` response with a simple message.
You can override this behavior for your own needs:
You can override this behavior for your own needs:
```php
```php
Flight::map('notFound', function(){
Flight::map('notFound', function () {
// Handle not found
// Handle not found
});
});
```
```
@ -701,26 +725,24 @@ $request = Flight::request();
The request object provides the following properties:
The request object provides the following properties:
```
- **url** - The URL being requested
url - The URL being requested
- **base** - The parent subdirectory of the URL
base - The parent subdirectory of the URL
- **method** - The request method (GET, POST, PUT, DELETE)
method - The request method (GET, POST, PUT, DELETE)
- **referrer** - The referrer URL
referrer - The referrer URL
- **ip** - IP address of the client
ip - IP address of the client
- **ajax** - Whether the request is an AJAX request
ajax - Whether the request is an AJAX request
- **scheme** - The server protocol (http, https)
scheme - The server protocol (http, https)
- **user_agent** - Browser information
user_agent - Browser information
- **type** - The content type
type - The content type
- **length** - The content length
length - The content length
- **query** - Query string parameters
query - Query string parameters
- **data** - Post data or JSON data
data - Post data or JSON data
- **cookies** - Cookie data
cookies - Cookie data
- **files** - Uploaded files
files - Uploaded files
- **secure** - Whether the connection is secure
secure - Whether the connection is secure
- **accept** - HTTP accept parameters
accept - HTTP accept parameters
- **proxy_ip** - Proxy IP address of the client
proxy_ip - Proxy IP address of the client
- **host** - The request host name
host - The request host name
```
You can access the `query` , `data` , `cookies` , and `files` properties
You can access the `query` , `data` , `cookies` , and `files` properties
as arrays or objects.
as arrays or objects.
@ -739,7 +761,8 @@ $id = Flight::request()->query->id;
## RAW Request Body
## RAW Request Body
To get the raw HTTP request body, for example when dealing with PUT requests, you can do:
To get the raw HTTP request body, for example when dealing with PUT requests,
you can do:
```php
```php
$body = Flight::request()->getBody();
$body = Flight::request()->getBody();
@ -747,8 +770,8 @@ $body = Flight::request()->getBody();
## JSON Input
## JSON Input
If you send a request with the type `application/json` and the data `{"id": 123}` it will be available
If you send a request with the type `application/json` and the data `{"id": 123}`
from the `data` property:
it will be available from the `data` property:
```php
```php
$id = Flight::request()->data->id;
$id = Flight::request()->data->id;
@ -768,7 +791,7 @@ and time a page was last modified. The client will continue to use their cache u
the last modified value is changed.
the last modified value is changed.
```php
```php
Flight::route('/news', function(){
Flight::route('/news', function () {
Flight::lastModified(1234567890);
Flight::lastModified(1234567890);
echo 'This content will be cached.';
echo 'This content will be cached.';
});
});
@ -780,7 +803,7 @@ Flight::route('/news', function(){
want for the resource:
want for the resource:
```php
```php
Flight::route('/news', function(){
Flight::route('/news', function () {
Flight::etag('my-unique-id');
Flight::etag('my-unique-id');
echo 'This content will be cached.';
echo 'This content will be cached.';
});
});
@ -847,12 +870,12 @@ Flight::set('flight.log_errors', true);
The following is a list of all the available configuration settings:
The following is a list of all the available configuration settings:
flight.base_url - Override the base url of the request. (default: null)
- **flight.base_url** - Override the base url of the request. (default: null)
flight.case_sensitive - Case sensitive matching for URLs. (default: false)
- **flight.case_sensitive** - Case sensitive matching for URLs. (default: false)
flight.handle_errors - Allow Flight to handle all errors internally. (default: true)
- **flight.handle_errors** - Allow Flight to handle all errors internally. (default: true)
flight.log_errors - Log errors to the web server's error log file. (default: false)
- **flight.log_errors** - Log errors to the web server's error log file. (default: false)
flight.views.path - Directory containing view template files. (default: ./views)
- **flight.views.path** - Directory containing view template files. (default: ./views)
flight.views.extension - View template file extension. (default: .php)
- **flight.views.extension** - View template file extension. (default: .php)
# Framework Methods
# Framework Methods
@ -864,15 +887,15 @@ or overridden.
## Core Methods
## Core Methods
```php
```php
Flight::map($name, $callback) // Creates a custom framework method.
Flight::map(string $name, callable $callback, bool $pass_route = false ) // Creates a custom framework method.
Flight::register($name, $class, [$params], [$callback] ) // Registers a class to a framework method.
Flight::register(string $name, string $class, array $params = [], ?callable $callback = null ) // Registers a class to a framework method.
Flight::before($name, $callback) // Adds a filter before a framework method.
Flight::before(string $name, callable $callback) // Adds a filter before a framework method.
Flight::after($name, $callback) // Adds a filter after a framework method.
Flight::after(string $name, callable $callback) // Adds a filter after a framework method.
Flight::path($path) // Adds a path for autoloading classes.
Flight::path(string $path) // Adds a path for autoloading classes.
Flight::get($key) // Gets a variable.
Flight::get(string $key) // Gets a variable.
Flight::set($key, $value) // Sets a variable.
Flight::set(string $key, mixed $value) // Sets a variable.
Flight::has($key) // Checks if a variable is set.
Flight::has(string $key) // Checks if a variable is set.
Flight::clear([$key ]) // Clears a variable.
Flight::clear(array|string $key = [ ]) // Clears a variable.
Flight::init() // Initializes the framework to its default settings.
Flight::init() // Initializes the framework to its default settings.
Flight::app() // Gets the application object instance
Flight::app() // Gets the application object instance
```
```
@ -882,16 +905,16 @@ Flight::app() // Gets the application object instance
```php
```php
Flight::start() // Starts the framework.
Flight::start() // Starts the framework.
Flight::stop() // Stops the framework and sends a response.
Flight::stop() // Stops the framework and sends a response.
Flight::halt([$code], [$message] ) // Stop the framework with an optional status code and message.
Flight::halt(int $code = 200, string $message = '' ) // Stop the framework with an optional status code and message.
Flight::route($pattern, $callback) // Maps a URL pattern to a callback.
Flight::route(string $pattern, callable $callback, bool $pass_route = false ) // Maps a URL pattern to a callback.
Flight::redirect($url, [$code] ) // Redirects to another URL.
Flight::redirect(string $url, int $code ) // Redirects to another URL.
Flight::render($file, [$data], [$key] ) // Renders a template file.
Flight::render(string $file, array $data, ?string $key = null ) // Renders a template file.
Flight::error($exception) // Sends an HTTP 500 response.
Flight::error(Throwable $exception) // Sends an HTTP 500 response.
Flight::notFound() // Sends an HTTP 404 response.
Flight::notFound() // Sends an HTTP 404 response.
Flight::etag($id, [$type] ) // Performs ETag HTTP caching.
Flight::etag(string $id, string $type = 'string' ) // Performs ETag HTTP caching.
Flight::lastModified($time) // Performs last modified HTTP caching.
Flight::lastModified(int $time) // Performs last modified HTTP caching.
Flight::json($data, [$code], [$encode], [$charset], [$option] ) // Sends a JSON response.
Flight::json(mixed $data, int $code = 200, bool $encode = true, string $charset = 'utf8', int $option ) // Sends a JSON response.
Flight::jsonp($data, [$param], [$code], [$encode], [$charset], [$option] ) // Sends a JSONP response.
Flight::jsonp(mixed $data, string $param = 'jsonp', int $code = 200, bool $encode = true, string $charset = 'utf8', int $option ) // Sends a JSONP response.
```
```
Any custom methods added with `map` and `register` can also be filtered.
Any custom methods added with `map` and `register` can also be filtered.
@ -905,11 +928,9 @@ as an object instance.
```php
```php
require 'flight/autoload.php';
require 'flight/autoload.php';
use flight\Engine;
$app = new flight\Engine();
$app = new Engine();
$app->route('/', function(){
$app->route('/', function () {
echo 'hello world!';
echo 'hello world!';
});
});