572

As I understand it, the following chain of events occurs in OAuth 2 in order for Site-A to access User's information from Site-B.

  1. Site-A registers on Site-B, and obtains a Secret and an ID.
  2. When User tells Site-A to access Site-B, User is sent to Site-B where they tell Site-B that they would indeed like to give Site-A permissions to specific information.
  3. Site-B redirects User back to Site-A, along with an Authorization Code.
  4. Site-A then passes that Authorization Code along with its Secret back to Site-B in return for a Security Token.
  5. Site-A then makes requests to Site-B on behalf of User by bundling the Security Token along with requests.

How does all of this work in terms of security and encryption, on a high level? How does OAuth 2 protect against things like replay attacks using the Security Token?

S.S. Anne
  • 13,819
  • 7
  • 31
  • 62
William Jones
  • 17,349
  • 16
  • 57
  • 97
  • 49
    oauth2 simply explained here: https://gist.github.com/mziwisky/10079157 – Paolo Aug 26 '14 at 15:52
  • 4
    Read the spec: http://tools.ietf.org/html/rfc6749 You might be surprised how understandable it is. It is also correct which may not be too bad. – Kris Vandermotten Oct 12 '14 at 10:22
  • 1
    This question and its (current) answers all focus on one particular "grant type" in OAuth 2.0 (i.e. `code`) but there are other grant types defined in OAuth 2.0 that are relevant for different use cases (e.g. non-user related ones). – Hans Z. Dec 28 '14 at 21:50
  • 4
    Oh, why not replace "Site B" with something more readable like "IdProvider Site"? – Yurii Aug 19 '15 at 14:16

8 Answers8

1408

How OAuth 2.0 works in real life:

I was driving by Olaf's bakery on my way to work when I saw the most delicious donut in the window -- I mean, the thing was dripping chocolatey goodness. So I went inside and demanded "I must have that donut!". He said "sure that will be $30."

Yeah I know, $30 for one donut! It must be delicious! I reached for my wallet when suddenly I heard the chef yell "NO! No donut for you". I asked: why? He said he only accepts bank transfers.

Seriously? Yep, he was serious. I almost walked away right there, but then the donut called out to me: "Eat me, I'm delicious...". Who am I to disobey orders from a donut? I said ok.

He handed me a note with his name on it (the chef, not the donut): "Tell them Olaf sent you". His name was already on the note, so I don't know what the point of saying that was, but ok.

I drove an hour and a half to my bank. I handed the note to the teller; I told her Olaf sent me. She gave me one of those looks, the kind that says, "I can read".

She took my note, asked for my id, asked me how much money was ok to give him. I told her $30 dollars. She did some scribbling and handed me another note. This one had a bunch of numbers on it, I guessed that's how they keep track of the notes.

At that point I'm starving. I rushed out of there, an hour and a half later I was back, standing in front of Olaf with my note extended. He took it, looked it over and said, "I'll be back".

I thought he was getting my donut, but after 30 minutes I started to get suspicious. So I asked the guy behind the counter "Where's Olaf?". He said "He went to get money". "What do you mean?". "He take note to bank".

Huh... so Olaf took the note that the bank gave me and went back to the bank to get money out of my account. Since he had the note the bank gave me, the bank knew he was the guy I was talking about, and because I spoke with the bank they knew to only give him $30.

It must have taken me a long time to figure that out because by the time I looked up, Olaf was standing in front of me finally handing me my donut. Before I left I had to ask, "Olaf, did you always sell donuts this way?". "No, I used to do it different."

Huh. As I was walking back to my car my phone rang. I didn't bother answering, it was probably my job calling to fire me, my boss is such a ***. Besides, I was caught up thinking about the process I just went through.

I mean think about it: I was able to let Olaf take $30 out of my bank account without having to give him my account information. And I didn't have to worry that he would take out too much money because I already told the bank he was only allowed to take $30. And the bank knew he was the right guy because he had the note they gave me to give to Olaf.

Ok, sure I would rather hand him $30 from my pocket. But now that he had that note I could just tell the bank to let him take $30 every week, then I could just show up at the bakery and I didn't have to go to the bank anymore. I could even order the donut by phone if I wanted to.

Of course I'd never do that -- that donut was disgusting.

I wonder if this approach has broader applications. He mentioned this was his second approach, I could call it Olaf 2.0. Anyway I better get home, I gotta start looking for a new job. But not before I get one of those strawberry shakes from that new place across town, I need something to wash away the taste of that donut.

