elcapitansponge/phlounder

Minimalistc semi-opinionated PHP router

v0.1.1 2024-03-19 12:49 UTC

This package is auto-updated.

Last update: 2024-04-19 13:13:54 UTC


README

Minimalistic opinionated PHP Routing engine

PHP

⇁ About

A minimalistic routing engine for PHP allowing route parameters for GET, POST, PUT, DELETE and OPTIONS. The only thing missing is your code.

⇁ Installation

Composer

composer require elcapitansponge/phlounder

Git

NOTE As this is still in development cloning the repo is the way to go.

git clone https://github.com/ElCapitanSponge/phlounder.git

or

git clone git@github.com:ElCapitanSponge/phlounder.git

⇁ Getting Started

Calling the library

Include the library in your script

Composer

require __DIR__ . "/vendor/autoload.php"

Git Clone

Alternitively you can load the files using the following snippet

$phlounder_path = "./phlounder/";

foreach (glob("{$phlounder_path}src/**/*.php") as $filename) {
    include $filename;
}
foreach (glob("{$phlounder_path}src/*.php") as $filename) {
    include $filename;
}

Using the library

An example implementation of phlounder is as follows

use phlounder\Router;
use phlounder\lib\ResponseCodes;
use phlounder\router\Request;
use phlounder\router\Response;

$router = new Router();

$router->get("/", function (Request $req, Response $res) {
    $res->to_json(ResponseCodes::OK, "Hello World!");
});

$router->get("/user/{id}", function (Request $req, Response $res) {
    $data = new \stdClass();
    $data->params = $req->get_params();
    $res->to_json(ResponseCodes::OK, $data);
});

$router->post("/user", function (Request $req, Response $res) {
    $res->to_json(ResponseCodes::CREATED);
});

$router->put("/user/{id}", function (Request $req, Response $res) {
    $res->to_json(ResponseCodes::OK);
});

$router->delete("/user/{id}", function (Request $req, Response $res) {
    $res->to_json(ResponseCodes::OK);
});

$router->none_found();

Route Handling

The routing due to the nature of implementation follows the order of precidence. In otherwords, a top to bottom approach when processing.

This is apparent with the following snippet:

$router->get("/user/{id}", function (Request $req, Response $res) {
    $data = new \stdClass();
    $data->params = $req->get_params();
    $res->to_json(ResponseCodes::OK, $data);
});

$router->get("/user/foo", function (Request $req, Response $res) {
    $res->to_json(ResponseCodes::OK, "Bar!");
});

In the above snippet if you hit /user/foo You don't recieve:

{
    "code": 200,
    "data": "Bar!"
}

Instead you recieve:

{
    "code": 200,
    "data": {
        "params": {
            "id": "foo"
        }
    }
}

To resolve this issue we have to place the /user/foo route before /user/{id}

$router->get("/user/foo", function (Request $req, Response $res) {
    $res->to_json(ResponseCodes::OK, "Bar!");
});

$router->get("/user/{id}", function (Request $req, Response $res) {
    $data = new \stdClass();
    $data->params = $req->get_params();
    $res->to_json(ResponseCodes::OK, $data);
});

Route paramater types

There is type handling for string or int in the route params if desired.

Taking the following:

$router->get("/users/{id:i}", function (Request $req, Response $res) {
    $data = new \stdClass();
    $data->params = $req->get_params();
    $res->to_json(ResponseCodes::OK, $data);
});

$router->get("/course/{code:s}", function (Request $req, Response $res) {
    $data = new \stdClass();
    $data->params = $req->get_params();
    $res->to_json(ResponseCodes::OK, $data);
});

$router->get("/category/{id}", function (Request $req, Response $res) {
    $data = new \stdClass();
    $data->params = $req->get_params();
    $res->to_json(ResponseCodes::OK, $data);
});
  • /users/{id:i}: The id param is specified to be an int
  • /course/{code:s}: The code param is specified to be a string
  • /category/{id}: The id param can be either a string or an int