Creating api class

I want to create an external api to accept vars from outside with the command and take action with vars accordingly.
Two ways:

Class Api {
AddClient()
DeleteClient()
AddOrder()
DeleteOrder()
}

I Have 52 commands/methods. You would add everything in one Api class or create a separate class for each area e.g. OrderApi or ClientApi extending the parent Api class and place methods in each class accordingly? E.g.

Class ClientApi extends Api {
CreateClient()
DeleteClient()
}

Which way better? If second, then only one script should accept command request. Command e.g. “CreateClient” then how that script should understand that it should call class ClientApi with method CreateClient() ?

When I receive a restapi request to take an operation, e.g. CreateOrder and DeleteClient etc. all method operations better to be in just one class or better to categorize methods in different classes e.g. one class for client operations like CreateClient and one class for Order operations like OrderCreate?

If categorizing methods in different classes is better, then the script which receives the restapi request how should know which class should call for which operation, assuming the sent request contains an action parameter like “create_order” or “delete_client”?

It’s definitely a good idea to separate your controller classes according to the resource they work with. Not only is it more logical to group things this way, but you minimize the number of dependencies you need to pass to each controller - eg. the Order controller needs only the OrderRepository, not the ClientRepository as well.

Judging by your questions here and in your other recent threads, it seems that perhaps you’re not completely familiar with the Front Controller pattern or how RESTful APIs work.

Using REST, each resource type is represented by a unique URL. In the case of orders, your URL might be something like api.example.com/orders. The operation to be performed on a resource is determined by the HTTP method (GET, POST, PUT, DELETE being the main ones).

So, for your order resource, you’d make the following requests to peform CRUD actions:

GET     /orders         - returns a collection of orders
POST    /orders         - creates a new order
GET     /orders/:id     - returns an existing order
PUT     /orders/:id     - updates an existing order
DELETE  /orders/:id     - deletes an existing order

So, how does the framework know what classes to load, and how do we make those requests if there’s only a single file (index.php) in the web root?

If you’re using Apache as your web server, you’ll usually put a .htaccess file in the web root containing some instructions to Apache telling it that for every request made the file index.php should be loaded, and the original URL passed to it. The application then looks at the original URL and compares it to a set of rules or predefined routes that determine which controller class should be loaded, and which method on the controller should be called.

Thanks for the very helpful answer. I understood everything. I searched and found Klein and Toro RESTapi library on github.

  1. Can you suggest some more powerful and sophisticated library that I can use?

One non-restapi question:
2) How can I update a record with PUT method? With POST i can get the posted id of a record with some field data to update that record with those posted data. How can I do the same with PUT? And the same question about DELETE. With POST i get an id of the record and delete it from db but how to do the same with DELETE?

  1. I did below. Please tell me if I am doing something wrong?

First I created the following htaccess for router to get first parameter as controller name.

Options +FollowSymLinks
RewriteEngine On
RewriteCond %{SCRIPT_FILENAME} !-d
RewriteCond %{SCRIPT_FILENAME} !-f
RewriteRule ^post/(.*)$ post.php
RewriteRule ^comment/(.*)$ comment.php

Then in each controller I have below to get params:

// post.php
    $requestURI = explode('/', $_SERVER['REQUEST_URI']);
    $scriptName = explode('/',$_SERVER['SCRIPT_NAME']);
    for($i= 0;$i < sizeof($scriptName);$i++)
    {
        if ($requestURI[$i]     == $scriptName[$i])
        {
            unset($requestURI[$i]);
        }
    }
    $command = array_values($requestURI);
    
    // $command[0] is the script name because of htaccess router, 
    // so we go with $command[1] to list of valid class methods. e.g. generate an error json message to respond.
    
    switch($command[1])
    {
    // list of valid methods.
    case 'edit' :
    case 'delete' :
    case 'create' :
                   break;
    default:
            // generate a json error message as response.
            break;
            die();
    }
    
    // main controller script goes here....

what about just using htaccess to call a separate script instead of just one api.php script? for example:

RewriteRule ^post/(.)$ post.php
RewriteRule ^comment/(.
)$ comment.php

then the url /api/post/123/archive just call post.php controller directly and this controller calls the required entities. rather than telling api.php to call which required entities? or still better to have api.php and this one manage which entities to call for which request? which one is better practice?

How to handle this kind of api: https://support.deskpro.com/kb/articles/90-api-people

I was thinking about parsing REQUEST_URI in api.php, so /people/<person_id>/emails/<email_id> will be an array like:
$param[0] = people
$param[1] = 1
$param[2] = emails
$param[3] = 50

then
$entity = new $param0;
if (isset($param[1])) && $param[2] = “emails” && isset($param[1]) && $method = “DELETE”) {
$entity->doDelete($param[1], $param[3]);
} elseif (isset($param[1])) && $param[2] = “emails” && isset($param[1]) && $method = “POST”) {
$entity->doAdd($param[1], $param[3]);
} elseif…

and so on we will have a looong IF statement. Do you have any better idea?

There are many. If you want something powerful and fully featured you could use something like Laravel, which has features like a command line utility that can generate a resource controller with methods that correspond to the HTTP methods. Alternatively, micro-frameworks like Slim, and routing libraries like Klein will also get the job done if you prefer something simpler and more light-weight.

PUT is very similar to POST, the data is sent in the request body. The real difference is with how the server handles the request. DELETE requests don’t need a request body, as the HTTP method specifies that the resource should be deleted, and the resource is identified by the URI.

I’m confused about what you’re trying to do - there doesn’t seem much point in using .htaccess to rewrite the requests if you’re not actually going to route them through a front controller.

To be honest, unless this is just a learning exercise, I’d go with some kind of framework (or a routing library, at least), otherwise you’re just wasting time re-inventing the wheel and it’s likely there’ll be use-cases or bugs that you’ll overlook.

Thanks.
I see Slim is mic-framework and Klein is standalone router. Laravel is great but I think it is not possible to download its router standalone via composer?
Among Slim and Klein which one do you suggest to go?

It’s difficult to give a specific recommendation - what exactly do you want to build and why? Do you have any other requirements that might influence your choice of framework/library?

I would say, though, that if you’re not interested in using Laravel as framework I wouldn’t bother trying to download its router as a component - it’d be easier just to pick a router library (of which there are many) and use that.

This topic was automatically closed 91 days after the last reply. New replies are no longer allowed.