Luis Perez
  • 26,159
  • 10
  • 76
  • 77
  • 42
    Well, in practice Olaf should be able to take $30 from your account anytime he wants, even if you don't order any donut. Interestingly that's the main goal in the real oauth2.0 scenarios :) This is certainly a great answer, but whoever is reading this please head to the git gist that Paolo mentioned in his comment of the question (https://gist.github.com/mziwisky/10079157). A good complementary read to make the concept crystal clear. – Samiron Dec 17 '16 at 14:08
  • 4
    Great answer but 2 points to raise: 1. As @Samiron pointed out, Olaf would be able to take 30$ anytime he wants. 2. In a real OAuth2.0 scenario, Olaf won't be able to serve the donut before taking money out of the bank. While in this example, he could've kept the cheque and simply handed Luis his well-earned donut. So if we alter the example to make it that I authorize Olaf to get dough from some third party that I know, then it would make more sense as Olaf would have to get the dough before he starts baking the donut (assuming the lonely donut Olaf had was for display purpose only!). – Ticker23 Mar 31 '17 at 14:03
  • 4
    ticker23, the donut story unfortunately beats your technical correction - I was sold on the story when I read it. It was written by Homer Simpson. – shevy Jun 25 '17 at 13:50
  • Suppose on the way to Olaf went to the bank he met 2 bandit and they stolen bank note where bank has given you.They are bit intelligent not to alter the note where then bank will refuse to give them money.But now will two bandit can get the bank note and get money from your account ?how bank overcome that situation ? – Prageeth godage Nov 12 '17 at 01:39
  • 4
    @Prageeth Olaf always carries the note to and from the bank in a secure box that leaks ink if tampered with, it would take many lifetimes to restore the note. The bank also takes customers fingerprints on their first visit, if Olaf loses his fingers in a baking accident then he'll have to ask Luis to setup the bank transfer again, and the bank will have to identify Olaf by his Breaking Bread tattoo next time. – Chris Dec 04 '17 at 03:10
  • 12
    I love cute answers as much as the next person, and when their cuteness helps make the answer more accessible that's awesome ... but at the end of the day Stack Overflow is about educating people, and this cute story doesn't do that. To even understand the doughnut analogy you have to already understand how OAuth2 works, but the whole point of the answer was supposed to be to explain precisely that. Please consider editing this (top) answer to actually explain the concepts, not just reference them obliquely at the end ... even if that comes at the cost of a joke or two. – machineghost Dec 13 '17 at 20:45
135

Based on what I've read, this is how it all works:

The general flow outlined in the question is correct. In step 2, User X is authenticated, and is also authorizing Site A's access to User X's information on Site B. In step 4, the site passes its Secret back to Site B, authenticating itself, as well as the Authorization Code, indicating what it's asking for (User X's access token).

Overall, OAuth 2 actually is a very simple security model, and encryption never comes directly into play. Instead, both the Secret and the Security Token are essentially passwords, and the whole thing is secured only by the security of the https connection.

OAuth 2 has no protection against replay attacks of the Security Token or the Secret. Instead, it relies entirely on Site B being responsible with these items and not letting them get out, and on them being sent over https while in transit (https will protect URL parameters).

The purpose of the Authorization Code step is simply convenience, and the Authorization Code is not especially sensitive on its own. It provides a common identifier for User X's access token for Site A when asking Site B for User X's access token. Just User X's user id on Site B would not have worked, because there could be many outstanding access tokens waiting to be handed out to different sites at the same time.

