Does Oauth 2.0 need consumer key/consumer secret - api

So evidently when using OAuth 1.0 you need to acquire consumer key and consumer secret from the API provider...
But then when I try to use OAuth 2.0 APIs such as Facebook, Google Oauth 2.0, etc I never needed to acquire consumer key/consumer secret (I acquired App ID and App secret for Facebook, but those are different from consumer key/consumer secret am I correct?)
So my question is...is it true that when using Oauth 2.0, you don't need to have a consumer key/consumer secret as in Oauth 1.0
Also there are no signature methods (HMAC-SHA1 etc) necessary for Oauth 2.0, is that correct? HMAC-SHA1 is only relevant for Oauth 1.0, correct?

OAuth 2 providers typically issue you an identifier for your client/app and some secret/password, the OAuth draft calls these client identifier and client secret. These are used to check if a call was really issued by your application. However, OAuth covers different Authorization Grant flows which are more or less secure and do not all require some kind of secret. Google calls them client ID and client secret, Facebook calls them App ID and App Secret, but they are both the same.
Yes, all cryptographic steps were moved to server side in OAuth 2.

The authorization grant flow that you are referring to is known as the Client Credentials Grant flow in the OAuth 2 specification. It is used to do application-only authentication. Meaning that no user is involved. A typical example is the display of a twitter feed on a home page.
Normally the application passes both consumer key (or app ID) and consumer secret (or app secret) over HTTPS to the server. This request is only protected by HTTPS; there is no additional encryption. The server returns a token that you can use from that point on to make requests to the API - given it does not require a user context.
The consumer key (or app ID) identifies your application and may have a meaningful value. You normally don't (or can't) change this anymore. The consumer secret however can be regenerated in case you believe it has been compromised. This explains why there are two keys.
Regenerating the consumer secret is different from invalidating the token which won't help you if the consumer key and consumer secret have been compromised.

Both are same. the terminology used are different by apps/users/clients. thats it.Both are same.

Related

Is the Authorization Code Grant still necessary when using TLS?

The primary purpose of an authorization code in the oAuth flow is to prevent replay attacks, TLS also prevents replay attacks.
If you simply made a password grant request to an oAuth enabled server using TLS would that not be sufficient?
The primary purpose of an authorization code in the oAuth flow is to
prevent replay attacks
I think the primary purpose of Authorization Code flow is different then prevent replay attacks. OAuth does not guarantee this and regardless of the grant, OAuth 2.0 suggests us use always TLS for all grants to transmit Access token:
Access token credentials MUST only be transmitted using TLS as
described in Section 1.6 with server authentication as defined by
[RFC2818].
There are also other grants in OAuth 2.0 like;
Authorization Code
PKCE
Implicit (Legacy)
Client Credentials
Password (Legacy)
Device Code
Refresh Token
and each has its own purpose. Password flow is legacy and you should have a strong reason to keep using it because of the following reasons:
Your user exposing their credentials to 3rd party for no reason. It was the reason OAuth exist, not sharing credentials to 3rd party (like e.g: Service Foo) to get access to their service (like Google, Facebook)
User does not have any control what your Service Foo can do with these credentials.
It was required before like Implicit flow, but both Password and Implicit flows are replaced now with Device and PKCE based on their usage. For instance; if the main reason one application uses Password Grant is their clients can not support redirection, they can also use now Device Code Grant.

identityserver4 protect public api

