Best practice to use User's stored third party API keys?

Viewed 223

I am building an application that requires users to store their third party API key's and secret's in order to use the third party service within my application. I have safely stored these keys into the database and hashed the secret. But I do not know the best practice for how I should be using the third party service in my application. Whether it is better to use it in the front end of my application or the back end.

For the front end option I will need to call the api key and secret from my database from the front end application. Which will then need to make the third party api call in order to pull the data and information from the third party. But wouldn't this potentially expose user api key's?

Or from the back end but then I will need to make the call from the server to the third party service and then send that information to the front end to be displayed to the user. Afraid of how many calls and loading time.

This data from the third party service might be needed frequently. Would it better to setup a websocket and call from backend?

Thanks in advance

1 Answers

First of all have in consideration the best practices for storing your API Keys (you already mentioned to store them in a Database so you are in the right way, still is a good point to mention it):

  1. Do not embed API keys directly in code.
  2. Do not store API keys in files inside your application's source tree, or in any browser storage option (sessionStorage, localStorage, cookies...)
  3. Try to restrict your API keys to be used by only the IP addresses, referrer URLs, or mobile apps that need them.
  4. Restrict your API keys to be usable only for certain APIs or grant them only the permissions it require to work (don't generate an API Key with write permissions if your app requires only to read info from that third party service, for example).

You can search further documentation about the best practices of securely using API Keys in each platform documentation (here are the Google recommendations for using Google Cloud Platform API Keys as example https://support.google.com/googleapi/answer/6310037)

Now for the usage that you describe I see several solutions, I'll try to expose the pros and cons I see with each approach:

  1. Use your backend to handle requests to the third party service: like you mentioned before, this approach will allow you to avoid the exposure of the API keys to the client app, however if your app don't have enough security and is vulnerable to an XSS or CSRF attack for example, it doesn't matter if you have the API Keys well secured in your Database, the attacker can potentially access to any info that your target user has access through your app. And still your backend will need to handle all the request it will normally handle, plus the queries to get the API Keys from the Database, plus the request that the backend will need to make to the third party service using that API Key.
  2. Handle the third party request on your frontend: for this approach you will have the same potential security issues with XSS and CSRF attacks (I'm not a cybersecurity expert, but as far as I know, those two are considered the most common types of attacks that can access to your secured backend info through a frontend app, any cybersecurity expert please correct me if I'm wrong). However if your frontend app is secure and you handle the API Keys correctly, and store them in memory (in redux for example) and not in any browser storage, then you front can handle the request to the third party service, and you will avoid a potential bottleneck on you backend.
  3. Use an API Gateway, with a microservice to handle only the request to the third party services, and store the API Keys in an in-memory Database like Redis: in my humble opinion this may be the best approach. Your backend don't take any charge overload so you avoid potential bottlenecks, your frontend won't expose any sensitive info since those will be handled by a service dedicated to this single task. The only drawback is that this may be the most difficult approach to build if you are not using a microservice architecture. I worked on an app using Apollo Gateway (GraphQL) that handled a use case similar to this one you need to use, you can read about this on the Apollo docs https://www.apollographql.com/docs/federation/v1/gateway/

Summary: if you have time enough, or if you can develop an API Gateway on your backend without much effort, then in my opinion option 3 may be the best one for you. By the contrary if option 3 is too hard to implement or too much time consuming, then in your case I'll rather go for option 2, having in consideration the best security practices for frontend applications.

You can read more about web application security on https://owasp.org/www-project-top-ten/ and specifically for react apps, this medium article may help you https://medium.com/strands-tech-corner/frontend-application-security-b1ea9999cd02

Related