William Jones
  • 17,349
  • 16
  • 57
  • 97
  • 28
    You've overlooked an important function of the authorization code. Why not just return the refresh token (what you call the Security Token) immediately, instead of having the extra step of swapping the authorization code for it? Because capturing the refresh token would allow replay attacks, whereas the authorization code can only be used once. – Maurice Naftalin May 11 '11 at 04:12
  • 3
    OK, @mauricen, that makes sense.... But couldn't the replay attack happen just as well with the refresh token, since that's what ends up being passed with each request? – Mr Mikkél Jul 20 '12 at 07:44
  • 15
    The authorization code is passed via the user, so (for example) could be stored as a cookie (see http://stackoverflow.com/questions/4065657/how-important-is-it-to-keep-oauths-access-token-secret?rq=1). The refresh token passes directly between the two sites, so is much less vulnerable. – Maurice Naftalin Nov 22 '12 at 09:18
  • Out of curiosity, does OAuth return any unique identifiers for the program to use? For example, I am currently relying on the MAC address for user identification, but with that said, MACs are unreliable/easilySpoofed/etc. I may just scrap the MAC address identification mechanism and go OAuth if it does allow me to uniquely identify users. – theGreenCabbage Feb 11 '14 at 15:45
  • 1
    Notice in this diagram: http://tools.ietf.org/html/rfc6749#section-4.1 that the "Secret" is not shown, only the Client Identifier (ID in the question). Why is the Secret important and why is it not included in the RFC? Also in the question there is also the local state which is recommended to be passed in the initial transmission of the Client Id (A), and the redirect back to the client along with the authorization code to protect against XSSF. – David Williams Jun 30 '14 at 23:08
  • I think the point is that Site-A can reuse the Security Token, until it "expires" after some time. It's like a "stay logged in for a login session" worth token. Also note that User is sent to Site-B and logs in there with their credentials, for number 2. I think you're right though in general they just assume secure connections and that tokens won't be leaked (because for No. 3 it redirects them back to a *pre configured well known url* that is assumed secure). – rogerdpack Sep 07 '18 at 20:39
109

OAuth is a protocol with which a 3-party app can access your data stored in another website without your account and password. For a more official definition, refer to the Wiki or specification.

Here is a use case demo:

  1. I login to LinkedIn and want to connect some friends who are in my Gmail contacts. LinkedIn supports this. It will request a secure resource (my gmail contact list) from gmail. So I click this button:
    Add Connection

  2. A web page pops up, and it shows the Gmail login page, when I enter my account and password:
    Add Connection

  3. Gmail then shows a consent page where I click "Accept": Add Connection

  4. Now LinkedIn can access my contacts in Gmail: Add Connection

Below is a flowchart of the example above:

Add Connection

Step 1: LinkedIn requests a token from Gmail's Authorization Server.

Step 2: The Gmail authorization server authenticates the resource owner and shows the user the consent page. (the user needs to login to Gmail if they are not already logged-in)

Step 3: User grants the request for LinkedIn to access the Gmail data.

Step 4: the Gmail authorization server responds back with an access token.

Step 5: LinkedIn calls the Gmail API with this access token.

Step 6: The Gmail resource server returns your contacts if the access token is valid. (The token will be verified by the Gmail resource server)

You can get more from details about OAuth here.

rogerdpack
  • 50,731
  • 31
  • 212
  • 332
Owen Cao
  • 7,294
  • 2
  • 24
  • 33
  • All your images have gone missing. Any chance you can load them to stack.imgur? – ChrisF Oct 16 '15 at 20:28
  • 1
    How can this be correct? Isn't this process initiated by by the user sitting in front of the brower, not LinkedIn. But you have that as step 3. This is what I don't get. – hookenz May 24 '16 at 23:16
  • 18
    The easiest explanation. Thanks, I'll never buy donuts again – OverCoder Oct 17 '16 at 20:13
  • 4th step linkedin returns with an authorization token. This has to be supplied in the 5th step, where we will get an access token and a refresh token which could be used further for protected resources. – amesh Oct 03 '17 at 06:40
  • @amesh Thanks,you're right, that's the authorization code flow, here I just stated in simplified way to show the basic idea of OAuth 2. – Owen Cao Oct 04 '17 at 03:19
  • By far the best answer. – lolololol ol Oct 08 '17 at 00:05
24

Figure 1, lifted from RFC6750:

     +--------+                               +---------------+
     |        |--(A)- Authorization Request ->|   Resource    |
     |        |                               |     Owner     |
     |        |<-(B)-- Authorization Grant ---|               |
     |        |                               +---------------+
     |        |
     |        |                               +---------------+
     |        |--(C)-- Authorization Grant -->| Authorization |
     | Client |                               |     Server    |
     |        |<-(D)----- Access Token -------|               |
     |        |                               +---------------+
     |        |
     |        |                               +---------------+
     |        |--(E)----- Access Token ------>|    Resource   |
     |        |                               |     Server    |
     |        |<-(F)--- Protected Resource ---|               |
     +--------+                               +---------------+
8bitjunkie
  • 11,360
  • 9
  • 49
  • 65
14

This is how Oauth 2.0 works, well explained in this article

enter image description here

Suraj
  • 1,437
  • 1
  • 11
  • 31
  • Can you describe OAUTH2 in terms of not using facebook or other 3rd party but if you use secret key and TOTP tokens with phone app to secure webapp? – Al Grant Jun 29 '17 at 22:50
  • Facebook is Authorisation server in this example which issues access token to any client so they can access Facebook APIs. If you want to secure your APIs you need to implement your own Authorisation server. Then you decide what Grant type you want to use to get access token. tell me what exactly you want? will explain. – Suraj Jun 30 '17 at 04:22
  • I am looking at setting up with springboot security. Client (phone) and webapp exchange secret at registration - then use google authenticator to generate time/secret based code to enter during login in addition to password. – Al Grant Jun 30 '17 at 08:33
  • does my last comment enlighten you anymore? See my profile for twitter info – Al Grant Jul 13 '17 at 02:41
  • you can get client Id and secret at registration. Then phone make a login request with client Id to your webapp(authorization server). web app validate the client id, and send the OTP to phone. Phone makes another request with client secret to webapp to exchange the OTP with access token. phone use this accss token to access the protected resources on webapp. I think this would be the Oauth2 flow for the given scenario. let me know if it helps you. – Suraj Jul 13 '17 at 07:08
11

This is a gem:

https://www.digitalocean.com/community/tutorials/an-introduction-to-oauth-2

Very brief summary:

OAuth defines four roles:

  1. Resource Owner
  2. Client
  3. Resource Server
  4. Authorization Server

You (Resource Owner) have a mobile phone. You have several different email accounts, but you want all your email accounts in one app, so you don't need to keep switching. So your GMail (Client) asks for access (via Yahoo's Authorization Server) to your Yahoo emails (Resource Server) so you can read both emails on your GMail application.