I am using identity server 4, I followed the tutorial, so I have an api, mvc client, console client, and js client.
I saw this blog too, which is probably close to what I need:
https://medium.com/all-technology-feeds/testing-your-asp-net-core-webapi-secured-with-identityserver4-in-postman-97eee976aa16
what I need is an api, where clients can access data, but first, they need authenticate.
we also have the console client, which is also close to what I need.
The only issue with this examples is that in both cases client knows the secret. But in our case multiple clients should use the same api, and if they all have the same secret, they can log in on behalf of each other, but I don't want to have different secrets.
So what I think I could do is to create an api which takes username and password, and returns the token. But I am not sure if this is the right way to do things? This feels like a resource owner flow, which is not supposed to be used for client facing APIs if I am correct. But in that case, how should I go it?
thanks
It seems that there is some confusion. Allow me to give a short summary. First the terminology:
A user is a human that is using a registered client to access resources.
A client is a piece of software that requests tokens from IdentityServer - either for authenticating a user (requesting an identity token) or for accessing a resource (requesting an access token). A client must be first registered with IdentityServer before it can request tokens.
Resources are something you want to protect with IdentityServer - either identity data of your users, or APIs.
Client credentials: The simplest grant type and is used for server to server communication - tokens are always requested on behalf of a client, not a user.
Now about authentication. The client requests tokens at the IdentityServer endpoint. When you use a client in combination with the client credentials flow, then you'll need a clientid + secret. Where secret is really secret and should be known to the client only. You can't use the same secret here. Seems logical when compared to users, they don't share the same password either.
This is close to the resource owner flow, however a client cannot login as a user. For that you'll need another flow, like the hybrid flow. In that case the client logs in on behalf of the user. The difference is the presence of the "sub" claim (the id of the user) in the token.
The client in this case is your app: console or mvc. The first only supports client credentials where the secret is mandatory, the second supports a hybrid flow, where secret may be omitted:
In certain situations, clients need to authenticate with
identityserver, e.g.
confidential applications (aka clients) requesting tokens at the token endpoint
APIs validating reference tokens at the introspection endpoint
The Api is your resource, that you want to protect. The Api never authenticates a user or client. This is done by IdentityServer. It only verifies the token (using the IdentityServer4.AccessTokenValidation package). For that it has its own secret that should only be known to the Api.
In order to grant the client access to the resource you'll need to add the scope to the client in the configuration of IdentityServer. The client is then allowed, not required, to request a token that grants access to the resource.
Again, the Api has nothing to do with authentication. It is also not bound to one client. Multiple clients can access the resource. All you have to do is add the scope to each client that should have access to the resource.
So there is really nothing against it that clients and resources know their secret. You don't have to change anything. All you have to do is choose the appropriate flow.

Authentication using SAML

My client asked me to develop a web api and use SAML as authentication.
I came across with the image below from this site, that shows the authentication flow.
However I don't know how to use the token that is generated after the authentication.
Do I need to store it as any other session variable?
Do I have to renew the token after a certain time or it lasts during all the session?
Note: The authorization server / idP is maintained by other party.
Since you develop the web API yourself, there's no need to refresh the token.
You're API needs to be added as relying party to the IdP. After that you can redirect to the IdP and initiate authentication. The token you get back contains several attributes (also configurable on the IdP) like unique user-id (uid), e-mail, name, country, etc...
In most cases this token is signed using a public/private key. Your API server needs to verify the signature, the issuer (the IdP), the audience (your API) of the token and consume the attributes. When everything is OK, you'll need to provision a local user account, link the external uid and create a local authentication cookie (or generate a OAuth2 token if your API uses OAUth2 or OpenIdConnect) for the locally provisioned user account.
Since this is a complex process, depending on the language/framework you're using, you might want to look into existing implementations.

Using openid-connect for authentication spa and rest api

