Play是一个轻巧的PHP框架。轻松,快速地构建高性能的RESTFULS应用程序。开箱即用的内置路由,数据库,缓存,错误处理,日志记录和作业计划库。专注于为Web应用程序的核心过程创建解决方案。保持简单且可扩展。
| 项目 | 描述 |
|---|---|
| 下车 | 基本框架内置路由,数据库,缓存等。 |
| 下山 | 基于下车的完整管理面板扩展名。无需前端编码。 |
| 下降项目 | 初学者可以轻松创建Web应用程序的模板。 |
PHP 7.4+
没有作曲家?首先安装作曲家。
$ composer create-project juneszh/alight-project {PROJECT_DIRECTORY}该项目模板包含适用于MVC模式的通用文件夹结构,请参阅:下降项目。
通过修改配置来自定义文件夹很容易。但是以下教程基于模板配置。
nginx示例(nginx 1.17.10,php 7.4.3,ubuntu 20.04.3):
server {
listen 80 ;
listen [::]:80;
root /var/www/{PROJECT_DIRECTORY}/public;
index index.php;
server_name {YOUR_DOMAIN};
location / {
try_files $uri $uri / /index.php? $query_string ;
}
location ~ .php$ {
include snippets/fastcgi-php.conf;
fastcgi_pass unix:/var/run/php/php7.4-fpm.sock;
}
}“ config/app.php'”的所有配置选项都将导入您需要创建自己的文件。例如:
文件:config/app.php
<?php
return [
' app ' => [
' debug ' => false ,
' timezone ' => ' Europe/Kiev ' ,
' storagePath ' => ' storage ' ,
' domainLevel ' => 2 ,
' corsDomain ' => null ,
' corsHeaders ' => null ,
' corsMethods ' => null ,
' cacheAdapter ' => null ,
' errorHandler ' => null ,
' errorPageHandler ' => null ,
],
' route ' => ' config/route/web.php ' ,
' database ' => [
' type ' => ' mysql ' ,
' host ' => ' 127.0.0.1 ' ,
' database ' => ' alight ' ,
' username ' => ' root ' ,
' password ' => '' ,
],
' cache ' => [
' type ' => ' file ' ,
],
' job ' => ' config/job.php ' ,
]; <?php
Alight Config:: get ( ' app ' );
Alight Config:: get ( ' app ' , ' storagePath ' );有关详细信息,请参见config.php。
在学习路由规则之前,您需要首先创建一个存储路由规则的PHP文件。由于路由缓存是否已更新,因此基于路由文件的修改时间。例如:
文件:config/route/web.php
Alight Route:: get ( ' / ' , ' Controller::index ' );文件:config/app.php
<?php
return [
' route ' => ' config/route/web.php '
// Also supports multiple files
// 'route' => ['config/route/web.php', config/route/api.php']
];顺便说一句,路由配置支持导入子域的指定文件:
<?php
return [
' route ' => [
//Import on any request
' * ' => ' config/route/web.php ' ,
//Import when requesting admin.yourdomain.com
' admin ' => ' config/route/admin.php ' ,
//Import multiple files when requesting api.yourdomain.com
' api ' => [ ' config/route/api.php ' , ' config/route/api_mobile.php ' ],
]
]; Alight Route:: get ( $ pattern , $ handler );
// Example
Alight Route:: get ( ' / ' , ' Controller::index ' );
Alight Route:: get ( ' / ' , [ ' Controller ' , ' index ' ]);
// Or try this to easy trigger hints from IDE
Alight Route:: get ( ' / ' , [Controller::class, ' index ' ]);
// With default args
Alight Route:: get ( ' post/list[/{page}] ' , [Controller::class, ' list ' ], [ ' page ' => 1 ]);
// Common HTTP request methods
Alight Route:: options ( ' / ' , ' handler ' );
Alight Route:: head ( ' / ' , ' handler ' );
Alight Route:: post ( ' / ' , ' handler ' );
Alight Route:: delete ( ' / ' , ' handler ' );
Alight Route:: put ( ' / ' , ' handler ' );
Alight Route:: patch ( ' / ' , ' handler ' );
// Map for Custom methods
Alight Route:: map ([ ' GET ' , ' POST ' ], ' test ' , ' handler ' );
// Any for all common methods
Alight Route:: any ( ' test ' , ' handler ' ); // Matches /user/42, but not /user/xyz
Alight Route:: get ( ' user/{id:d+} ' , ' handler ' );
// Matches /user/foobar, but not /user/foo/bar
Alight Route:: get ( ' user/{name} ' , ' handler ' );
// Matches /user/foo/bar as well, using wildcards
Alight Route:: get ( ' user/{name:.+} ' , ' handler ' );
// The /{name} suffix is optional
Alight Route:: get ( ' user[/{name}] ' , ' handler ' );
// Root wildcards for single page app
Alight Route:: get ( ' /{path:.*} ' , ' handler ' );Nikic/Fast-Route处理路由路径中的所有正则表达式。有关详细信息,请参见Fastroute用法。
Alight Route:: group ( ' admin ' );
// Matches /admin/role/list
Alight Route:: get ( ' role/list ' , ' handler ' );
// Matches /admin/role/info
Alight Route:: get ( ' role/info ' , ' handler ' );
// Override the group
Alight Route:: group ( ' api ' );
// Matches /api/news/list
Alight Route:: get ( ' news/list ' , ' handler ' );您可以自定义AlightRoute::any()中包含的方法。
Alight Route:: setAnyMethods ([ ' GET ' , ' POST ' ]);
Alight Route:: any ( ' only/get/and/post ' , ' handler ' );如果您想在路由处理程序之前运行一些常见的代码。
// For example log every hit request
Alight Route:: beforeHandler ([ svc Request::class, ' log ' ]);
Alight Route:: get ( ' test ' , ' handler ' );
Alight Route:: post ( ' test ' , ' handler ' );不建议,但是如果您的代码需要:
// Effective in the current route file
Alight Route:: disableCache ();所有路由选项仅在当前文件中生效,并且将在导入下一个文件之前通过AlightRoute::init()自动重置。例如:
文件:config/admin.php
Alight Route:: group ( ' admin ' );
Alight Route:: setAnyMethods ([ ' GET ' , ' POST ' ]);
// Matches '/admin/login' by methods 'GET', 'POST'
Alight Route:: any ( ' login ' , ' handler ' );文件:config/web.php
// Matches '/login' by methods 'GET', 'POST', 'PUT', 'DELETE', etc
Alight Route:: any ( ' login ' , ' handler ' );发送缓存控制标头以控制浏览器和共享缓存(CDN)中的缓存,以优化对未修改数据的访问速度。
// Cache one day
Alight Route:: get ( ' about/us ' , ' handler ' )-> cache ( 86400 );
// Or force disable cache
Alight Route:: put ( ' user/info ' , ' handler ' )-> cache ( 0 );我们提供一个简单的授权处理程序来管理用户登录状态。
// Define a global authorization verification handler
Alight Route:: authHandler ([ svc Auth::class, ' verify ' ]);
// Enable verification in routes
Alight Route:: get ( ' user/info ' , ' handler ' )-> auth ();
Alight Route:: get ( ' user/password ' , ' handler ' )-> auth ();
// No verification by default
Alight Route:: get ( ' about/us ' , ' handler ' );
// In general, routing with authorization will not use browser cache
// So auth() has built-in cache(0) to force disable cache
// Please add cache(n) after auth() to override the configuration if you need
Alight Route:: get ( ' user/rank/list ' , ' handler ' )-> auth ()-> cache ( 3600 );文件:app/service/auth.php
namespace svc ;
class Auth
{
public static function verify ()
{
// Some codes about get user session from cookie or anywhere
// Returns the user id if authorization is valid
// Otherwise returns 0 or something else for failure
// Then use Router::getAuthId() in the route handler to get this id again
return $ userId ;
}
}很多时候,用户提交的数据需要时间来处理,我们不想在处理之前接收相同的数据。因此,我们需要设置请求冷却时间。在冷却器中再次请求时,用户将收到429错误。
// Cooldown only takes effect when authorized
Alight Route:: put ( ' user/info ' , ' handler ' )-> auth ()-> cd ( 2 );
Alight Route:: post ( ' user/status ' , ' handler ' )-> auth ()-> cd ( 2 );当第三方网站(或您的项目具有多个域)需要将API用于AJAX请求时,您需要发送一组CORS标题。由于特定的原因,请参阅:Mozilla文档。
// Domains in config will receive the common cors header
Alight Route:: put ( ' share/config ' , ' handler ' )-> cors ();
// The specified domain will receive the common cors header
Alight Route:: put ( ' share/specified ' , ' handler ' )-> cors ( ' abc.com ' );
// The specified domain will receive the specified cors header
Alight Route:: put ( ' share/specified2 ' , ' handler ' )-> cors ( ' abc.com ' , ' Authorization ' , [ ' GET ' , ' POST ' ]);
// All domains will receive a 'Access-Control-Allow-Origin: *' header
Alight Route:: put ( ' share/all/http ' , ' handler ' )-> cors ( ' * ' );
// All domains will receive a 'Access-Control-Allow-Origin: [From Origin]' header
Alight Route:: put ( ' share/all/https ' , ' handler ' )-> cors ( ' origin ' );如果您的网站正在使用CDN,请仔细使用此实用程序。为了避免在cdn缓存标头后的请求故障。
下点将“数据库”配置直接传递给CATFAN/MEDOO 。有关特定配置选项,请参阅Medoo入门。例如:
文件:config/app.php
<?php
return [
' database ' => [
' type ' => ' mysql ' ,
' host ' => ' 127.0.0.1 ' ,
' database ' => ' alight ' ,
' username ' => ' root ' ,
' password ' => '' ,
],
// Multiple databases (The first database is default)
// 'database' => [
// 'main' => [
// 'type' => 'mysql',
// 'host' => '127.0.0.1',
// 'database' => 'alight',
// 'username' => 'root',
// 'password' => '',
// ],
// 'remote' => [
// 'type' => 'mysql',
// 'host' => '1.1.1.1',
// 'database' => 'alight',
// 'username' => 'root',
// 'password' => '',
// ],
// ]
];AlightDatabase::init()是new MedooMedoo()的静态实例实现,因此它继承了Medoo()的所有函数。单个实例使每个请求仅连接到数据库并重复使用一次,从而有效减少了数据库连接的数量。
// Initializes the default database
$ db = Alight Database:: init ();
// Initializes others database with key
$ db2 = Alight Database:: init ( ' remote ' );
$ userList = $ db -> select ( ' user ' , ' * ' , [ ' role ' => 1 ]);
$ userInfo = $ db -> get ( ' user ' , ' * ' , [ ' id ' => 1 ]);
$ db -> insert ( ' user ' , [ ' name ' => ' anonymous ' , ' role ' => 2 ]);
$ id = $ db -> id ();
$ result = $ db -> update ( ' user ' , [ ' name ' => ' alight ' ], [ ' id ' => $ id ]);
$ result -> rowCount ();有关使用详细信息,请参见Medoo文档。
下落支持具有Symfony/Cache的多个缓存驱动程序和多个缓存接口。配置选项“ DSN”和“选项”将传递给缓存适配器,更多详细信息请参阅可用的缓存适配器。例如:
文件:config/app.php
<?php
return [
' cache ' => [
' type ' => ' file ' ,
],
// Multiple cache (The first cache is the default)
// 'cache' => [
// 'file' => [
// 'type' => 'file',
// ],
// 'memcached' => [
// 'type' => 'memcached',
// 'dsn' => 'memcached://localhost',
// 'options' => [],
// ],
// 'redis' => [
// 'type' => 'redis',
// 'dsn' => 'redis://localhost',
// 'options' => [],
// ],
// ]
];像数据库一样, AlightCache::init()是缓存客户端的静态实例实现,可改善并发的请求性能。
// Initializes the default cache
$ cache = Alight Cache:: init ();
// Initializes others cache with key
$ cache2 = Alight Cache:: init ( ' redis ' );
// Use SimpleCache(PSR-16) interface
if (! $ cache -> has ( ' test ' )){
$ cache -> set ( ' test ' , ' hello world! ' , 3600 );
}
$ cacheData = $ cache -> get ( ' test ' );
$ cache -> delete ( ' test ' ); $ cache6 = Alight Cache:: psr6 ( ' memcached ' );
$ cacheItem = $ cache6 -> getItem ( ' test ' );
if (! $ cacheItem -> isHit ()){
$ cacheItem -> expiresAfter ( 3600 );
$ cacheItem -> set ( ' hello world! ' );
// Bind to a tag
$ cacheItem -> tag ( ' alight ' );
}
$ cacheData = $ cacheItem -> get ();
$ cache6 -> deleteItem ( ' test ' );
// Delete all cached items in the same tag
$ cache6 -> invalidateTags ( ' alight ' )
// Or symfony/cache adapter style
$ cacheData = $ cache6 -> get ( ' test ' , function ( $ item ){
$ item -> expiresAfter ( 3600 );
return ' hello world! ' ;
});
$ cache6 -> delete ( ' test ' );还支持用于使用高级缓存的备用或重新的本地界面:
$ memcached = Alight Cache:: memcached ( ' memcached ' );
$ memcached -> increment ( ' increment ' );
$ redis = Alight Cache:: redis ( ' redis ' );
$ redis -> lPush ( ' list ' , ' first ' );Symfony/Cache支持10个以上的适配器,但是我们只使用了常用的3个常见的3个适配器,例如文件系统,MEMCACHED,REDIS。如果您需要更多的适配器,则可以将其扩展。例如:
文件:config/app.php
<?php
return [
' app ' => [
' cacheAdapter ' => [ svc Cache::class, ' adapter ' ],
],
' cache ' => [
// ...
' apcu ' => [
' type ' => ' apcu '
],
' array ' => [
' type ' => ' array ' ,
' defaultLifetime ' => 3600
]
]
];文件:app/service/cache.php
namespace svc ;
use Symfony Component Cache Adapter ApcuAdapter ;
use Symfony Component Cache Adapter ArrayAdapter ;
use Symfony Component Cache Adapter NullAdapter ;
class Cache
{
public static function adapter ( array $ config )
{
switch ( $ config [ ' type ' ]) {
case ' apcu ' :
return new ApcuAdapter ();
break ;
case ' array ' :
return new ArrayAdapter ( $ config [ ' defaultLifetime ' ]);
default :
return new NullAdapter ();
break ;
}
}
}有关更多信息,请参见Symfony Cache组件。
下落通过AlightApp::start()捕获所有错误。当在应用程序配置中打开“调试”时,将在漂亮的HTML(通过菲尔普/whops )或JSON中输出错误。
文件:config/app.php
<?php
return [
' app ' => [
' debug ' => true ,
]
];当关闭生产环境中的“调试”时,下落只会记录错误并输出HTTP状态。您可以通过应用程序配置覆盖这些默认行为。例如:
文件:config/app.php
<?php
return [
' app ' => [
' errorHandler ' => [ svc Error::class, ' catch ' ],
' errorPageHandler ' => [ svc Error::class, ' page ' ],
]
];文件:app/service/error.php
namespace svc ;
class Error
{
public static function catch ( Throwable $ exception )
{
// Some code like sending an email or using Sentry or something
}
public static function page ( int $ status )
{
switch ( $ status ) {
case 400 :
// Page code...
break ;
case 401 :
// Page code...
break ;
case 403 :
// Page code...
break ;
case 404 :
// Page code...
break ;
case 500 :
// Page code...
break ;
default :
// Page code...
break ;
}
}
}如果您需要定期在后台运行PHP脚本。
$ sudo contab -e将以下内容添加到终点:
* * * * * sudo -u www-data /usr/bin/php /var/www/{PROJECT_DIRECTORY}/app/scheduler.php >> /dev/null 2>&1文件:config/job.php
Alight Job:: call ( ' handler ' )-> minutely ();
Alight Job:: call ( ' handler ' )-> hourly ();
Alight Job:: call ( ' handler ' )-> daily ();
Alight Job:: call ( ' handler ' )-> weekly ();
Alight Job:: call ( ' handler ' )-> monthly ();
Alight Job:: call ( ' handler ' )-> yearly ();
Alight Job:: call ( ' handler ' )-> everyMinutes ( 5 );
Alight Job:: call ( ' handler ' )-> everyHours ( 2 );
Alight Job:: call ( ' handler ' )-> date ( ' 2022-08-02 22:00 ' );每个处理程序一次仅运行一个进程,并且一个过程的默认最大运行时间为1小时。如果您的处理程序需要更长的运行时间,请使用timelimit()。
Alight Job:: call ( ' handler ' )-> hourly ()-> timeLimit ( 7200 ); // 7200 seconds Alight提供AlightApp::root()以标准化项目中文件路径的格式。
// Suppose the absolute path of the project is /var/www/my_project/
Alight App:: root ( ' public/favicon.ico ' ); // /var/www/my_project/public/favicon.ico
// Of course, you can also use absolute path files with the first character '/'
Alight App:: root ( ' /var/data/config/web.php ' );配置中的文件路径均基于AlightApp::root() 。例如:
Alight App:: start ([
' route ' => ' config/route/web.php ' , // /var/www/my_project/config/route/web.php
' job ' => ' config/job.php ' // /var/www/my_project/config/job.php
]);Alight提供了AlightResponse::api()以标准化API响应的格式。
HTTP 200 OK
{
" error " : 0 , // API error code
" message ": " OK ", // API status description
" data": {} // Object data
}状态定义:
| HTTP状态 | API错误 | 描述 |
|---|---|---|
| 200 | 0 | 好的 |
| 200 | 1xxx | 一般业务错误,仅向用户显示消息 |
| 200 | 2xxx | 特殊业务错误,需要为用户定义下一个操作 |
| 4xx | 4xx | 客户端错误 |
| 5xx | 5xx | 服务器错误 |
例如:
Alight Response:: api ( 0 , null , [ ' name ' => ' alight ' ]);
// Response:
// HTTP 200 OK
//
// {
// "error": 0,
// "message": "OK",
// "data": {
// "name": "alight"
// }
// }
Alight Response:: api ( 1001 , ' Invalid request parameter. ' );
// Response:
// HTTP 200 OK
//
// {
// "error": 1001,
// "message": "Invalid request parameter.",
// "data": {}
// }
Alight Response:: api ( 500 , ' Unable to connect database. ' );
// Response:
// HTTP 500 Internal Server Error
//
// {
// "error": 500,
// "message": "Unable to connect database.",
// "data": {}
// }Alight提供了AlightResponse::render()以显示视图模板调用模板文件路径和可选模板数据的渲染方法:
文件:app/controller/pages.php
namespace ctr ;
class Pages
{
public static function index ()
{
Alight Response:: render ( ' hello.php ' , [ ' name ' => ' Ben ' ]);
}
}文件:app/view/hello.php
<h1>Hello, <?= $ name ?> !</h1>文件:config/route/web.php
Alight Route:: get ( ' / ' , [ ctr Pages::class, ' index ' ]);该项目的主页输出将是:
Hello, Ben!还有一些有用的帮助者放置在不同的名称空间中。请单击文件以获取详细信息:
| 名称空间 | 文件 |
|---|---|
| 点亮请求 | request.php |
| 下降响应 | Response.php |
| 下降实用程序 | 实用程序.php |