2-legged vs. 3-legged OAuth

Published on and tagged with oauth

From emails I receive it seems like there is a bit of confusion about what the terms 2-legged OAuth and 3-legged OAuth mean. I hope I can clear up this confusion with this article (and don’t contribute more to the confusion…).

In short, they describe two different usage scenarios of OAuth involving two respectively three parties.

3-legged OAuth describes the scenario for which OAuth was originally developed: a resource owner wants to give a client access to a server without sharing his credentials (i.e. username/password). A typical example is a user (resource owner) who wants to give a third-party application (client) access to his Twitter account (server).

On a conceptual level it works in the following way:

  • Client has signed up to the server and got his client credentials (also known as “consumer key and secret”) ahead of time
  • User wants to give the client access to his protected resources on the server
  • Client retrieves the temporary credentials (also known as “request token”) from the server
  • Client redirects the resource owner to the server
  • Resource owner grants the client access to his protected resources on the server
  • Server redirects the user back to the client
  • Client uses the temporary credentials to retrieve the token credentials (also known as “access token”) from the server
  • Client uses the token credentials to access the protected resources on the server

2-legged OAuth, on the other hand, describes a typical client-server scenario, without any user involvement. An example for such a scenario could be a local Twitter client application accessing your Twitter account.

On a conceptual level 2-legged OAuth simply consists of the first and last steps of 3-legged OAuth:

  • Client has signed up to the server and got his client credentials (also known as “consumer key and secret”)
  • Client uses his client credentials (and empty token credentials) to access the protected resources on the server

Above I used Twitter as an example, though strictly speaking, they don’t use 2-legged OAuth, but a variant of it. They not only provide the client credentials but also the token credentials (see also Using one access token with OAuth).

As you have seen, 2-legged OAuth is nothing new, it is simply using OAuth in a different scenario than it was designed for. And hence you can use (almost?) all existing OAuth libraries for 2-legged OAuth, too.

