PHP Rest Server

SensioLabsInsight

Description

Enable to create RESTFull services with strong model schema. The main goal is to abstract the class transformation into JSON/XML and encapsulate the server commands.

Usage

The main purpose of this package is abstract all complexity to process a RESTFull request and handle the object response.

The quick guide is:

For example, if you want to process the HTTP method POST you have to do:

namespace Sample

class MyClass extends \ByJG\RestServer\ServiceAbstract
{

    public function post()
    {
        $id = $this->getRequest()->get('id');

        // Do something here...

        $this->getResponse()->write( [ 'result' => 'ok' ] );
    }
}

The usual url for call this class is (see more in Routing below):

http://yourserver.com/1.0/Sample.MyClass/1234.json     # Or xml or csv

Processing the request

All $_GET, $_SERVER, $_POST, etc are encapsulated in the HttpRequest object. Inside the ServiceAbstract class you just call $this->getRequest() method.

The available options are:

Output your data

The main goal of the RestServer ByJG is work with the objects in your native form. The processing to the proper output like JSON, XML or CSV is done by the platform. See below some examples:

namespace Sample

class MyClass extends \ByJG\RestServer\ServiceAbstract
{

    public function get()
    {
        // Output an array
        $array = ["field" => "value"];
        $this->getResponse()->write($array);

        // Output a stdClass
        $obj = new \stdClass();
        $obj->MyField = [ "teste1" => "value1", "test2" => [ "3", "4"]];
        $obj->OtherField = "OK";
        $this->getResponse()->write($obj);

        // Model  
        // Can be an object :
        //    - with public properties 
        //    - with getters and setters
        //    - with mixed public properties and getters and setters
        // See more about object transformations in the project https://github.com/byjg/anydataset
        // For this example, assume that Model have two properties: prop1 and prop2
        $model = new Model('tests', 'another test');
        $this->getResponse()->write($model);
    }
}

The result will be something like:

{
    "field":"value",
    "MyField":{
        "teste1":"value1",
        "test2":["3","4"]
    },
    "OtherField":"OK",
    "Model":{
        "prop1":"tests",
        "prop2":"another test"
    }
}

Combining HTTP Methods with ACTION

If you pass a query parameter called action you can combine the HTTP Request and the action for create a specific method for handle this specific action. Some examples below:

HTTP Method Action Parameter Method in the class
GET - get()
POST - post()
DELETE - delete()
PUT - put()
GET someaction getSomeaction()
POST someaction postSomeaction()
PUT someaction putSomeaction()
DELETE someactiom deleteSomeaction()

Routing

RestServer ByJG uses the Nikic/FastRoute project to do the routing. Yout need copy the file httpdocs/route-dist.php as route.php into the root of your public folder accessible throught the web.

This file setup all routing process and handle the execution of the proper rest class.

There some pre-defined routes as you can see below but you can change it any time you want.

The pre-defined routes are:

Pattern Exeample
/{version}/{module}/{action}/{id:[0-9]+}/{secondid}.{output} /1.0/MyNameSpace.Module/list/1/2345.json
/{version}/{module}/{action}/{id:[0-9]+}.{output} /1.0/MyNameSpace.Module/list/1.json
/{version}/{module}/{id:[0-9]+}/{action}.{output} /1.0/MyNameSpace.Module/1/list.json
/{version}/{module}/{id:[0-9]+}.{output} /1.0/MyNameSpace.Module/1.json
/{version}/{module}/{action}.{output} /1.0/MyNameSpace.Module/list.json
/{version}/{module}.{output} /1.0/MyNameSpace.Module.json

All variables defined above will be available throught the $_GET. The variables output, module and version having a special meaning into the system:

Creating Module Alias

Instead to pass the full namespace class you can create a module alias. Just add in the route.php file the follow code:

$route->addModuleAlias('somealias', 'Full.NameSpace.To.Module');

In the example above if the parameter "module" matches with the value "somealias" will be mapped to the class "\Full\NameSpace\To\Module"

Versioning your rest service

You can define a version to yout rest service and create a EOL for changes in the services that breaking the interface. Just set in the "route.php" file the follow line:

$route->setDefaultRestVersion('2.0');

This will populate de variable "version".

Creating your own routes

You can override the default route values and create your own.

$route->setDefaultMethods([
    [ "method" => ['GET'], "pattern" => '/{module}/{action}/{id:[0-9]+}.{output}', "handler" => 'service' ],
]);

This will override all previous routes and setup the one defined above.

Install

Just type: composer install "byjg/restserver=~1.0"

Running Tests


Open source ByJG