Available Endpoints

WARNING

This section assumes that Models do not have any request validation rules. If you want to see how to validate requests, according to your model needs, see the Validating Request section.

WARNING

In this section we are not discussing handling files in the request. If you are interested about handling files in an endpoint see Working With Files section.

TIP

In this section we assume that the route prefix that is set in the routes/api.php file remains the same as the initial which is /aap. If you changed the default route prefix, you are advised to replace /aap according to your selected prefix.

Single Model Endpoints

After the package installation these 5 endpoints are activated for all of your application's models.

HTTP VerbURIResponse Code on SuccessEndpoint Description
GET/api/aap/{model}200 - OKReturns All Models
GET/api/aap/{model}/{id}200 - OKReturns a Model
with the specified id
POST/api/aap/{model}200 - OKCreates a new Model
POST/api/aap/update/{model}/{id}/200 - OKUpdates values of an
existing Model
DELETE/api/aap/{model}/{id}200 - OKDeletes an existing Model

WARNING

Since there is an incompatibility of Patch Requests that use Form-Data, in php the update endpoint is different from the naming convention for endpoints, and its url is /api/aap/update/{model}/{id}/ until the issue is resolved.

Let's assume the following model exists within your application:

 Post:
    id - integer
    title - string
    body - text
    created_at - timestamp
    updated_at - timestamp

Create

To create a new Post Model and insert it into the database, the URL will be /api/aap/post, with the Request Body containing all the required columns, since we are not going to validate values here. For the Post Model specified above we need a title, and a body, and the final request JSON will contain:

{
    "title": "A new post created with Api Auto Pilot",
    "body": "Lorem ipsum dolor sit amet, consectetur adipiscing elit. "
}

If everything went alright, didn't miss any required columns in the request, then the response will have a 200 OK HTTP Response Code, and the response body will contain the newly created Model, without any properties that are hidden.

{
    "title": "Creating a Post Model Through Api Auto Pilot",
    "body": "Lorem ipsum dolor sit amet, consectetur adipiscing elit.",
    "updated_at": "2022-11-22T16:15:53.000000Z",
    "created_at": "2022-11-22T16:15:53.000000Z",
    "id": 1
}

Read

To get a specific model using your API, make a GET Request and as a route parameter you should use the name of the Model that you want to get followed by the id of the specific Model.

TIP

If you want to get all the models, do not use id parameter and instead make a GET Request to the Model Name endpoint in SINGULAR. In the Model Case will be: /api/aap/post.
To use pagination see the Additional Settings section.

In our case, Lets get the Post Model, that we created previously. So will perform a GET Request to the/api/aap/post/1 The response will contain all the Post Model Values.

{
    "id": 1,
    "title": "Creating a Post Model Through Api Auto Pilot",
    "body": "Lorem ipsum dolor sit amet, consectetur adipiscing elit.",
    "created_at": "2022-11-22T16:15:53.000000Z",
    "updated_at": "2022-11-22T16:15:53.000000Z"
}

Update

To Update an existing model, use the POST HTTP Verb, using the Model Name as route parameter, followed by the id of the model that you wish to update. The Request Body should contain all the values that you want to be updated. In our case we will update the title of the Post Model that we created before, so we will fill only the title property in the request body, coupled with new title that we want that post to have. The Request route should: /api/aap/post/1

{
    "title": "Updated Title! Creating a Post Model Through Api Auto Pilot"
}

The response will contain the model with the new updated values, the updated_at time, followed by a 200 OK HTTP Response Code.

{
    "id": 1,
    "title": "Updated Title! Creating a Post Model Through Api Auto Pilot",
    "body": "Lorem ipsum dolor sit amet, consectetur adipiscing elit.",
    "created_at": "2022-11-22T16:15:53.000000Z",
    "updated_at": "2022-11-22T17:06:54.000000Z"
}

Delete

To Delete an existing model from the database, use the DELETE HTTP Verb, the Model Name that you want to delete, followed by id id of the model you wish to be deleted. In our case, we will delete the Post Model, that we previously, created and then updated. The URL for that operation will be /api/aap/post/1 without Request Body.

The response body will contain a Model Deleted Successfully message, followed by a 200 - OK HTTP Response Code.

{
    "success": {
        "message": "deleted record with id: 1"
    }
}

Models With Relationships Endpoints

There are many times that makes sense to perform CRUD operations involving related models all at once. Well, we got you covered. After successfully installing the package, these API endpoints are activated as well.

HTTP VerbURIResponse Code on SuccessEndpoint Description
GET/api/aap/{model}/{id}/{relationship-method-name}200 - OKReturns a Model
with the specified id with all related models
POST/api/aap/{model}/{relationship-method-name}200 - OKCreates a new Model with related model(s)

