> For the complete documentation index, see [llms.txt](https://kdongs.gitbook.io/kdocs/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://kdongs.gitbook.io/kdocs/rest/rest.md).

# REST

## About

Simple and stateless way to syncronously communicate with services.

It is possible to cache data.

## Levels of Maturity

### Level 0

Only states that all traffic over HTTP has a purpose to execute a transaction.

*(Like do something on DB, or call for execution of a procedure)*

There is no level of pattern in it's use.

### Level 1

Start using resources.

| Verb     | URI           | Operation     |
| -------- | ------------- | ------------- |
| `GET`    | `/products/1` | Retrieve Info |
| `POST`   | `/products`   | Insert        |
| `PUT`    | `/products/1` | Alter         |
| `DELETE` | `/products/1` | Remove        |

### Level 2

When you organize and make sure you use the correct `verb` for the correct `operation`, in each `URI`.

This means for instance, no `updates` with `POST`.

### Leve 3

`HATEOAS` (Hypermedia as the Engine of Application State)

Not only awnsers your request, but also, brings others things that you can do from what you just did.

{% code title="response" %}

```json
{
  "account": {
    "account_number": 1234,
    "balance": {
      "currency": "brl",
      "value": 500.00
    },
    "links": {
      "deposit": "/accounts/1234/deposit",
      "withdraw": "/accounts/1234/withdraw",
      "close": "/accounts/1234/close",
    }
  }
}
```

{% endcode %}

## Good Practices

* Use unique URIs for each exposed service.
* Use the correct `verbs` to execute the correct actions.
* Provide links exemplifying how to use the API.

## Response Patterns

Just `JSON` doesn't provides a hypermedia pattern for responses.

### HAL

*(Hypermedia Application Language)*

Media Type: `application/hal+json`

In this pattern, besides providing the data from the requested service, it also provides:

* `_links` that always tells you the current resource you are accessing. (`self`).
* There is also an `_embedded` that can bring related data from the main data.

{% code title="response" %}

```json
{
  "_links": {
    "self": {
      "href": "http://url/api/user/bill"
    }
  },
  "id": "s9-s0dsf-12fasd",
  "name": "Bill Someone",
  "_embedded": {
    "family": {
      "_links": {
        "self": {
          "href": "http://url/api/user/maria"
        }
      },
      "id": "asd9-asfasd9",
      "name": "Maria Else"
    }
  }
}
```

{% endcode %}

### Collection+JSON

### Siren

## Method Negotiation

HTTP has an `OPTIONS` method. This method allows us to inform which methods are allowed or not in each resource.

**Ex.:**

{% code title="request" %}

```
OPTIONS /api/product HTTP/1.1
Host: url.com
```

{% endcode %}

`OPTIONS` *anwser could be:*

{% code title="response" %}

```
HTTP/1.1 200 OK
Allow: GET, POST
```

{% endcode %}

If request sent to this same URI was invalid, like a `PUT`:

{% code title="response" %}

```
HTTP/1.1 405 Not Allowed
Allow: GET, POST
```

{% endcode %}

## Content Negotiation

The content negotiation process is based on the request the client is doing to the server.

In this case, the user request what and how he wants the anwser to be. The server then might or might not return the request in the desired format.

### Accept Negotiation

The client requests the data and the return type, based on a given `media type` in order of priority.

**Ex.:**

{% code title="request" %}

```
GET /product
Accept: application/json
```

{% endcode %}

*The anwser could be:*

{% code title="response" %}

```
HTTP/1.1 406 Not Acceptable
```

{% endcode %}

### Content-Type Negotiation

Through a `content-type` in the request header, the server can verify is it will be able to process the data to return.

{% code title="request" %}

```
POST /product HTTP/1.1
Accept: application/json
Content-Type: application/json

{
  "name": "Product 1"
}
```

{% endcode %}

In case the server doesn't support the `content-type` it can return:

{% code title="response" %}

```
HTTP/1.1 415 Unsupported Media Type
```

{% endcode %}
