ubalo 0.1 → 0.2
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/bin/ubalo +131 -215
- data/lib/ubalo/account.rb +93 -0
- data/lib/ubalo/pod.rb +99 -0
- data/lib/ubalo/pod_archive.rb +54 -0
- data/lib/ubalo/pod_dir.rb +81 -0
- data/lib/ubalo/task.rb +87 -0
- data/lib/ubalo/util.rb +189 -0
- data/lib/ubalo/version.rb +2 -2
- data/lib/ubalo.rb +9 -321
- metadata +24 -13
data/bin/ubalo
CHANGED
@@ -1,6 +1,8 @@
|
|
1
1
|
#!/usr/bin/env ruby
|
2
2
|
|
3
3
|
require 'gli'
|
4
|
+
include GLI
|
5
|
+
|
4
6
|
require 'yaml'
|
5
7
|
require 'fileutils'
|
6
8
|
|
@@ -8,63 +10,38 @@ require 'highline'
|
|
8
10
|
hl = HighLine.new
|
9
11
|
|
10
12
|
require 'ubalo'
|
11
|
-
|
12
|
-
include GLI
|
13
|
-
|
14
|
-
use_openstruct true
|
15
|
-
|
16
|
-
class Ubalo
|
17
|
-
class << self
|
18
|
-
def config
|
19
|
-
if @config
|
20
|
-
@config
|
21
|
-
elsif File.exists?(config_path)
|
22
|
-
@config = YAML.load_file(config_path)
|
23
|
-
else
|
24
|
-
{}
|
25
|
-
end
|
26
|
-
end
|
27
|
-
|
28
|
-
def write_config new_config
|
29
|
-
h = config.merge(new_config)
|
30
|
-
File.open(config_path, 'w') do |f|
|
31
|
-
YAML.dump(h, f)
|
32
|
-
end
|
33
|
-
config
|
34
|
-
end
|
13
|
+
include Ubalo
|
35
14
|
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
end
|
15
|
+
module Ubalo
|
16
|
+
def config_filename
|
17
|
+
File.expand_path("~/.ubaloconfig")
|
40
18
|
end
|
41
19
|
end
|
42
20
|
|
43
|
-
|
44
|
-
@ubalo
|
45
|
-
end
|
21
|
+
use_openstruct true
|
46
22
|
|
47
|
-
|
48
|
-
|
23
|
+
logger = Util::Logger.new
|
24
|
+
|
25
|
+
def connect_url
|
26
|
+
@connect_url
|
49
27
|
end
|
50
28
|
|
51
|
-
def
|
52
|
-
|
53
|
-
|
54
|
-
pod_name
|
55
|
-
else
|
56
|
-
"#{local_username}/#{pod_name}"
|
57
|
-
end
|
58
|
-
else
|
59
|
-
raise UbaloMessage, "Please specify a pod name"
|
29
|
+
def account
|
30
|
+
unless @account.authorized?
|
31
|
+
raise Ubalo::Error, "Could not find your credentials. Please run ubalo login."
|
60
32
|
end
|
33
|
+
@account
|
61
34
|
end
|
62
35
|
|
63
|
-
def
|
64
|
-
|
65
|
-
|
36
|
+
def pod_dir
|
37
|
+
@pod_dir
|
38
|
+
end
|
39
|
+
|
40
|
+
def pod
|
41
|
+
unless @pod
|
42
|
+
@pod = account.pod_or_create_by_name!(pod_dir.name)
|
66
43
|
end
|
67
|
-
@
|
44
|
+
@pod
|
68
45
|
end
|
69
46
|
|
70
47
|
program_desc 'Command-line access to ubalo.com.'
|
@@ -72,79 +49,74 @@ program_desc 'Command-line access to ubalo.com.'
|
|
72
49
|
desc "Change the connect url"
|
73
50
|
flag 'connect-url'
|
74
51
|
|
75
|
-
desc "
|
76
|
-
|
52
|
+
desc "Override the active pod"
|
53
|
+
flag 'pod'
|
54
|
+
|
55
|
+
desc "Override the active pod directory"
|
56
|
+
flag 'pod-dir'
|
57
|
+
|
58
|
+
desc 'Display version'
|
59
|
+
command :version do |c|
|
60
|
+
c.action do |global_options,options,args|
|
61
|
+
puts Ubalo::VERSION
|
62
|
+
end
|
63
|
+
end
|
77
64
|
|
78
65
|
desc 'Display authentication information'
|
79
66
|
command :whoami do |c|
|
80
67
|
c.action do |global_options,options,args|
|
81
|
-
puts
|
68
|
+
puts "You are logged in as #{account.username}."
|
69
|
+
end
|
70
|
+
end
|
71
|
+
|
72
|
+
desc 'Enter username and password for access'
|
73
|
+
command :login do |c|
|
74
|
+
c.desc "Username"
|
75
|
+
c.flag :username
|
76
|
+
c.desc "Password"
|
77
|
+
c.flag :password
|
78
|
+
|
79
|
+
c.action do |global_options,options,args|
|
80
|
+
unless options[:username] and options[:password]
|
81
|
+
puts "Please enter your Ubalo details for command-line access."
|
82
|
+
end
|
83
|
+
|
84
|
+
login = options[:username] || hl.ask(" login: "){|q| q.echo = true}
|
85
|
+
password = options[:password] || hl.ask(" password: "){|q| q.echo = false}
|
86
|
+
|
87
|
+
@account.authorize(login, password)
|
88
|
+
Util.append_config(Ubalo.config_filename, account.base_url, account.as_hash)
|
89
|
+
logger.puts "Success! Ready to use as #{account.username}."
|
82
90
|
end
|
83
91
|
end
|
84
92
|
|
85
93
|
desc 'Display a list of available pods'
|
86
94
|
command :pods do |c|
|
87
95
|
c.action do |global_options,options,args|
|
88
|
-
pods
|
89
|
-
|
90
|
-
$stderr.puts "You do not currently have any pods."
|
91
|
-
else
|
92
|
-
pods.each do |pod|
|
93
|
-
puts Ubalo.format_pod(pod)
|
94
|
-
end
|
96
|
+
account.pods.each do |pod|
|
97
|
+
puts "#{pod.fullname} #{pod.state} updated #{Util.time_ago_in_words pod.updated_at}"
|
95
98
|
end
|
96
99
|
end
|
97
100
|
end
|
98
101
|
|
99
102
|
desc 'Display tasks'
|
100
103
|
command :tasks do |c|
|
101
|
-
c.desc 'maximum number of tasks to display'
|
102
|
-
c.default_value 20
|
103
|
-
c.flag 'max'
|
104
|
-
|
105
104
|
c.action do |global_options,options,args|
|
106
|
-
|
107
|
-
puts
|
105
|
+
account.tasks.each do |task|
|
106
|
+
puts "#{task.label} (#{task.state}) #{task.pod_name} #{Util.time_ago_in_words task.submitted_at}"
|
108
107
|
end
|
109
108
|
end
|
110
109
|
end
|
111
110
|
|
112
|
-
def process_download pod_response, destination_path=nil
|
113
|
-
name = pod_response.fetch('name')
|
114
|
-
fullname = pod_response.fetch('fullname')
|
115
|
-
pod_url = pod_response.fetch('url')
|
116
|
-
files_url = pod_response.fetch('archive').fetch('get_url')
|
117
|
-
|
118
|
-
destination_path ||= name
|
119
|
-
|
120
|
-
if File.exists?(destination_path)
|
121
|
-
raise UbaloMessage, "directory #{destination_path.inspect} already exists"
|
122
|
-
end
|
123
|
-
|
124
|
-
FileUtils.mkdir(destination_path)
|
125
|
-
FileUtils.mkdir(File.join(destination_path, ".ubalo"))
|
126
|
-
|
127
|
-
ubalo.retrieve_files(destination_path, files_url)
|
128
|
-
|
129
|
-
File.open(File.join(destination_path, ".ubalo", "config"), "w") do |f|
|
130
|
-
f.puts(YAML.dump("pod_url" => pod_url))
|
131
|
-
end
|
132
|
-
|
133
|
-
[fullname, destination_path]
|
134
|
-
end
|
135
|
-
|
136
111
|
desc 'Clone a pod to your computer'
|
137
112
|
arg_name '<pod name>'
|
138
113
|
command :clone do |c|
|
139
114
|
c.action do |global_options,options,args|
|
140
|
-
|
141
|
-
|
142
|
-
|
143
|
-
|
144
|
-
|
145
|
-
|
146
|
-
fullname, destination_path = process_download(pod_response)
|
147
|
-
$stderr.puts " saved to #{destination_path}."
|
115
|
+
pod = account.pod_by_name!(args.shift)
|
116
|
+
pod_dir = PodDir.new(args.shift || pod.name)
|
117
|
+
logger.print "Fetching #{pod.fullname} to #{pod_dir.path}..."
|
118
|
+
pod.clone_to(pod_dir)
|
119
|
+
logger.puts " saved."
|
148
120
|
end
|
149
121
|
end
|
150
122
|
|
@@ -154,179 +126,123 @@ command :delete do |c|
|
|
154
126
|
c.switch :force
|
155
127
|
|
156
128
|
c.action do |global_options,options,args|
|
157
|
-
|
129
|
+
pod = account.pod_by_name!(args.shift)
|
158
130
|
|
159
131
|
if options.force
|
160
|
-
|
132
|
+
pod.delete!
|
161
133
|
else
|
162
134
|
hl.choose do |menu|
|
163
|
-
menu.prompt = "Are you sure you want to delete #{
|
135
|
+
menu.prompt = "Are you sure you want to delete #{pod.fullname}? "
|
164
136
|
menu.choice :yes do
|
165
|
-
|
166
|
-
response = ubalo.delete_pod(pod_name)
|
167
|
-
$stderr.puts " done."
|
137
|
+
pod.delete!
|
168
138
|
end
|
169
139
|
menu.choice :no do
|
170
|
-
raise
|
140
|
+
raise Ubalo::Error, "Cancelled! No changes made to #{pod.fullname}."
|
171
141
|
end
|
172
142
|
end
|
173
143
|
end
|
144
|
+
if pod.deleted?
|
145
|
+
logger.puts "Deleted #{pod.fullname}."
|
146
|
+
end
|
174
147
|
end
|
175
148
|
end
|
176
149
|
|
177
|
-
desc '
|
178
|
-
|
179
|
-
|
150
|
+
desc 'Initialize this directory as a pod directory'
|
151
|
+
command :init do |c|
|
152
|
+
c.desc "Pod name"
|
153
|
+
c.flag :name
|
154
|
+
|
180
155
|
c.action do |global_options,options,args|
|
181
|
-
|
182
|
-
|
183
|
-
|
184
|
-
|
185
|
-
response = ubalo.submit_task(pod_name, arg)
|
186
|
-
task_label = response.fetch('label')
|
187
|
-
result = ubalo.wait_task(task_label)
|
188
|
-
ubalo.show_result(result)
|
156
|
+
name = options[:name] || hl.ask(" pod name: "){|q| q.echo = true}
|
157
|
+
pod = account.pod_or_create_by_name!(name)
|
158
|
+
pod_dir.write_name(pod.fullname)
|
159
|
+
logger.puts "Success! Next, run ubalo push."
|
189
160
|
end
|
190
161
|
end
|
191
162
|
|
192
|
-
desc '
|
193
|
-
|
194
|
-
command :submit do |c|
|
163
|
+
desc 'Run a pod'
|
164
|
+
command :run do |c|
|
195
165
|
c.action do |global_options,options,args|
|
196
|
-
|
197
|
-
|
198
|
-
|
199
|
-
|
200
|
-
|
201
|
-
|
202
|
-
|
166
|
+
logger.puts "Running #{pod.fullname}."
|
167
|
+
task = pod.run(nil)
|
168
|
+
logger.poll_on("Waiting for task #{task.label.inspect}") do
|
169
|
+
task.refresh!
|
170
|
+
task.complete?
|
171
|
+
end
|
172
|
+
puts task.printable_result
|
203
173
|
end
|
204
174
|
end
|
205
175
|
|
206
|
-
desc '
|
207
|
-
|
208
|
-
command :check do |c|
|
176
|
+
desc 'Run a pod in the background'
|
177
|
+
command :submit do |c|
|
209
178
|
c.action do |global_options,options,args|
|
210
|
-
|
211
|
-
|
212
|
-
|
213
|
-
|
214
|
-
$stderr.puts " found."
|
215
|
-
|
216
|
-
ubalo.show_result(result)
|
179
|
+
logger.print "Submitting #{pod.fullname}..."
|
180
|
+
task = pod.run(nil)
|
181
|
+
logger.puts " done."
|
182
|
+
puts task.printable_result
|
217
183
|
end
|
218
184
|
end
|
219
185
|
|
220
|
-
desc '
|
221
|
-
|
186
|
+
desc 'Get the status of a task'
|
187
|
+
arg_name '<task label>'
|
188
|
+
command :task do |c|
|
222
189
|
c.action do |global_options,options,args|
|
223
|
-
|
224
|
-
|
225
|
-
|
226
|
-
|
227
|
-
|
228
|
-
|
229
|
-
|
230
|
-
|
190
|
+
unless label = args.shift
|
191
|
+
raise Ubalo::Error, "please specify a task label"
|
192
|
+
end
|
193
|
+
task = account.task_by_label!(label)
|
194
|
+
logger.print "Getting the status for task #{task.label.inspect}..."
|
195
|
+
task.refresh!
|
196
|
+
logger.puts " found."
|
197
|
+
puts task.printable_result
|
231
198
|
end
|
232
199
|
end
|
233
200
|
|
234
201
|
desc 'Push files to Ubalo'
|
235
202
|
command :push do |c|
|
236
203
|
c.action do |global_options,options,args|
|
237
|
-
|
238
|
-
pod
|
239
|
-
|
240
|
-
|
241
|
-
|
242
|
-
|
243
|
-
|
244
|
-
desc 'Enter username and password for access'
|
245
|
-
command :login do |c|
|
246
|
-
c.desc "Username"
|
247
|
-
c.flag :username
|
248
|
-
c.desc "Password"
|
249
|
-
c.flag :password
|
250
|
-
|
251
|
-
c.action do |global_options,options,args|
|
252
|
-
unless options[:username] and options[:password]
|
253
|
-
puts "Please enter your Ubalo details for command-line access."
|
204
|
+
logger.print "Pushing files to #{pod.fullname.inspect}..."
|
205
|
+
pod.push_from(pod_dir)
|
206
|
+
logger.puts " done."
|
207
|
+
logger.poll_on("Waiting for #{pod.fullname.inspect} to compile") do
|
208
|
+
pod.refresh!
|
209
|
+
pod.compiled?
|
254
210
|
end
|
255
|
-
|
256
|
-
login = options[:username] || hl.ask(" login: "){|q| q.echo = true}
|
257
|
-
password = options[:password] || hl.ask(" password: "){|q| q.echo = false}
|
258
|
-
|
259
|
-
response = ubalo.get_authorization(login, password)
|
260
|
-
ubalo.authorization = response.fetch('authorization')
|
261
|
-
username = response.fetch('username')
|
262
|
-
|
263
|
-
Ubalo.write_config(ubalo.base_url => {'authorization' => ubalo.authorization, 'username' => username})
|
264
|
-
puts "Success! Ready to use as #{username}."
|
265
211
|
end
|
266
212
|
end
|
267
213
|
|
268
|
-
def unauthorized_command?(command)
|
269
|
-
command && [:login, :help].include?(command.name)
|
270
|
-
end
|
271
|
-
|
272
214
|
pre do |global,command,options,args|
|
273
|
-
|
274
|
-
connect_url = global['connect-url'] || config['connect-url'] || "https://ubalo.com"
|
215
|
+
@connect_url = ENV['UBALO_CONNECT_URL'] || "https://ubalo.com"
|
275
216
|
|
276
|
-
|
277
|
-
|
278
|
-
|
279
|
-
|
280
|
-
|
281
|
-
# When logging in, don't use the authorization:
|
282
|
-
unless unauthorized_command?(command)
|
283
|
-
if host_config = config[connect_url]
|
284
|
-
@local_username = host_config['username']
|
285
|
-
authorization = host_config['authorization']
|
286
|
-
end
|
287
|
-
end
|
288
|
-
|
289
|
-
unless authorization or unauthorized_command?(command)
|
290
|
-
raise UbaloMessage, "No credentials found. Please run 'ubalo login'."
|
217
|
+
config = Util.read_config(Ubalo.config_filename)
|
218
|
+
if account_config = config[connect_url]
|
219
|
+
@account = Account.from_hash(account_config)
|
220
|
+
else
|
221
|
+
@account = Account.new(connect_url)
|
291
222
|
end
|
292
223
|
|
293
|
-
|
294
|
-
|
295
|
-
full_path = File.expand_path(local_config_filename)
|
296
|
-
@local_config = YAML.load_file(full_path)
|
224
|
+
if pod_name = global['pod']
|
225
|
+
@pod = account.pod_or_create_by_name!(pod_name)
|
297
226
|
end
|
298
227
|
|
299
|
-
@
|
228
|
+
@pod_dir = PodDir.new(global['pod-dir'] || ".")
|
300
229
|
|
301
230
|
true
|
302
231
|
end
|
303
232
|
|
304
233
|
on_error do |exception|
|
305
|
-
|
234
|
+
logger.complete_line
|
306
235
|
case exception
|
307
|
-
when
|
308
|
-
|
309
|
-
|
310
|
-
when RestClient::ResourceNotFound
|
311
|
-
$stderr.puts exception.inspect
|
312
|
-
false # no additional raise required.
|
313
|
-
when RestClient::Unauthorized, RestClient::Forbidden
|
314
|
-
$stderr.puts "Invalid credentials. Please run ubalo login."
|
315
|
-
true # fall back to GLI's handling
|
316
|
-
when GLI::BadCommandLine
|
317
|
-
true # fall back to GLI's handling
|
318
|
-
when UbaloOKExit
|
319
|
-
# Normal exit, preserving the correct exit code.
|
320
|
-
exit 0
|
321
|
-
when UbaloMessage
|
322
|
-
$stderr.puts "Error: #{exception.message}"
|
236
|
+
when Ubalo::Error, GLI::UnknownCommand
|
237
|
+
logger.complete_line
|
238
|
+
logger.puts "Error: #{exception.message}"
|
323
239
|
exit 1
|
324
240
|
when Interrupt
|
325
|
-
|
241
|
+
logger.complete_line
|
242
|
+
logger.puts "Cancelled!"
|
326
243
|
exit 1
|
327
244
|
else
|
328
|
-
|
329
|
-
raise # and go on to raise
|
245
|
+
raise
|
330
246
|
end
|
331
247
|
end
|
332
248
|
|
@@ -0,0 +1,93 @@
|
|
1
|
+
module Ubalo
|
2
|
+
class Account
|
3
|
+
def self.from_hash(h)
|
4
|
+
account = new h.fetch(:base_url)
|
5
|
+
account.username = h.fetch(:username)
|
6
|
+
account.authorization = h.fetch(:authorization)
|
7
|
+
account
|
8
|
+
end
|
9
|
+
|
10
|
+
attr_accessor :username, :authorization
|
11
|
+
attr_reader :base_url
|
12
|
+
|
13
|
+
def initialize(base_url)
|
14
|
+
@base_url = base_url
|
15
|
+
end
|
16
|
+
|
17
|
+
def authorized?
|
18
|
+
!!@authorization
|
19
|
+
end
|
20
|
+
|
21
|
+
def request method, path = nil, options = {}
|
22
|
+
if authorization
|
23
|
+
options[:authorization] = authorization
|
24
|
+
end
|
25
|
+
Util.http_request(method, "#{@base_url}#{path}", options)
|
26
|
+
end
|
27
|
+
|
28
|
+
def authorize(login, password)
|
29
|
+
response = request(:post, "/user/authorization", :params => {:user => {:login => login, :password => password}})
|
30
|
+
@username = response.fetch("username")
|
31
|
+
@authorization = response.fetch("authorization")
|
32
|
+
rescue RestClient::BadRequest
|
33
|
+
raise Ubalo::Error, "Incorrect login or password"
|
34
|
+
end
|
35
|
+
|
36
|
+
def pod_from_json(pod_json)
|
37
|
+
Pod.create_with_json(self, pod_json)
|
38
|
+
end
|
39
|
+
|
40
|
+
def task_from_json(task_json)
|
41
|
+
Task.create_with_json(self, task_json)
|
42
|
+
end
|
43
|
+
|
44
|
+
def archive_from_json(archive_json)
|
45
|
+
PodArchive.create_with_json(self, archive_json)
|
46
|
+
end
|
47
|
+
|
48
|
+
def pods
|
49
|
+
request(:get, "/pods").map do |pod_json|
|
50
|
+
pod_from_json(pod_json)
|
51
|
+
end
|
52
|
+
end
|
53
|
+
|
54
|
+
def pod_by_name!(name)
|
55
|
+
pod_username, pod_name = Util.normalize_pod_name(username, name)
|
56
|
+
pod = Pod.new(self, pod_username, pod_name, {})
|
57
|
+
pod.refresh!
|
58
|
+
end
|
59
|
+
|
60
|
+
def pod_or_create_by_name!(name)
|
61
|
+
pod_username, pod_name = Util.normalize_pod_name(username, name)
|
62
|
+
pod = Pod.new(self, pod_username, pod_name, {})
|
63
|
+
pod.update!
|
64
|
+
end
|
65
|
+
|
66
|
+
def task_by_label!(label)
|
67
|
+
task = Task.new(self, label, {})
|
68
|
+
task.refresh!
|
69
|
+
end
|
70
|
+
|
71
|
+
def tasks
|
72
|
+
request(:get, "/tasks").map do |task_json|
|
73
|
+
task_from_json(task_json)
|
74
|
+
end
|
75
|
+
end
|
76
|
+
|
77
|
+
def as_hash
|
78
|
+
{
|
79
|
+
:base_url => @base_url,
|
80
|
+
:username => username,
|
81
|
+
:authorization => authorization
|
82
|
+
}
|
83
|
+
end
|
84
|
+
|
85
|
+
def inspect
|
86
|
+
"#<Account #{username} #{base_url} #{'authorized' if authorization}>"
|
87
|
+
end
|
88
|
+
|
89
|
+
def ==(other)
|
90
|
+
[base_url, username, authorization] == [base_url, other.username, other.authorization]
|
91
|
+
end
|
92
|
+
end
|
93
|
+
end
|
data/lib/ubalo/pod.rb
ADDED
@@ -0,0 +1,99 @@
|
|
1
|
+
module Ubalo
|
2
|
+
class Pod
|
3
|
+
include Ubalo::Util
|
4
|
+
|
5
|
+
def self.create_with_json(account, json)
|
6
|
+
new(account, json.fetch('user').fetch('username'), json.fetch('name'), json)
|
7
|
+
end
|
8
|
+
|
9
|
+
attr_reader :username, :name, :state, :archive, :updated_at
|
10
|
+
|
11
|
+
def initialize(account, username, name, attributes)
|
12
|
+
@account = account
|
13
|
+
@username = username
|
14
|
+
@name = name
|
15
|
+
update_attributes(attributes)
|
16
|
+
end
|
17
|
+
|
18
|
+
def update!
|
19
|
+
update_attributes(request(:put))
|
20
|
+
rescue RestClient::ResourceNotFound
|
21
|
+
raise Ubalo::Error, "Could not update pod #{fullname.inspect}"
|
22
|
+
end
|
23
|
+
|
24
|
+
def refresh!
|
25
|
+
update_attributes(request(:get))
|
26
|
+
rescue RestClient::ResourceNotFound
|
27
|
+
raise Ubalo::Error, "Could not find pod #{fullname.inspect}"
|
28
|
+
end
|
29
|
+
|
30
|
+
def fullname
|
31
|
+
"#{@username}/#{@name}"
|
32
|
+
end
|
33
|
+
|
34
|
+
def tasks
|
35
|
+
request(:get, "/tasks").map do |task_json|
|
36
|
+
@account.task_from_json(task_json)
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
def run(arg)
|
41
|
+
params = {
|
42
|
+
:arg_content_type => UbaloJSON.content_type,
|
43
|
+
:arg => UbaloJSON.dump(arg)
|
44
|
+
}
|
45
|
+
@account.task_from_json(request(:post, "/tasks", :params => params))
|
46
|
+
end
|
47
|
+
|
48
|
+
def push_from(pod_dir)
|
49
|
+
new_archive.activate_from(pod_dir)
|
50
|
+
refresh!
|
51
|
+
end
|
52
|
+
|
53
|
+
def clone_to(pod_dir)
|
54
|
+
refresh!
|
55
|
+
archive.extract_to(pod_dir)
|
56
|
+
pod_dir.write_name(fullname)
|
57
|
+
end
|
58
|
+
|
59
|
+
def compiled?
|
60
|
+
state == 'compiled'
|
61
|
+
end
|
62
|
+
|
63
|
+
def delete!
|
64
|
+
request(:delete, nil, :parse => false)
|
65
|
+
@deleted = true
|
66
|
+
end
|
67
|
+
|
68
|
+
def deleted?
|
69
|
+
!!@deleted
|
70
|
+
end
|
71
|
+
|
72
|
+
def inspect
|
73
|
+
"#<Pod #{fullname.inspect} state=#{state.inspect}>"
|
74
|
+
end
|
75
|
+
|
76
|
+
def ==(other)
|
77
|
+
fullname == other.fullname
|
78
|
+
end
|
79
|
+
|
80
|
+
private
|
81
|
+
def update_attributes(attributes)
|
82
|
+
@state = attributes['state']
|
83
|
+
if archive_attr = attributes['archive']
|
84
|
+
@archive = @account.archive_from_json(archive_attr)
|
85
|
+
end
|
86
|
+
@updated_at = attributes['updated_at']
|
87
|
+
@deleted = false
|
88
|
+
self
|
89
|
+
end
|
90
|
+
|
91
|
+
def new_archive
|
92
|
+
@account.archive_from_json(request(:post, "/archives"))
|
93
|
+
end
|
94
|
+
|
95
|
+
def request method, path = nil, options = {}
|
96
|
+
@account.request(method, "/pods/#{fullname}#{path}", options)
|
97
|
+
end
|
98
|
+
end
|
99
|
+
end
|