class BrowseEverything::Driver::GoogleDrive

Attributes

authentication_klass[RW]
credentials[R]

Public Class Methods

default_authentication_klass() click to toggle source
# File lib/browse_everything/driver/google_drive.rb, line 14
def default_authentication_klass
  Google::Auth::UserAuthorizer
end
new(config_values) click to toggle source

Constructor @param config_values [Hash] configuration for the driver

Calls superclass method BrowseEverything::Driver::Base::new
# File lib/browse_everything/driver/google_drive.rb, line 23
def initialize(config_values)
  self.class.authentication_klass ||= self.class.default_authentication_klass
  super(config_values)
end

Public Instance Methods

authorize!() click to toggle source

Request to authorize the provider This is the method which, passing an HTTP request, redeems an authorization code for an access token @return [String] a new access token

# File lib/browse_everything/driver/google_drive.rb, line 168
def authorize!
  @credentials = authorizer.get_credentials_from_code(user_id: user_id, code: code)
  @token = @credentials.access_token
  @code = nil # The authorization code can only be redeemed for an access token once
  @token
end
authorized?() click to toggle source

Whether or not the current provider is authorized @return [true,false]

# File lib/browse_everything/driver/google_drive.rb, line 130
def authorized?
  @token.present?
end
authorizer() click to toggle source

Authorization Object for Google API @return [Google::Auth::UserAuthorizer]

# File lib/browse_everything/driver/google_drive.rb, line 161
def authorizer
  @authorizer ||= authenticate
end
client_id() click to toggle source

Client ID for authorizing against the Google API's @return [Google::Auth::ClientId]

# File lib/browse_everything/driver/google_drive.rb, line 136
def client_id
  @client_id ||= Google::Auth::ClientId.from_hash(client_secrets)
end
connect(params, _data, _url_options) click to toggle source

This is the method accessed by the BrowseEverythingController for authorizing using an authorization code @param params [Hash] HTTP response passed to the OAuth callback @param _data [Object,nil] an unused parameter @return [String] a new access token

# File lib/browse_everything/driver/google_drive.rb, line 179
def connect(params, _data, _url_options)
  @code = params[:code]
  authorize!
end
contents(path = '') click to toggle source

Retrieve the files for any given resource on Google Drive @param path [String] the root or Folder path for which to list contents @return [Array<BrowseEverything::FileEntry>] file entries for the path

# File lib/browse_everything/driver/google_drive.rb, line 96
def contents(path = '')
  @entries = []
  drive_service.batch do |drive|
    request_params = Auth::Google::RequestParameters.new
    request_params.q += " and '#{path}' in parents " if path.present?
    list_files(drive, request_params, path: path)
  end

  @sorter.call(@entries)
end
details(file, _path = '') click to toggle source

Retrieve the file details @param file [Google::Apis::DriveV3::File] the Google Drive File @param path [String] path for the resource details (unused) @return [BrowseEverything::FileEntry] file entry for the resource node

# File lib/browse_everything/driver/google_drive.rb, line 54
def details(file, _path = '')
  mime_folder = file.mime_type == 'application/vnd.google-apps.folder'
  BrowseEverything::FileEntry.new(
    file.id,
    "#{key}:#{file.id}",
    file.name,
    file.size.to_i,
    file.modified_time || Time.new,
    mime_folder,
    mime_folder ? 'directory' : file.mime_type
  )
end
drive_service() click to toggle source

Construct a new object for interfacing with the Google Drive API @return [Google::Apis::DriveV3::DriveService]

# File lib/browse_everything/driver/google_drive.rb, line 186
def drive_service
  Google::Apis::DriveV3::DriveService.new.tap do |s|
    s.authorization = credentials
  end
end
icon() click to toggle source
# File lib/browse_everything/driver/google_drive.rb, line 40
def icon
  'google-plus-sign'
end
list_files(drive, request_params, path: '') click to toggle source

Lists the files given a Google Drive context @param drive [Google::Apis::DriveV3::DriveService] the Google Drive context @param request_params [RequestParameters] the object containing the parameters for the Google Drive API request @param path [String] the path (default to the root) @return [Array<BrowseEverything::FileEntry>] file entries for the path