I have an API Server (Resource server) and multiple apps, Web GUI (SPA) and a Desktop client and maybe more coming.
I'd like to use openid-connect besides http basic authentication for my API Server.
It should be configurable which openid provider to use. My own, facebook, google...
I only want to do authentication, I do not need their API. I only need some profile data like email or firstname.
Let's say I have configured google as my IdP and I'm currently using my Web GUI (SPA). I need to login, no problem, according to https://developers.google.com/identity/protocols/OpenIDConnect I redirect the user to google, get my authorization code and the Web Gui (SPA) gets an id_token and access_token from google.
No problem so far, but now the SPA has to work with my API Server and the API Server needs to authenticate every request (since it is a stateless rest api) coming from the Client (WebGui SPA) and needs to know which user actually did this.
A
So the access_token from google is meant to be used to access google api's right? But I also could just pass this access_token with every request to my api server and the api server calls https://www.googleapis.com/oauth2/v3/tokeninfo?access_token=xxx to verify the access_token and get the account name (mail). But this doesn't sound right, does it?
B
I also have and id_token which I can verify without calling google server everytime. So could I also just pass the id_token as bearer with every request to my api server and the api server can verify the id_token? But according to openid-connect spec the access_token is actually the one which just get passed to the api server and the id_token must stay on the client.
But then the id_token would be completely useless to me, the API server needs to know who the user is, the client (Web GUI) doesn't really care.
C
Or since it is my own API Server, does my API Server actually needs to implement the whole oauth2 system by itself, just not authentication but creating access_token and more. So I would have a /api/tokensign to which I can pass the id_token from google, the API verifies the id_token and creates an access_token for my WebGUI (SPA). And this new access_token can be passed as bearer to every api request. This actually sounds as the best solution according to specs, but do I really need to implement oauth2 by myself into my API? Sounds like a heavy addition since A and B could also be implemented.
My rest-api needs authentication with every request so is A, B, C the right approach? Please don't tell me this is opinion based, it is not.
What is the right way using oauth2/openid-connect for authentication?
You can use all three methods you have mentioned above, but indeed with some considerations. I will explain them with regards to available specifications.
Scenario - Two systems S1, S2
S1 - Identity provider
S2 - API endpoint
What you need - Trust and use 'Tokens' issued by S1 to access S2
Explanations for proposed solutioins A, B and C
A - Verify tokens issued by S1 for each call
This can be done using the RFC7662 - OAuth 2.0 Token Introspection endpoint. This validation is valid by the specification so yes you can use the token verification endpoint.
Advantage for this method is that, if a token is revoked, the effect is instantaneous. The very next API call will fail. But indeed there's the implication on performance. You need an extra verification service call.
Note that you do not need to get the account name from this verification response. It could be taken from ID token and could be used to verify for extra protection.
B - Trust tokens issued by S1 for each call
Now this approach is something extended from RFC6750 - The OAuth 2.0 Authorization Framework: Bearer Token Usage. You can indeed use ID toke to authenticate and authorise an end user. This link contains a good explanation on the ID token usage as a bearer token.
You can indeed verify the validity of token using MAC and even encryption. But be mindful to use short lived tokens and to always use TLS. And be mindful about refreshing tokens.! Because according to openID connect specification, ID token is not a mandatory item for a refresh token request.
C - A wrapper for federation
For this you can write your own solution or use an existing solutions (ex:- WSO2 identity server). This identity server will configured to choose the identity provider on your application (client like desktop app or web app). Identity server will do the necessary redirects and provide you the required tokens. But indeed you will need to use introspection endpoint to validate the token validity.
If you go one step ahead of this solution, you can try to implement a code exchange mechanism. You can exchange the token carry from external to tokens issued internally by one of your system (ex:- Google access token to your internal access token). The advantage of this approach is you have control over validation. Also since subsequent token validations are done internally, there should be a performance improvement.
Hope this explains some doubts you have.

Use cases of OAuth2.0

I am building a muli-tenant saas(software as a service) architecture. I have to build the authentication system for the system.
From what I have studied, I think I need to the build the authentication system based on OAuth2.0 and the bearer token with JWT tokens.
After reading a lot about OAuth2.0 of how to build an OAuth2.0 server I still didn't understand the full concept of OAuth and also have confusion about whether I need it or not or I need some other Authentication system.
What my system need is we will provide an SDK to all our customer and each client will have an Application Id and a secret key using the SDK client will connect to his application present in our system.
The application ID will map the customer to his application present in our system and the client secret key will authenticate the client inside the application.Do I still need to build an authentication system based on OAuth2.0 or can I build my own authentication system based on our need?
What are the use cases of OAUTH2.0 and when we won't need it to implement?
First, as clearly indicated in OAuth authentication
OAuth 2.0 is not an authentication protocol.
Authentication in the context of a user accessing an application tells an application who the current user is and whether or not they're present. A full authentication protocol will probably also tell you a number of attributes about this user, such as a unique identifier, an email address, and what to call them when the application says "Good Morning".
However, OAuth tells the application none of that.
OAuth says absolutely nothing about the user, nor does it say how the user proved their presence or even if they're still there.
As far as an OAuth client is concerned, it asked for a token, got a token, and eventually used that token to access some API. It doesn't know anything about who authorized the application or if there was even a user there at all.
There is a standard for user authentication using OAuth: OpenID Connect, compatible with OAuth2.
The OpenID Connect ID Token is a signed JSON Web Token (JWT) that is given to the client application along side the regular OAuth access token.
The ID Token contains a set of claims about the authentication session, including an identifier for the user (sub), the identifier for the identity provider who issued the token (iss), and the identifier of the client for which this token was created (aud).
In Go, you can look at coreos/dex, an OpenID Connect Identity (OIDC) and OAuth 2.0 Provider with Pluggable Connector.