15 comments baked

  • Lennaert Ekelmans

    A good example of 2-legged oAuth is the Google Apps API.

    In our business software we’re using the 2-legged oAuth API from Google Apps so all employers don’t have to give permission like in the 3-legged oAuth.

    The only thing we use is the `master` key/secret from the Administrator account so we have access to all data to Calendar/Mail feed/contacts..

  • Tweets that mention 2-legged vs. 3-legged OAuth - cakebaker -- Topsy.com

    […] This post was mentioned on Twitter by Planet CakePHP. Planet CakePHP said: #cakephp 2-legged vs. 3-legged OAuth http://bit.ly/dX4kG9 […]

  • cakebaker

    @Lennaert: Thanks for sharing this example!

  • Dave

    Thanks for writing, this seems a very concise and effective description.

    As a newcomer to this, I’m confused on who exactly are the principals in 3 legged OAuth.

    In particular:
    – how is “user” distinguished from “client”? The user is a human, and the client is the software they are using directly? I guess not, as “the server redirects the user back to the client”
    – is the server in “signed up to the server” necessarily the same server as the one containing the “protected resources”, or can the be different servers?

    Thanks!

  • cakebaker

    @Dave: Thanks for your questions.

    Yes, in the article “user” is human, but in the spec a “user” resp. “resource owner” is more broadly defined as: “An entity capable of accessing and controlling protected resources by using credentials to authenticate with the server.”

    And “client” is a web application in the article. This term, too, is more broadly defined in the spec as: “An HTTP client capable of making OAuth-authenticated requests.”

    To better understand “the server redirects the user back to the client”, we can use a real scenario: “Twitter redirects the user (or more precisely: the user’s browser) back to TwitPic”.

    Yes, the server in “signed up to the server” and the server containing the protected resources are conceptually the same. For example: you sign up to Twitter and you access the tweets (the protected resources) via Twitter’s API. In both cases the “server” is Twitter.

    I hope this answers your questions.

  • Abhay

    That is seriously very well ‘baked’.

    But still, I am rather confused on how 2LO works.

    I have a web app. I would like my users to integrate it with their Google Apps Domain, So that on their behalf, my app can access/modify/create/delete their resources on Google Apps server.
    So if my user says show me my docs, i will show him/her docs from his/her Google apps docs as well as any other that are local to my app.

    Who is consumer here? whose secret key is needed?
    is 2LO the right way in this scene?

    Can someone please elaborate?

    Thanks

  • cakebaker

    @Abhay: Thanks for your question!

    In the scenario you described your application is the consumer, and you have to use the secret key you got from Google.

    If your users have Google Apps for Business and Education accounts, and the APIs you want to use support 2LO, then I would use 2LO. Otherwise, you have to use the traditional 3LO approach. See also Google’s OAuth 1.0 for web applications.

    Maybe it helps to build a quick prototype to see whether 2LO works in your scenario.

    I hope this answers your questions.

  • Abhay

    Thanks for the reply.

    Well, i did build a prototype and found that if 2LO is used, some of the resources are accessed in read-only mode. So i had to go with 3LO.

    I am also opting for provisioning. Therein lies my next doubt.

    Google Apps admin (only) are allowed to create users in their domain. But non-admin users are also able to grant access to Provisioning API, if i am using 3LO.
    Am i missing something here? I mean, shouldn’t be non-admin users restricted from granting my app such an access? or should they not be? What should happen in such case?

    Also i am not clear if i am asking for grant using 3LO, only and only for Provisioning access, to a non-admin user, what should ideally happen? I don”t have the luxury of having multiple domains/accounts to test this with. Thats why the question. Can you please help?

  • cakebaker

    @Abhay: I’m sorry, I never used Google Apps and so I can’t answer your questions…

  • A Note on Providing OAuth for Your Mobile App « iamcam

    […] to use a two-legged OAuth implementation – username & password plus some secret keys (3-legged vs 2-legged explanation). This is what your users will expect when logging into your app & service. Before you can […]

  • Gail Houston

    Hello, I have a question about doing two-legged OAuth authentification. I implemented a rest API and OAUTH 2 legs in the server side. I want to sign my request using a Java library, so I tried signpost. I have a valid consumerKey and consumerSecret, but when I ran my test I get a 401 response code whith the following message : Authorization Required. Here is a sample code of my client :

    private OAuthConsumer consumer; 
    public LiveClient(String consumerKey, String consumerSecret) { 
      this.consumer = new DefaultOAuthConsumer(consumerKey, consumerSecret); 
      this.consumer.setTokenWithSecret(null, "");
      this.consumer.setMessageSigner(new HmacSha1MessageSigner());
      this.consumer.setTokenWithSecret(consumerKey, consumerSecret);
    } 
    
    public void sendRequest(String strUrl) throws MalformedURLException, OAuthMessageSignerException, OAuthExpectationFailedException, OAuthCommunicationException, IOException { 
      URL url = new URL(strUrl); 
      HttpURLConnection request = (HttpURLConnection) url.openConnection(); // sign the request (consumer is a Signpost DefaultOAuthConsumer) 
      consumer.sign(request); // send the request request.connect(); 
      ..... 
    }

    What I’m doing wrong? Any Ideas please? Regards.

  • cakebaker

    @Gail: You could try to use the following statement:

    this.consumer.setSendEmptyTokens(true);
    

    Hope this helps!

  • Tom

    I have a question as well. I’m working in a software service provider industry with many clients. We are trying to implement, OAuth 2.0. Questions that I have is, if the company that we are working with, our client wants to access our API resources. Should we become the consumer and the service provider?

  • cakebaker

    @Tom: I’m not sure I understand your question correctly. But your company is only the service provider, offering an API. And your client will be the consumer, accessing your API.

  • OAuth 2.0 소개 | Chanlee's Weblog

    […] 클라이언트 신임장 플로우 – 클라이언트는 억세스 토큰을 획득하기 위해 신임장을 사용합니다. 이 플로우는 2-legged 시나리오에 대해 지원합니다. (http://cakebaker.42dh.com/2011/01/10/2-legged-vs-3-legged-oauth/ 참고.) […]

Bake a comment




(for code please use <code>...</code> [no escaping necessary])

© daniel hofstetter. Licensed under a Creative Commons License