8

So we are a group of students making an online platform for our University. We are modelling our platform as a set of services.

For example, a service "A" might store only personal information of users and expose a REST API on top of it. Another service "B" might only be sending emails.

A rough structure would look like this: Rough SOA architecture

Now we want to use OAuth for Authentication and Authorization (I know OAuth is an Authorization framework but we want to do roughly what google does).

A typical scenario could be something like:

  1. User requests webpage of service "A".
  2. Service "A" sees that user is not authenticated, so it will send a redirect to Auth Server.
  3. User enters its credentials, and an access token is granted to service "A".

Now, service "A" may need to call another service "B". Note that this is an internal server to server request. Various other services might be calling service "B".

I want to make sure that when service "B" is called, only allowed services can call it. For example, "A" has the right to call "B", but "C" doesn't. In other words, I want to ensure only whitelisted callers for a particular service can call it.

So my question is, is it possible to secure internal service-to-service calls using OAuth?

Can it be done in a simpler yet secure way?

I don't want token delegation: that is, I don't want the first token issued to service A being used somewhere else. It is assumed that if "A" is calling "B", then "A" has the right to do so, even if there is no user logged in.

My attempt: (might be wrong, please correct me) * The Auth server can issue clientIds and client secrets to each service. * A service which wants to call another service identifies itself to Auth server using key and secret. * If the service is allowed to call the target service, Auth server issues a token, else returns forbidden.

But even in this case, the Auth server is doing too much.

Can't each service itself control what other services can call it?

Thanks.

3 Answers 3

6

This started out as a comment, but it grew a bit large for that, so I've moved it to an 'answer'.

The step that is missing from the OAuth2.0 specs is the 'backend communication': the part where the authorization server and the various services agree on what is a valid token and what scope is associated with it. These 'implementation details' are is left the discretion of the OAuth Service Provider.

Also, your diagram is could be improved by sticking closer to the OAuth2.0 terminology (I'm not saying you did a bad job, the diagram is helpful, but it could be more clear).

Your 'User' in this case is (presumably) the Resource Owner. The 'Frontend' could (I'm guessing here) be a single-page application, running inside the User Agent.

It is the API Server that is receives the Access Token from the Authorization Server, to access data on behalf of the Resource Owner.

In other words, your diagram is missing the communication between the 'User' and the 'Auth Server'.

For the flow of OAuth, maybe the follwing diagram is helpful:

enter image description here Figure 1: OAuth flow for (confidential) clients.

To answer your question: OAuth is about delegation of authorization from a Resource Owner to some service to access the Resource Owner's data on their behalf.

So, using OAuth may not be your best option. However, I don't know of any out-of-the box solutions that really solve your problem (delegation of access rights, on behalf of a user). You could take a look at authoriZation Based Access Control (ZBAC) but it may be quite an overkill for what you are attempting to achieve.

4
  • Thank you. The diagram is very helpful. I was researching more into it. If you know, does JWT (JSON web token) be used here somehow? (really a noob question) Oct 5, 2016 at 9:13
  • 1
    JWT is just a fashionable replacement for a (cookie-based) session token, only without the extra security features that have, over the years, been added to cookies. JWT is often proclaimed to be 'stateless' but don't be fooled. The actual difference is that with JWT, the state is kept on the client side, which is a scalability feature you won't need unless you reach the size of a baby tech elephant. By that time, you should have the resources to switch, if server side state turn out to be your bottle bottleneck.
    – Jacco
    Oct 5, 2016 at 9:26
  • One quibble with this answer: It's not the User Agent that gets the token from the Provider. It's the API server. That's confirmed by the chart. And it's an important distinction, because it means that the end user never has access to the token. When the API server exchanges the authorization_code for an access_token, it typically has to provide its own secret, and the tokens it gets back are secrets that never get exposed to the frontend.
    – btubbs
    Jun 13, 2019 at 15:34
  • 1
    @btubbs well spotted. I've updated it, although it does not change the conclusion in my answer.
    – Jacco
    Jun 17, 2019 at 6:47
1

Your attempt is half way there.

There is a grant type in OAuth2 called Client Credentials which is probably what you are looking for.

The Client Credentials grant type is used by clients to obtain an access token outside of the context of a user.

Basically, the client exchanges its Client ID and Client Secret for an access token which it can then use to make requests to the Resource Server on its own behalf.

 +---------+                                  +---------------+
 |         |                                  |               |
 |         |>--(A)- Client Authentication --->| Authorization |
 | Client  |                                  |     Server    |
 |         |<--(B)---- Access Token ---------<|               |
 |         |                                  |               |
 +---------+                                  +---------------+

Check out these for more information:

https://oauth.net/2/grant-types/client-credentials/

https://www.oauth.com/oauth2-servers/access-tokens/client-credentials/

0

Maybe I'm missing something, but if at that point you just want to control which services can call a given service X at all, e.g. either they can call all endpoints or no endpoints, then why not just use basic auth with service X? Another service then would either have the basic auth credentials for service X or it would not. Obviously the bad thing here is that - should the credentials leak, you need to update all services that have them. Individual credentials give limit that scope and allow you to identify who is calling based on the credentials used.

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .