PHP 0 to hero pt.8 - HTTP methods and handling
Tags: webdev, php, beginners, tutorial
Published: 2024-01-11 23:01:14

What's up - today another part of this crash course

Do you remember, when in part 2, we have written this
```php
<form action="page.php" method="GET"></form>
```
And I told you
> It sound's a bit enigmatic, but I'll cover basics it soon.

And then, this
> [...]That's how we get data from GET form - inside single quotes we place name of the field. But about it, later in this course [...]

High time has come - here is a quick summary of what will we learn today

1. HTTP - What is it and how it works
2. HTTP methods and HTTP response codes
3. `POST` method more in depth
4. `POST` vs `GET` - what are differences 
5. Handling other HTTP methods
6. Overview of `$_SERVER`

So, let's not waste time and start learning

## HTTP - what is it?

HTTP stands for "Hypertext Transfer Protocol" - It's basic protocol of web communication and foundation of world wide web. 

It functions as a request-response protocol in `client-server` model

And a quick explanation
- Request - package of data, that our browser sends (Like we want to visit dev.to)
- Response - package of data sent by server to us. That's the content that we wanted (and requested)
- Client - One, that sends requests (browser, application)
- Server - One, that responds to requests (Web server)

I won't go into technical depths of how it works - That's PHP, not networking course

If you are really into it, you can read [RFC 9113](https://datatracker.ietf.org/doc/html/rfc9113) - it defines, how it works and explains whole magic behind it

And to some clarification - what's the difference between HTTP and HTTPS?

HTTPS is secure version of HTTP (S in that acronym stands for *Secure*) - That means, whole connection is encrypted and after intercepting such traffic, attacker has some additional work to do, but sometimes it might be impossible for threat actor to decipher that communication

Yeah, there was a little bit of offtop, so let's get into something strictly connected to HTTP

## HTTP Response status codes

This part is important - as it might be useful in typical life too

Browsers should know, what happened to their requests - they receive this information through response status codes

They are grouped in 5 classes
- 1xx - Informational
- 2xx - Success
- 3xx - Redirection
- 4xx - Client error
- 5xx - Server error

Of course `xx` is replaced with some number - you will see it

Every code can be found [here](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status), and here are some of the most common ones

**`200 OK`** - Success, everything went as it should

**`301 Moved Permanently`** - there was something at that URL, but it was moved. It also provides you with new URL of that asset

**`403 Forbidden`** - We don't have permissions to access that resource

**`404 Not Found`** - I think you are familiar with this code. It means, that the URL we want to access, does not exist
Here, sometimes servers send `403` instead of `404` - to hide existence of some URL/resource

**`500 Internal Server Error`** - There was some error, and server doesn't know how to handle it

**`503 Service Unavailable`** - Server can't handle the request. It can be everything, but mostly may be either down for maintenance or server is overloaded


On the side, there is a code called `418 I'm a teapot`. 

As [MDN](https://developer.mozilla.org/en-US/docs/Web/HTTP/Status/418) says
>The HTTP `418 I'm a teapot` client error response code indicates that the server refuses to brew coffee because it is, permanently, a teapot. 

Yeah it really exists, I'm not kidding. It was created as a reference to April Fools' joke from 1998 and 2014 - Hyper Text Coffee Pot Control Protocol

And yes, it has [it's own RFC specification](https://www.rfc-editor.org/rfc/rfc2324#section-2.3.2)

## HTTP methods

These are used to indicate desired action for some resource.
Although they might be nouns, we can hear people commonly  referring to them as HTTP verbs.

There are plenty of them, each has it's own semantics - but here I'll focus on 4 basic ones

1. `GET` - Retrieve data from server
2. `POST` - Submit something to the server, often causing some changes or side effects
3. `PUT` - Often disabled method, as it allows to create/update resources on the server ([example](https://developer.mozilla.org/en-US/docs/Web/HTTP/Methods/PUT))
4. `DELETE` - Deletes the specific resource. It's also kind of insecure, as `PUT`


To be fair, we will only focus on first 2 - as rest is rarely used in PHP 

## `POST` method

As I mentioned before - It's another HTTP method in requests

We access form fields content just like in get, but with a little difference  - via superglobal `$_POST` (Not `$_GET`)

```php
$field = $_POST['field'];
```
It has the same qualities as `$_GET` - And after parts 3 and 4, I think you know how to use it

But, why do we have 2 of them? Can't there be just one? What are the differences?

## `POST` vs `GET`

So, let's start with data visibility

Have you ever seen a URL looking something like this?
```
http://example.com/page?data=val
```

The end of this URL (`?data=val`) contains our `GET` data

So if user requested that page, we could access it with

```php
$data = $_GET['data'];

echo $_GET['data'];
// Output: val
```

But if the request used `POST` method - URL would look like this
```
http://example.com/page
```

As we see, no additional data. But why? 

Because `POST` data is added only to a request itself, not to the URL

And here, we come to the next part -  Usage

I'll repeat myself.
So, as I mentioned before

- `GET` should be used, when we want to **request** data from server ex. finding something using search bar
- `POST` is meant to be utilized, when we need to **pass data to the server**, for it to further process them - like login or register

To sum up
`GET` - To show user something dynamically
`POST` - To send data from user, to be processed by server


## Handling other HTTP methods

While we have `$_GET` and `$_POST` superglobals for that methods, there aren't any equivalents for another methods like `PUT` or `DELETE`

I don't really recommend using them, but if you really have to there is a simple trick to do it - here for `PUT` method (same applies to delete)

```php
$method = $_SERVER['REQUEST_METHOD'];
if ('PUT' === $method) {
    parse_str(file_get_contents('php://input'), $_PUT);
    var_dump($_PUT);
}
```
source: [Stack Overflow](https://stackoverflow.com/questions/27941207/http-protocols-put-and-delete-and-their-usage-in-php)

I will talk about `$_SERVER` later, and there are 2 function I'll explain

1. [`parse_str()`](https://www.php.net/manual/en/function.parse-str.php) - It parses string in URL format (first argument), and writes it to array (second argument)

2. `file_get_contents()` - As the name says, it reads contents of a file, and saves it as a string
And inside it `php://input` reads data from request body - that's so called PHP wrapper


## `$_SERVER` superglobal

Last thing I'd like to mention here is `$_SERVER` 

What is it? It's superglobal that contains execution and server information

Unlike `$_GET` or `$_POST` - we can't really define it's values from PHP code
But it allows us to access some pretty interesting data - A few examples:

- `$_SERVER['PHP_SELF']` - Returns filename of currently executed file
- `$_SERVER['SERVER_ADDR']` - IP address of server that executes PHP code
- `$_SERVER['REQUEST_METHOD']` - This one contains request method. It was used in code snippet above
- `$_SERVER['REMOTE_ADDR']` - By reading this property we can obtain  IP address of user (client)

There are of course much more of them - you can find them all [here](https://www.php.net/manual/en/reserved.variables.server.php)

And, that's it - you should now understand what's going on with this 

## Conclusion

I hope you enjoyed that tutorial - Every feedback is appreciated, so comments are for you 

There are 9 more parts left, and then we will start our projects

Also, check out other articles in this series (If you hadn't read them) and rest of my posts 

So, see you in next articles