Reputation: 1590
I'm trying to get offline access
with Google APIs. I have to pull data from Google Calendar without having the user sign-in everytime.
I've added this to my Gemfile:
gem 'google-api-client', '~> 0.9'
... And added this to my controller:
require 'google/api_client/client_secrets'
class Api::V1::CalendarAccountsController < Api::V1::BaseController
...
And in my action:
client_secrets = Google::APIClient::ClientSecrets.load(
File.join(
Rails.root,
'config',
'client_secrets.json')
)
@auth_client = client_secrets.to_authorization
@auth_client.update!(
:scope => 'https://www.googleapis.com/auth/calendar.readonly',
:redirect_uri => '/{callback URL}',
:additional_parameters => {
"access_type" => "offline",
"include_granted_scopes" => "true"
}
)
redirect_to @auth_client.authorization_uri.to_s
The problem is -- even though I'm specifying "access_type" as "offline", I still don't get asked for offline-access privileges in the Google privileges list (I'm attaching a screenie below).
And here's the page Google loads (no offline-access):
And here's the URL that got generated when I called @auth_client.authorization_uri.to_s
Am I missing something?
Upvotes: 3
Views: 2946
Reputation: 5611
You can try using something like this:
client = Signet::OAuth2::Client.new({
client_id: your_client_id,
client_secret: your_secret_id,
authorization_uri: 'https://accounts.google.com/o/oauth2/auth',
scope: Google::Apis::CalendarV3::AUTH_CALENDAR_READONLY,
redirect_uri: your_callback_url
})
client.update!(
additional_parameters: {
access_type: 'offline',
prompt: 'consent'
}
)
redirect_to client.authorization_uri.to_s
Note that I am using a more recent version of the google-api-client
gem, configured this way:
gem 'google-api-client', '~> 0.11', require: 'google/apis/calendar_v3'
This way Google will ask you for permission to interact with the Calendar API and correctly setting the access_type
parameter to grant you offline access to the same APIs.
This approach will prompt the user for the authorization each time you call the code. If you want to prevent this, you have to change it this way:
client.update!(
additional_parameters: {
access_type: 'offline'
}
)
If you have already authorized your app without the access_type: 'offline'
parameter Google will grant you an authentication token without the offline permits. To reset this situation it is sufficient to go into your Google profile permissions and revoke the previous authorization for your application. Then try again.
(Note: the signet
gem is a dependency of googleauth
, which in turn is a dependency of google-api-client
, so you get this code for free, without the need to add more gems to the Gemfile
)
Upvotes: 2
Reputation: 6791
Try adding this code. If your application needs offline access to a Google API, set the API client's access type to offline:
auth_client.update!(
:additional_parameters => {"access_type" => "offline"}
)
After a user grants offline access to the requested scopes, you can continue to use the API client to access Google APIs on the user's behalf when the user is offline. The client object will refresh the access token as needed.
Also use the Google client library, this will help you with refreshing an access token (offline access).
Hope this helps.
Upvotes: 1