Home > Enterprise >  Is there any security benefit making a new OAuth2 client ID or each customer?
Is there any security benefit making a new OAuth2 client ID or each customer?

Time:10-13

Main question

Should we be making a new OAuth client ID & secret for each customer or just using one for all customers of our app?

Some of my colleagues seem to think that if we use one, and it somehow leaks it will impact all customers. So if we make one for each customer, we minimize damage. But my (limited) understanding is that the main risk to customers is only if the access token / refresh token leak.

If the OAuth client ID & secret leak, someone could try phishing someone to believe they were giving permission to our app to do actions, when they would really be giving access to a malicious actor. But this would still require customers to fall for the phishing attempt. Even then, it would only impact the customers that fall for it and not the other customers.

The part I am less sure of is the impact of our actions AFTER we found out about a leaked client ID/Secret. We would likely need to delete the OAuth client and make a new one to prevent phishing attempts with the leaked one(s) being possible.

I believe on a single client ID model, this would break all API calls for all customers since the access tokens we stored internally would be the ones generated from the previous client ID (the one we just deleted). The user would need to open our app, log in to their google account again, and click "allow" again to get us a new access token from the new client ID we made to allow us to call APIs again. Where if we had a different client ID for each customer, we could do this process for just a sub set of customers or a single customer.

But I also feel that under the multi-client ID model, if a client ID did leak for one customer, how can we be sure it didn't leak for the others? Wouldn't you want to get new client IDs for all customers anyways?

I see the following options:

  1. The leaker got access to our google cloud project and has access to all active client IDs. They can even make themselves new ones, so having multiple client IDs doesn't help.
  2. The leaker got access to our internal DB and was able to decrypt it. So they can get all the client IDs stored in the DB anyways, so having multiple client IDs doesn't help. (They might also be able to get access tokens/refresh tokens which is a much a bigger concern!)
  3. Someone mistakenly included client ID & secret in some log file or email. This may provide access to less than the full list of client IDs, but again how do we know how many log files leaked or how many emails were sent? Wouldn't it be a bad practice to not change all of them?

Please help me if I'm overlooking anything.

Here's a diagram for more visual thinkers (values in DB would be encrypted/salted/etc.)

two options for Client ID structure

Update Since there seems to be confusion, here is the terminology from auth0.com

Resource Owner(s): School1, School2, etc.

Client: Our "app" server

Resource Server: Google - specifically "Google Workspace" or "Google Workspace Admin SDK APIs" (I believe)

Authorization Server: Google - specifically "Google Identity" (I believe)

User Agent: Browser

Is the Client the Resource Owner?: No. School owns the chromebooks and manages the student/teacher accounts using them through Google Workspace.

Is the Client a web app executing on the server?: Yes. We are following "Authorization Code Flow" to get access tokens from Google for each customer. We store them on our private DB.

Customer's experience - They download and run an installer and enter the license activation code. A website with the UI will be hosted. (let's say www.school1.com/App) It can be in their network, on cloud, wherever, they just need to make sure the hosting server's network can access to our internal server (let's say at 1.2.3.4). When opening www.school1.com/App they need to setup a new admin account and login. Then they click a setup button and get google pop up asking to login to their Google account (This is how we get the access token). Then they can interact with the website in their browser clicking buttons to make actions happen.

API flow - Clicks in browser become API calls to our server (1.2.3.4) with info for us to authenticate/authorize them as a valid App customer making the call. If authorized, our server then uses the access token we have stored internally to call the Google APIs.

Optional Background

My company is looking to make a product for schools using Google Workspace to manage their Chromebooks.

Google already has some APIs that we plan to use. We hope to leverage these with our own business logic. As a dummy example let's imagine we know schools want to reboot their Chromebooks every day at a specific time. The issueCommand REST API can be used to do the reboot. Our app would handle the scheduling of calling the API.

To be able to call these APIs requires permission from the Google Workspace administrator using OAuth 2.0 to authorize us to make the requests (No other authorization protocols are supported). There seems to be two ways to do this.

  1. Service account apparently for server to server applications
  2. OAuth Client ID apparently for server-side web apps

The service account requires the administrator to log in to their Admin Console and take a bunch of manual steps to grant our app permission, where the OAuth Client ID seems more user friendly. The admin just signs into the google pop up and is shown all the scopes we request, and can just click "Allow"

(There are other differences such as the service account will keep working even if the admin changes, but let's just assume we're committed to OAuth Client ID)

CodePudding user response:

There are 2 parts to the authorization code flow:

  • A front channel request in the browser that uses the client ID and gets an authorization code
  • A back channel request that uses both a client ID and secret, to swap the code for tokens

If these leak you can replace the client secret without impacting end users, since it is private between the web back end and the Authorization Server. You may need to redeploy the web app but that should be something you already have a plan for.

I'd recommend keeping the client ID the same though. This is not a secret anyway and any end user can see what it is when the app redirects them to sign in - eg if they use browser tools to view the HTTP request.

You have a single app so use a single client ID and secret. Trying to do otherwise would not work since when a user starts authentication you don't know who they are yet since they have not identified themselves.

The above is standard OAuth and I would stick to that since it results in simple code and a solution that is easy to manage.

  • Related