WARNING

The {relationship-method-name} route parameter, MUST match with the method name you have set on the model class, to define a relationship.
For example, lets say that on your Post Model you have a belongsToMany Relationship to your Tag Model.

namespace App\Models;

use Illuminate\Database\Eloquent\Relations\BelongsToMany;

class Post extends Model{
   
    use HasFactory;
    
    protected $fillable = [
        'body', 'title', 
    ];
    
    public function tags(): BelongsToMany{
        return $this->belongsToMany(App\Models\Tag::class);
    }
}

To perform CRUD operations using the Post Model and the Tag Model the
{relationship-method-name} route parameter should be the method name of the relationship, which is tags. For example, GET /api/aap/post/1/tags

Create

To demonstrate how to create models with their related models in the same request, we will distinguish it in 3 possible scenarios

One to One

To create models that are related with a One-to-One relationship, we will be using a User model, and a Phone model. A user model is saved into a users table and a Phone model is saved into phones table, referencing the users table with a foreign key. Let's see the Model classes one by one

<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Relations\HasOne;
use Illuminate\Foundation\Auth\User as Authenticatable;
use Illuminate\Notifications\Notifiable;
use Laravel\Sanctum\HasApiTokens;

class User extends Authenticatable
{
    use HasApiTokens, HasFactory, Notifiable;


    protected $fillable = [
        'name', 'email', 'password',
    ];

    protected $hidden = [
        'password',
        'remember_token',
    ];

    protected $casts = [
        'email_verified_at' => 'datetime',
    ];

    public function phone(): HasOne
    {
        return $this->hasOne(Phone::class);
    }
}

This is the default Laravel User Model class, the only difference is that we added a HasOne relationship with the Phone Model, under the name of phone as relationship method name.

Let's now see the Phone Class.

<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Relations\BelongsTo;

class Phone extends Model
{
    use HasFactory;

    protected $fillable = [
        'user_id', 'number', 'country'
    ];

    public function user(): BelongsTo
    {
        return $this->belongsTo(User::class);
    }
}

The Phone class is a small Model class that defines a BelongsTo relationship with the User Model, under the method name of user

To create both the User and the Phone models, make a POST request using the main model first, which is user followed by the relationship method name as the second route parameter. This will result to the following request URI for the POST Request /api/aap/user/phone And the Request Body Should look like this:

{
    "name": "Someone Somewhere",
    "email": "foo@bar.com",
    "password": "123",
    "phone": {
        "number": "1234472612",
        "country": "us"
    }
}

Consider not allowing users to use this password 😂

Notice that for the fields that correspond to the related model, in our case the phone model, the JSON index is again the relationship method name that was defined in the User model.


The successful execution of this request will result in a response body containing the main model, which in our case is User along with the related Model, which in our case is Phone followed by a 200 OK HTTP Response Code

{
    "name": "Someone Somewhere",
    "email": "foo@bar.com",
    "updated_at": "2022-11-22T18:15:28.000000Z",
    "created_at": "2022-11-22T18:15:28.000000Z",
    "id": 1,
    "phone": {
        "id": 1,
        "number": "1234472612",
        "country": "us",
        "user_id": 2,
        "created_at": "2022-11-22T18:15:28.000000Z",
        "updated_at": "2022-11-22T18:15:28.000000Z"
    }
}

If the relationship route parameter is not the same with the model method name that defines the relationship, for example, request url be: /api/aap/user/phones and not /api/aap/user/phone will result in a 404 NOT FOUND HTTP Response code along with the following response body:

{
    "error": {
        "error_message": "Endpoint Not Found!",
        "error_code": "404"
    }
}

One to Many

Let's now create a One-To-Many relationship using a single request. For this case, we will take a Post Model and a Tag Model.

<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Relations\BelongsTo;
use Illuminate\Database\Eloquent\Relations\BelongsToMany;
use Illuminate\Database\Eloquent\Relations\MorphToMany;

class Post extends Model
{
    use HasFactory;

    protected $fillable = [
        'body', 'title', 'user_id', 
    ];

    public function tags(): BelongsTo
    {
        return $this->hasMany(Tag::class);
    }
}

The Post model is associated with a Tag Model with a hasMany relationship under the tags method name.

<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Relations\BelongsToMany;

class Tag extends Model
{
    use HasFactory;

    protected $fillable = [
        'name', 'post_id'
    ];

    public function posts(): BelongsToMany
    {
        return $this->belongsToMany(Post::class);
    }
}

The Tag Model is now associated with a Post Model, with a belongsTo relationship under the posts method name.

So we have established a One-To-Many relationship, where a Post has many Tags and a Tag can belong to one Post
To Create both the Post model and some Tags along, the request URI must be must contain the main model name, which in our case is the Post model, followed by the method name of the Post Model Class that defines the relationship, which in our case is tags.

The request URI will be /api/aap/post/tags with the following JSON request body

{
    "title": "Post that was created from Api Auto Pilot",
    "body": "Lorem ipsum dolor sit amet, consectetur adipiscing elit.",
    "tags": [
        {
            "name": "first tag"
        },
        {
            "name": "second tag"
        },
        {
            "name": "third tag"
        }
    ]
}

When this request successfully runs, will return response containing the created Post including all the related Tags followed by a 200 OK HTTP Status Code.

{
    "id": 1,
    "title": "Post that was created from Api Auto Pilot",
    "body": "Lorem ipsum dolor sit amet, consectetur adipiscing elit.",
    "updated_at": "2022-11-23T01:04:09.000000Z",
    "created_at": "2022-11-23T01:04:09.000000Z",
    "tags": [
        {
            "id": 1,
            "name": "first tag",
            "post_id": 1,
            "created_at": "2022-11-23T01:04:09.000000Z",
            "updated_at": "2022-11-23T01:04:09.000000Z"
        },
        {
            "id": 2,
            "name": "second tag",
            "post_id": 1,
            "created_at": "2022-11-23T01:04:09.000000Z",
            "updated_at": "2022-11-23T01:04:09.000000Z"
        },
        {
            "id": 3,
            "name": "third tag",
            "post_id": 1,
            "created_at": "2022-11-23T01:04:09.000000Z",
            "updated_at": "2022-11-23T01:04:09.000000Z"
        }
    ]
}

TIP

You can always create the related model independently. Simply make a POST Request to the model URI, and do not forget to add the foreign key id. For our example, make a POST Request to the /api/aap/tag, but append to the request body, the post id that you want to relate to.

Many to Many

Suppose we have the same Post model from the previous cases. Let's now associate it with a Category model, forming a many-to-many relationship.The Post Model will contain a categories() method and the Category model will contain a posts() method.

   <?php

namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;

class  Category extends Model
{
    use HasFactory;

    protected $fillable = [
        'name'
    ];
    public function posts(): BelongsToMany
    {
        return $this->belongsToMany(Post::class);
    }
}
<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Factories\HasFactory;
use Illuminate\Database\Eloquent\Model;
use Illuminate\Database\Eloquent\Relations\BelongsToMany;


class Post extends Model
{
    use HasFactory;

    protected $fillable = [
        'title', 'body', 'user_id',
    ];

    public function categories(): BelongsToMany
    {
        return $this->belongsToMany(Tag::class);
    }
}

TIP

Do not forget to create a pivot table that holds the post id and the category id , you do not need to fill it, Api Auto Pilot handles it automatically for you, when it detects that the models that you want to associate are related with a many-to-many relationship.

To simultaneously create both Category and Post models, you shall make a POST request to /api/aap/post/categories with request body containing all the required model fields. In our case the request body will look like this:

{
    "title": "Creating Many To Many with Api Auto Pilot",
    "body": "Lorem ipsum dolor sit amet, consectetur adipiscing elit.",
    "user_id": "1",
    "categories": [
        {
            "name": "category 1"
        },
        {
            "name": "category 2"
        },
        {
            "name": "category 4"
        }
    ]
}

When the request successfully runs, the response will contain the new created models containing thier pivot table values, followed by a 200 OK HTTP Response Code. In our case the response body will look like this:

{
    "title": "Creating Many To Many with Api Auto Pilot",
    "body": "Lorem ipsum dolor sit amet, consectetur adipiscing elit.",
    "user_id": "1",
    "updated_at": "2022-11-23T01:57:33.000000Z",
    "created_at": "2022-11-23T01:57:33.000000Z",
    "id": 4,
    "categories": [
        {
            "id": 1,
            "name": "category 1",
            "created_at": "2022-11-23T01:57:33.000000Z",
            "updated_at": "2022-11-23T01:57:33.000000Z",
            "pivot": {
                "post_id": 4,
                "category_id": 1
            }
        },
        {
            "id": 2,
            "name": "category 2",
            "created_at": "2022-11-23T01:57:33.000000Z",
            "updated_at": "2022-11-23T01:57:33.000000Z",
            "pivot": {
                "post_id": 4,
                "category_id": 2
            }
        },
        {
            "id": 3,
            "name": "category 3",
            "created_at": "2022-11-23T01:57:33.000000Z",
            "updated_at": "2022-11-23T01:57:33.000000Z",
            "pivot": {
                "post_id": 4,
                "category_id": 3
            }
        }
    ]
}

Creating Models, and relating already existing

If you want to create just a new Post model and assign in with already existing categories, or the inverse, the request body should contain the values that the new Post model should have and on the request body index that defines the relationship, which in our case is categories, you should put the ids of the existing related models, that you want to assign to.

{
    "title": "Creating Many To Many with Api Auto Pilot",
    "body": "Lorem ipsum dolor sit amet, consectetur adipiscing elit.",
    "user_id": "1",
    "categories": [
        1,
        2
    ]
}

Then, the request response will contain the same response body as previously, followed by a 200 OK HTTP Status Code:

{
    "title": "Creating Many To Many with Api Auto Pilot",
    "body": "Lorem ipsum dolor sit amet, consectetur adipiscing elit.",
    "user_id": "1",
    "updated_at": "2022-11-23T02:25:44.000000Z",
    "created_at": "2022-11-23T02:25:44.000000Z",
    "id": 5,
    "categories": [
        {
            "id": 1,
            "name": "category 1",
            "created_at": "2022-11-23T01:57:33.000000Z",
            "updated_at": "2022-11-23T01:57:33.000000Z",
            "pivot": {
                "post_id": 5,
                "category_id": 1
            }
        },
        {
            "id": 2,
            "name": "category 2",
            "created_at": "2022-11-23T01:57:33.000000Z",
            "updated_at": "2022-11-23T01:57:33.000000Z",
            "pivot": {
                "post_id": 5,
                "category_id": 2
            }
        }
    ]
}

Polymorphic Create

TIP

To create models that are related with a polymorphic relationship, you can follow the Api Auto Pilot URI convention which is described on the relational CRUD above, it will work as expected. It doesn't matter if its one-to-many, one-to-one, or many-to-many polymorphic relations.


Let's say that the Post and the Category models, are related with a polymorphic many-to-many and not in normal many-to-many relationship, the request URI and the request body, would remain the same. Api Auto Pilot will handle the changes for you!

Read

HTTP VerbURIResponse Code on SuccessEndpoint Description
GET/api/aap/{model}/{id}/{relationship-method-name}200 - OKFetches the requested model with it's specified related models

To read a model with a specified relationship, the GET request URI should contain the main model that you want to read, for example Post model followed by the id of the model, along with method name that defines the relationship. For example, lets get the Post with id 4, and its tags. The Request URI should look like this: /api/aap/post/4/tags.

the response will contain the main model which in our case is Post and the related tags with an index of the relationship name which is tags along with a 200 OK HTTP Response Code.

{
    "id": 4,
    "title": "Creating Many To Many with Api Auto Pilot",
    "body": "Lorem ipsum dolor sit amet, consectetur adipiscing elit.",
    "user_id": 1,
    "created_at": "2022-11-23T01:57:33.000000Z",
    "updated_at": "2022-11-23T01:57:33.000000Z",
    "tags": [
        {
            "id": 1,
            "name": "tag 1",
            "created_at": "2022-11-23T01:57:33.000000Z",
            "updated_at": "2022-11-23T01:57:33.000000Z"
        },
        {
            "id": 2,
            "name": "tag 2",
            "created_at": "2022-11-23T01:57:33.000000Z",
            "updated_at": "2022-11-23T01:57:33.000000Z"
        },
        {
            "id": 3,
            "name": "tag 3",
            "created_at": "2022-11-23T01:57:33.000000Z",
            "updated_at": "2022-11-23T01:57:33.000000Z"
        }
    ]
}

Many to Many Only Endpoints And Polymorphic Many to Many

There might be times, that you want to associate or disassociate models in a many-to-many relationship. Api Auto Pilot, has you covered for that, and it provides 3 additional endpoints,for models that do implement a many-to-many relationship, polymorphic or not.

These endpoints provide a functionality similar to Laravel's attach()open in new window, detach()open in new window, and sync()open in new window methods

HTTP VerbURIResponse Code on SuccessEndpoint Description
POST/api/aap/{model}/{id}/{relationship-method-name}/attach200 - OKEnters the related models' IDs provided in the request, to the pivot table
POST/api/aap/{model}/{relationship-method-name}/sync200 - OKRemoves all IDs from pivot table that are not present in the request
DELETE/api/aap/{model}/{relationship-method-name}/detach204 - NO CONTENTRemoves the related models IDs that are present in the request from the pivot table

TIP

For demonstration purposes, we will use the Post and Category models that we used earlier on Create many-to-many section.

Attach

