这是一个 QueryPHP 应用,其核心框架可以在这里找到 Framework。
QueryPHP 是一款现代化的高性能 PHP 渐进式协程框架, 我们还是主要面向传统 PHP-FPM 场景,以工程师用户体验为历史使命,让每一个 PHP 应用都有一个好框架。
百分之百单元测试覆盖直面 Bug,基于 Zephir 实现框架核心常驻,依托 Swoole 协程提升业务性能,此刻未来逐步渐进。 我们的愿景是 USE LEEVEL WITH SWOOLE DO BETTER , 让您的业务撑起更多的用户服务。
代码如诗,自由如风, 此刻携手 QueryPHP 共创美好.
QueryPHP 基于一款成立于 2010 年的 PHP 框架 DoYouHaoBaby 开发,继承了上一代产品的优秀之处,彻底革新并进行了长达 2 年重构.
composer create-project hunzhiwange/queryphp myapp dev-master
php leevel server <Visite http://127.0.0.1:9527/>
CREATE DATABASE IF NOT EXISTS myapp DEFAULT CHARSET utf8 COLLATE utf8_general_ci;
vim .env ... // Database DATABASE_DRIVER = mysql DATABASE_HOST = 127.0.0.1 DATABASE_PORT = 3306 DATABASE_NAME = queryphp_development_db DATABASE_USER = root DATABASE_PASSWORD = ... to ... // Database DATABASE_DRIVER = mysql DATABASE_HOST = 127.0.0.1 DATABASE_PORT = 3306 DATABASE_NAME = myapp DATABASE_USER = root DATABASE_PASSWORD = 123456 ...
php leevel migrate:migrate php leevel server
http://127.0.0.1:9527/api/entity
{ count: 4, :trace: { ... } }
第一步安装前端,细节信息可以在 frontend/README.md 查看.
frontend/README.md
cd frontend npm install -g cnpm --registry=https://registry.npm.taobao.org // Just once cnpm install npm run serve # npm run dev
接着访问这个登陆地址. http://127.0.0.1:9528/#/login
user: admin password: 123456
CREATE DATABASE IF NOT EXISTS test DEFAULT CHARSET utf8 COLLATE utf8_general_ci;
vim .testing ... // Database DATABASE_DRIVER = mysql DATABASE_HOST = 127.0.0.1 DATABASE_PORT = 3306 DATABASE_NAME = test DATABASE_USER = root DATABASE_PASSWORD = ... to ... // Database DATABASE_DRIVER = mysql DATABASE_HOST = 127.0.0.1 DATABASE_PORT = 3306 DATABASE_NAME = test DATABASE_USER = root DATABASE_PASSWORD = 123456 ...
php leevel migrate:migrate -e testing
_____________ _______________ ______/ \__ _____ ____ ______ / /_ _________ ____/ __ / / / / _ \/ __`\/ / __ \/ __ \/ __ \___ __/ / / / /_/ / __/ / \ / /_/ / / / / /_/ /__ \_\ \_/\____/\___/_/ / / .___/_/ /_/ .___/ \_\ /_/_/ /_/ $cd /data/codes/queryphp/ $vim .testing # modify database redis and other $php leevel migrate:migrate -e testing - $php vendor/bin/phpunit + $php ./build/phpunit
修改 .env 或者 runtime/bootstrap/option.php.
// Environment production、testing and development ENVIRONMENT = production // Debug DEBUG = false DEBUG_JSON = false DEBUG_CONSOLE = false DEBUG_JAVASCRIPT = false
下面的指令可以让 QueryPHP 运行得更加快速。
php leevel router:cache php leevel option:cache php leevel i18n:cache php leevel view:cache php leevel autoload (Equivalent to `composer dump-autoload --optimize --no-dev`)
或者
php leevel production
// Environment production、testing and development ENVIRONMENT = development // Debug DEBUG = true DEBUG_JSON = true DEBUG_CONSOLE = true DEBUG_JAVASCRIPT = true
php leevel i18n:clear php leevel log:clear php leevel option:clear php leevel router:clear php leevel session:clear php leevel view:clear php leevel autoload --dev (Equivalent to `composer dump-autoload --optimize`)
Or
php leevel development
后续会提供 dll 扩展.
从下面的仓库下载源代码.
git clone git@github.com:hunzhiwange/leevel.git cd ext
GCC 编译源码.
$/path/to/phpize $./configure --with-php-config=/path/to/php-config $make && make install
将扩展添加到你的 php.ini, 使用 php -m 查看扩展是否被安装.
extension = leevel.so
php leevel http:server # php leevel http:server -d php leevel http:reload php leevel http:stop php leevel http:status
Swoole http 和 php-fpm 保持一致
root@vagrant-ubuntu-10-0-2-5:/data/codes/queryphp# php leevel http:server _____________ _______________ ______/ \__ _____ ____ ______ / /_ _________ ____/ __ / / / / _ \/ __`\/ / __ \/ __ \/ __ \___ __/ / / / /_/ / __/ / \ / /_/ / / / / /_/ /__ \_\ \_/\____/\___/_/ / / .___/_/ /_/ .___/ \_\ /_/_/ /_/ Http Server Version 1.0.0 +-----------------------+---------------------------------+ | Item | Value | +-----------------------+---------------------------------+ | host | 0.0.0.0 | | port | 9501 | | process_name | leevel.http | | pid_path | @path/runtime/protocol/http.pid | | worker_num | 8 | | daemonize | 0 | | enable_static_handler | 1 | | document_root | @path/www | | task_worker_num | 4 | +-----------------------+---------------------------------+
php leevel websocket:server # php leevel websocket:server -d php leevel websocket:reload php leevel websocket:stop php leevel websocket:status
一个聊天室测试
root@vagrant-ubuntu-10-0-2-5:/data/codes/queryphp# php leevel websocket:server _____________ _______________ ______/ \__ _____ ____ ______ / /_ _________ ____/ __ / / / / _ \/ __`\/ / __ \/ __ \/ __ \___ __/ / / / /_/ / __/ / \ / /_/ / / / / /_/ /__ \_\ \_/\____/\___/_/ / / .___/_/ /_/ .___/ \_\ /_/_/ /_/ Websocket Server Version 1.0.0 +-----------------+--------------------------------------+ | Item | Value | +-----------------+--------------------------------------+ | host | 0.0.0.0 | | port | 9502 | | process_name | leevel.websocket | | pid_path | @path/runtime/protocol/websocket.pid | | worker_num | 8 | | daemonize | 0 | | task_worker_num | 4 | +-----------------+--------------------------------------+
访问 http://127.0.0.1:9527/websocket/chat
php leevel rpc:server # php leevel rpc:server -d php leevel rpc:reload php leevel rpc:stop php leevel rpc:status
Rpc thrift 协议
Leevel/Protocol/Thrift/Struct/leevel.thrift
namespace php Leevel.Protocol.Thrift.Service /** * --------------------------------------------------------------- * 定义一个请求包结构 * --------------------------------------------------------------- * * 约定请求数据包,方便只定义一个结构全自动调用 MVC 服务 */ struct Request { // call 为字符串类型,是指 Service 接口的名称 // 例如:home/blog/info@get 为调用 mvc 接口中的数据 1: required string call; // params 为 list 类型数据,一个元素可重复的有序列表,C++ 之 vector,Java 之 ArrayList,PHP 之 array 2: list<string> params; // 服务端客户端共享自定义共享数据 // 相当于 PHP 中的关联数组 3: map<string,string> metas; } /** * --------------------------------------------------------------- * 定义一个响应包结构 * --------------------------------------------------------------- * * 通用响应接口,数据以 JSON 进行交互 */ struct Response { // status 为响应状态,200 表示成功,其他参考 HTTP 状态 1: required i16 status; // code 为 JSON 字符串,客户端自主进行解析 2: required string data; } /** * --------------------------------------------------------------- * 定义一个通用的服务 * --------------------------------------------------------------- * * 通用调用服务,通过一个 call */ service Thrift { Response call(1: Request request) }
一个 rpc 测试
root@vagrant-ubuntu-10-0-2-5:/data/codes/queryphp# php leevel rpc:server _____________ _______________ ______/ \__ _____ ____ ______ / /_ _________ ____/ __ / / / / _ \/ __`\/ / __ \/ __ \/ __ \___ __/ / / / /_/ / __/ / \ / /_/ / / / / /_/ /__ \_\ \_/\____/\___/_/ / / .___/_/ /_/ .___/ \_\ /_/_/ /_/ Rpc Server Version 1.0.0 +-----------------------+--------------------------------+ | Item | Value | +-----------------------+--------------------------------+ | host | 0.0.0.0 | | port | 1355 | | process_name | leevel.rpc | | pid_path | @path/runtime/protocol/rpc.pid | | worker_num | 8 | | daemonize | 0 | | dispatch_mode | 1 | | open_length_check | 1 | | package_max_length | 8192000 | | package_length_type | N | | package_length_offset | 0 | | package_body_offset | 4 | | task_worker_num | 4 | +-----------------------+--------------------------------+
访问 http://127.0.0.1:9527/api/rpc
<?php declare(strict_types=1); /* * This file is part of the your app package. * * The PHP Application For Code Poem For You. * (c) 2018-2099 http://yourdomian.com All rights reserved. * * For the full copyright and license information, please view the LICENSE * file that was distributed with this source code. */ namespace App\App\Controller\Api; use Leevel\Http\IResponse; use Leevel\Protocol\Proxy\Rpc as Rpcs; /** * rpc tests. * * @author Name Your <your@mail.com> * * @since 2018.08.31 * * @version 1.0 */ class Rpc { /** * 默认方法. * * @return \Leevel\Http\IResponse */ public function handle(): IResponse { return Rpcs::call('api/rpc/rpc-result', ['foo', 'bar'], ['arg1' => 'hello', 'arg2' => 'world']); } /** * RPC 结果. * * @return array */ public function rpcResult(string $arg1, string $arg2, array $metas): array { return ['arg1' => $arg1, 'arg2' => $arg2, 'metas' => $metas]; } } // The result // {"arg1":"foo","arg2":"bar","metas":{"arg1":"hello","arg2":"world"}}
RoadRunner 是一个开源的高性能 PHP 应用服务器、负载均衡器和流程管理器。它支持作为一个服务运行,能够在每个项目的基础上扩展其功能。
你可以下载二进制文件.
cd /data/server wget https://github.com/spiral/roadrunner/releases/download/v1.3.5/roadrunner-1.3.5-darwin-amd64.zip unzip roadrunner-1.3.5-darwin-amd64.zip cd /data/codes/queryphp
/data/server/roadrunner-1.3.5-darwin-amd64/rr serve -d -v # -d = debug /data/server/roadrunner-1.3.5-darwin-amd64/rr http:reset /data/server/roadrunner-1.3.5-darwin-amd64/rr http:workers -i
Roadrunner 和 php-fpm 保持一致
root@vagrant-ubuntu-10-0-2-5:/data/codes/queryphp# /data/server/roadrunner-1.3.5-darwin-amd64/rr serve -d -v DEBU[0000] [static]: disabled DEBU[0000] [rpc]: started DEBU[0000] [http]: started INFO[0060] 127.0.0.1 {23.1ms} 200 GET http://127.0.0.1:9601/api/test
https://github.com/friendsofphp/php-cs-fixer
不需要安装即可使用,我们已经下载了版本。
$cd /data/codes/queryphp - $php-cs-fixer fix --config=.php_cs.dist + $./build/php-cs-fixer fix --config=.php_cs.dist
添加一个 pre-commit 钩子.
cp ./build/pre-commit.sh ./.git/hooks/pre-commit chmod 777 ./.git/hooks/pre-commit
跳过钩子
# git commit -h # git commit -n -m 'pass hook' #bypass pre-commit and commit-msg hooks
php ./build/phpstan analyse
感谢同事 毛飞 在开发这个项目过程中的无私帮助,让我有了很多新的认识, 这让 QueryPHP 变得更加的美好.
也非常感谢下面的这些优秀的开源软件, 我们也参考了很多的设计与思想, 让我们可以站在巨人的肩膀上保持创新.
QueryPHP 是一个基于 MIT license 授权许可协议的开源软件.