Using Multiple Google API services independently - google-api

I'm working with 3 Google API Services(Analytics, Webmasters, PageSpeed). I have a single Google API client ID(with all 3 services activated) and common Google API PHP SDK in my server.
User of this aplication should be able to grant and revoke access for each service independently at any point of time depending on his usage. Is this possible?
Testcase:
If user wants to use only analytics service initially, he should be able to grant access for only analytics and later if he wants to use pagespeed service also, he should be able to grant for pagespeed also without compromising access for analytics. If he wants to use analytics & webmasters later, he should be able to revoke only pagespeed access without compromising the access for analytics or webmasters.

When you request an access token, you specify the resources you want access to. If later you need to access another resource, you request another token for that resource.
You can simplify your implementation by setting the include_granted_scopes to true when requesting the token. This will include all previous authorizations so you only need to deal with the new token.
AFAIK there's no way to revoke access to specific scopes, even though the documentation mentions that "When you revoke a token which represents a combined authorization, all of the authorizations are revoked simultaneously;". This actually happens even when revoking individual tokens. Also, the Google account user interface does not allow the user to specify which permissions he wants to keep, it's only possible to revoke all access from an application.
See the docs for incremental authorization.

Related

How to programmatically request domain-wide delegation for Google Calendar API?

I've spent a few hours now looking through the docs + reading other SO posts, and it's still not clear to me how to simply request domain-wide credentials for Google Calendar API (for other domains; not my own).
Our current web app kicks off an OAuth flow to request Calendar API credentials for a single user; however, there doesn't seem to be a simple way like this to request credentials for an entire domain. It seems that acquiring domain-level access requires the admin to manually set up a service account and then pass that information over (https://developers.google.com/admin-sdk/directory/v1/guides/delegation) which is incredibly cumbersome.
With Microsoft's Calendar API, this is a very straightforward process where you simply specify "Application Permissions" and then the OAuth flow must be completed by an Admin to get the expected set of access and refresh tokens. For GSuite, I can find no such equivalent...
To clarify based on some comments, I'm trying to figure out if GSuite has anything equivalent to what Microsoft Graph offers as described here:
https://learn.microsoft.com/en-us/graph/auth-v2-service
The closest I've seen requires publishing to the Google Apps Marketplace; however, the documentation here seems to be quite lacking and it's unclear how things like redirect_uri for handing over credentials to the backend server are handled.
If I've missed any documentation and someone can just point me in the right direction then that would be greatly appreciated.
The best documentation for how to set up domain wide delegation to a service account is -> Perform Google Workspace Domain-Wide Delegation of Authority
request domain-wide credentials for Google Calendar API (for other domains; not my own).
You can not. The admin of the google workspace domain sets up domain wide delegation for service accounts owned by the domain.
there doesn't seem to be a simple way like this to request credentials for an entire domain.
Service account authorization is very different from Oauth2 authorization. Service account authorization is is intended for backend systems that need access to data without requesting user permission.
Oauth2 allows you to grant authorization on a per user basis. The user must grant an application access to their data by accepting the consent screen.
There is no oauth2 flow that would grant your application to all the users on a workspace domain. TBH I think thats a good thing.
Only super administrators can configure domain-wide delegation, this is done in the Google Workspace Admin console
When you enable domain-wide delegation for a service account, basically you are giving it the permission to impersonate any user within your domain
If you need to make Calendar requests on behalf your users, in your app you will need to implement impersonation, that way you will use the service account with wide-domain delegation to make the requests on behalf your users
Here you can find the documentation explaining how to set up wide-domain delegation and an example for making the API calls implementing impersonation https://developers.google.com/identity/protocols/oauth2/service-account#authorizingrequests

Google API Authentication for App That Only Accesses One Account

Should I use a Service Account or an OAuth 2.0 Client ID?
I'm struggling to understand Google's documentation on authenticating for their APIs. I'm creating a basic application that will help users add and modify Google Calendar events for a single Google account (the account is shared between all users). I only need the application to access that one account, it'll never need to access any others.
It seems to me that Service Account would be best for this, but Google's documentation suggests Service Accounts should only be used for automated processes (unless I'm misunderstanding). For instance this page contains the following, describing when to use Service Accounts.
Would my application qualify as acting on the users behalf?
If so, I would want to use OAuth Client ID credentials, which will ask the user to sign in to a google account. In this case, is there a way I can guarantee they only sign in to the one account I want modified?
I can't find any decent documentation on the OAuth authentication requests to figure this out myself. If there is any could you point me there?
I'm sure I'm misunderstanding something basic here, but thank you for any help!
First off you should know that you can only use service accounts with Google aclendar api if you have a google workspace domain account.
You can then set up a calendar and a domain user that the service account can act on behalf of to control the access of that calendar.
Assuming that your application is going to preform all actions on this calendar then yes i would say that you could use a service account for this. If your app bacly has a ui with a calendar on it your just using google calendar to store the data.
However if you intend to share this calendar with the users themselves, this way they could see it within their own google Calendar account. Im not sure a service account would be the way to go.
If you want the users to be able to see it and make changes then you may want to just use Oauth2. Grant them access to the calendar and then request access to their calendar account.
Drawback to that option is going to be the verification process. You will get access to all the users calendars and your going to need write access.
If you can go with a service account you really should consider it it will save you a lot of hassle with verification.

