class Googledriver::Uploader

Uploads a filesystem to Google Drive and saves file ids.

Public Class Methods

new(client_secrets_path) click to toggle source

Constructs a new Uploader by building an empty hash for file ids and making an Authorizer object to handle the creation of REST resources.

# File lib/googledriver/uploader.rb, line 7
def initialize(client_secrets_path)
  @file_ids = {}
  @authorizer = Googledriver::Authorizer.new(client_secrets_path)
  @authorizer.create_refresh_token
  @authorizer.refresh_access_token
  @access_token = @authorizer.access_token
  @token_tob = @authorizer.token_tob
  @token_lifetime = @authorizer.token_lifetime
  create_manager_resource
  create_uploader_resource
end

Public Instance Methods

archive_file_ids() click to toggle source

Saves the file ids hash to a json file in the working directory.

# File lib/googledriver/uploader.rb, line 110
def archive_file_ids
  archive = File.open('drive_file_ids.json', 'w')
  File.write('drive_file_ids.json', @file_ids.to_json)
  archive.close
end
obtain_file_metadata(file_id) click to toggle source

Returns the metadata of a given file.

# File lib/googledriver/uploader.rb, line 117
def obtain_file_metadata(file_id)
  begin
    metadata = @drive_manager[file_id].get
  rescue StandardError => error
    warn "#{error};  METHOD  #{__callee__};  RESOURCE  #{file_path}"
    return
  end

  metadata = JSON.parse(metadata)
  metadata
end
update_file_metadata(file_id, element, new_data) click to toggle source

Updates a piece of metadata for a given file.

# File lib/googledriver/uploader.rb, line 130
def update_file_metadata(file_id, element, new_data)
  payload = { 'uploadType' => 'resumable', element => new_data }.to_json

  begin
    update = @drive_manager[file_id].patch(
      payload
    )
  rescue StandardError => error
    warn "#{error};  METHOD  #{__callee__};  RESOURCE  #{file_path}"
    return
  end

  update
end
update_file_permission(file_id, email) click to toggle source

Shares a given file with an individual or group email address.

# File lib/googledriver/uploader.rb, line 146
def update_file_permission(file_id, email)
  payload = { 'role' => 'writer', 'type' => 'group',
              'emailAddress' => email }.to_json

  begin
    update = @drive_manager[file_id + '/permissions'].post(
      payload
    )
  rescue StandardError => error
    warn "#{error};  METHOD  #{__callee__};  RESOURCE  #{file_path}"
    return
  end

  update
end
upload_file(file_path, file_name, location: 'root') click to toggle source

Uploads a local file specified by a file path to a given folder in Google Drive.

# File lib/googledriver/uploader.rb, line 72
def upload_file(file_path, file_name, location: 'root')
  begin
    payload = File.open(file_path)
  rescue StandardError => error
    warn "#{error};  METHOD  #{__callee__};  RESOURCE  #{file_path}"
    return
  end

  begin
    update_refresh_token if refresh_due?
    upload = @drive_uploader.post(
      payload
    )
  rescue StandardError => error
    warn "#{error};  METHOD  #{__callee__};  RESOURCE  #{file_path}"
    retry
  end

  file_id = JSON.parse(upload)['id']
  @file_ids[file_path] = file_id

  begin
    update_refresh_token if refresh_due?
    @drive_manager[file_id + '?addParents=' + location +
                   '&removeParents=root&alt=json'].patch(
                     { 'uploadType' => 'resumable',
                       'name' => file_name }.to_json
                   )
  rescue StandardError => error
    warn "#{error};  METHOD  #{__callee__};  RESOURCE  #{file_path}"
    retry
  end

  payload.close
  file_id
end
upload_filesystem(directory: '', upload_dest: 'root') click to toggle source

Recursively uploads a local filesystem specified by a file path to a given folder in Google Drive.

# File lib/googledriver/uploader.rb, line 21
def upload_filesystem(directory: '', upload_dest: 'root')
  directory = "#{directory}/" unless directory[-1] == '/'

  Dir[directory + '*'].each do |object|
    if File.directory?(object)
      folder_name = File.basename(object)
      folder_id = upload_folder(folder_name, location: upload_dest)
      upload_filesystem(upload_dest: folder_id,
                        directory: "#{directory}#{folder_name}/")
    else
      file_name = File.basename(object)
      file_id = upload_file(object, file_name, location: upload_dest)
      @file_ids[object] = file_id
    end
  end
end
upload_folder(folder_name, location: 'root') click to toggle source

Uploads a local folder specified by a file path to a given folder in Google Drive.

# File lib/googledriver/uploader.rb, line 40
def upload_folder(folder_name, location: 'root')
  begin
    update_refresh_token if refresh_due?
    upload = @drive_manager.post(
      { 'name' => folder_name,
        'mimeType' => 'application/vnd.google-apps.folder' }.to_json
    )
  rescue StandardError => error
    warn "#{error};  METHOD  #{__callee__};  RESOURCE  #{folder_name}"
    retry
  end

  folder_id = JSON.parse(upload)['id']

  if location != 'root'
    begin
      update_refresh_token if refresh_due?
      @drive_manager[folder_id + '?addParents=' + location +
                     '&removeParents=root&alt=json'].patch(
                       { 'uploadType' => 'resumable' }.to_json
                     )
    rescue StandardError => error
      warn "#{error};  METHOD  #{__callee__};  RESOURCE  #{folder_name}"
      retry
    end
  end

  folder_id
end

Private Instance Methods

create_manager_resource() click to toggle source
# File lib/googledriver/uploader.rb, line 164
def create_manager_resource
  @drive_manager = RestClient::Resource.new(
    'https://www.googleapis.com/drive/v3/files/',
    headers: { 'Authorization' => "Bearer #{@access_token}",
               'Content-Type' => 'application/json' }
  )
end
create_uploader_resource() click to toggle source
# File lib/googledriver/uploader.rb, line 172
def create_uploader_resource
  @drive_uploader = RestClient::Resource.new(
    'https://www.googleapis.com/upload/drive/v3/files',
    headers: { 'Authorization' => "Bearer #{@access_token}" }
  )
end
refresh_due?() click to toggle source
# File lib/googledriver/uploader.rb, line 188
def refresh_due?
  token_timer = Time.now - @token_tob
  return false unless token_timer > @token_lifetime * 0.9
  true
end
update_refresh_token() click to toggle source
# File lib/googledriver/uploader.rb, line 179
def update_refresh_token
  @authorizer.refresh_access_token
  @access_token = @authorizer.access_token
  @token_lifetime = @authorizer.token_lifetime
  @token_tob = @authorizer.token_tob
  create_manager_resource
  create_uploader_resource
end