# File lib/browse_everything/driver/google_drive.rb, line 72
def list_files(drive, request_params, path: '')
  drive.list_files(request_params.to_h) do |file_list, error|
    # Raise an exception if there was an error Google API's
    if error.present?
      # In order to properly trigger reauthentication, the token must be cleared
      # Additionally, the error is not automatically raised from the Google Client
      @token = nil
      raise error
    end

    values = file_list.files.map do |gdrive_file|
      details(gdrive_file, path)
    end
    @entries += values.compact

    request_params.page_token = file_list.next_page_token
  end

  @entries += list_files(drive, request_params, path: path) if request_params.page_token.present?
end
session() click to toggle source
# File lib/browse_everything/driver/google_drive.rb, line 147
def session
  AuthenticationFactory.new(
    self.class.authentication_klass,
    client_id,
    scope,
    token_store,
    callback
  )
end
token=(value) click to toggle source

The token here must be set using a Hash @param value [String, Hash] the new access token

Calls superclass method
# File lib/browse_everything/driver/google_drive.rb, line 30
def token=(value)
  # This is invoked within BrowseEverythingController using a Hash
  value = value.fetch('access_token') if value.is_a? Hash

  # Restore the credentials if the access token string itself has been cached
  restore_credentials(value) if @credentials.nil?

  super(value)
end
token_store() click to toggle source

Token store file used for authorizing against the Google API's (This is fundamentally used to temporarily cache access tokens) @return [Google::Auth::Stores::FileTokenStore]

# File lib/browse_everything/driver/google_drive.rb, line 143
def token_store
  Google::Auth::Stores::FileTokenStore.new(file: file_token_store_path)
end
validate_config() click to toggle source

Validates the configuration for the Google Drive provider

# File lib/browse_everything/driver/google_drive.rb, line 45
def validate_config
  raise InitializationError, 'GoogleDrive driver requires a :client_id argument' unless config[:client_id]
  raise InitializationError, 'GoogleDrive driver requires a :client_secret argument' unless config[:client_secret]
end

Private Instance Methods

client_secrets() click to toggle source
# File lib/browse_everything/driver/google_drive.rb, line 194
def client_secrets
  {
    Google::Auth::ClientId::WEB_APP => {
      Google::Auth::ClientId::CLIENT_ID => config[:client_id],
      Google::Auth::ClientId::CLIENT_SECRET => config[:client_secret]
    }
  }
end
download_url(id) click to toggle source

Please see developers.google.com/drive/v3/web/manage-downloads @param id [String] the ID for the Google Drive File @return [String] the URL for the file download

# File lib/browse_everything/driver/google_drive.rb, line 224
def download_url(id)
  "https://www.googleapis.com/drive/v3/files/#{id}?alt=media"
end
file_token_store_path() click to toggle source

This is required for using the googleauth Gem @see www.rubydoc.info/gems/googleauth/Google/Auth/Stores/FileTokenStore FileTokenStore for googleauth @return [Tempfile] temporary file within which to cache credentials

# File lib/browse_everything/driver/google_drive.rb, line 206
def file_token_store_path
  Tempfile.new('gdrive.yaml')
end
restore_credentials(access_token) click to toggle source

Restore the credentials for the Google API @param access_token [String] the access token redeemed using an authorization code @return Credentials credentials restored from a cached access token

# File lib/browse_everything/driver/google_drive.rb, line 231
def restore_credentials(access_token)
  client = Auth::Google::Credentials.new
  client.client_id = client_id.id
  client.client_secret = client_id.secret
  client.update_token!('access_token' => access_token)
  @credentials = client
end
scope() click to toggle source
# File lib/browse_everything/driver/google_drive.rb, line 210
def scope
  Google::Apis::DriveV3::AUTH_DRIVE
end
user_id() click to toggle source

Provides the user ID for caching access tokens (This is a hack which attempts to anonymize the access tokens) @return [String] the ID for the user

# File lib/browse_everything/driver/google_drive.rb, line 217
def user_id
  'current_user'
end