Class: BitsService::Client

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

Constant Summary collapse

ResourceTypeNotPresent =
Class.new(StandardError)
ConfigurationError =
Class.new(StandardError)

Instance Method Summary collapse

Constructor Details

#initialize(bits_service_options:, resource_type:, vcap_request_id: '', request_timeout_in_seconds: 900) ⇒ Client

Returns a new instance of Client.



12
13
14
15
16
17
18
19
20
21
22
23
24
# File 'lib/bits_service_client/client.rb', line 12

def initialize(bits_service_options:, resource_type:, vcap_request_id: '', request_timeout_in_seconds: 900)
  @username = validated(bits_service_options, :username)
  @password = validated(bits_service_options, :password)
  @private_endpoint = validated_http_url(bits_service_options, :private_endpoint)
  @public_endpoint = validated_http_url(bits_service_options, :public_endpoint)

  raise ResourceTypeNotPresent.new('Must specify resource type') unless resource_type
  @resource_type = resource_type
  @vcap_request_id = vcap_request_id

  @private_http_client = create_logging_http_client(@private_endpoint, bits_service_options, request_timeout_in_seconds)
  @public_http_client = create_logging_http_client(@public_endpoint, bits_service_options, request_timeout_in_seconds)
end

Instance Method Details

#blob(key) ⇒ Object



103
104
105
106
107
108
109
110
111
112
113
# File 'lib/bits_service_client/client.rb', line 103

def blob(key)
  Blob.new(
    key: key,
    private_http_client: @private_http_client,
    private_endpoint: @private_endpoint,
    vcap_request_id: @vcap_request_id,
    username: @username,
    password: @password,
    resource_type: @resource_type
  )
end

#cp_file_between_keys(source_key, destination_key) ⇒ Object



88
89
90
91
92
# File 'lib/bits_service_client/client.rb', line 88

def cp_file_between_keys(source_key, destination_key)
  temp_downloaded_file = Tempfile.new('foo')
  download_from_blobstore(source_key, temp_downloaded_file.path)
  cp_to_blobstore(temp_downloaded_file.path, destination_key)
end

#cp_to_blobstore(source_path, destination_key, resources: nil) ⇒ Object



37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
# File 'lib/bits_service_client/client.rb', line 37

def cp_to_blobstore(source_path, destination_key, resources: nil)
  if source_path.to_s.empty?
    file = Tempfile.new(['empty', '.zip'])
    source_path = file.path
    file.close!
    Dir.mktmpdir do |dir|
      output, error, status = Open3.capture3(%(/usr/bin/zip #{source_path} #{dir}))
      unless status.success?
        logger.error("Could not create a zip with no contents.\n STDOUT: \"#{output}\"\n STDERR: \"#{error}\"")
        raise Errors::Error.new('Could not create a zip with no contents')
      end
    end
  end

  body = { :"#{@resource_type.to_s.singularize}" => UploadIO.new(source_path, 'application/octet-stream') }

  if resources != nil
    body[:resources] = resources.to_json
  end

  response = @private_http_client.do_request(Net::HTTP::Put::Multipart.new(resource_path(destination_key), body), @vcap_request_id)
  validate_response_code!(201, response)
  if response.body == nil
    logger.error("UnexpectedMissingBody: expected body with json payload. Got empty body.")

    fail BlobstoreError.new({
      response_code: response.code,
      response_body: response.body,
      response: response
    }.to_json)
  end
  shas = JSON.parse(response.body, symbolize_names: true)
  validate_keys_present!([:sha1, :sha256], shas, response)
  return shas
end

#delete(key) ⇒ Object



94
95
96
97
98
99
100
101
# File 'lib/bits_service_client/client.rb', line 94

def delete(key)
  response = @private_http_client.delete(resource_path(key), @vcap_request_id)
  validate_response_code!([204, 404], response)

  if response.code.to_i == 404
    raise FileNotFound.new("Could not find object '#{key}', #{response.code}/#{response.body}")
  end
end

#delete_all(_ = nil) ⇒ Object

Raises:

  • (NotImplementedError)


119
120
121
122
123
124
125
# File 'lib/bits_service_client/client.rb', line 119

def delete_all(_=nil)
  raise NotImplementedError unless :buildpack_cache == resource_type

  @private_http_client.delete(resource_path(''), @vcap_request_id).tap do |response|
    validate_response_code!(204, response)
  end
end

#delete_all_in_path(path) ⇒ Object

Raises:

  • (NotImplementedError)


127
128
129
130
131
132
133
# File 'lib/bits_service_client/client.rb', line 127

def delete_all_in_path(path)
  raise NotImplementedError unless :buildpack_cache == resource_type

  @private_http_client.delete(resource_path(path.to_s), @vcap_request_id).tap do |response|
    validate_response_code!(204, response)
  end
end

#delete_blob(blob) ⇒ Object



115
116
117
# File 'lib/bits_service_client/client.rb', line 115

def delete_blob(blob)
  delete(blob.guid)
end

#download_from_blobstore(source_key, destination_path, mode: nil) ⇒ Object



73
74
75
76
77
78
79
80
81
82
83
84
85
86
# File 'lib/bits_service_client/client.rb', line 73

def download_from_blobstore(source_key, destination_path, mode: nil)
  FileUtils.mkdir_p(File.dirname(destination_path))
  File.open(destination_path, 'wb') do |file|
    response = @private_http_client.get(resource_path(source_key), @vcap_request_id)

    if response.code == '302'
      response = Net::HTTP.get_response(URI(response['location']))
    end

    validate_response_code!(200, response)
    file.write(response.body)
    file.chmod(mode) if mode
  end
end

#exists?(key) ⇒ Boolean

Returns:

  • (Boolean)


30
31
32
33
34
35
# File 'lib/bits_service_client/client.rb', line 30

def exists?(key)
  response = @private_http_client.head(resource_path(key), @vcap_request_id)
  validate_response_code!([200, 302, 404], response)

  response.code.to_i != 404
end

#local?Boolean

Returns:

  • (Boolean)


26
27
28
# File 'lib/bits_service_client/client.rb', line 26

def local?
  false
end