Class: Glass::Mirror

Inherits:
Object
  • Object
show all
Defined in:
lib/glass.rb

Constant Summary collapse

@@config =
Config.new()

Class Attribute Summary collapse

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Class Attribute Details

.client_idObject

Returns the value of attribute client_id.



21
22
23
# File 'lib/glass.rb', line 21

def client_id
  @client_id
end

.client_secretObject

Returns the value of attribute client_secret.



21
22
23
# File 'lib/glass.rb', line 21

def client_secret
  @client_secret
end

.redirect_uriObject

Returns the value of attribute redirect_uri.



21
22
23
# File 'lib/glass.rb', line 21

def redirect_uri
  @redirect_uri
end

.scopesObject

Returns the value of attribute scopes.



21
22
23
# File 'lib/glass.rb', line 21

def scopes
  @scopes
end

Instance Attribute Details

#clientObject

Returns the value of attribute client.



35
36
37
# File 'lib/glass.rb', line 35

def client
  @client
end

Class Method Details

.build_client(credentials) ⇒ Google::APIClient

Build a Mirror client instance.

Parameters:

  • credentials (Signet::OAuth2::Client)

    OAuth 2.0 credentials.

Returns:

  • (Google::APIClient)

    Client instance



226
227
228
229
230
231
232
# File 'lib/glass.rb', line 226

def self.build_client(credentials)
  m = Mirror.new()
  m.client = Google::APIClient.new
  m.client.authorization = credentials
  m.client = m.client.discovered_api('mirror', 'v1')
  m
end

.build_with_code(authorization_code) ⇒ Object



234
235
236
# File 'lib/glass.rb', line 234

def self.build_with_code(authorization_code)
  return build_client(get_credentials(authorization_code))
end

.exchange_code(authorization_code) ⇒ Signet::OAuth2::Client

Exchange an authorization code for OAuth 2.0 credentials.

Parameters:

  • auth_code (String)

    Authorization code to exchange for OAuth 2.0 credentials.

Returns:

  • (Signet::OAuth2::Client)

    OAuth 2.0 credentials.



105
106
107
108
109
110
111
112
113
114
115
116
117
118
# File 'lib/glass.rb', line 105

def self.exchange_code(authorization_code)
  client = Google::APIClient.new
  client.authorization.client_id = client_id
  client.authorization.client_secret = client_secret
  client.authorization.code = authorization_code
  client.authorization.redirect_uri = redirect_uri

  begin
    client.authorization.fetch_access_token!
    return client.authorization
  rescue Signet::AuthorizationError
    raise CodeExchangeError.new(nil)
  end
end

.get_authorization_url(user_id, state) ⇒ String

Retrieve authorization URL.

Parameters:

  • user_id (String)

    User’s Google ID.

  • state (String)

    State for the authorization URL.

Returns:

  • (String)

    Authorization URL to redirect the user to.



155
156
157
158
159
160
161
162
163
164
165
166
167
168
# File 'lib/glass.rb', line 155

def self.get_authorization_url(user_id, state)
  client = Google::APIClient.new
  client.authorization.client_id = client_id
  client.authorization.redirect_uri = redirect_uri
  client.authorization.scope = scopes

  return client.authorization.authorization_uri(
      :options => {
          :approval_prompt => :force,
          :access_type => :offline,
          :user_id => user_id,
          :state => state
      }).to_s
end

.get_credentials(authorization_code, state = "OAuth Failed") ⇒ Signet::OAuth2::Client

Retrieve credentials using the provided authorization code.

This function exchanges the authorization code for an access token and queries
the UserInfo API to retrieve the user's Google ID.
If a refresh token has been retrieved along with an access token, it is stored
in the application database using the user's Google ID as key.
If no refresh token has been retrieved, the function checks in the application
database for one and returns it if found or raises a NoRefreshTokenError
with an authorization URL to redirect the user to.

Parameters:

  • auth_code (String)

    Authorization code to use to retrieve an access token.

  • state (String) (defaults to: "OAuth Failed")

    State to set to the authorization URL in case of error.

Returns:

  • (Signet::OAuth2::Client)

    OAuth 2.0 credentials containing an access and refresh token.

Raises:



188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
# File 'lib/glass.rb', line 188

