diff --git a/.editorconfig b/.editorconfig
new file mode 100644
index 0000000..e8d15f4
--- /dev/null
+++ b/.editorconfig
@@ -0,0 +1,12 @@
+root = true
+
+[*]
+indent_style = space
+indent_size = 4
+end_of_line = lf
+charset = utf-8
+trim_trailing_whitespace = true
+insert_final_newline = true
+
+[*.md]
+indent_size = 2
diff --git a/.gitignore b/.gitignore
index 2161d40..efa50c0 100644
--- a/.gitignore
+++ b/.gitignore
@@ -5,3 +5,4 @@ composer.lock
.phpunit.result.cache
coverage/
.vscode/settings.json
+*.sublime-workspace
diff --git a/README.md b/README.md
index 61083e9..469c5f7 100644
--- a/README.md
+++ b/README.md
@@ -1,13 +1,16 @@
# What is Flight?
-Flight is a fast, simple, extensible framework for PHP. Flight enables you to
+![](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)
+
+Flight is a fast, simple, extensible framework for PHP. Flight enables you to
quickly and easily build RESTful web applications.
```php
require 'flight/Flight.php';
-Flight::route('/', function(){
- echo 'hello world!';
+Flight::route('/', function() {
+ echo 'hello world!';
});
Flight::start();
@@ -27,14 +30,15 @@ Flight is released under the [MIT](http://flightphp.com/license) license.
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
```
-OR you can [download](https://github.com/mikecao/flight/archive/master.zip) them directly
-and extract them to your web directory.
+OR you can [download](https://github.com/mikecao/flight/archive/master.zip)
+them directly and extract them to your web directory.
2\. Configure your webserver.
@@ -47,15 +51,16 @@ RewriteCond %{REQUEST_FILENAME} !-d
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:
```
server {
- location / {
- try_files $uri $uri/ /index.php;
- }
+ location / {
+ try_files $uri $uri/ /index.php;
+ }
}
```
3\. Create your `index.php` file.
@@ -75,8 +80,8 @@ require 'vendor/autoload.php';
Then define a route and assign a function to handle the request.
```php
-Flight::route('/', function(){
- echo 'hello world!';
+Flight::route('/', function () {
+ echo 'hello world!';
});
```
@@ -91,16 +96,16 @@ Flight::start();
Routing in Flight is done by matching a URL pattern with a callback function.
```php
-Flight::route('/', function(){
- echo 'hello world!';
+Flight::route('/', function () {
+ echo 'hello world!';
});
```
The callback can be any object that is callable. So you can use a regular function:
```php
-function hello(){
- echo 'hello world!';
+function hello() {
+ echo 'hello world!';
}
Flight::route('/', 'hello');
@@ -110,9 +115,9 @@ Or a class method:
```php
class Greeting {
- public static function hello() {
- echo 'hello world!';
- }
+ public static function hello() {
+ echo 'hello world!';
+ }
}
Flight::route('/', array('Greeting', 'hello'));
@@ -123,18 +128,18 @@ Or an object method:
```php
class Greeting
{
- public function __construct() {
- $this->name = 'John Doe';
- }
+ public function __construct() {
+ $this->name = 'John Doe';
+ }
- public function hello() {
- echo "Hello, {$this->name}!";
- }
+ public function hello() {
+ echo "Hello, {$this->name}!";
+ }
}
$greeting = new Greeting();
-Flight::route('/', array($greeting, 'hello'));
+Flight::route('/', array($greeting, 'hello'));
```
Routes are matched in the order they are defined. The first route to match a
@@ -146,20 +151,20 @@ By default, route patterns are matched against all request methods. You can resp
to specific methods by placing an identifier before the URL.
```php
-Flight::route('GET /', function(){
- echo 'I received a GET request.';
+Flight::route('GET /', function () {
+ echo 'I received a GET request.';
});
-Flight::route('POST /', function(){
- echo 'I received a POST request.';
+Flight::route('POST /', function () {
+ echo 'I received a POST request.';
});
```
You can also map multiple methods to a single callback by using a `|` delimiter:
```php
-Flight::route('GET|POST /', function(){
- echo 'I received either a GET or a POST request.';
+Flight::route('GET|POST /', function () {
+ echo 'I received either a GET or a POST request.';
});
```
@@ -168,8 +173,8 @@ Flight::route('GET|POST /', function(){
You can use regular expressions in your routes:
```php
-Flight::route('/user/[0-9]+', function(){
- // This will match /user/1234
+Flight::route('/user/[0-9]+', function () {
+ // This will match /user/1234
});
```
@@ -179,8 +184,8 @@ You can specify named parameters in your routes which will be passed along to
your callback function.
```php
-Flight::route('/@name/@id', function($name, $id){
- echo "hello, $name ($id)!";
+Flight::route('/@name/@id', function(string $name, string $id) {
+ echo "hello, $name ($id)!";
});
```
@@ -188,9 +193,9 @@ You can also include regular expressions with your named parameters by using
the `:` delimiter:
```php
-Flight::route('/@name/@id:[0-9]{3}', function($name, $id){
- // This will match /bob/123
- // But will not match /bob/12345
+Flight::route('/@name/@id:[0-9]{3}', function(string $name, string $id) {
+ // This will match /bob/123
+ // But will not match /bob/12345
});
```
@@ -202,13 +207,16 @@ You can specify named parameters that are optional for matching by wrapping
segments in parentheses.
```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:
// /blog/2012/12/10
// /blog/2012/12
// /blog/2012
// /blog
-});
+ }
+);
```
Any optional parameters that are not matched will be passed in as NULL.
@@ -219,16 +227,16 @@ Matching is only done on individual URL segments. If you want to match multiple
segments you can use the `*` wildcard.
```php
-Flight::route('/blog/*', function(){
- // This will match /blog/2000/02/01
+Flight::route('/blog/*', function () {
+ // This will match /blog/2000/02/01
});
```
To route all requests to a single callback, you can do:
```php
-Flight::route('*', function(){
- // Do something
+Flight::route('*', function () {
+ // Do something
});
```
@@ -238,16 +246,16 @@ You can pass execution on to the next matching route by returning `true` from
your callback function.
```php
-Flight::route('/user/@name', function($name){
- // Check some condition
- if ($name != "Bob") {
- // Continue to next route
- return true;
- }
+Flight::route('/user/@name', function (string $name) {
+ // Check some condition
+ if ($name != "Bob") {
+ // Continue to next route
+ return true;
+ }
});
-Flight::route('/user/*', function(){
- // This will get called
+Flight::route('/user/*', function () {
+ // This will get called
});
```
@@ -259,18 +267,18 @@ the route method. The route object will always be the last parameter passed to y
callback function.
```php
-Flight::route('/', function($route){
- // Array of HTTP methods matched against
- $route->methods;
+Flight::route('/', function(\flight\net\Route $route) {
+ // Array of HTTP methods matched against
+ $route->methods;
- // Array of named parameters
- $route->params;
+ // Array of named parameters
+ $route->params;
- // Matching regular expression
- $route->regex;
+ // Matching regular expression
+ $route->regex;
- // Contains the contents of any '*' used in the URL pattern
- $route->splat;
+ // Contains the contents of any '*' used in the URL pattern
+ $route->splat;
}, true);
```
@@ -286,8 +294,8 @@ To map your own custom method, you use the `map` function:
```php
// Map your method
-Flight::map('hello', function($name){
- echo "hello $name!";
+Flight::map('hello', function ($name) {
+ echo "hello $name!";
});
// Call your custom method
@@ -318,7 +326,7 @@ Flight::register('db', 'PDO', array('mysql:host=localhost;dbname=test','user','p
// Get an instance of your class
// This will create an object with the defined parameters
//
-// new PDO('mysql:host=localhost;dbname=test','user','pass');
+// new PDO('mysql:host=localhost;dbname=test','user','pass');
//
$db = Flight::db();
```
@@ -329,8 +337,8 @@ new object. The callback function takes one parameter, an instance of the new ob
```php
// The callback will be passed the object that was constructed
-Flight::register('db', 'PDO', array('mysql:host=localhost;dbname=test','user','pass'), function($db){
- $db->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
+Flight::register('db', 'PDO', array('mysql:host=localhost;dbname=test','user','pass'), function (PDO $db): void {
+ $db->setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
});
```
@@ -359,8 +367,8 @@ by using the `map` method:
```php
Flight::map('notFound', function(){
- // Display custom 404 page
- include 'errors/404.html';
+ // Display custom 404 page
+ include 'errors/404.html';
});
```
@@ -387,8 +395,8 @@ methods as well as any custom methods that you've mapped.
A filter function looks like this:
```php
-function(&$params, &$output) {
- // Filter code
+function (array &$params, string &$output) {
+ // Filter code
}
```
@@ -397,16 +405,16 @@ 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:
```php
-Flight::before('start', function(&$params, &$output){
- // Do something
+Flight::before('start', function (array &$params, string &$output) {
+ // Do something
});
```
You can have a filter run after a method by doing:
```php
-Flight::after('start', function(&$params, &$output){
- // Do something
+Flight::after('start', function (array &$params, string &$output) {
+ // Do something
});
```
@@ -417,20 +425,20 @@ Here's an example of the filtering process:
```php
// Map a custom method
-Flight::map('hello', function($name){
- return "Hello, $name!";
+Flight::map('hello', function ($name) {
+ return "Hello, $name!";
});
// Add a before filter
-Flight::before('hello', function(&$params, &$output){
- // Manipulate the parameter
- $params[0] = 'Fred';
+Flight::before('hello', function (array &$params, string &$output) {
+ // Manipulate the parameter
+ $params[0] = 'Fred';
});
// Add an after filter
-Flight::after('hello', function(&$params, &$output){
- // Manipulate the output
- $output .= " Have a nice day!";
+Flight::after('hello', function (array &$params, string &$output) {
+ // Manipulate the output
+ $output .= " Have a nice day!";
});
// Invoke the custom method
@@ -439,26 +447,28 @@ echo Flight::hello('Bob');
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`
in any of your filter functions:
```php
-Flight::before('start', function(&$params, &$output){
- echo 'one';
+Flight::before('start', function (array &$params, string &$output){
+ echo 'one';
});
-Flight::before('start', function(&$params, &$output){
- echo 'two';
+Flight::before('start', function (array &$params, string &$output): bool {
+ echo 'two';
- // This will end the chain
- return false;
+ // This will end the chain
+ return false;
});
// This will not get called
-Flight::before('start', function(&$params, &$output){
- echo 'three';
+Flight::before('start', function (array &$params, string &$output){
+ echo 'three';
});
```
@@ -480,7 +490,7 @@ To see if a variable has been set you can do:
```php
if (Flight::has('id')) {
- // Do something
+ // Do something
}
```
@@ -515,12 +525,14 @@ be reference like a local variable. Template files are simply PHP files. If the
content of the `hello.php` template file is:
```php
-Hello, ''!
+Hello, !
```
The output would be:
- Hello, Bob!
+```
+Hello, Bob!
+```
You can also manually set view variables by using the set method:
@@ -580,26 +592,26 @@ If the template files looks like this:
```php
-
-
-
-
-
-
-
+
+
+
+
+
+
+
```
The output would be:
```html
-
-Home Page
-
-
-Hello
-World
-
+
+ Home Page
+
+
+ Hello
+ World
+
```
@@ -615,11 +627,11 @@ require './Smarty/libs/Smarty.class.php';
// Register Smarty as the view class
// Also pass a callback function to configure Smarty on load
-Flight::register('view', 'Smarty', array(), function($smarty){
- $smarty->template_dir = './templates/';
- $smarty->compile_dir = './templates_c/';
- $smarty->config_dir = './config/';
- $smarty->cache_dir = './cache/';
+Flight::register('view', 'Smarty', array(), function (Smarty $smarty) {
+ $smarty->setTemplateDir() = './templates/';
+ $smarty->setCompileDir() = './templates_c/';
+ $smarty->setConfigDir() = './config/';
+ $smarty->setCacheDir() = './cache/';
});
// Assign template data
@@ -633,8 +645,8 @@ For completeness, you should also override Flight's default render method:
```php
Flight::map('render', function($template, $data){
- Flight::view()->assign($data);
- Flight::view()->display($template);
+ Flight::view()->assign($data);
+ Flight::view()->display($template);
});
```
# Error Handling
@@ -648,9 +660,9 @@ response with some error information.
You can override this behavior for your own needs:
```php
-Flight::map('error', function(Exception $ex){
- // Handle error
- echo $ex->getTraceAsString();
+Flight::map('error', function(Throwable $ex){
+ // Handle error
+ echo $ex->getTraceAsString();
});
```
@@ -669,8 +681,8 @@ behavior is to send an `HTTP 404 Not Found` response with a simple message.
You can override this behavior for your own needs:
```php
-Flight::map('notFound', function(){
- // Handle not found
+Flight::map('notFound', function () {
+ // Handle not found
});
```
@@ -701,26 +713,24 @@ $request = Flight::request();
The request object provides the following properties:
-```
-url - The URL being requested
-base - The parent subdirectory of the URL
-method - The request method (GET, POST, PUT, DELETE)
-referrer - The referrer URL
-ip - IP address of the client
-ajax - Whether the request is an AJAX request
-scheme - The server protocol (http, https)
-user_agent - Browser information
-type - The content type
-length - The content length
-query - Query string parameters
-data - Post data or JSON data
-cookies - Cookie data
-files - Uploaded files
-secure - Whether the connection is secure
-accept - HTTP accept parameters
-proxy_ip - Proxy IP address of the client
-host - The request host name
-```
+- **url** - The URL being requested
+- **base** - The parent subdirectory of the URL
+- **method** - The request method (GET, POST, PUT, DELETE)
+- **referrer** - The referrer URL
+- **ip** - IP address of the client
+- **ajax** - Whether the request is an AJAX request
+- **scheme** - The server protocol (http, https)
+- **user_agent** - Browser information
+- **type** - The content type
+- **length** - The content length
+- **query** - Query string parameters
+- **data** - Post data or JSON data
+- **cookies** - Cookie data
+- **files** - Uploaded files
+- **secure** - Whether the connection is secure
+- **accept** - HTTP accept parameters
+- **proxy_ip** - Proxy IP address of the client
+- **host** - The request host name
You can access the `query`, `data`, `cookies`, and `files` properties
as arrays or objects.
@@ -739,7 +749,8 @@ $id = Flight::request()->query->id;
## 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
$body = Flight::request()->getBody();
@@ -747,8 +758,8 @@ $body = Flight::request()->getBody();
## JSON Input
-If you send a request with the type `application/json` and the data `{"id": 123}` it will be available
-from the `data` property:
+If you send a request with the type `application/json` and the data `{"id": 123}`
+it will be available from the `data` property:
```php
$id = Flight::request()->data->id;
@@ -768,9 +779,9 @@ and time a page was last modified. The client will continue to use their cache u
the last modified value is changed.
```php
-Flight::route('/news', function(){
- Flight::lastModified(1234567890);
- echo 'This content will be cached.';
+Flight::route('/news', function () {
+ Flight::lastModified(1234567890);
+ echo 'This content will be cached.';
});
```
@@ -780,9 +791,9 @@ Flight::route('/news', function(){
want for the resource:
```php
-Flight::route('/news', function(){
- Flight::etag('my-unique-id');
- echo 'This content will be cached.';
+Flight::route('/news', function () {
+ Flight::etag('my-unique-id');
+ echo 'This content will be cached.';
});
```
@@ -847,12 +858,12 @@ Flight::set('flight.log_errors', true);
The following is a list of all the available configuration settings:
- flight.base_url - Override the base url of the request. (default: null)
- flight.case_sensitive - Case sensitive matching for URLs. (default: false)
- 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.views.path - Directory containing view template files. (default: ./views)
- flight.views.extension - View template file extension. (default: .php)
+- **flight.base_url** - Override the base url of the request. (default: null)
+- **flight.case_sensitive** - Case sensitive matching for URLs. (default: false)
+- **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.views.path** - Directory containing view template files. (default: ./views)
+- **flight.views.extension** - View template file extension. (default: .php)
# Framework Methods
@@ -864,15 +875,15 @@ or overridden.
## Core Methods
```php
-Flight::map($name, $callback) // Creates a custom framework method.
-Flight::register($name, $class, [$params], [$callback]) // Registers a class to a framework method.
-Flight::before($name, $callback) // Adds a filter before a framework method.
-Flight::after($name, $callback) // Adds a filter after a framework method.
-Flight::path($path) // Adds a path for autoloading classes.
-Flight::get($key) // Gets a variable.
-Flight::set($key, $value) // Sets a variable.
-Flight::has($key) // Checks if a variable is set.
-Flight::clear([$key]) // Clears a variable.
+Flight::map(string $name, callable $callback, bool $pass_route = false) // Creates a custom framework method.
+Flight::register(string $name, string $class, array $params = [], ?callable $callback = null) // Registers a class to a framework method.
+Flight::before(string $name, callable $callback) // Adds a filter before a framework method.
+Flight::after(string $name, callable $callback) // Adds a filter after a framework method.
+Flight::path(string $path) // Adds a path for autoloading classes.
+Flight::get(string $key) // Gets a variable.
+Flight::set(string $key, mixed $value) // Sets a variable.
+Flight::has(string $key) // Checks if a variable is set.
+Flight::clear(array|string $key = []) // Clears a variable.
Flight::init() // Initializes the framework to its default settings.
Flight::app() // Gets the application object instance
```
@@ -882,16 +893,16 @@ Flight::app() // Gets the application object instance
```php
Flight::start() // Starts the framework.
Flight::stop() // Stops the framework and sends a response.
-Flight::halt([$code], [$message]) // Stop the framework with an optional status code and message.
-Flight::route($pattern, $callback) // Maps a URL pattern to a callback.
-Flight::redirect($url, [$code]) // Redirects to another URL.
-Flight::render($file, [$data], [$key]) // Renders a template file.
-Flight::error($exception) // Sends an HTTP 500 response.
+Flight::halt(int $code = 200, string $message = '') // Stop the framework with an optional status code and message.
+Flight::route(string $pattern, callable $callback, bool $pass_route = false) // Maps a URL pattern to a callback.
+Flight::redirect(string $url, int $code) // Redirects to another URL.
+Flight::render(string $file, array $data, ?string $key = null) // Renders a template file.
+Flight::error(Throwable $exception) // Sends an HTTP 500 response.
Flight::notFound() // Sends an HTTP 404 response.
-Flight::etag($id, [$type]) // Performs ETag HTTP caching.
-Flight::lastModified($time) // Performs last modified HTTP caching.
-Flight::json($data, [$code], [$encode], [$charset], [$option]) // Sends a JSON response.
-Flight::jsonp($data, [$param], [$code], [$encode], [$charset], [$option]) // Sends a JSONP response.
+Flight::etag(string $id, string $type = 'string') // Performs ETag HTTP caching.
+Flight::lastModified(int $time) // Performs last modified HTTP caching.
+Flight::json(mixed $data, int $code = 200, bool $encode = true, string $charset = 'utf8', int $option) // Sends a JSON 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.
@@ -905,12 +916,10 @@ as an object instance.
```php
require 'flight/autoload.php';
-use flight\Engine;
+$app = new flight\Engine();
-$app = new Engine();
-
-$app->route('/', function(){
- echo 'hello world!';
+$app->route('/', function () {
+ echo 'hello world!';
});
$app->start();
diff --git a/VERSION b/VERSION
index 38f77a6..e9307ca 100644
--- a/VERSION
+++ b/VERSION
@@ -1 +1 @@
-2.0.1
+2.0.2
diff --git a/composer.json b/composer.json
index 8e2611b..2becdbc 100644
--- a/composer.json
+++ b/composer.json
@@ -1,5 +1,5 @@
{
- "name": "mikecao/flight",
+ "name": "faslatam/flight",
"description": "Flight is a fast, simple, extensible framework for PHP. Flight enables you to quickly and easily build RESTful web applications.",
"homepage": "http://flightphp.com",
"license": "MIT",
@@ -9,16 +9,39 @@
"email": "mike@mikecao.com",
"homepage": "http://www.mikecao.com/",
"role": "Original Developer"
+ },
+ {
+ "name": "Franyer Sánchez",
+ "email": "franyeradriansanchez@gmail.com",
+ "homepage": "https://faslatam.000webhostapp.com",
+ "role": "Maintainer"
}
],
"require": {
- "php": "^7.4|^8.0|^8.1",
+ "php": "^7.4|^8.0|^8.1|^8.2",
"ext-json": "*"
},
"autoload": {
- "files": [ "flight/autoload.php", "flight/Flight.php" ]
+ "files": [
+ "flight/autoload.php",
+ "flight/Flight.php"
+ ]
},
"require-dev": {
- "phpunit/phpunit": "^9.5"
+ "phpunit/phpunit": "^9.5",
+ "phpstan/phpstan": "^1.10",
+ "phpstan/extension-installer": "^1.3"
+ },
+ "config": {
+ "allow-plugins": {
+ "phpstan/extension-installer": true
+ }
+ },
+ "scripts": {
+ "test": "phpunit tests",
+ "lint": "phpstan --no-progress -cphpstan.neon"
+ },
+ "suggest": {
+ "phpstan/phpstan": "PHP Static Analysis Tool"
}
}
diff --git a/flight.sublime-project b/flight.sublime-project
new file mode 100644
index 0000000..26552b2
--- /dev/null
+++ b/flight.sublime-project
@@ -0,0 +1,21 @@
+{
+ "folders": [
+ {
+ "path": ".",
+ }
+ ],
+ "settings": {
+ "LSP": {
+ "LSP-intelephense": {
+ "settings": {
+ "intelephense.environment.phpVersion": "7.4.0",
+ "intelephense.format.braces": "psr12",
+ },
+ },
+ "formatters":
+ {
+ "embedding.php": "LSP-intelephense"
+ },
+ },
+ },
+}
diff --git a/flight/Engine.php b/flight/Engine.php
index f8c996b..66442fc 100644
--- a/flight/Engine.php
+++ b/flight/Engine.php
@@ -40,7 +40,7 @@ use Throwable;
* Request-response
* @method Request request() Gets current request
* @method Response response() Gets current response
- * @method void error(Exception $e) Sends an HTTP 500 response for any errors.
+ * @method void error(Throwable $e) Sends an HTTP 500 response for any errors.
* @method void notFound() Sends an HTTP 404 response when a URL is not found.
* @method void redirect(string $url, int $code = 303) Redirects the current request to another URL.
* @method void json(mixed $data, int $code = 200, bool $encode = true, string $charset = 'utf-8', int $option = 0) Sends a JSON response.
@@ -54,6 +54,7 @@ class Engine
{
/**
* Stored variables.
+ * @var array
*/
protected array $vars;
@@ -84,7 +85,7 @@ class Engine
* Handles calls to class methods.
*
* @param string $name Method name
- * @param array $params Method parameters
+ * @param array $params Method parameters
*
* @throws Exception
*
@@ -155,8 +156,8 @@ class Engine
$this->before('start', function () use ($self) {
// Enable error handling
if ($self->get('flight.handle_errors')) {
- set_error_handler([$self, 'handleError']);
- set_exception_handler([$self, 'handleException']);
+ set_error_handler(array($self, 'handleError'));
+ set_exception_handler(array($self, 'handleException'));
}
// Set case-sensitivity
@@ -177,18 +178,21 @@ class Engine
* @param int $errline Error file line number
*
* @throws ErrorException
+ * @return bool
*/
public function handleError(int $errno, string $errstr, string $errfile, int $errline)
{
if ($errno & error_reporting()) {
throw new ErrorException($errstr, $errno, 0, $errfile, $errline);
}
+
+ return false;
}
/**
* Custom exception handler. Logs exceptions.
*
- * @param Exception $e Thrown exception
+ * @param Throwable $e Thrown exception
*/
public function handleException($e): void
{
@@ -203,7 +207,7 @@ class Engine
* Maps a callback to a framework method.
*
* @param string $name Method name
- * @param callback $callback Callback function
+ * @param callable $callback Callback function
*
* @throws Exception If trying to map over a framework method
*/
@@ -218,11 +222,12 @@ class Engine
/**
* Registers a class to a framework method.
+ * @template T of object
*
* @param string $name Method name
- * @param string $class Class name
- * @param array $params Class initialization parameters
- * @param callable|null $callback $callback Function to call after object instantiation
+ * @param class-string $class Class name
+ * @param array $params Class initialization parameters
+ * @param ?callable(T $instance): void $callback Function to call after object instantiation
*
* @throws Exception If trying to map over a framework method
*/
@@ -239,7 +244,7 @@ class Engine
* Adds a pre-filter to a method.
*
* @param string $name Method name
- * @param callback $callback Callback function
+ * @param callable $callback Callback function
*/
public function before(string $name, callable $callback): void
{
@@ -250,7 +255,7 @@ class Engine
* Adds a post-filter to a method.
*
* @param string $name Method name
- * @param callback $callback Callback function
+ * @param callable $callback Callback function
*/
public function after(string $name, callable $callback): void
{
@@ -392,9 +397,10 @@ class Engine
*/
public function _error($e): void
{
- $msg = sprintf('500 Internal Server Error
' .
- '%s (%s)
' .
- '%s
',
+ $msg = sprintf(
+ '500 Internal Server Error
' .
+ '%s (%s)
' .
+ '%s
',
$e->getMessage(),
$e->getCode(),
$e->getTraceAsString()
@@ -437,7 +443,7 @@ class Engine
* Routes a URL to a callback function.
*
* @param string $pattern URL pattern to match
- * @param callback $callback Callback function
+ * @param callable $callback Callback function
* @param bool $pass_route Pass the matching route object to the callback
*/
public function _route(string $pattern, callable $callback, bool $pass_route = false): void
@@ -449,7 +455,7 @@ class Engine
* Routes a URL to a callback function.
*
* @param string $pattern URL pattern to match
- * @param callback $callback Callback function
+ * @param callable $callback Callback function
* @param bool $pass_route Pass the matching route object to the callback
*/
public function _post(string $pattern, callable $callback, bool $pass_route = false): void
@@ -461,7 +467,7 @@ class Engine
* Routes a URL to a callback function.
*
* @param string $pattern URL pattern to match
- * @param callback $callback Callback function
+ * @param callable $callback Callback function
* @param bool $pass_route Pass the matching route object to the callback
*/
public function _put(string $pattern, callable $callback, bool $pass_route = false): void
@@ -473,7 +479,7 @@ class Engine
* Routes a URL to a callback function.
*
* @param string $pattern URL pattern to match
- * @param callback $callback Callback function
+ * @param callable $callback Callback function
* @param bool $pass_route Pass the matching route object to the callback
*/
public function _patch(string $pattern, callable $callback, bool $pass_route = false): void
@@ -485,7 +491,7 @@ class Engine
* Routes a URL to a callback function.
*
* @param string $pattern URL pattern to match
- * @param callback $callback Callback function
+ * @param callable $callback Callback function
* @param bool $pass_route Pass the matching route object to the callback
*/
public function _delete(string $pattern, callable $callback, bool $pass_route = false): void
@@ -519,8 +525,8 @@ class Engine
->status(404)
->write(
'404 Not Found
' .
- 'The page you have requested could not be found.
' .
- str_repeat(' ', 512)
+ 'The page you have requested could not be found.
' .
+ str_repeat(' ', 512)
)
->send();
}
@@ -555,7 +561,7 @@ class Engine
* Renders a template.
*
* @param string $file Template file
- * @param array|null $data Template data
+ * @param ?array $data Template data
* @param string|null $key View variable name
*
* @throws Exception
@@ -639,8 +645,10 @@ class Engine
$this->response()->header('ETag', $id);
- if (isset($_SERVER['HTTP_IF_NONE_MATCH']) &&
- $_SERVER['HTTP_IF_NONE_MATCH'] === $id) {
+ if (
+ isset($_SERVER['HTTP_IF_NONE_MATCH']) &&
+ $_SERVER['HTTP_IF_NONE_MATCH'] === $id
+ ) {
$this->halt(304);
}
}
@@ -654,8 +662,10 @@ class Engine
{
$this->response()->header('Last-Modified', gmdate('D, d M Y H:i:s \G\M\T', $time));
- if (isset($_SERVER['HTTP_IF_MODIFIED_SINCE']) &&
- strtotime($_SERVER['HTTP_IF_MODIFIED_SINCE']) === $time) {
+ if (
+ isset($_SERVER['HTTP_IF_MODIFIED_SINCE']) &&
+ strtotime($_SERVER['HTTP_IF_MODIFIED_SINCE']) === $time
+ ) {
$this->halt(304);
}
}
diff --git a/flight/Flight.php b/flight/Flight.php
index 101c455..e6cdcac 100644
--- a/flight/Flight.php
+++ b/flight/Flight.php
@@ -18,36 +18,27 @@ use flight\template\View;
/**
* The Flight class is a static representation of the framework.
*
- * Core.
- *
* @method static void start() Starts the framework.
- * @method static void path($path) Adds a path for autoloading classes.
+ * @method static void path(string $path) Adds a path for autoloading classes.
* @method static void stop() Stops the framework and sends a response.
- * @method static void halt($code = 200, $message = '') Stop the framework with an optional status code and message.
+ * @method static void halt(int $code = 200, string $message = '') Stop the framework with an optional status code and message.
*
- * Routing.
- * @method static void route($pattern, $callback) Maps a URL pattern to a callback.
+ * @method static void route(string $pattern, callable $callback, bool $pass_route = false) Maps a URL pattern to a callback.
* @method static Router router() Returns Router instance.
*
- * Extending & Overriding.
- * @method static void map($name, $callback) Creates a custom framework method.
- * @method static void register($name, $class, array $params = array(), $callback = null) Registers a class to a framework method.
+ * @method static void map(string $name, callable $callback) Creates a custom framework method.
*
- * Filtering.
* @method static void before($name, $callback) Adds a filter before a framework method.
* @method static void after($name, $callback) Adds a filter after a framework method.
*
- * Variables.
* @method static void set($key, $value) Sets a variable.
* @method static mixed get($key) Gets a variable.
* @method static bool has($key) Checks if a variable is set.
* @method static void clear($key = null) Clears a variable.
*
- * Views.
* @method static void render($file, array $data = null, $key = null) Renders a template file.
* @method static View view() Returns View instance.
*
- * Request & Response.
* @method static Request request() Returns Request instance.
* @method static Response response() Returns Response instance.
* @method static void redirect($url, $code = 303) Redirects to another URL.
@@ -56,7 +47,6 @@ use flight\template\View;
* @method static void error($exception) Sends an HTTP 500 response.
* @method static void notFound() Sends an HTTP 404 response.
*
- * HTTP Caching.
* @method static void etag($id, $type = 'strong') Performs ETag HTTP caching.
* @method static void lastModified($time) Performs last modified HTTP caching.
*/
@@ -72,19 +62,34 @@ class Flight
{
}
- private function __destruct()
+ private function __clone()
{
}
- private function __clone()
+ /**
+ * Registers a class to a framework method.
+ * @template T of object
+ * @param string $name Static method name
+ * ```
+ * Flight::register('user', User::class);
+ *
+ * Flight::user(); # <- Return a User instance
+ * ```
+ * @param class-string $class Fully Qualified Class Name
+ * @param array $params Class constructor params
+ * @param ?Closure(T $instance): void $callback Perform actions with the instance
+ * @return void
+ */
+ static function register($name, $class, $params = array(), $callback = null)
{
+ static::__callStatic('register', func_get_args());
}
/**
* Handles calls to static methods.
*
* @param string $name Method name
- * @param array $params Method parameters
+ * @param array $params Method parameters
*
* @throws Exception
*
diff --git a/flight/core/Dispatcher.php b/flight/core/Dispatcher.php
index 50b73f0..0f810bd 100644
--- a/flight/core/Dispatcher.php
+++ b/flight/core/Dispatcher.php
@@ -23,11 +23,13 @@ class Dispatcher
{
/**
* Mapped events.
+ * @var array
*/
protected array $events = [];
/**
* Method filters.
+ * @var array>>
*/
protected array $filters = [];
@@ -35,9 +37,9 @@ class Dispatcher
* Dispatches an event.
*
* @param string $name Event name
- * @param array $params Callback parameters
+ * @param array $params Callback parameters
*
- *@throws Exception
+ * @throws Exception
*
* @return mixed|null Output of callback
*/
@@ -65,7 +67,7 @@ class Dispatcher
* Assigns a callback to an event.
*
* @param string $name Event name
- * @param callback $callback Callback function
+ * @param callable $callback Callback function
*/
final public function set(string $name, callable $callback): void
{
@@ -77,7 +79,7 @@ class Dispatcher
*
* @param string $name Event name
*
- * @return callback $callback Callback function
+ * @return callable $callback Callback function
*/
final public function get(string $name): ?callable
{
@@ -118,7 +120,7 @@ class Dispatcher
*
* @param string $name Event name
* @param string $type Filter type
- * @param callback $callback Callback function
+ * @param callable $callback Callback function
*/
final public function hook(string $name, string $type, callable $callback): void
{
@@ -128,8 +130,8 @@ class Dispatcher
/**
* Executes a chain of method filters.
*
- * @param array $filters Chain of filters
- * @param array $params Method parameters
+ * @param array $filters Chain of filters
+ * @param array $params Method parameters
* @param mixed $output Method output
*
* @throws Exception
@@ -148,10 +150,10 @@ class Dispatcher
/**
* Executes a callback function.
*
- * @param array|callback $callback Callback function
- * @param array $params Function parameters
+ * @param callable|array $callback Callback function
+ * @param array $params Function parameters
*
- *@throws Exception
+ * @throws Exception
*
* @return mixed Function results
*/
@@ -170,7 +172,7 @@ class Dispatcher
* Calls a function.
*
* @param callable|string $func Name of function to call
- * @param array $params Function parameters
+ * @param array $params Function parameters
*
* @return mixed Function results
*/
@@ -203,7 +205,7 @@ class Dispatcher
* Invokes a method.
*
* @param mixed $func Class method
- * @param array $params Class method parameters
+ * @param array $params Class method parameters
*
* @return mixed Function results
*/
diff --git a/flight/core/Loader.php b/flight/core/Loader.php
index 95874a6..5ff66fe 100644
--- a/flight/core/Loader.php
+++ b/flight/core/Loader.php
@@ -10,6 +10,7 @@ declare(strict_types=1);
namespace flight\core;
+use Closure;
use Exception;
use ReflectionClass;
use ReflectionException;
@@ -24,26 +25,30 @@ class Loader
{
/**
* Registered classes.
+ * @var array, ?callable}> $classes
*/
protected array $classes = [];
/**
* Class instances.
+ * @var array
*/
protected array $instances = [];
/**
* Autoload directories.
+ * @var array
*/
protected static array $dirs = [];
/**
* Registers a class.
+ * @template T of object
*
* @param string $name Registry name
- * @param callable|string $class Class name or function to instantiate class
- * @param array $params Class initialization parameters
- * @param callable|null $callback $callback Function to call after object instantiation
+ * @param class-string $class Class name or function to instantiate class
+ * @param array $params Class initialization parameters
+ * @param ?callable(T $instance): void $callback $callback Function to call after object instantiation
*/
public function register(string $name, $class, array $params = [], ?callable $callback = null): void
{
@@ -77,7 +82,7 @@ class Loader
$obj = null;
if (isset($this->classes[$name])) {
- [$class, $params, $callback] = $this->classes[$name];
+ [0 => $class, 1 => $params, 2 => $callback] = $this->classes[$name];
$exists = isset($this->instances[$name]);
@@ -116,15 +121,16 @@ class Loader
/**
* Gets a new instance of a class.
+ * @template T of object
*
- * @param callable|string $class Class name or callback function to instantiate class
- * @param array $params Class initialization parameters
+ * @param class-string|Closure(): class-string $class Class name or callback function to instantiate class
+ * @param array $params Class initialization parameters
*
* @throws Exception
*
- * @return object Class instance
+ * @return T Class instance
*/
- public function newInstance($class, array $params = []): object
+ public function newInstance($class, array $params = [])
{
if (\is_callable($class)) {
return \call_user_func_array($class, $params);
@@ -179,7 +185,7 @@ class Loader
* Starts/stops autoloader.
*
* @param bool $enabled Enable/disable autoloading
- * @param mixed $dirs Autoload directories
+ * @param string|iterable $dirs Autoload directories
*/
public static function autoload(bool $enabled = true, $dirs = []): void
{
@@ -216,7 +222,7 @@ class Loader
/**
* Adds a directory for autoloading classes.
*
- * @param mixed $dir Directory path
+ * @param string|iterable $dir Directory path
*/
public static function addDirectory($dir): void
{
diff --git a/flight/net/Request.php b/flight/net/Request.php
index 75d4665..8f8ecf8 100644
--- a/flight/net/Request.php
+++ b/flight/net/Request.php
@@ -18,23 +18,24 @@ use flight\util\Collection;
* are stored and accessible via the Request object.
*
* The default request properties are:
- * url - The URL being requested
- * base - The parent subdirectory of the URL
- * method - The request method (GET, POST, PUT, DELETE)
- * referrer - The referrer URL
- * ip - IP address of the client
- * ajax - Whether the request is an AJAX request
- * scheme - The server protocol (http, https)
- * user_agent - Browser information
- * type - The content type
- * length - The content length
- * query - Query string parameters
- * data - Post parameters
- * cookies - Cookie parameters
- * files - Uploaded files
- * secure - Connection is secure
- * accept - HTTP accept parameters
- * proxy_ip - Proxy IP address of the client
+ *
+ * - **url** - The URL being requested
+ * - **base** - The parent subdirectory of the URL
+ * - **method** - The request method (GET, POST, PUT, DELETE)
+ * - **referrer** - The referrer URL
+ * - **ip** - IP address of the client
+ * - **ajax** - Whether the request is an AJAX request
+ * - **scheme** - The server protocol (http, https)
+ * - **user_agent** - Browser information
+ * - **type** - The content type
+ * - **length** - The content length
+ * - **query** - Query string parameters
+ * - **data** - Post parameters
+ * - **cookies** - Cookie parameters
+ * - **files** - Uploaded files
+ * - **secure** - Connection is secure
+ * - **accept** - HTTP accept parameters
+ * - **proxy_ip** - Proxy IP address of the client
*/
final class Request
{
@@ -131,9 +132,9 @@ final class Request
/**
* Constructor.
*
- * @param array $config Request configuration
+ * @param array $config Request configuration
*/
- public function __construct(array $config = [])
+ public function __construct($config = array())
{
// Default properties
if (empty($config)) {
@@ -165,7 +166,8 @@ final class Request
/**
* Initialize request properties.
*
- * @param array $properties Array of request properties
+ * @param array $properties Array of request properties
+ * @return static
*/
public function init(array $properties = [])
{
@@ -199,6 +201,8 @@ final class Request
}
}
}
+
+ return $this;
}
/**
@@ -287,11 +291,11 @@ final class Request
*
* @param string $url URL string
*
- * @return array Query parameters
+ * @return array>
*/
public static function parseQuery(string $url): array
{
- $params = [];
+ $params = array();
$args = parse_url($url);
if (isset($args['query'])) {
diff --git a/flight/net/Response.php b/flight/net/Response.php
index e21fc9a..6b69c67 100644
--- a/flight/net/Response.php
+++ b/flight/net/Response.php
@@ -25,7 +25,7 @@ class Response
public bool $content_length = true;
/**
- * @var array HTTP status codes
+ * @var array HTTP status codes
*/
public static array $codes = [
100 => 'Continue',
@@ -103,7 +103,7 @@ class Response
protected int $status = 200;
/**
- * @var array HTTP headers
+ * @var array> HTTP headers
*/
protected array $headers = [];
@@ -124,7 +124,7 @@ class Response
*
* @throws Exception If invalid status code
*
- * @return int|object Self reference
+ * @return int|static Self reference
*/
public function status(?int $code = null)
{
@@ -144,10 +144,10 @@ class Response
/**
* Adds a header to the response.
*
- * @param array|string $name Header name or array of names and values
+ * @param array|string $name Header name or array of names and values
* @param string|null $value Header value
*
- * @return object Self reference
+ * @return static Self reference
*/
public function header($name, ?string $value = null)
{
@@ -164,8 +164,7 @@ class Response
/**
* Returns the headers from the response.
- *
- * @return array
+ * @return array>
*/
public function headers()
{
@@ -203,7 +202,7 @@ class Response
/**
* Sets caching headers for the response.
*
- * @param int|string $expires Expiration time
+ * @param int|string|false $expires Expiration time
*
* @return Response Self reference
*/
@@ -252,7 +251,8 @@ class Response
'%s %d %s',
$_SERVER['SERVER_PROTOCOL'] ?? 'HTTP/1.1',
$this->status,
- self::$codes[$this->status]),
+ self::$codes[$this->status]
+ ),
true,
$this->status
);
diff --git a/flight/net/Route.php b/flight/net/Route.php
index 91a6aff..fbfc20b 100644
--- a/flight/net/Route.php
+++ b/flight/net/Route.php
@@ -28,12 +28,12 @@ final class Route
public $callback;
/**
- * @var array HTTP methods
+ * @var array HTTP methods
*/
public array $methods = [];
/**
- * @var array Route parameters
+ * @var array Route parameters
*/
public array $params = [];
@@ -56,8 +56,8 @@ final class Route
* Constructor.
*
* @param string $pattern URL pattern
- * @param mixed $callback Callback function
- * @param array $methods HTTP methods
+ * @param callable $callback Callback function
+ * @param array $methods HTTP methods
* @param bool $pass Pass self in callback parameters
*/
public function __construct(string $pattern, $callback, array $methods, bool $pass)
diff --git a/flight/net/Router.php b/flight/net/Router.php
index dcf1591..f1f8842 100644
--- a/flight/net/Router.php
+++ b/flight/net/Router.php
@@ -23,6 +23,7 @@ class Router
public bool $case_sensitive = false;
/**
* Mapped routes.
+ * @var array
*/
protected array $routes = [];
@@ -34,7 +35,7 @@ class Router
/**
* Gets mapped routes.
*
- * @return array Array of routes
+ * @return array Array of routes
*/
public function getRoutes(): array
{
@@ -53,7 +54,7 @@ class Router
* Maps a URL pattern to a callback function.
*
* @param string $pattern URL pattern to match
- * @param callback $callback Callback function
+ * @param callable $callback Callback function
* @param bool $pass_route Pass the matching route object to the callback
*/
public function map(string $pattern, callable $callback, bool $pass_route = false): void
@@ -81,7 +82,7 @@ class Router
{
$url_decoded = urldecode($request->url);
while ($route = $this->current()) {
- if (false !== $route && $route->matchMethod($request->method) && $route->matchUrl($url_decoded, $this->case_sensitive)) {
+ if ($route->matchMethod($request->method) && $route->matchUrl($url_decoded, $this->case_sensitive)) {
return $route;
}
$this->next();
diff --git a/flight/template/View.php b/flight/template/View.php
index 90dbb81..f4d866c 100644
--- a/flight/template/View.php
+++ b/flight/template/View.php
@@ -34,7 +34,7 @@ class View
/**
* View variables.
*
- * @var array
+ * @var array
*/
protected $vars = [];
@@ -70,8 +70,9 @@ class View
/**
* Sets a template variable.
*
- * @param mixed $key Key
- * @param string $value Value
+ * @param string|iterable $key Key
+ * @param mixed $value Value
+ * @return static
*/
public function set($key, $value = null)
{
@@ -82,6 +83,8 @@ class View
} else {
$this->vars[$key] = $value;
}
+
+ return $this;
}
/**
@@ -100,6 +103,7 @@ class View
* Unsets a template variable. If no key is passed in, clear all variables.
*
* @param string $key Key
+ * @return static
*/
public function clear($key = null)
{
@@ -108,15 +112,18 @@ class View
} else {
unset($this->vars[$key]);
}
+
+ return $this;
}
/**
* Renders a template.
*
* @param string $file Template file
- * @param array $data Template data
+ * @param array $data Template data
*
* @throws \Exception If template not found
+ * @return void
*/
public function render($file, $data = null)
{
@@ -139,7 +146,7 @@ class View
* Gets the output of a template.
*
* @param string $file Template file
- * @param array $data Template data
+ * @param array $data Template data
*
* @return string Output of template
*/
@@ -196,5 +203,6 @@ class View
public function e($str)
{
echo htmlentities($str);
+ return htmlentities($str);
}
}
diff --git a/flight/util/Collection.php b/flight/util/Collection.php
index 97658ec..5998b25 100644
--- a/flight/util/Collection.php
+++ b/flight/util/Collection.php
@@ -11,7 +11,6 @@ declare(strict_types=1);
namespace flight\util;
use ArrayAccess;
-use function count;
use Countable;
use Iterator;
use JsonSerializable;
@@ -23,18 +22,21 @@ if (!interface_exists('JsonSerializable')) {
/**
* The Collection class allows you to access a set of data
* using both array and object notation.
+ * @implements ArrayAccess
+ * @implements Iterator
*/
final class Collection implements ArrayAccess, Iterator, Countable, JsonSerializable
{
/**
* Collection data.
+ * @var array
*/
private array $data;
/**
* Constructor.
*
- * @param array $data Initial data
+ * @param array $data Initial data
*/
public function __construct(array $data = [])
{
@@ -102,11 +104,11 @@ final class Collection implements ArrayAccess, Iterator, Countable, JsonSerializ
/**
* Sets an item at the offset.
*
- * @param string $offset Offset
+ * @param ?string $offset Offset
* @param mixed $value Value
*/
#[\ReturnTypeWillChange]
- public function offsetSet($offset, $value)
+ public function offsetSet($offset, $value): void
{
if (null === $offset) {
$this->data[] = $value;
@@ -169,13 +171,11 @@ final class Collection implements ArrayAccess, Iterator, Countable, JsonSerializ
/**
* Gets the next collection value.
- *
- * @return mixed Value
*/
#[\ReturnTypeWillChange]
- public function next()
+ public function next(): void
{
- return next($this->data);
+ next($this->data);
}
/**
@@ -187,7 +187,7 @@ final class Collection implements ArrayAccess, Iterator, Countable, JsonSerializ
{
$key = key($this->data);
- return null !== $key && false !== $key;
+ return null !== $key;
}
/**
@@ -203,7 +203,7 @@ final class Collection implements ArrayAccess, Iterator, Countable, JsonSerializ
/**
* Gets the item keys.
*
- * @return array Collection keys
+ * @return array Collection keys
*/
public function keys(): array
{
@@ -213,7 +213,7 @@ final class Collection implements ArrayAccess, Iterator, Countable, JsonSerializ
/**
* Gets the collection data.
*
- * @return array Collection data
+ * @return array Collection data
*/
public function getData(): array
{
@@ -223,19 +223,15 @@ final class Collection implements ArrayAccess, Iterator, Countable, JsonSerializ
/**
* Sets the collection data.
*
- * @param array $data New collection data
+ * @param array $data New collection data
*/
public function setData(array $data): void
{
$this->data = $data;
}
- /**
- * Gets the collection data which can be serialized to JSON.
- *
- * @return array Collection data which can be serialized by json_encode
- */
- public function jsonSerialize(): array
+ #[\ReturnTypeWillChange]
+ public function jsonSerialize()
{
return $this->data;
}
diff --git a/flight/util/LegacyJsonSerializable.php b/flight/util/LegacyJsonSerializable.php
index 0c973aa..39e1721 100644
--- a/flight/util/LegacyJsonSerializable.php
+++ b/flight/util/LegacyJsonSerializable.php
@@ -9,5 +9,9 @@ declare(strict_types=1);
*/
interface LegacyJsonSerializable
{
+ /**
+ * Gets the collection data which can be serialized to JSON.
+ * @return mixed Collection data which can be serialized by json_encode
+ */
public function jsonSerialize();
}
diff --git a/flight/util/ReturnTypeWillChange.php b/flight/util/ReturnTypeWillChange.php
new file mode 100644
index 0000000..3ed841b
--- /dev/null
+++ b/flight/util/ReturnTypeWillChange.php
@@ -0,0 +1,3 @@
+