gooddata 0.6.0 → 0.6.2
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +13 -5
- data/.rubocop.yml +23 -0
- data/.travis.yml +9 -4
- data/CLI.md +439 -0
- data/Gemfile +0 -1
- data/README.md +2 -2
- data/Rakefile +60 -8
- data/doc/templates/default/module/setup.rb +1 -1
- data/examples.rb +2 -0
- data/gooddata +2 -0
- data/gooddata.gemspec +12 -8
- data/lib/gooddata.rb +0 -2
- data/lib/gooddata/bricks/base_downloader.rb +52 -47
- data/lib/gooddata/bricks/brick.rb +20 -31
- data/lib/gooddata/bricks/bricks.rb +1 -1
- data/lib/gooddata/bricks/middleware/base_middleware.rb +9 -7
- data/lib/gooddata/bricks/middleware/bench_middleware.rb +12 -10
- data/lib/gooddata/bricks/middleware/bulk_salesforce_middleware.rb +28 -28
- data/lib/gooddata/bricks/middleware/fs_upload_middleware.rb +20 -16
- data/lib/gooddata/bricks/middleware/gooddata_middleware.rb +21 -19
- data/lib/gooddata/bricks/middleware/logger_middleware.rb +10 -8
- data/lib/gooddata/bricks/middleware/restforce_middleware.rb +36 -34
- data/lib/gooddata/bricks/middleware/stdout_middleware.rb +11 -9
- data/lib/gooddata/bricks/middleware/twitter_middleware.rb +14 -12
- data/lib/gooddata/bricks/pipeline.rb +28 -0
- data/lib/gooddata/bricks/utils.rb +10 -8
- data/lib/gooddata/cli/cli.rb +1 -6
- data/lib/gooddata/cli/commands/auth_cmd.rb +1 -1
- data/lib/gooddata/cli/commands/console_cmd.rb +7 -5
- data/lib/gooddata/cli/commands/domain_cmd.rb +45 -0
- data/lib/gooddata/cli/commands/process_cmd.rb +42 -5
- data/lib/gooddata/cli/commands/project_cmd.rb +96 -36
- data/lib/gooddata/cli/commands/projects_cmd.rb +21 -0
- data/lib/gooddata/cli/commands/role_cmd.rb +28 -0
- data/lib/gooddata/cli/commands/run_ruby_cmd.rb +5 -5
- data/lib/gooddata/cli/commands/scaffold_cmd.rb +1 -1
- data/lib/gooddata/cli/commands/{profile_cmd.rb → user_cmd.rb} +7 -9
- data/lib/gooddata/cli/shared.rb +3 -2
- data/lib/gooddata/client.rb +16 -304
- data/lib/gooddata/commands/api.rb +13 -5
- data/lib/gooddata/commands/auth.rb +47 -40
- data/lib/gooddata/commands/base.rb +4 -2
- data/lib/gooddata/commands/commands.rb +1 -1
- data/lib/gooddata/commands/datasets.rb +20 -7
- data/lib/gooddata/commands/domain.rb +23 -0
- data/lib/gooddata/commands/process.rb +23 -117
- data/lib/gooddata/commands/project.rb +147 -0
- data/lib/gooddata/commands/projects.rb +8 -102
- data/lib/gooddata/commands/role.rb +26 -0
- data/lib/gooddata/commands/runners.rb +41 -38
- data/lib/gooddata/commands/scaffold.rb +46 -43
- data/lib/gooddata/commands/user.rb +33 -0
- data/lib/gooddata/connection.rb +43 -353
- data/lib/gooddata/core/connection.rb +389 -0
- data/lib/gooddata/core/core.rb +5 -4
- data/lib/gooddata/core/logging.rb +48 -0
- data/lib/gooddata/core/nil_logger.rb +13 -0
- data/lib/gooddata/core/project.rb +70 -0
- data/lib/gooddata/core/rest.rb +120 -0
- data/lib/gooddata/core/threaded.rb +14 -0
- data/lib/gooddata/core/user.rb +19 -0
- data/lib/gooddata/data/data.rb +2 -1
- data/lib/gooddata/data/guesser.rb +16 -12
- data/lib/gooddata/exceptions/command_failed.rb +1 -1
- data/lib/gooddata/exceptions/exceptions.rb +2 -1
- data/lib/gooddata/exceptions/no_project_error.rb +11 -0
- data/lib/gooddata/exceptions/project_not_found.rb +1 -1
- data/lib/gooddata/extensions/big_decimal.rb +6 -2
- data/lib/gooddata/extract.rb +10 -8
- data/lib/gooddata/goodzilla/goodzilla.rb +61 -59
- data/lib/gooddata/helpers.rb +15 -9
- data/lib/gooddata/models/account_settings.rb +124 -0
- data/lib/gooddata/models/attributes/anchor.rb +37 -0
- data/lib/gooddata/models/attributes/attributes.rb +8 -0
- data/lib/gooddata/models/attributes/date_attribute.rb +25 -0
- data/lib/gooddata/models/attributes/time_attribute.rb +24 -0
- data/lib/gooddata/models/columns/attribute.rb +71 -0
- data/lib/gooddata/models/columns/columns.rb +8 -0
- data/lib/gooddata/models/columns/date_column.rb +63 -0
- data/lib/gooddata/models/columns/fact_model.rb +54 -0
- data/lib/gooddata/models/columns/label.rb +55 -0
- data/lib/gooddata/models/columns/reference.rb +57 -0
- data/lib/gooddata/models/dashboard_builder.rb +26 -0
- data/lib/gooddata/models/data_result.rb +10 -9
- data/lib/gooddata/models/domain.rb +131 -0
- data/lib/gooddata/models/empty_result.rb +5 -8
- data/lib/gooddata/models/facts/facts.rb +8 -0
- data/lib/gooddata/models/facts/time_fact.rb +20 -0
- data/lib/gooddata/models/folders/attribute_folder.rb +20 -0
- data/lib/gooddata/models/folders/fact_folder.rb +20 -0
- data/lib/gooddata/models/folders/folders.rb +8 -0
- data/lib/gooddata/models/invitation.rb +78 -0
- data/lib/gooddata/models/links.rb +6 -6
- data/lib/gooddata/models/md_object.rb +25 -0
- data/lib/gooddata/models/metadata.rb +160 -62
- data/lib/gooddata/models/metadata/attribute.rb +81 -0
- data/lib/gooddata/models/metadata/column.rb +61 -0
- data/lib/gooddata/models/{dashboard.rb → metadata/dashboard.rb} +12 -7
- data/lib/gooddata/models/{data_set.rb → metadata/data_set.rb} +5 -4
- data/lib/gooddata/models/metadata/date_dimension.rb +26 -0
- data/lib/gooddata/models/metadata/display_form.rb +61 -0
- data/lib/gooddata/models/metadata/fact.rb +36 -0
- data/lib/gooddata/models/metadata/folder.rb +24 -0
- data/lib/gooddata/models/metadata/metadata.rb +8 -0
- data/lib/gooddata/models/metadata/metric.rb +197 -0
- data/lib/gooddata/models/metadata/report.rb +115 -0
- data/lib/gooddata/models/{report_definition.rb → metadata/report_definition.rb} +16 -10
- data/lib/gooddata/models/metadata/schema.rb +227 -0
- data/lib/gooddata/models/model.rb +38 -1339
- data/lib/gooddata/models/models.rb +5 -2
- data/lib/gooddata/models/module_constants.rb +29 -0
- data/lib/gooddata/models/process.rb +142 -13
- data/lib/gooddata/models/profile.rb +4 -6
- data/lib/gooddata/models/project.rb +406 -136
- data/lib/gooddata/models/project_blueprint.rb +221 -0
- data/lib/gooddata/models/project_builder.rb +136 -0
- data/lib/gooddata/models/project_creator.rb +138 -0
- data/lib/gooddata/models/project_metadata.rb +11 -10
- data/lib/gooddata/models/project_role.rb +92 -0
- data/lib/gooddata/models/references/date_reference.rb +44 -0
- data/lib/gooddata/models/references/references.rb +8 -0
- data/lib/gooddata/models/references/time_reference.rb +13 -0
- data/lib/gooddata/models/report_data_result.rb +11 -11
- data/lib/gooddata/models/schedule.rb +284 -0
- data/lib/gooddata/models/schema_blueprint.rb +158 -0
- data/lib/gooddata/models/schema_builder.rb +81 -0
- data/lib/gooddata/models/tab_builder.rb +23 -0
- data/lib/gooddata/models/user.rb +165 -0
- data/lib/gooddata/version.rb +1 -1
- data/lib/templates/project/data/devs.csv +1 -1
- data/lib/templates/project/data/repos.csv +1 -1
- data/lib/templates/project/model/model.rb.erb +7 -11
- data/spec/bricks/bricks_spec.rb +2 -0
- data/spec/data/test-ci-data.csv +2 -0
- data/spec/data/test_project_model_spec.json +7 -27
- data/spec/helpers/blueprint_helper.rb +2 -0
- data/spec/helpers/cli_helper.rb +2 -0
- data/spec/helpers/connection_helper.rb +14 -1
- data/spec/helpers/project_helper.rb +16 -0
- data/spec/helpers/schema_helper.rb +16 -0
- data/spec/integration/command_projects_spec.rb +7 -7
- data/spec/integration/create_from_template_spec.rb +2 -2
- data/spec/integration/full_project_spec.rb +160 -7
- data/spec/integration/partial_md_export_import_spec.rb +3 -3
- data/spec/logging_in_logging_out_spec.rb +2 -1
- data/spec/spec_helper.rb +26 -4
- data/spec/unit/bricks/bricks_spec.rb +15 -7
- data/spec/unit/bricks/middleware/bench_middleware_spec.rb +2 -0
- data/spec/unit/bricks/middleware/bulk_salesforce_middleware_spec.rb +2 -0
- data/spec/unit/bricks/middleware/gooddata_middleware_spec.rb +2 -0
- data/spec/unit/bricks/middleware/logger_middleware_spec.rb +2 -0
- data/spec/unit/bricks/middleware/restforce_middleware_spec.rb +2 -0
- data/spec/unit/bricks/middleware/stdout_middleware_spec.rb +2 -0
- data/spec/unit/bricks/middleware/twitter_middleware_spec.rb +2 -0
- data/spec/unit/cli/cli_spec.rb +2 -0
- data/spec/unit/cli/commands/cmd_api_spec.rb +23 -15
- data/spec/unit/cli/commands/cmd_auth_spec.rb +8 -4
- data/spec/unit/cli/commands/cmd_domain_spec.rb +82 -0
- data/spec/unit/cli/commands/cmd_process_spec.rb +29 -13
- data/spec/unit/cli/commands/cmd_project_spec.rb +51 -30
- data/spec/unit/cli/commands/cmd_role_spec.rb +44 -0
- data/spec/unit/cli/commands/cmd_run_ruby_spec.rb +8 -4
- data/spec/unit/cli/commands/cmd_scaffold_spec.rb +48 -11
- data/spec/unit/cli/commands/cmd_user_spec.rb +29 -0
- data/spec/unit/commands/command_api_spec.rb +1 -1
- data/spec/unit/commands/command_auth_spec.rb +100 -18
- data/spec/unit/commands/command_dataset_spec.rb +4 -0
- data/spec/unit/commands/command_process_spec.rb +9 -4
- data/spec/unit/commands/command_projects_spec.rb +10 -6
- data/spec/unit/commands/command_scaffold_spec.rb +5 -1
- data/spec/unit/commands/command_user_spec.rb +22 -0
- data/spec/unit/core/connection_spec.rb +35 -6
- data/spec/unit/core/logging_spec.rb +65 -0
- data/spec/unit/core/nil_logger_spec.rb +9 -0
- data/spec/unit/core/project_spec.rb +51 -0
- data/spec/unit/core/rest_spec.rb +33 -0
- data/spec/unit/data/guesser_spec.rb +5 -0
- data/spec/unit/godzilla/goodzilla_spec.rb +2 -0
- data/spec/unit/models/account_settings_spec.rb +28 -0
- data/spec/unit/models/anchor_spec.rb +32 -0
- data/spec/unit/models/attribute_column_spec.rb +7 -0
- data/spec/unit/models/domain_spec.rb +45 -0
- data/spec/unit/models/invitation_spec.rb +13 -0
- data/spec/unit/models/md_object_spec.rb +47 -0
- data/spec/unit/models/metric.rb +92 -0
- data/spec/unit/{model → models}/model_spec.rb +9 -7
- data/spec/unit/models/project_blueprint_spec.rb +202 -0
- data/spec/unit/models/project_creator.rb +73 -0
- data/spec/unit/models/project_role_spec.rb +90 -0
- data/spec/unit/models/project_spec.rb +143 -0
- data/spec/unit/models/schedule_spec.rb +491 -0
- data/spec/unit/{model → models}/schema_builder_spec.rb +2 -0
- data/spec/unit/{model → models}/tools_spec.rb +13 -7
- data/spec/unit/models/user_spec.rb +16 -0
- data/test/test_upload.rb +2 -0
- metadata +189 -86
- data/lib/gooddata/commands/profile.rb +0 -11
- data/lib/gooddata/models/attribute.rb +0 -29
- data/lib/gooddata/models/display_form.rb +0 -9
- data/lib/gooddata/models/fact.rb +0 -19
- data/lib/gooddata/models/metric.rb +0 -99
- data/lib/gooddata/models/report.rb +0 -89
- data/spec/data/blueprint_valid.json +0 -37
- data/spec/unit/cli/commands/cmd_profile_spec.rb +0 -16
- data/spec/unit/commands/command_profile_spec.rb +0 -18
- data/spec/unit/core/core_spec.rb +0 -7
- data/spec/unit/model/blueprint_spec.rb +0 -132
- data/spec/unit/model/project_blueprint_spec.rb +0 -44
@@ -0,0 +1,29 @@
|
|
1
|
+
# encoding: UTF-8
|
2
|
+
|
3
|
+
module GoodData
|
4
|
+
module Model
|
5
|
+
# GoodData REST API categories
|
6
|
+
LDM_CTG = 'ldm'
|
7
|
+
LDM_MANAGE_CTG = 'ldm-manage2'
|
8
|
+
|
9
|
+
# Model naming conventions
|
10
|
+
FIELD_PK = 'id'
|
11
|
+
FK_SUFFIX = '_id'
|
12
|
+
FACT_COLUMN_PREFIX = 'f_'
|
13
|
+
DATE_COLUMN_PREFIX = 'dt_'
|
14
|
+
TIME_COLUMN_PREFIX = 'tm_'
|
15
|
+
LABEL_COLUMN_PREFIX = 'nm_'
|
16
|
+
ATTRIBUTE_FOLDER_PREFIX = 'dim'
|
17
|
+
ATTRIBUTE_PREFIX = 'attr'
|
18
|
+
LABEL_PREFIX = 'label'
|
19
|
+
FACT_PREFIX = 'fact'
|
20
|
+
DATE_FACT_PREFIX = 'dt'
|
21
|
+
DATE_ATTRIBUTE = 'date'
|
22
|
+
DATE_ATTRIBUTE_DEFAULT_DISPLAY_FORM = 'mdyy'
|
23
|
+
TIME_FACT_PREFIX = 'tm.dt'
|
24
|
+
TIME_ATTRIBUTE_PREFIX = 'attr.time'
|
25
|
+
FACT_FOLDER_PREFIX = 'ffld'
|
26
|
+
|
27
|
+
SKIP_FIELD = false
|
28
|
+
end
|
29
|
+
end
|
@@ -4,49 +4,178 @@ require 'pry'
|
|
4
4
|
|
5
5
|
module GoodData
|
6
6
|
class Process
|
7
|
+
attr_reader :data
|
8
|
+
|
7
9
|
class << self
|
8
|
-
def [](id)
|
10
|
+
def [](id, options = {})
|
9
11
|
if id == :all
|
10
12
|
uri = "/gdc/projects/#{GoodData.project.pid}/dataload/processes"
|
11
|
-
GoodData.get(uri)
|
13
|
+
data = GoodData.get(uri)
|
14
|
+
data['processes']['items'].map do |process_data|
|
15
|
+
Process.new(process_data)
|
16
|
+
end
|
12
17
|
else
|
13
18
|
uri = "/gdc/projects/#{GoodData.project.pid}/dataload/processes/#{id}"
|
14
|
-
|
19
|
+
new(GoodData.get(uri))
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
def all
|
24
|
+
Process[:all]
|
25
|
+
end
|
26
|
+
|
27
|
+
# TODO: Check the params.
|
28
|
+
def with_deploy(dir, options = {}, &block)
|
29
|
+
# verbose = options[:verbose] || false
|
30
|
+
GoodData.with_project(options[:project_id]) do |project|
|
31
|
+
params = options[:params].nil? ? [] : [options[:params]]
|
32
|
+
if block
|
33
|
+
begin
|
34
|
+
res = GoodData::Process.deploy(dir, options.merge(:files_to_exclude => params))
|
35
|
+
block.call(res)
|
36
|
+
ensure
|
37
|
+
res.delete if res
|
38
|
+
end
|
39
|
+
else
|
40
|
+
GoodData::Process.deploy(dir, options.merge(:files_to_exclude => params))
|
41
|
+
end
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
def upload_package(dir, files_to_exclude)
|
46
|
+
Tempfile.open('deploy-graph-archive') do |temp|
|
47
|
+
Zip::OutputStream.open(temp.path) do |zio|
|
48
|
+
FileUtils.cd(dir) do
|
49
|
+
|
50
|
+
files_to_pack = Dir.glob('./**/*').reject { |f| files_to_exclude.include?(Pathname(dir) + f) }
|
51
|
+
files_to_pack.each do |item|
|
52
|
+
# puts "including #{item}" if verbose
|
53
|
+
unless File.directory?(item)
|
54
|
+
zio.put_next_entry(item)
|
55
|
+
zio.print IO.read(item)
|
56
|
+
end
|
57
|
+
end
|
58
|
+
end
|
59
|
+
end
|
60
|
+
GoodData.upload_to_user_webdav(temp.path)
|
61
|
+
temp
|
15
62
|
end
|
16
63
|
end
|
64
|
+
|
65
|
+
def deploy(dir, options = {})
|
66
|
+
dir = Pathname(dir) || fail('Directory is not specified')
|
67
|
+
fail "\"#{dir}\" is not a directory" unless dir.directory?
|
68
|
+
files_to_exclude = options[:files_to_exclude].map { |p| Pathname(p) }
|
69
|
+
process_id = options[:process_id]
|
70
|
+
|
71
|
+
type = options[:type] || 'GRAPH'
|
72
|
+
deploy_name = options[:name]
|
73
|
+
verbose = options[:verbose] || false
|
74
|
+
puts HighLine.color("Deploying #{dir}", HighLine::BOLD) if verbose
|
75
|
+
deployed_path = Process.upload_package(dir, files_to_exclude)
|
76
|
+
data = {
|
77
|
+
:process => {
|
78
|
+
:name => deploy_name,
|
79
|
+
:path => "/uploads/#{File.basename(deployed_path.path)}",
|
80
|
+
:type => type
|
81
|
+
}
|
82
|
+
}
|
83
|
+
res = if process_id.nil?
|
84
|
+
GoodData.post("/gdc/projects/#{GoodData.project.pid}/dataload/processes", data)
|
85
|
+
else
|
86
|
+
GoodData.put("/gdc/projects/#{GoodData.project.pid}/dataload/processes/#{process_id}", data)
|
87
|
+
end
|
88
|
+
process = Process.new(res)
|
89
|
+
puts HighLine.color("Deploy DONE #{dir}", HighLine::GREEN) if verbose
|
90
|
+
process
|
91
|
+
end
|
17
92
|
end
|
18
93
|
|
19
94
|
def initialize(data)
|
20
95
|
@data = data
|
21
96
|
end
|
22
97
|
|
98
|
+
def delete
|
99
|
+
GoodData.delete(uri)
|
100
|
+
end
|
101
|
+
|
102
|
+
def deploy(dir, options = {})
|
103
|
+
process = Process.upload(dir, options.merge(:process_id => process_id))
|
104
|
+
puts HighLine.color("Deploy DONE #{dir}", HighLine::GREEN) if verbose
|
105
|
+
process
|
106
|
+
end
|
107
|
+
|
108
|
+
def process
|
109
|
+
raw_data['process']
|
110
|
+
end
|
111
|
+
|
112
|
+
def name
|
113
|
+
process['name']
|
114
|
+
end
|
115
|
+
|
116
|
+
def type
|
117
|
+
process['type'].downcase.to_sym
|
118
|
+
end
|
119
|
+
|
23
120
|
def links
|
24
|
-
|
121
|
+
process['links']
|
25
122
|
end
|
26
123
|
|
27
124
|
def link
|
28
125
|
links['self']
|
29
126
|
end
|
127
|
+
alias_method :uri, :link
|
128
|
+
|
129
|
+
def obj_id
|
130
|
+
uri.split('/').last
|
131
|
+
end
|
132
|
+
|
133
|
+
alias_method :process_id, :obj_id
|
30
134
|
|
31
135
|
def executions_link
|
32
136
|
links['executions']
|
33
137
|
end
|
34
138
|
|
35
|
-
def
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
139
|
+
def graphs
|
140
|
+
process['graphs']
|
141
|
+
end
|
142
|
+
|
143
|
+
def executables
|
144
|
+
process['executables']
|
145
|
+
end
|
146
|
+
|
147
|
+
def schedules
|
148
|
+
res = []
|
149
|
+
|
150
|
+
scheds = GoodData::Schedule[:all]
|
151
|
+
scheds['schedules']['items'].each do |item|
|
152
|
+
if item['schedule']['params']['PROCESS_ID'] == obj_id
|
153
|
+
res << GoodData::Schedule.new(item)
|
154
|
+
end
|
155
|
+
end
|
156
|
+
|
157
|
+
res
|
158
|
+
end
|
159
|
+
|
160
|
+
alias_method :raw_data, :data
|
161
|
+
|
162
|
+
def execute(executable, options = {})
|
163
|
+
params = options[:params] || {}
|
164
|
+
hidden_params = options[:hidden_params] || {}
|
165
|
+
result = GoodData.post(executions_link,
|
166
|
+
:execution => {
|
167
|
+
:graph => executable.to_s,
|
168
|
+
:params => params,
|
169
|
+
:hiddenParams => hidden_params
|
170
|
+
})
|
42
171
|
begin
|
43
172
|
GoodData.poll(result, 'executionTask')
|
44
173
|
rescue RestClient::RequestFailed => e
|
45
|
-
|
174
|
+
raise(e)
|
46
175
|
ensure
|
47
176
|
result = GoodData.get(result['executionTask']['links']['detail'])
|
48
177
|
if result['executionDetail']['status'] == 'ERROR'
|
49
|
-
fail "Runing process failed. You can look at a log here #{result[
|
178
|
+
fail "Runing process failed. You can look at a log here #{result["executionDetail"]["logFileName"]}"
|
50
179
|
end
|
51
180
|
end
|
52
181
|
result
|
@@ -3,7 +3,7 @@
|
|
3
3
|
module GoodData
|
4
4
|
class Profile
|
5
5
|
private_class_method :new
|
6
|
-
attr_reader :user
|
6
|
+
attr_reader :user, :json
|
7
7
|
|
8
8
|
class << self
|
9
9
|
def load
|
@@ -16,11 +16,9 @@ module GoodData
|
|
16
16
|
@json['accountSetting']['links']['projects']
|
17
17
|
end
|
18
18
|
|
19
|
-
|
20
|
-
@json
|
21
|
-
end
|
19
|
+
alias_method :to_json, :json
|
22
20
|
|
23
|
-
def [](key)
|
21
|
+
def [](key, options = {})
|
24
22
|
@json['accountSetting'][key]
|
25
23
|
end
|
26
24
|
|
@@ -31,4 +29,4 @@ module GoodData
|
|
31
29
|
@user = @json['accountSetting']['firstName'] + ' ' + @json['accountSetting']['lastName']
|
32
30
|
end
|
33
31
|
end
|
34
|
-
end
|
32
|
+
end
|
@@ -3,17 +3,19 @@
|
|
3
3
|
require 'zip'
|
4
4
|
require 'fileutils'
|
5
5
|
|
6
|
-
|
7
|
-
|
8
|
-
|
6
|
+
require_relative 'process'
|
7
|
+
require_relative '../exceptions/no_project_error'
|
8
|
+
require_relative 'project_role'
|
9
9
|
|
10
|
+
module GoodData
|
10
11
|
class Project
|
11
12
|
USERSPROJECTS_PATH = '/gdc/account/profile/%s/projects'
|
12
13
|
PROJECTS_PATH = '/gdc/projects'
|
13
14
|
PROJECT_PATH = '/gdc/projects/%s'
|
14
15
|
SLIS_PATH = '/ldm/singleloadinterface'
|
16
|
+
DEFAULT_INVITE_MESSAGE = 'Join us!'
|
15
17
|
|
16
|
-
attr_accessor :connection
|
18
|
+
attr_accessor :connection, :json
|
17
19
|
|
18
20
|
class << self
|
19
21
|
# Returns an array of all projects accessible by
|
@@ -31,13 +33,13 @@ module GoodData
|
|
31
33
|
# - /gdc/projects/<id>
|
32
34
|
# - <id>
|
33
35
|
#
|
34
|
-
def [](id)
|
35
|
-
return id if id.respond_to?(:
|
36
|
+
def [](id, options = {})
|
37
|
+
return id if id.respond_to?(:project?) && id.project?
|
36
38
|
if id == :all
|
37
39
|
Project.all
|
38
40
|
else
|
39
|
-
if id.to_s !~
|
40
|
-
|
41
|
+
if id.to_s !~ %r{^(\/gdc\/(projects|md)\/)?[a-zA-Z\d]+$}
|
42
|
+
fail(ArgumentError, 'wrong type of argument. Should be either project ID or path')
|
41
43
|
end
|
42
44
|
|
43
45
|
id = id.match(/[a-zA-Z\d]+$/)[0] if id =~ /\//
|
@@ -57,103 +59,45 @@ module GoodData
|
|
57
59
|
GoodData.logger.info "Creating project #{attributes[:title]}"
|
58
60
|
|
59
61
|
auth_token = attributes[:auth_token] || GoodData.connection.auth_token
|
60
|
-
fail
|
61
|
-
|
62
|
-
json = {
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
62
|
+
fail 'You have to provide your token for creating projects as :auth_token parameter' if auth_token.nil? || auth_token.empty?
|
63
|
+
|
64
|
+
json = {
|
65
|
+
'project' =>
|
66
|
+
{
|
67
|
+
'meta' => {
|
68
|
+
'title' => attributes[:title],
|
69
|
+
'summary' => attributes[:summary] || 'No summary'
|
70
|
+
},
|
71
|
+
'content' => {
|
72
|
+
'guidedNavigation' => attributes[:guided_navigation] || 1,
|
73
|
+
'authorizationToken' => auth_token,
|
74
|
+
'driver' => attributes[:driver] || 'Pg'
|
75
|
+
}
|
76
|
+
}
|
77
|
+
}
|
78
|
+
|
79
|
+
json['project']['meta']['projectTemplate'] = attributes[:template] if attributes[:template] && !attributes[:template].empty?
|
76
80
|
project = Project.new json
|
77
81
|
project.save
|
78
82
|
|
79
83
|
# until it is enabled or deleted, recur. This should still end if there is a exception thrown out from RESTClient. This sometimes happens from WebApp when request is too long
|
80
|
-
while project.state.to_s !=
|
81
|
-
if project.state.to_s ==
|
84
|
+
while project.state.to_s != 'enabled'
|
85
|
+
if project.state.to_s == 'deleted'
|
82
86
|
# if project is switched to deleted state, fail. This is usually problem of creating a template which is invalid.
|
83
|
-
fail
|
87
|
+
fail 'Project was marked as deleted during creation. This usually means you were trying to create from template and it failed.'
|
84
88
|
end
|
85
89
|
sleep(3)
|
86
90
|
project.reload!
|
87
91
|
end
|
88
92
|
|
89
93
|
if block
|
90
|
-
GoodData
|
94
|
+
GoodData.with_project(project) do |p|
|
91
95
|
block.call(p)
|
92
96
|
end
|
93
97
|
end
|
98
|
+
sleep 3
|
94
99
|
project
|
95
100
|
end
|
96
|
-
|
97
|
-
end
|
98
|
-
|
99
|
-
def initialize(json)
|
100
|
-
@json = json
|
101
|
-
end
|
102
|
-
|
103
|
-
def save
|
104
|
-
response = GoodData.post PROJECTS_PATH, raw_data
|
105
|
-
if uri == nil
|
106
|
-
response = GoodData.get response['uri']
|
107
|
-
@json = response
|
108
|
-
end
|
109
|
-
end
|
110
|
-
|
111
|
-
def saved?
|
112
|
-
!!uri
|
113
|
-
end
|
114
|
-
|
115
|
-
def reload!
|
116
|
-
if saved?
|
117
|
-
response = GoodData.get(uri)
|
118
|
-
@json = response
|
119
|
-
end
|
120
|
-
self
|
121
|
-
end
|
122
|
-
|
123
|
-
def delete
|
124
|
-
raise "Project '#{title}' with id #{uri} is already deleted" if state == :deleted
|
125
|
-
GoodData.delete(uri)
|
126
|
-
end
|
127
|
-
|
128
|
-
def uri
|
129
|
-
data['links']['self'] if data && data['links'] && data['links']['self']
|
130
|
-
end
|
131
|
-
|
132
|
-
def browser_uri(options={})
|
133
|
-
ui = options[:ui]
|
134
|
-
if ui
|
135
|
-
GoodData.connection.url + '#s=' + uri
|
136
|
-
else
|
137
|
-
GoodData.connection.url + uri
|
138
|
-
end
|
139
|
-
end
|
140
|
-
|
141
|
-
def obj_id
|
142
|
-
uri.split('/').last
|
143
|
-
end
|
144
|
-
|
145
|
-
alias :pid :obj_id
|
146
|
-
|
147
|
-
def title
|
148
|
-
data['meta']['title'] if data['meta']
|
149
|
-
end
|
150
|
-
|
151
|
-
def state
|
152
|
-
data['content']['state'].downcase.to_sym if data['content'] && data['content']['state']
|
153
|
-
end
|
154
|
-
|
155
|
-
def md
|
156
|
-
@md ||= Links.new GoodData.get(data['links']['metadata'])
|
157
101
|
end
|
158
102
|
|
159
103
|
# Creates a data set within the project
|
@@ -167,44 +111,119 @@ module GoodData
|
|
167
111
|
builder = block.call(Model::SchemaBuilder.new(schema_def))
|
168
112
|
builder.to_schema
|
169
113
|
else
|
170
|
-
sch = {:title => schema_def, :columns => columns} if columns
|
114
|
+
sch = { :title => schema_def, :columns => columns } if columns
|
171
115
|
sch = Model::Schema.new schema_def if schema_def.is_a? Hash
|
172
116
|
sch = schema_def if schema_def.is_a?(Model::Schema)
|
173
|
-
|
117
|
+
fail(ArgumentError, 'Required either schema object or title plus columns array') unless schema_def.is_a? Model::Schema
|
174
118
|
sch
|
175
119
|
end
|
176
120
|
Model.add_schema(schema, self)
|
177
121
|
end
|
178
122
|
|
179
|
-
def add_metric(options={})
|
180
|
-
|
123
|
+
def add_metric(options = {})
|
124
|
+
options[:expression] || fail('Metric has to have its expression defined')
|
181
125
|
m1 = GoodData::Metric.create(options)
|
182
126
|
m1.save
|
183
127
|
end
|
184
128
|
|
185
|
-
def add_report(options={})
|
129
|
+
def add_report(options = {})
|
186
130
|
rep = GoodData::Report.create(options)
|
187
131
|
rep.save
|
188
132
|
end
|
189
133
|
|
190
|
-
|
191
|
-
|
192
|
-
|
134
|
+
# Gets author of project
|
135
|
+
#
|
136
|
+
# @return [String] Project author
|
137
|
+
def author
|
138
|
+
# TODO: Return object instead
|
139
|
+
@json['project']['meta']['author']
|
193
140
|
end
|
194
141
|
|
142
|
+
# Adds user to project
|
143
|
+
#
|
144
|
+
# TODO: Discuss with @fluke777 if is not #invite sufficient
|
195
145
|
def add_user(email_address, domain)
|
196
|
-
|
146
|
+
fail 'Not implemented'
|
197
147
|
end
|
198
148
|
|
199
|
-
|
200
|
-
|
149
|
+
# Returns web interface URI of project
|
150
|
+
#
|
151
|
+
# @return [String] Project URL
|
152
|
+
def browser_uri(options = {})
|
153
|
+
grey = options[:grey]
|
154
|
+
if grey
|
155
|
+
GoodData.connection.url + uri
|
156
|
+
else
|
157
|
+
GoodData.connection.url + '#s=' + uri
|
158
|
+
end
|
201
159
|
end
|
202
160
|
|
203
|
-
|
204
|
-
|
161
|
+
# Clones project
|
162
|
+
#
|
163
|
+
# @return [GoodData::Project] Newly created project
|
164
|
+
def clone(options = {})
|
165
|
+
# TODO: Refactor so if export or import fails the new_project will be cleaned
|
166
|
+
with_data = options[:data] || true
|
167
|
+
with_users = options[:users] || false
|
168
|
+
title = options[:title] || "Clone of #{title}"
|
169
|
+
|
170
|
+
# Create the project first so we know that it is passing. What most likely is wrong is the tokena and the export actaully takes majoiryt of the time
|
171
|
+
new_project = GoodData::Project.create(options.merge(:title => title))
|
172
|
+
|
173
|
+
export = {
|
174
|
+
:exportProject => {
|
175
|
+
:exportUsers => with_users ? 1 : 0,
|
176
|
+
:exportData => with_data ? 1 : 0
|
177
|
+
}
|
178
|
+
}
|
205
179
|
|
206
|
-
|
207
|
-
|
180
|
+
result = GoodData.post("/gdc/md/#{obj_id}/maintenance/export", export)
|
181
|
+
export_token = result['exportArtifact']['token']
|
182
|
+
status_url = result['exportArtifact']['status']['uri']
|
183
|
+
|
184
|
+
state = GoodData.get(status_url)['taskState']['status']
|
185
|
+
while state == 'RUNNING'
|
186
|
+
sleep 5
|
187
|
+
result = GoodData.get(status_url)
|
188
|
+
state = result['taskState']['status']
|
189
|
+
end
|
190
|
+
|
191
|
+
import = {
|
192
|
+
:importProject => {
|
193
|
+
:token => export_token
|
194
|
+
}
|
195
|
+
}
|
196
|
+
|
197
|
+
result = GoodData.post("/gdc/md/#{new_project.obj_id}/maintenance/import", import)
|
198
|
+
status_url = result['uri']
|
199
|
+
state = GoodData.get(status_url)['taskState']['status']
|
200
|
+
while state == 'RUNNING'
|
201
|
+
sleep 5
|
202
|
+
result = GoodData.get(status_url)
|
203
|
+
state = result['taskState']['status']
|
204
|
+
end
|
205
|
+
new_project
|
206
|
+
end
|
207
|
+
|
208
|
+
# Project contributor
|
209
|
+
#
|
210
|
+
# @return [String] Project contributor
|
211
|
+
# TODO: Return as object
|
212
|
+
def contributor
|
213
|
+
# TODO: Return object instead
|
214
|
+
@json['project']['meta']['contributor']
|
215
|
+
end
|
216
|
+
|
217
|
+
# Gets the date when created
|
218
|
+
#
|
219
|
+
# @return [DateTime] Date time when created
|
220
|
+
def created
|
221
|
+
DateTime.parse(@json['meta']['created'])
|
222
|
+
end
|
223
|
+
|
224
|
+
# Gets ruby wrapped raw project JSON data
|
225
|
+
def data
|
226
|
+
raw_data['project']
|
208
227
|
end
|
209
228
|
|
210
229
|
def datasets
|
@@ -215,67 +234,318 @@ module GoodData
|
|
215
234
|
end
|
216
235
|
end
|
217
236
|
|
218
|
-
|
219
|
-
|
237
|
+
# Deletes project
|
238
|
+
def delete
|
239
|
+
fail "Project '#{title}' with id #{uri} is already deleted" if state == :deleted
|
240
|
+
GoodData.delete(uri)
|
220
241
|
end
|
221
242
|
|
222
|
-
|
223
|
-
|
243
|
+
# Deletes dashboards for project
|
244
|
+
def delete_dashboards
|
245
|
+
Dashboard.all.map { |data| Dashboard[data['link']] }.each { |d| d.delete }
|
224
246
|
end
|
225
247
|
|
248
|
+
# Gets project role by its identifier
|
249
|
+
#
|
250
|
+
# @param [String] role_name Title of role to look for
|
251
|
+
# @return [GoodData::ProjectRole] Project role if found
|
252
|
+
def get_role_by_identifier(role_name)
|
253
|
+
tmp = roles
|
254
|
+
tmp.each do |role|
|
255
|
+
return role if role.identifier.downcase == role_name.downcase
|
256
|
+
end
|
257
|
+
nil
|
258
|
+
end
|
259
|
+
|
260
|
+
# Gets project role byt its summary
|
261
|
+
#
|
262
|
+
# @param [String] role_summary Summary of role to look for
|
263
|
+
# @return [GoodData::ProjectRole] Project role if found
|
264
|
+
def get_role_by_summary(role_summary)
|
265
|
+
tmp = roles
|
266
|
+
tmp.each do |role|
|
267
|
+
return role if role.summary.downcase == role_summary.downcase
|
268
|
+
end
|
269
|
+
nil
|
270
|
+
end
|
271
|
+
|
272
|
+
# Gets project role by its name
|
273
|
+
#
|
274
|
+
# @param [String] role_title Title of role to look for
|
275
|
+
# @return [GoodData::ProjectRole] Project role if found
|
276
|
+
def get_role_by_title(role_title)
|
277
|
+
tmp = roles
|
278
|
+
tmp.each do |role|
|
279
|
+
return role if role.title.downcase == role_title.downcase
|
280
|
+
end
|
281
|
+
nil
|
282
|
+
end
|
283
|
+
|
284
|
+
# Initializes object instance from raw wire JSON
|
285
|
+
#
|
286
|
+
# @param json Json used for initialization
|
287
|
+
def initialize(json)
|
288
|
+
@json = json
|
289
|
+
end
|
290
|
+
|
291
|
+
# Invites new user to project
|
292
|
+
#
|
293
|
+
# @param email [String] User to be invited
|
294
|
+
# @param role [String] Role URL or Role ID to be used
|
295
|
+
# @param msg [String] Optional invite message
|
296
|
+
#
|
297
|
+
# TODO: Return invite object
|
298
|
+
def invite(email, role, msg = DEFAULT_INVITE_MESSAGE)
|
299
|
+
puts "Inviting #{email}, role: #{role}"
|
300
|
+
|
301
|
+
role_url = nil
|
302
|
+
if role.index('/gdc/') != 0
|
303
|
+
tmp = get_role_by_identifier(role)
|
304
|
+
tmp = get_role_by_title(role) if tmp.nil?
|
305
|
+
role_url = tmp['url'] if tmp
|
306
|
+
else
|
307
|
+
role_url = role if role_url.nil?
|
308
|
+
end
|
309
|
+
|
310
|
+
data = {
|
311
|
+
:invitations => [
|
312
|
+
{
|
313
|
+
:invitation => {
|
314
|
+
:content => {
|
315
|
+
:email => email,
|
316
|
+
:role => role_url,
|
317
|
+
:action => {
|
318
|
+
:setMessage => msg
|
319
|
+
}
|
320
|
+
}
|
321
|
+
}
|
322
|
+
}
|
323
|
+
]
|
324
|
+
}
|
325
|
+
|
326
|
+
url = "/gdc/projects/#{pid}/invitations"
|
327
|
+
GoodData.post(url, data)
|
328
|
+
end
|
329
|
+
|
330
|
+
# Returns invitations to project
|
331
|
+
#
|
332
|
+
# @return [Array<GoodData::Invitation>] List of invitations
|
333
|
+
def invitations
|
334
|
+
res = []
|
335
|
+
|
336
|
+
tmp = GoodData.get @json['project']['links']['invitations']
|
337
|
+
tmp['invitations'].each do |invitation|
|
338
|
+
res << GoodData::Invitation.new(invitation)
|
339
|
+
end
|
340
|
+
|
341
|
+
res
|
342
|
+
end
|
343
|
+
|
344
|
+
# Returns project related links
|
345
|
+
#
|
346
|
+
# @return [Hash] Project related links
|
226
347
|
def links
|
227
348
|
data['links']
|
228
349
|
end
|
229
350
|
|
230
|
-
def
|
231
|
-
|
351
|
+
def md
|
352
|
+
@md ||= Links.new GoodData.get(data['links']['metadata'])
|
232
353
|
end
|
233
354
|
|
234
|
-
|
235
|
-
|
355
|
+
# Gets raw resource ID
|
356
|
+
#
|
357
|
+
# @return [String] Raw resource ID
|
358
|
+
def obj_id
|
359
|
+
uri.split('/').last
|
236
360
|
end
|
237
361
|
|
238
|
-
|
362
|
+
alias_method :pid, :obj_id
|
363
|
+
|
364
|
+
def partial_md_export(objects, options = {})
|
239
365
|
# TODO: refactor polling to md_polling in client
|
240
366
|
|
241
|
-
fail
|
367
|
+
fail 'Nothing to migrate. You have to pass list of objects, ids or uris that you would like to migrate' if objects.nil? || objects.empty?
|
368
|
+
fail 'The objects to migrate has to be provided as an array' unless objects.is_a?(Array)
|
369
|
+
|
242
370
|
target_project = options[:project]
|
243
|
-
fail
|
371
|
+
fail 'You have to provide a project instance or project pid to migrate to' if target_project.nil?
|
244
372
|
target_project = GoodData::Project[target_project]
|
245
|
-
objects = objects.map {|obj| GoodData::MdObject[obj]}
|
246
|
-
GoodData.logging_on
|
373
|
+
objects = objects.map { |obj| GoodData::MdObject[obj] }
|
247
374
|
export_payload = {
|
248
|
-
|
249
|
-
|
250
|
-
|
375
|
+
:partialMDExport => {
|
376
|
+
:uris => objects.map { |obj| obj.uri }
|
377
|
+
}
|
251
378
|
}
|
252
379
|
result = GoodData.post("#{GoodData.project.md['maintenance']}/partialmdexport", export_payload)
|
253
|
-
polling_url = result[
|
254
|
-
token = result[
|
380
|
+
polling_url = result['partialMDArtifact']['status']['uri']
|
381
|
+
token = result['partialMDArtifact']['token']
|
255
382
|
|
256
|
-
polling_result = GoodData.
|
257
|
-
|
258
|
-
|
259
|
-
end
|
260
|
-
fail "Exporting objects failed" if polling_result["wTaskStatus"]["poll"]["status"] == "ERROR"
|
383
|
+
polling_result = GoodData.wait_for_polling_result(polling_url)
|
384
|
+
|
385
|
+
fail 'Exporting objects failed' if polling_result['wTaskStatus']['status'] == 'ERROR'
|
261
386
|
|
262
387
|
import_payload = {
|
263
|
-
|
264
|
-
|
265
|
-
|
266
|
-
|
388
|
+
:partialMDImport => {
|
389
|
+
:token => token,
|
390
|
+
:overwriteNewer => '1',
|
391
|
+
:updateLDMObjects => '0'
|
267
392
|
}
|
268
393
|
}
|
269
394
|
|
270
395
|
result = GoodData.post("#{target_project.md['maintenance']}/partialmdimport", import_payload)
|
271
|
-
|
272
|
-
polling_result = GoodData.
|
273
|
-
|
274
|
-
|
396
|
+
polling_url = result['uri']
|
397
|
+
polling_result = GoodData.wait_for_polling_result(polling_url)
|
398
|
+
|
399
|
+
fail 'Exporting objects failed' if polling_result['wTaskStatus']['status'] == 'ERROR'
|
400
|
+
end
|
401
|
+
|
402
|
+
alias_method :transfer_objects, :partial_md_export
|
403
|
+
|
404
|
+
# Checks if this object instance is project
|
405
|
+
#
|
406
|
+
# @return [Boolean] Return true for all instances
|
407
|
+
def project?
|
408
|
+
true
|
409
|
+
end
|
410
|
+
|
411
|
+
# Forces project to reload
|
412
|
+
def reload!
|
413
|
+
if saved?
|
414
|
+
response = GoodData.get(uri)
|
415
|
+
@json = response
|
275
416
|
end
|
276
|
-
|
417
|
+
self
|
418
|
+
end
|
419
|
+
|
420
|
+
# Gets the list or project roles
|
421
|
+
#
|
422
|
+
# @return [Array<GoodData::ProjectRole>] List of roles
|
423
|
+
def roles
|
424
|
+
url = "/gdc/projects/#{pid}/roles"
|
277
425
|
|
426
|
+
res = []
|
427
|
+
|
428
|
+
tmp = GoodData.get(url)
|
429
|
+
tmp['projectRoles']['roles'].each do |role_url|
|
430
|
+
json = GoodData.get role_url
|
431
|
+
res << GoodData::ProjectRole.new(json)
|
432
|
+
end
|
433
|
+
|
434
|
+
res
|
435
|
+
end
|
436
|
+
|
437
|
+
# Saves project
|
438
|
+
def save
|
439
|
+
response = GoodData.post PROJECTS_PATH, raw_data
|
440
|
+
if uri.nil?
|
441
|
+
response = GoodData.get response['uri']
|
442
|
+
@json = response
|
443
|
+
end
|
444
|
+
end
|
445
|
+
|
446
|
+
# Checks if is project saved
|
447
|
+
#
|
448
|
+
# @return [Boolean] True if saved, false if not
|
449
|
+
def saved?
|
450
|
+
res = uri.nil?
|
451
|
+
!res
|
452
|
+
end
|
453
|
+
|
454
|
+
# Gets project schedules
|
455
|
+
#
|
456
|
+
# @return [Array<GoodData::Schedule>] List of schedules
|
457
|
+
def schedules
|
458
|
+
res = []
|
459
|
+
tmp = GoodData.get @json['project']['links']['schedules']
|
460
|
+
tmp['schedules']['items'].each do |schedule|
|
461
|
+
res << GoodData::Schedule.new(schedule)
|
462
|
+
end
|
463
|
+
res
|
464
|
+
end
|
465
|
+
|
466
|
+
# Gets SLIs data
|
467
|
+
#
|
468
|
+
# @return [GoodData::Metadata] SLI Metadata
|
469
|
+
def slis
|
470
|
+
link = "#{data['links']['metadata']}#{SLIS_PATH}"
|
471
|
+
|
472
|
+
# TODO: Review what to do with passed extra argument
|
473
|
+
Metadata.new GoodData.get(link)
|
474
|
+
end
|
475
|
+
|
476
|
+
# Gets project state
|
477
|
+
#
|
478
|
+
# @return [String] Project state
|
479
|
+
def state
|
480
|
+
data['content']['state'].downcase.to_sym if data['content'] && data['content']['state']
|
481
|
+
end
|
482
|
+
|
483
|
+
# Gets project summary
|
484
|
+
#
|
485
|
+
# @return [String] Project summary
|
486
|
+
def summary
|
487
|
+
data['meta']['summary'] if data['meta']
|
488
|
+
end
|
489
|
+
|
490
|
+
# Gets project title
|
491
|
+
#
|
492
|
+
# @return [String] Project title
|
493
|
+
def title
|
494
|
+
data['meta']['title'] if data['meta']
|
495
|
+
end
|
496
|
+
|
497
|
+
# Gets project update date
|
498
|
+
#
|
499
|
+
# @return [DateTime] Date time of last update
|
500
|
+
def updated
|
501
|
+
DateTime.parse(@json['meta']['updated'])
|
502
|
+
end
|
503
|
+
|
504
|
+
# Uploads file to project
|
505
|
+
#
|
506
|
+
# @param file File to be uploaded
|
507
|
+
# @param schema Schema to be used
|
508
|
+
def upload(file, schema, mode = 'FULL')
|
509
|
+
schema.upload file, self, mode
|
510
|
+
end
|
511
|
+
|
512
|
+
def uri
|
513
|
+
data['links']['self'] if data && data['links'] && data['links']['self']
|
514
|
+
end
|
515
|
+
|
516
|
+
# List of users in project
|
517
|
+
#
|
518
|
+
# @return [Array<GoodData::User>] List of users
|
519
|
+
def users
|
520
|
+
res = []
|
521
|
+
|
522
|
+
tmp = GoodData.get @json['project']['links']['users']
|
523
|
+
tmp['users'].map do |user|
|
524
|
+
res << GoodData::User.new(user)
|
525
|
+
end
|
526
|
+
|
527
|
+
res
|
528
|
+
end
|
529
|
+
|
530
|
+
# Run validation on project
|
531
|
+
# Valid settins for validation are (default all):
|
532
|
+
# ldm - Checks the consistency of LDM objects.
|
533
|
+
# pdm Checks LDM to PDM mapping consistency, also checks PDM reference integrity.
|
534
|
+
# metric_filter - Checks metadata for inconsistent metric filters.
|
535
|
+
# invalid_objects - Checks metadata for invalid/corrupted objects.
|
536
|
+
# asyncTask response
|
537
|
+
def validate(filters = %w(ldm, pdm, metric_filter, invalid_objects))
|
538
|
+
response = GoodData.post "#{GoodData.project.md['validate-project']}", 'validateProject' => filters
|
539
|
+
polling_link = response['asyncTask']['link']['poll']
|
540
|
+
polling_result = GoodData.get(polling_link)
|
541
|
+
while polling_result['wTaskStatus'] && polling_result['wTaskStatus']['status'] == 'RUNNING'
|
542
|
+
sleep(3)
|
543
|
+
polling_result = GoodData.get(polling_link)
|
544
|
+
end
|
545
|
+
polling_result
|
278
546
|
end
|
279
547
|
|
548
|
+
alias_method :to_json, :json
|
549
|
+
alias_method :raw_data, :json
|
280
550
|
end
|
281
551
|
end
|