def self.get_credentials(authorization_code, state="OAuth Failed")
  user_id = ''
  begin
    credentials = exchange_code(authorization_code)
     = (credentials)
    user_id = .id
    if credentials.refresh_token != nil
      store_credentials(user_id, credentials)
      return credentials
    else
      credentials = get_stored_credentials(user_id)
      if credentials != nil && credentials.refresh_token != nil
        return credentials
      end
    end
  rescue CodeExchangeError => error
    print 'An error occurred during code exchange.'
    # Drive apps should try to retrieve the user and credentials for the current
    # session.
    # If none is available, redirect the user to the authorization URL.
    error.authorization_url = get_authorization_url(user_id, state)
    raise error
  rescue NoUserIdError
    print 'No user ID could be retrieved.'
  end

  authorization_url = get_authorization_url(user_id, state)
  raise NoRefreshTokenError.new(authorization_url)
end

.get_stored_credentials(user_id) ⇒ Signet::OAuth2::Client

Retrieved stored credentials for the provided user ID.

Parameters:

  • user_id (String)

    User’s ID.

Returns:

  • (Signet::OAuth2::Client)

    Stored OAuth 2.0 credentials if found, nil otherwise.



68
69
70
71
72
73
74
75
# File 'lib/glass.rb', line 68

def self.get_stored_credentials(user_id)
  unless @@config.no_redis
    hash = Redis.get(user_id)
    client = Google::APIClient.new
    client.authorization.dup
    client.update_token!(hash)
  end
end

.get_user_info(credentials) ⇒ Google::APIClient::Schema::Oauth2::V2::Userinfo

Send a request to the UserInfo API to retrieve the user’s information.

Parameters:

  • credentials (Signet::OAuth2::Client)

    OAuth 2.0 credentials to authorize the request.

Returns:

  • (Google::APIClient::Schema::Oauth2::V2::Userinfo)

    User’s information.

Raises:



128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
# File 'lib/glass.rb', line 128

def self.(credentials)
  client = Google::APIClient.new
  client.authorization = credentials
  oauth2 = client.discovered_api('oauth2', 'v2')
  result = client.execute!(:api_method => oauth2.userinfo.get)
   = nil
  if result.status == 200
     = result.data
  else
    puts "An error occurred: #{result.data['error']['message']}"
  end
  if  != nil && .id != nil
    return 
  end
  raise NoUserIdError, "Unable to retrieve the user's Google ID."
end

.hello_worldObject



38
39
40
# File 'lib/glass.rb', line 38

def self.hello_world
  "Hello World!"
end

.no_redis=(val) ⇒ Object



56
57
58
# File 'lib/glass.rb', line 56

def self.no_redis= val
  @@config.no_redis=val
end

.redisObject

Returns the current Redis connection. If none has been created, will create a new one.



44
45
46
# File 'lib/glass.rb', line 44

def self.redis
  @@config.redis
end

.redis=(val) ⇒ Object



48
49
50
# File 'lib/glass.rb', line 48

def self.redis= val
  @@config.redis = val
end

.redis_idObject



52
53
54
# File 'lib/glass.rb', line 52

def self.redis_id
  @@config.redis_id
end

.store_credentials(user_id, credentials) ⇒ Object

Store OAuth 2.0 credentials in the application’s database.

Parameters:

  • user_id (String)

    User’s ID.

  • credentials (Signet::OAuth2::Client)

    OAuth 2.0 credentials to store.



85
86
87
88
89
90
91
92
93
94
95
# File 'lib/glass.rb', line 85

def self.store_credentials(user_id, credentials)
  unless @@config.no_redis
    hash = Hash.new()
    hash[:access_token] = credentials.access_token
    hash[:refresh_token] = credentials.refresh_token
    hash[:expires_in] = credentials.expires_in
    hash[:issued_at] = credentials.issued_at

    Redis.set(user_id, hash)
  end
end

Instance Method Details

#delete(item) ⇒ Object



242
243
244
# File 'lib/glass.rb', line 242

def delete(item)
  item.delete(client)
end

#insert(item) ⇒ Object



238
239
240
# File 'lib/glass.rb', line 238

def insert(item)
  item.insert(client)
end