PhpClosureBasedFramework
This is my simple php framework for api development developed for learning how big framework like laravel, slim works on routes dispatching and executing middleware
Install / Use
/learn @ashish336b/PhpClosureBasedFrameworkREADME
PhpClosureBasedFramework
This is simple php closure based framework for api development
Installation
composer create-project ashish336b/carpo-php-framework blog
With this Installation is completed. Run the command to open web server in port 1212.
php -S localhost:1212 -t public/
Project Folder Structure.
├───app </br> │ ├───controller </br> │ ├───middleware </br> │ ├───model </br> │ └───views </br> ├───public </br> └───vendor </br>
- app/controller contains all your controller class for project
- app/middleware contains all your middleware class fro project.
- app/views contains all views files for project.
with this Full installation is completed.
Routes
You can create routes by calling static class Application
use ashish336b\PhpCBF\Application as App;
App::get("/", function (Request $request, Response $response) {
echo "My First Route.";
});
Methods
App::get("/urlPattern" , function(){});
App::post("/urlPattern" , function(){});
App::put("/urlPattern" , function(){});
App::delete("/urlPattern",function(){});
There is also another method you can access from \ashish\PhpCBF\Application class
App::on("EVENT_TYPE" , function(){});
EVENTTYPE can be either BEFORE or AFTER
- BEFORE : This event run before all application middleware and routes. Best usecase to set CORS header.
- AFTER : If you need to run a piece of code after running your middleware and routes function use this. For example global response header is set here
URL Pattern
-
Url pattern is used to define routes. Both static pattern and dynamic pattern can be defined mostly same as laravel.
-
static Routes:
App::get("/users", Closure);baseurl/usersurl is dispatched with this pattern.
-
Variable Routes:
APP::get("/home/{id}", closure)baseurl/home/1orbaseurl/home/2` ... is dispatch. -
You cannot register two same pattern.
Optional Pattern.
App::get("/user/{id?}" , closure);</br> bothbaseurl/user/1andbaseurl/userare dispatched here id params is optional.
- You should not define any required placeholder/params after optional placeholder/params.</br>
/user/{id?}/{userId}This is completely wrong. </br>/user/{userId}/{id?}This is correct way. - It is good practice to have only one optional params in pattern and it must be last placeholder.
- However two or more optional params are supported if only one required params appears before any optional params. Using more than one optional params may lead to confusion and hard to debug so is not recommended</br>
- You cannot register static Routes after any variable routes that matches static route pattern. Example: </br>
suppose this variable pattern is defined at first
user/{id}and you define another patternuser/homewhich matches``user/{id}` It gives you error. - However you can define
user/homeat first and thenuser/{id}. This is completely fine.
Routes Group
- Your can define routes group just like in other famous framework like laravel, slim. etc.
- First Params is array which can have two keys params and middleware.
- Params : For defining common url pattern that appears in every routes group.
- Middleware : name of middleware class that is inside
/App/middleware/namespace.
App::group(["prefix"=>"/admin"],function(){
// every GET POST PUT DELETE methods routes can be define.
App::get("/login",Closure);
//dispatch /admin/login
App::get("/login/{id}", Closure);
//dispatch /admin/login/1 , /admin/login/anything etc.
});
get,post,putanddeletemethod have two parameters. url pattern and closure respectively.- closure can have two paramas $request and $response of type
RequestandResponserespectively
App::get("/user/{id}/{anotherParams}", function (Request $request, Response $response) {
// Access params value with $request->params.
$request->params->id;
$request->params->anotherParams;
});
Controller
You can create controller class inside app/controller with namespace namespace App\controller;
<?php
namespace App\controller;
use ashish336b\PhpCBF\Request;
use ashish336b\PhpCBF\Response;
class AdminController
{
public function index(Request $request, Response $response)
{
$request->url = $request->getUrl();
return $response->toJSON($request);
}
public function user(Request $request, Response $response)
{
echo $response->render("/admin", ['fullUrl' => $request->fullURL]);
}
}
you can define class and method to execute in route with classname@methodname.
App::get("/admin/user", "AdminController@user");
-
In routes "AdminController@user" means AdminController is directly inside controller folder which have user method that is to be executed for response.
-
If your controller is inside /app/controller/user/UserController.php and method is index that is to be executed then </br>
App::get("/user", "user\UserController@index")
Model
This contains data related logic such as retriving data from database and passing to controller.<br/> you have to create model class inside model folder. This folder can contain sub folder to group models.
<?php
namespace App\model;
use ashish336b\PhpCBF\DB;
use ashish336b\PhpCBF\Model;
class Auth extends Model
{
protected $table = "user";
public function fetchUser()
{
//directly run query from model
return $this->query("select * from user")->results();
// fetch all row of table specified in $table
return $this->fetch();
// get columns of table
return $this->getColumns();
}
}
To access model function from controller.
$user = $this->model("Auth")->fetchUser();
Here Auth is the name of file that is inside model folder and fetchUser() is method inside Auth file/class.
$this->model("Admin\Auth")->fetchUser();
In above case Auth class is inside Admin folder which is inside model folder.
Database
This framework mainly support mysql database. However you can integrate any database with the help other open source project.
- To fetch all data from table(eg. user)
DB::table("user")->get();
- To run any query
$result = DB::raw()->query("select * from user where id = ?",[1])->result();
- count result
$noOfRow = DB::raw()->query("select * from user")->count();
Migration
you can use migration to run create table, alert etc. every migration should be inside app/migration directory.
<?php
namespace App\migrations;
use ashish336b\PhpCBF\Application;
class create_user_table
{
public function up()
{
$SQL = "CREATE TABLE users (
id INT AUTO_INCREMENT PRIMARY KEY,
firstname VARCHAR(255) NOT NULL,
lastname VARCHAR(255) NOT NULL,
email VARCHAR(255) NOT NULL,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
)";
Application::$pdo->exec($SQL);
}
public function down()
{
$SQL = "DROP TABLE users;";
Application::$pdo->exec($SQL);
}
}
every migration should be created in this manner. Till now sub directory is not allowed to store migration. Every migration should be in app/migrations directory.
Middleware
Middleware provide a convenient mechanism for filtering HTTP requests entering your application. For Example if you want to check if user is authenticated or not you can check it in middleware. If user is not authenticated you can throw response of 403 which does not allow routes closure to execute.
Your can define Middleware in routes groups as well as individual routes.
App::group(["prefix"=>"/admin","middleware"=>["Auth"]],function(){
App::get("/",function(){
echo "/admin";
})
});
Auth class should be inside app/middleware/Auth.php with namespace namespace app\\middleware\\;
- Middleware should always return true if none of the condition meets.
<?php
namespace App\middleware;
use ashish336b\PhpCBF\Request;
use ashish336b\PhpCBF\Response;
class Auth
{
public function run(Request $request, Response $response)
{
$auth = false;
if(!$auth){
return $response->toJSON(["message" => "not authenticated"]);
}
return true;
}
}
- You can define middleware in individual middleware in get,post,put and delete method.
App::get("/user","UserController@index",["Guest"]);
Request
Request and Response can be accessed in both controller method and closure from parameter.
-return url without get params. eg. /admin/index
$request->getUrl();
- Return all body from post request as object.
$request->body
- Access Body with name. If BODY_NAME is in object of
$request->bodythen it return value else returnnull.
$request->body("BODY_NAME");
- Get all get params from url as object.
$request->query
- Return get query params value. If
QUERY_NAMEis not set it returnnull
$request->query("QUERY_NAME");
- return all request headers as object.
$request->allHeaders();
- Return header value. If not set return false
$request->header("Header_NAME");
Response
Response class have two method as of now.
- Return object to json.
$response->toJSON($obj);
- render method return view containing html files. Accept two params first is path of folder from view folder and another is associative array.
$response->render("/admin",array);
/adminis file from/app/view/admin.php/admin/loginis file from `/app/view
Related Skills
node-connect
354.3kDiagnose OpenClaw node connection and pairing failures for Android, iOS, and macOS companion apps
frontend-design
112.3kCreate distinctive, production-grade frontend interfaces with high design quality. Use this skill when the user asks to build web components, pages, or applications. Generates creative, polished code that avoids generic AI aesthetics.
openai-whisper-api
354.3kTranscribe audio via OpenAI Audio Transcriptions API (Whisper).
qqbot-media
354.3kQQBot 富媒体收发能力。使用 <qqmedia> 标签,系统根据文件扩展名自动识别类型(图片/语音/视频/文件)。
