gooddata 0.6.12 → 0.6.13

Sign up to get free protection for your applications and to get access to all the features.
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: gooddata
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.6.12
4
+ version: 0.6.13
5
5
  platform: ruby
6
6
  authors:
7
7
  - Pavel Kolesnikov
@@ -11,7 +11,7 @@ authors:
11
11
  autorequire:
12
12
  bindir: bin
13
13
  cert_chain: []
14
- date: 2015-01-21 00:00:00.000000000 Z
14
+ date: 2015-02-09 00:00:00.000000000 Z
15
15
  dependencies:
16
16
  - !ruby/object:Gem::Dependency
17
17
  name: rake
@@ -201,6 +201,34 @@ dependencies:
201
201
  - - ">="
202
202
  - !ruby/object:Gem::Version
203
203
  version: 0.7.0
204
+ - !ruby/object:Gem::Dependency
205
+ name: debase
206
+ requirement: !ruby/object:Gem::Requirement
207
+ requirements:
208
+ - - ">="
209
+ - !ruby/object:Gem::Version
210
+ version: '0'
211
+ type: :development
212
+ prerelease: false
213
+ version_requirements: !ruby/object:Gem::Requirement
214
+ requirements:
215
+ - - ">="
216
+ - !ruby/object:Gem::Version
217
+ version: '0'
218
+ - !ruby/object:Gem::Dependency
219
+ name: ruby-debug-ide
220
+ requirement: !ruby/object:Gem::Requirement
221
+ requirements:
222
+ - - ">="
223
+ - !ruby/object:Gem::Version
224
+ version: '0'
225
+ type: :development
226
+ prerelease: false
227
+ version_requirements: !ruby/object:Gem::Requirement
228
+ requirements:
229
+ - - ">="
230
+ - !ruby/object:Gem::Version
231
+ version: '0'
204
232
  - !ruby/object:Gem::Dependency
205
233
  name: activesupport
206
234
  requirement: !ruby/object:Gem::Requirement
@@ -621,7 +649,6 @@ files:
621
649
  - lib/gooddata/commands/scaffold.rb
622
650
  - lib/gooddata/commands/user.rb
623
651
  - lib/gooddata/connection.rb
624
- - lib/gooddata/core/connection.rb
625
652
  - lib/gooddata/core/core.rb
626
653
  - lib/gooddata/core/logging.rb
627
654
  - lib/gooddata/core/nil_logger.rb
@@ -698,6 +725,7 @@ files:
698
725
  - lib/gooddata/models/metadata.rb
699
726
  - lib/gooddata/models/metadata/attribute.rb
700
727
  - lib/gooddata/models/metadata/dashboard.rb
728
+ - lib/gooddata/models/metadata/dataset.rb
701
729
  - lib/gooddata/models/metadata/dimension.rb
702
730
  - lib/gooddata/models/metadata/fact.rb
703
731
  - lib/gooddata/models/metadata/label.rb
@@ -881,7 +909,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
881
909
  version: '0'
882
910
  requirements: []
883
911
  rubyforge_project:
884
- rubygems_version: 2.4.5
912
+ rubygems_version: 2.1.9
885
913
  signing_key:
886
914
  specification_version: 4
887
915
  summary: A convenient Ruby wrapper around the GoodData RESTful API