To attach some existing model ids, into an existing model, the POST request URI will be formed by the first model followed by its id, then name of the method that defines the many-to-many, relationship in the first model, in our case the method name is called categories() and then the word attach. So we end up with the following request URI: /api/aap/post/5/categories/attach.
The request body, should contain only the ids of the categories that we want to attach, lets say the categories with ids 1,2 and 3, with a json index of ids We end up with this request body:

{
    "ids": [
        1,
        2,
        3
    ]
}

The request response will contain the first model with it's id and the model type and ids of the related model that were just associated, with a 200 OK HTTP Response Code. In our case the response will look like this:

Detach

To detach some existing models, from an existing model, the DELETE request URI will be formed by the first model followed by its id, then name of the method that defines the many-to-many, relationship in the first model, in our case the method name is called categories() and then the word detach. So we end up with the following request URI: /api/aap/post/5/categories/detach.
The request body, should contain only the ids of the categories that we want to detach, lets say the categories with ids 1,2 and 3, with a json index of ids We end up with this request body:

{
    "ids": [
        1,
        2,
        3
    ]
}

The request response will be empty, with a 204 NO CONTENT HTTP Response Code.

Sync

To sync some existing models, from an existing model, the PATCH request URI will be formed by the first model followed by its id, then name of the method that defines the many-to-many, relationship in the first model, in our case the method name is called categories() and then the word sync. So we end up with the following request URI: /api/aap/post/5/categories/sync.
The request body, should contain only the ids of the categories that we want to detach, lets say the categories with ids 1,2 and 3, with a json index of ids We end up with this request body:

{
    "ids": [
        1,
        2,
        3
    ]
}

The request response will contain the first model with it's id and the model type and ids of the related model that were dissociated, with a 204 NO-CONTENT HTTP Response Code.

Pivot Table Values

If your pivot table contains more fields than the 2 model Ids that you connect, instead of just passing an array of ids to the ids JSON index, you need to pass an array of objects, with the key being the id of the model that you are relating to, and the value being an object containing all the pivot table values that you want to insert additional data to.

As an example lets assume that the pivot table that relates the Tag and the Post models, has an additional column named meta. The request body should change to:

{
    "ids":[
      {
            "3":{
                "meta":"meta value 1"
            }
        },
        {
            "1":{
                "meta": "meta value 2"
            }
        }
    ]
}

The response body will be:

{
    "id": 5,
    "title": "Fuga architecto et pariatur magni tempore.",
    "body": "Voluptatem laborum enim eligendi esse. Excepturi sint voluptatum sunt modi et cum totam. Et dolorem voluptate sapiente. Suscipit praesentium aliquam molestiae sit voluptatibus vero. Et accusantium ut voluptatem alias cupiditate necessitatibus ex. Rerum ea molestiae quo quia error dolores quasi nostrum. Qui vel consequuntur nobis nobis deserunt. Eos qui qui ab voluptatum labore dicta. Cupiditate nesciunt id unde beatae sunt.",
    "tags": [
        {
            "id": 3,
            "name": "tag2",
            "pivot": {
                "post_id": 5,
                "tag_id": 3,
                "meta": "meta value 1", 
            }
        },
        {
            "id": 1,
            "name": "tag1",
            "pivot": {
                "post_id": 5,
                "tag_id": 1,
                "meta": "meta value 2",
            }
        }
    ]
}

Searching

HTTP VerbURIResponse Code on SuccessEndpoint Description
GET/api/aap/search/query/{modelame}?params200 - OKEnters the related models' IDs in the request, in the pivot table

Api Auto Pilot, supports searching for models, with all operators, which are =, >, >=, <, <= and LIKE. Because HTTP URLs cannot have those symbols, except the equal sign, we provide a table that describes how to form search queries that include those operators:

Lexical OperatorMathematical SymbolURL Symbol
Equal=[eq]
Greater Than>[gt]
Greater Or Equal to> =[gte]
Less Than<[lt]
Less Or Equal to<=[lte]
LikeLIKE[like]

TIP

When you query results with the SQL Like keyword the value that you query with, should have percentage symbols according to what comes next. for example if you wish to query based on the starting letter the querying value should f%, if you query based on containing a letter, query value should be %f%. Exactly like SQL

So to form a request to query results, you need to set the name of the column that you wish to query, coupled with the URL symbol that is mentioned in the table above equal to your searching value.


For example, lets query Posts that have a title starting with f .
the request URI would be /api/aap/search/query/post and the URI Parameter will be title[like]=f% Combining them, should give the final Request URI which is:
/api/aap/search/query/post?title[like]=f%

Last Updated:
Contributors: GeorgeFourkas