peburrows / goth

Elixir package for Oauth authentication via Google Cloud APIs
http://hexdocs.pm/goth
MIT License
289 stars 111 forks source link

Honor credentials from gcloud application defaults #24

Closed dazuma closed 7 years ago

dazuma commented 7 years ago

The overall goal here is to complete support for application default credentials. This PR provides an implementation of the last piece, gcloud sdk credentials provided by gcloud auth application-default login.

It involves two general parts:

  1. The logic for resolving the configuration in config.ex now includes a step looking for a credentials file in the well-known path used by gcloud. This location is $HOME/.config/gcloud/application_default_credentials.json on unix systems, but %APPDATA%\gcloud\application_default_credentials.json on windows. (I picked up this logic from the Ruby auth library

  2. Gcloud-provided ADCs are in the form of a refresh token rather than a private key. So I had to implement the oauth flow for that case. I defined a new token_source value for this case (:oauth_refresh, renaming the current :oauth to :oauth_jwt to avoid confusion), and then made the appropriate call in client.ex.

When writing tests for these cases, I had to create two new "test credentials" files. One is a normal private key file but slightly modified to be distinct from the default (so the existing GOOGLE_APPLICATION_CREDENTIALS test can distinguish it). The other is an application default credentials file (which is a refresh_token file) in its proper directory structure. Because there are now three separate files, I moved them out of the config directory and into test/data so we wouldn't have to keep whitelisting them in .gitignore. I also modified the private key files to remove identifying project info since the tests don't depend on them.

I did some ad-hoc e2e testing using my own gcloud credentials and verifying that Goth.Token.for_scope returns a valid token.

One existing caveat. Gcloud application default credentials don't include a project ID in the credentials file—and indeed, AIUI the "project" may not be well-defined anyway since the credentials are based on the user rather than on a project-connected service account. Goth, however, requires that the project be defined somewhere, so using gcloud-provided credentials requires that you specify the project in an environment variable or some other mechanism. One way to make this nicer for users is to pick up the default project (if set) from gcloud config but I'm not convinced that's really necessary. Let me know if you have any opinions on that.

peburrows commented 7 years ago

Awesome, thanks @dazuma!

peburrows commented 7 years ago

Pushed to hex as v0.7.0.