Userless Automated server to server Oauth2 2 legged authentication to Gmail

I've found plenty of information on implementing Oauth2 using a user authorization step, but I'm trying to run a container that automatically scrapes a gmail inbox for attachments transforms them, and exports to prometheus, and I'm having trouble figuring out how to implement this library: https://pkg.go.dev/golang.org/x/oauth2/clientcredentials#Config or any other for that matter to retrieve a token without involving a manual user step.
Will doing this in Go require writing direct API calls since I can't find an existing library to handle this scenario? Would it make more sense to create a Google App password and use generic user/pass SMTP authentication?
First off i understand what you are trying to do.
You have a backend system running in a container which will access a single gmail account and process the emails.
Now you need to understand the limitations of the API you are working with.
There are two types of authorization used to access private user data
service account - server to server interaction only works with workspace domains. No authorization popup required.
Oauth2 - authorize normal user gmail accounts, requires user interaction to authorize the consent screen
If you do not have a workspace account and this is a normal gmail user then you have no choice you must use Oauth2, which will require that a user authorize the application at least once.
Using Oauth2 you can request offline access and receive a refresh token which you can use to request new access tokens when ever you wish. The catch is that your application will need to be in production and verified, because your refresh token will only work for seven days and then it will expire. To fix this and get a refresh token that does not expire means that your application must in production and verified. This means you need to go though Googles verification process with a restricted gmail scope which requires third party security check and costs between 15k - 75k depending upon your application.
I understand that this is a single user system but that does not mean that you still need to go though verification. When google added the need for application verification they did not take into account single user systems like yours.
Option
Have you considered going directly though the SMPT server instead of using the Gmail api? If you use an apps password you should bypass everything by loging in using the login and the apps password.

How to grant my youtube-api application read-only access to many Youtube accounts?

I'm working on application which generates reports and statistics about youtubers channels. I couldn't find in Google docs, how the Youtube User can grant read-only access from my application to his Youtube account? (I'm meant something like facebook application).
I'm a little confused how many ways of authentication are in Google API and which one should I use.
When you want to access private channel data, you will need to use OAuth authorization.
The way this works is that your app redirects clients to Google's authorization page, on which they can pick a YouTube channel associated with their Google account. If they are not already logged-in, they will first be asked by Google to log in (authenticate) and then proceed to the authorization page.
Once on the authorization page, they can decide to grant or refuse your application access to whatever it is your application demands access to. This is the important part: When your application redirects the user to the authorization page, it must specify one or more scopes.
Scopes define sets of actions that an application can perform once the user gives their permission. An application cannot perform operations that aren't within the scope of its powers. The three most important scopes of the YouTube API are:
https://www.googleapis.com/auth/youtube: Manage your YouTube account
https://www.googleapis.com/auth/youtube.readonly: View your YouTube account
https://www.googleapis.com/auth/youtube.upload: Manage your YouTube videos
That means that you can ask users to give your application read-only access to their channel by configuring your app to use the https://www.googleapis.com/auth/youtube.readonly scope. This is an example of what the URL that your application redirects its users to could look like:
https://accounts.google.com/o/oauth2/v2/auth?
scope=https%3A%2F%2Fwww.googleapis.com%2Fauth%2Fyoutube.readonly&
access_type=offline&
redirect_uri=http%3A%2F%2Flocalhost%2Foauth2callback&
response_type=code&
client_id=CLIENT_ID
If the user accepts, your server will be given an authorization code which it can exchange for a set of access and refresh tokens. The resource server (Google, in this case) will know with which scope these tokens were originally obtained and reject any calls outside of the scope.
This is what the authorization page currently looks like:
For more information, please read 'Using OAuth 2.0 for Web Server Applications' on Google Developers.

Using regular Google account as service account

I have an application using Google Drive that must (a) not require user login and (b) populate a document that authorised users can view.
Because of this it appears that using a regular account as a service account is my only option, as described here https://developers.google.com/drive/web/service-accounts
Use regular Google accounts as application-owned accounts
You may create a regular Google account like any user would, by going
through the Google account sign-up flow or by creating an account on
your Google Apps domain. Make sure it is then never used by an actual
person but only by your application.
To be able to access the account’s Drive programmatically you need to
manually go through the OAuth 2.0 web-server flow once and then store
or hard-code the user’s credentials, such as the refresh token, to be
able to programmatically access its Drive. For more information about
the web server flow for Drive, see Implementing Server-side
Authorization.
While it discourages user access, it doesn't ban it. However I am confused by the line
you need to manually go through the OAuth 2.0 web-server flow once and
then store or hard-code the user’s credentials
There doesn't seem to be a documented way to do this (yes, I have searched) - could someone step me though it?
You don't use a regular account as a service account, these are different things. Each one is a type of application-owned account.
The regular account is just a normal Google account that your application uses. Since regular accounts require the manual authorization step (going to the browser, logging in to Google and authorizing your app), you need to do this manually the first time and then save the token. There's some examples in this page. After you save the token, your app can authorize itself without your intervention.
The service account is an account that is not associated with an user and that do not require manual authorization. You can create a service account in the Developers Console as described here. With this type of account, you use a private key file to authorize your app.
Unless you need access to the web interface of the account that will manage your files (for example, to buy more storage), I'd recommend using the service account, since it doesn't require the manual step.

Resources