class Google::Apis::Core::DownloadCommand
Streaming/resumable media download support
Constants
- RANGE_HEADER
Attributes
File or IO to write content to @return [String, File, write]
Public Instance Methods
Execute the upload request once. Overrides the default implementation to handle streaming/chunking of file content.
@private @param [Hurley::Client] client
HTTP client
@yield [result, err] Result or error if block supplied @return [Object] @raise [Google::Apis::ServerError] An error occurred on the server and the request can be retried @raise [Google::Apis::ClientError] The request is invalid and should not be retried without modification @raise [Google::Apis::AuthorizationError] Authorization is required
# File lib/google/apis/core/download.rb, line 67 def execute_once(client, &block) client.get(@download_url || url) do |req| apply_request_options(req) check_if_rewind_needed = false if @offset > 0 logger.debug { sprintf('Resuming download from offset %d', @offset) } req.header[RANGE_HEADER] = sprintf('bytes=%d-', @offset) check_if_rewind_needed = true end req.on_body(200, 201, 206) do |res, chunk| check_status(res.status_code, chunk) unless res.status_code.nil? if check_if_rewind_needed && res.status_code != 206 # Oh no! Requested a chunk, but received the entire content # Attempt to rewind the stream @download_io.rewind check_if_rewind_needed = false end logger.debug { sprintf('Writing chunk (%d bytes)', chunk.length) } @offset += chunk.length @download_io.write(chunk) @download_io.flush end end if @close_io_on_finish result = nil else result = @download_io end success(result, &block) rescue => e error(e, rethrow: true, &block) end
Ensure the download destination is a writable stream.
@return [void]
# File lib/google/apis/core/download.rb, line 34 def prepare! @state = :start @download_url = nil @offset = 0 if download_dest.respond_to?(:write) @download_io = download_dest @close_io_on_finish = false elsif download_dest.is_a?(String) @download_io = File.open(download_dest, 'wb') @close_io_on_finish = true else @download_io = StringIO.new('', 'wb') @close_io_on_finish = false end super end
Close IO stream when command done. Only closes the stream if it was opened by the command.
# File lib/google/apis/core/download.rb, line 52 def release! @download_io.close if @close_io_on_finish end