The reason OAuth exists is because it is unsecure for GMail to store your Yahoo username and password.

enter image description here

Belfield
  • 1,119
  • 1
  • 11
  • 17
8

The other answer is very detailed and addresses the bulk of the questions raised by the OP.

To elaborate, and specifically to address the OP's question of "How does OAuth 2 protect against things like replay attacks using the Security Token?", there are two additional protections in the official recommendations for implementing OAuth 2:

1) Tokens will usually have a short expiration period (http://tools.ietf.org/html/rfc6819#section-5.1.5.3):

A short expiration time for tokens is a means of protection against the following threats:

  • replay...

2) When the token is used by Site A, the recommendation is that it will be presented not as URL parameters but in the Authorization request header field (http://tools.ietf.org/html/rfc6750):

Clients SHOULD make authenticated requests with a bearer token using the "Authorization" request header field with the "Bearer" HTTP authorization scheme. ...

The "application/x-www-form-urlencoded" method SHOULD NOT be used except in application contexts where participating browsers do not have access to the "Authorization" request header field. ...

URI Query Parameter... is included to document current use; its use is not recommended, due to its security deficiencies

Will
  • 3,506
  • 2
  • 21
  • 35
4

Here is perhaps the simplest explanation of how OAuth2 works for all 4 grant types, i.e., 4 different flows where the app can acquire the access token.

Similarity

All grant type flows have 2 parts:

  • Get access token
  • Use access token

The 2nd part 'use access token' is the same for all flows

Difference

The 1st part of the flow 'get access token' for each grant type varies.

However, in general the 'get access token' part can be summarized as consisting 5 steps:

  1. Pre-register your app (client) with OAuth provider, e.g., Twitter, etc. to get client id/secret
  2. Create a social login button with client id & required scopes/permissions on your page so when clicked user gets redirected to OAuth provider to be authenticated
  3. OAuth provider request user to grant permission to your app (client)
  4. OAuth provider issues code
  5. App (client) acquires access token

Here is a side-by-side diagram comparing how each grant type flow is different based on the 5 steps.

This diagram is from https://blog.oauth.io/introduction-oauth2-flow-diagrams/

enter image description here

Each have different levels of implementation difficulty, security, and uses cases. Depending on your needs and situation, you will have to use one of them. Which to use?

Client Credential: If your app is only serving a single user

Resource Owner Password Crendential: This should be used only as last resort as the user has to hand over his credentials to the app, which means the app can do everything the user can

Authorization Code: The best way to get user authorization

Implicit: If you app is mobile or single-page app

There is more explanation of the choice here: https://blog.oauth.io/choose-oauth2-flow-grant-types-for-app/

nethsix
  • 702
  • 6
  • 15