Idempotence is a word I hadn’t come across before I started working with HTTP methods in Sinatra and Ruby on Rails.
I didn’t know what it meant, so my first port of call was, of course, Wikipedia:
Idempotence (UK: /ˌɪdɛmˈpoʊtəns/, US: /ˌaɪdəm-/) is the property of certain operations in mathematics and computer science whereby they can be applied multiple times without changing the result beyond the initial application. The concept of idempotence arises in a number of places in abstract algebra (in particular, in the theory of projectors and closure operators) and functional programming (in which it is connected to the property of referential transparency).https://en.wikipedia.org/wiki/Idempotence
Unfortunately after reading this I was still none the wiser, so I decided to look into idempotence further.
MDN told me:
An HTTP method is idempotent if an identical request can be made once or several times in a row with the same effect while leaving the server in the same state.https://developer.mozilla.org/en-US/docs/Glossary/Idempotent
That’s a bit more helpful. So, an operation is idempotent if you can do the same thing over and over, without having an effect on the state of the server.
The four most used HTTP methods are:
DELETE. Let’s have a look at each of them in term, and see whether or not they are idempotent.
GET is a read-only method. When used properly, GET requests should only be used for retrieving data from the server.
With a GET request, a user might refresh the page 100 times and see the same result every time. One thing to remember is that idempotence is about the effect on the server, it isn’t about the client side. Idempotency does not necessarily mean that the user receives the same response to their request. So, if my website were to stop responding in between my user’s 98th and 99th GET request, and my user saw a different status code, the operation remains idempotent, as the data on the server will not have not changed. All we’re doing is retrieving information from the server and presenting it to the user. The server is not being altered. It’s idempotent!
We also consider GET to be a safe method. Back to MDN for the definition of ‘safe’ in this context:
An HTTP method is safe if it doesn't alter the state of the server. In other words, a method is safe if it leads to a read-only operation... All safe methods are also idempotent as well as some, but not all, unsafe methods like PUT, or DELETE.https://developer.mozilla.org/en-US/docs/Glossary/Safe
So safe methods are idempotent, but idempotent methods are not necessarily safe. It’s safe to make GET requests without being concerned about potential side effects.
When learning about RESTful actions, at first I didn’t quite get the difference between ‘put’ and post’. Idempotence is an important part of why they are different.
Let’s take a look.
Say that we were to send these four PUT requests to the server:
name = "Kay"
name = "Kay"
name = "Kay"
name = "Kay"
Lines 2 through 4 don’t really do anything. The first line has assigned the string “Kay” to the variable ‘name’. We could send 200 PUT identical PUT requests but there will be no difference to the server versus sending just one PUT request, all that will have changed is that we’ll have updated the name to ‘Kay’ .
Therefore it follows that PUT, like GET, is idempotent. If I make multiple PUT requests, only the first PUT request will have an impact on the server.
But, PUT is not safe.We’re updating a record, we’re changing the data on the server. Unlike GET, it’s not read-only. It’s idempotent, but unsafe.
POSTis not idempotent. Every time we submit data to the server, a new record is created. If you submit the same data to the server twice, unless you have built-in validations checking for unique values, you will create multiple records on the server. This is why if you hit the back buttton after submitting a form, you‘ll often see a warning message. Unlike GET, PUT, and delete, it is not safe to make multiple POST requests.
The key difference between PUT and POST request are that POST requests are creating a record.
DELETE is idempotent.
Say we sent a delete request to delete a record from the server. Our first request deletes the record from the server. If we attempt to delete the record again, nothing will happen as the record doesn’t exist. We will probably get a 200 status code after the first request, and a 404 status code after subsequent requests. It’s unsafe, as we’re changing data on the server.
To summarise, HTTP methods are idempotent if they do not cause subsequent effects if you make the same request many times.
- GET is safe and idempotent.
- PUT isn’t safe, but is idempotent.
- DELETE isn’t safe but is idempotent.
- POST is neither safe nor idempotent.