@@ -1,376 +0,0 @@
1
- # encoding: UTF-8
2
-
3
- require 'multi_json'
4
- require 'rest-client'
5
-
6
- require_relative '../version'
7
-
8
- module GoodData
9
- # # GoodData HTTP wrapper
10
- #
11
- # Provides a convenient HTTP wrapper for talking with the GoodData API.
12
- #
13
- # Remember that the connection is shared amongst the entire application.
14
- # Therefore you can't be logged in to more than _one_ GoodData account.
15
- # per session. Simultaneous connections to multiple GoodData accounts is not
16
- # supported at this time.
17
- #
18
- # The GoodData API is a RESTful API that communicates using JSON. This wrapper
19
- # makes sure that the session is stored between requests and that the JSON is
20
- # parsed both when sending and receiving.
21
- #
22
- # ## Usage
23
- #
24
- # Before a connection can be made to the GoodData API, you have to supply the user credentials like this:
25
- #
26
- # Connection.new(username, password)
27
- #
28
- # To send a HTTP request use either the get, post or delete methods documented below.
29
- #
30
- class Connection
31
- DEFAULT_URL = 'https://secure.gooddata.com'
32
- LOGIN_PATH = '/gdc/account/login'
33
- TOKEN_PATH = '/gdc/account/token'
34
-
35
- attr_reader(:auth_token, :url)
36
- attr_accessor :status, :options
37
-
38
- # Options:
39
- # * :tries - Number of retries to perform. Defaults to 1.
40
- # * :on - The Exception on which a retry will be performed. Defaults to Exception, which retries on any Exception.
41
- #
42
- # ### Example
43
- #
44
- # retryable(:tries => 1, :on => OpenURI::HTTPError) do
45
- # # your code here
46
- # end
47
- #
48
- def retryable(options = {})
49
- opts = { :tries => 1, :on => Exception }.merge(options)
50
-
51
- retry_exception, retries = opts[:on], opts[:tries]
52
-
53
- begin
54
- return yield
55
- rescue retry_exception
56
- retry if (retries -= 1) > 0
57
- end
58
-
59
- yield
60
- end
61
-
62
- # Set the GoodData account credentials.
63
- #
64
- # This have to be performed before any calls to the API.
65
- #
66
- # @param username The GoodData account username
67
- # @param password The GoodData account password
68
- #
69
- def initialize(username, password, options = {})
70
- @status = :not_connected
71
- @username = username
72
- @password = password
73
- @url = options[:server] || DEFAULT_URL
74
- @auth_token = options[:gdc_temporary_token]
75
- @options = options
76
-
77
- @headers = options[:headers] || {}
78
-
79
- default_headers = {
80
- :content_type => :json,
81
- :accept => [:json, :zip],
82
- :user_agent => GoodData.gem_version_string
83
- }
84
- default_headers.merge! @headers
85
-
86
- @server = RestClient::Resource.new @url,
87
- :timeout => @options[:timeout],
88
- :headers => default_headers
89
-
90
- @server = create_server_connection(@url, @options)
91
- end
92
-
93
- # Returns the user JSON object of the currently logged in GoodData user account.
94
- def user
95
- ensure_connection
96
- @user
97
- end
98
-
99
- # Performs a HTTP GET request.
100
- #
101
- # Retuns the JSON response formatted as a Hash object.
102
- #
103
- # @param path The HTTP path on the GoodData server (must be prefixed with a forward slash)
104
- #
105
- # ### Examples
106
- #
107
- # Connection.new(username, password).get '/gdc/projects'
108
- #
109
- def get(path, options = {})
110
- GoodData.logger.debug "GET #{@server}#{path}"
111
- ensure_connection
112
- b = proc { @server[path].get cookies }
113
- process_response(options, &b)
114
- end
115
-
116
- # Performs a HTTP POST request.
117
- #
118
- # Retuns the JSON response formatted as a Hash object.
119
- #
120
- # @param path The HTTP path on the GoodData server (must be prefixed with a forward slash)
121
- # @param data The payload data in the format of a Hash object
122
- #
123
- # ### Examples
124
- #
125
- # Connection.new(username, password).post '/gdc/projects', { ... }
126
- #
127
- def post(path, data, options = {})
128
- GoodData.logger.debug("POST #{@server}#{path}, payload: #{scrub_params(data, [:password, :login, :authorizationToken])}")
129
- ensure_connection
130
- payload = data.is_a?(Hash) ? data.to_json : data
131
- b = proc { @server[path].post payload, cookies }
132
- process_response(options, &b)
133
- end
134
-
135
- # Performs a HTTP PUT request.
136
- #
137
- # Retuns the JSON response formatted as a Hash object.
138
- #
139
- # @param path The HTTP path on the GoodData server (must be prefixed with a forward slash)
140
- # @param data The payload data in the format of a Hash object
141
- #
142
- # ### Examples
143
- #
144
- # Connection.new(username, password).put '/gdc/projects', { ... }
145
- #
146
- def put(path, data, options = {})
147
- payload = data.is_a?(Hash) ? data.to_json : data
148
- GoodData.logger.debug "PUT #{@server}#{path}, payload: #{payload}"
149
- ensure_connection
150
- b = proc { @server[path].put payload, cookies }
151
- process_response(options, &b)
152
- end
153
-
154
- # Performs a HTTP DELETE request.
155
- #
156
- # Retuns the JSON response formatted as a Hash object.
157
- #
158
- # @param path The HTTP path on the GoodData server (must be prefixed with a forward slash)
159
- #
160
- # ### Examples
161
- #
162
- # Connection.new(username, password).delete '/gdc/project/1'
163
- #
164
- def delete(path, options = {})
165
- GoodData.logger.debug "DELETE #{@server}#{path}"
166
- ensure_connection
167
- b = proc { @server[path].delete cookies }
168
- process_response(options, &b)
169
- end
170
-
171
- # Get the cookies associated with the current connection.
172
- def cookies
173
- @cookies ||= { :cookies => {} }
174
- end
175
-
176
- # Set the cookies used when communicating with the GoodData API.
177
- def merge_cookies!(cookies)
178
- self.cookies
179
- @cookies[:cookies].merge! cookies
180
- end
181
-
182
- # Returns true if a connection have been established to the GoodData API
183
- # and the login was successful.
184
- def logged_in?
185
- @status == :logged_in
186
- end
187
-
188
- def url=(url = nil)
189
- @url = url || DEFAULT_URL
190
- @server = create_server_connection(@url, @options)
191
- end
192
-
193
- # The connection will automatically be established once it's needed, which it
194
- # usually is when either the user, get, post or delete method is called. If you
195
- # want to force a connection (or a re-connect) you can use this method.
196
- def connect!
197
- connect
198
- end
199
-
200
- # Uploads a file to GoodData server
201
- # /uploads/ resources are special in that they use a different
202
- # host and a basic authentication.
203
- def upload(file, options = {})
204
- ensure_connection
205
-
206
- dir = options[:directory] || ''
207
- staging_uri = options[:staging_url].to_s
208
- url = dir.empty? ? staging_uri : URI.join(staging_uri, "#{dir}/").to_s
209
-
210
- # Make a directory, if needed
211
- unless dir.empty?
212
- method = :get
213
- GoodData.logger.debug "#{method}: #{url}"
214
- begin
215
- # first check if it does exits
216
- RestClient::Request.execute({
217
- :method => method,
218
- :url => url,
219
- :timeout => @options[:timeout],
220
- :headers => {
221
- :user_agent => GoodData.gem_version_string
222
- }
223
- }.merge(cookies))
224
- rescue RestClient::Exception => e
225
- if e.http_code == 404
226
- method = :mkcol
227
- GoodData.logger.debug "#{method}: #{url}"
228
- RestClient::Request.execute({
229
- :method => method,
230
- :url => url,
231
- :timeout => @options[:timeout],
232
- :headers => {
233
- :user_agent => GoodData.gem_version_string
234
- }
235
- }.merge(cookies))
236
- end
237
- end
238
- end
239
-
240
- payload = options[:stream] ? 'file' : File.read(file)
241
- filename = options[:filename] || options[:stream] ? 'randome-filename.txt' : File.basename(file)
242
-
243
- # Upload the file
244
- # puts "uploading the file #{URI.join(url, filename).to_s}"
245
- req = RestClient::Request.new(
246
- :method => :put,
247
- :url => URI.join(url, filename).to_s,
248
- :timeout => @options[:timeout],
249
- :headers => {
250
- :user_agent => GoodData.gem_version_string
251
- },
252
- :payload => payload,
253
- :raw_response => true,
254
- :user => @username,
255
- :password => @password
256
- )
257
- # .merge(cookies))
258
- req.execute
259
- true
260
- end
261
-
262
- def download(what, where, options = {})
263
- staging_uri = options[:staging_url].to_s
264
- url = staging_uri + what
265
- req = RestClient::Request.new({
266
- :method => 'GET',
267
- :url => url,
268
- :user => @username,
269
- :password => @password
270
- }.merge(cookies))
271
-
272
- if where.is_a?(String)
273
- File.open(where, 'w') do |f|
274
- req.execute do |chunk, _, _|
275
- f.write chunk
276
- end
277
- end
278
- else
279
- # Assume it is a IO stream
280
- req.execute do |chunk, _, _|
281
- where.write chunk
282
- end
283
- end
284
- end
285
-
286
- def connected?
287
- @status == :logged_in
288
- end
289
-
290
- def disconnect
291
- return if !connected? && !GoodData.connection.user['state']
292
- GoodData.delete(GoodData.connection.user['state'])
293
- @status = :not_connected
294
- end
295
-
296
- private
297
-
298
- def create_server_connection(url, options)
299
- RestClient::Resource.new url,
300
- :timeout => options[:timeout],
301
- :headers => {
302
- :content_type => :json,
303
- :accept => [:json, :zip],
304
- :user_agent => GoodData.gem_version_string
305
- }
306
- end
307
-
308
- def ensure_connection
309
- connect if @status == :not_connected
310
- end
311
-
312
- def connect
313
- GoodData.logger.info 'Connecting to GoodData...'
314
- @status = :connecting
315
- authenticate
316
- end
317
-
318
- def authenticate
319
- credentials = {
320
- 'postUserLogin' => {
321
- 'login' => @username,
322
- 'password' => @password,
323
- 'remember' => 1
324
- }
325
- }
326
- GoodData.logger.debug 'Logging in...'
327
- @user = post(LOGIN_PATH, credentials, :dont_reauth => true)['userLogin']
328
- refresh_token :dont_reauth => true # avoid infinite loop if refresh_token fails with 401
329
-
330
- @status = :logged_in
331
- end
332
-
333
- def process_response(options = {}, &block)
334
- begin
335
- response = block.call
336
- rescue RestClient::Unauthorized
337
- raise $ERROR_INFO if options[:dont_reauth]
338
- refresh_token
339
- response = block.call
340
- end
341
- merge_cookies! response.cookies
342
- content_type = response.headers[:content_type]
343
- return response if options[:process] == false
344
-
345
- if content_type == 'application/json' || content_type == 'application/json;charset=UTF-8'
346
- result = response.to_str == '""' ? {} : MultiJson.load(response.to_str)
347
- GoodData.logger.debug "Response: #{result.inspect}"
348
- elsif content_type == 'application/zip'
349
- result = response
350
- GoodData.logger.debug 'Response: a zipped stream'
351
- elsif response.headers[:content_length].to_s == '0'
352
- result = nil
353
- GoodData.logger.debug 'Response: Empty response possibly 204'
354
- elsif response.code == 204
355
- result = nil
356
- GoodData.logger.debug 'Response: 204 no content'
357
- else
358
- fail "Unsupported response content type '%s':\n%s" % [content_type, response.to_str[0..127]]
359
- end
360
- result
361
- rescue RestClient::Exception => e
362
- GoodData.logger.debug "Response: #{e.response}"
363
- raise $ERROR_INFO
364
- end
365
-
366
- def refresh_token(options = {})
367
- GoodData.logger.debug 'Getting authentication token...'
368
- begin
369
- get TOKEN_PATH, :dont_reauth => true # avoid infinite loop GET fails with 401
370
- rescue RestClient::Unauthorized
371
- raise $ERROR_INFO if options[:dont_reauth]
372
- authenticate
373
- end
374
- end
375
- end
376
- end