backup 3.2.0 → 3.3.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +3 -5
- data/lib/backup/archive.rb +11 -1
- data/lib/backup/cli.rb +252 -141
- data/lib/backup/database/base.rb +50 -24
- data/lib/backup/database/mongodb.rb +101 -127
- data/lib/backup/database/mysql.rb +50 -76
- data/lib/backup/database/postgresql.rb +44 -70
- data/lib/backup/database/redis.rb +61 -66
- data/lib/backup/database/riak.rb +64 -43
- data/lib/backup/dependency.rb +1 -1
- data/lib/backup/model.rb +10 -7
- data/lib/backup/storage/cloudfiles.rb +2 -0
- data/lib/backup/storage/cycler.rb +2 -1
- data/lib/backup/storage/dropbox.rb +66 -5
- data/lib/backup/utilities.rb +29 -14
- data/lib/backup/version.rb +1 -1
- data/templates/cli/archive +2 -0
- data/templates/cli/database/mongodb +1 -4
- data/templates/cli/database/mysql +0 -3
- data/templates/cli/database/postgresql +0 -3
- data/templates/cli/database/redis +11 -9
- data/templates/cli/database/riak +11 -14
- metadata +2 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 8030ea8ce771bafd23266be65ddac30e62d9954b
|
4
|
+
data.tar.gz: bc53925b9956147157e9200d4cfb9d8c7886d343
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: b9631215669b56c92b1694d5a1005d5292ae9d3e25dd2da717cfbe40e30af80d6163b38e6662b7c309c2b480d4d69fe953458171c7dcd5fa908a51314d1ab584
|
7
|
+
data.tar.gz: 799f65d322c49d396d9301163412db25369ced068c6260a66fb54444cbd234da73fa07d92c3f6b8e8a58f6bfc241d763c1261d475dc2d3580f6acee02e295cce
|
data/README.md
CHANGED
@@ -68,10 +68,8 @@ $ tar -tvf my_backup.tar
|
|
68
68
|
my_backup/archives/user_avatars.tar.gz
|
69
69
|
my_backup/archives/log_files.tar.gz
|
70
70
|
my_backup/databases/
|
71
|
-
my_backup/databases/PostgreSQL
|
72
|
-
my_backup/databases/
|
73
|
-
my_backup/databases/Redis/
|
74
|
-
my_backup/databases/Redis/redis_db_name.rdb.gz
|
71
|
+
my_backup/databases/PostgreSQL.sql.gz
|
72
|
+
my_backup/databases/Redis.rdb.gz
|
75
73
|
```
|
76
74
|
|
77
75
|
### Storages
|
@@ -200,7 +198,7 @@ Backup::Model.new(:my_backup, 'Description for my_backup') do
|
|
200
198
|
mail.user_name = "sender@email.com"
|
201
199
|
mail.password = "my_password"
|
202
200
|
mail.authentication = "plain"
|
203
|
-
mail.
|
201
|
+
mail.encryption = :starttls
|
204
202
|
end
|
205
203
|
|
206
204
|
notify_by Twitter do |tweet|
|
data/lib/backup/archive.rb
CHANGED
@@ -53,6 +53,7 @@ module Backup
|
|
53
53
|
@model = model
|
54
54
|
@name = name.to_s
|
55
55
|
@options = {
|
56
|
+
:sudo => false,
|
56
57
|
:root => false,
|
57
58
|
:paths => [],
|
58
59
|
:excludes => [],
|
@@ -69,7 +70,7 @@ module Backup
|
|
69
70
|
|
70
71
|
pipeline = Pipeline.new
|
71
72
|
pipeline.add(
|
72
|
-
"#{
|
73
|
+
"#{ tar_command } #{ tar_options } -cPf -#{ tar_root } " +
|
73
74
|
"#{ paths_to_exclude } #{ paths_to_package }",
|
74
75
|
tar_success_codes
|
75
76
|
)
|
@@ -95,6 +96,11 @@ module Backup
|
|
95
96
|
|
96
97
|
private
|
97
98
|
|
99
|
+
def tar_command
|
100
|
+
tar = utility(:tar)
|
101
|
+
options[:sudo] ? "#{ utility(:sudo) } -n #{ tar }" : tar
|
102
|
+
end
|
103
|
+
|
98
104
|
def tar_root
|
99
105
|
options[:root] ? " -C '#{ File.expand_path(options[:root]) }'" : ''
|
100
106
|
end
|
@@ -129,6 +135,10 @@ module Backup
|
|
129
135
|
@options = options
|
130
136
|
end
|
131
137
|
|
138
|
+
def use_sudo(val = true)
|
139
|
+
@options[:sudo] = val
|
140
|
+
end
|
141
|
+
|
132
142
|
def root(path)
|
133
143
|
@options[:root] = path
|
134
144
|
end
|
data/lib/backup/cli.rb
CHANGED
@@ -4,25 +4,17 @@
|
|
4
4
|
# Build the Backup Command Line Interface using Thor
|
5
5
|
module Backup
|
6
6
|
class CLI < Thor
|
7
|
-
include Thor::Actions
|
8
7
|
|
9
8
|
##
|
10
9
|
# [Perform]
|
11
|
-
# Performs the backup process. The only required option is the --trigger [-t].
|
12
|
-
# If the other options (--config-file, --data-path, --cache-path, --tmp-path)
|
13
|
-
# aren't specified they will fallback to the (good) defaults.
|
14
10
|
#
|
11
|
+
# The only required option is the --trigger [-t].
|
12
|
+
# If --config-file, --data-path, --cache-path, --tmp-path aren't specified
|
13
|
+
# they will fallback to defaults defined in Backup::Config.
|
15
14
|
# If --root-path is given, it will be used as the base path for our defaults,
|
16
15
|
# as well as the base path for any option specified as a relative path.
|
17
16
|
# Any option given as an absolute path will be used "as-is".
|
18
17
|
#
|
19
|
-
# If the --check option is given, the config.rb and all model files will be
|
20
|
-
# loaded, but no triggers will be run. If the check fails, errors will be
|
21
|
-
# reported to the console. If the check passes, a success message will be
|
22
|
-
# reported to the console unless --quiet is set. Use --no-quiet to ensure
|
23
|
-
# these messages are output. The command will exit with status 0 if
|
24
|
-
# successful, or status 1 if there were problems.
|
25
|
-
#
|
26
18
|
# This command will exit with one of the following status codes:
|
27
19
|
#
|
28
20
|
# 0: All triggers were successful and no warnings were issued.
|
@@ -30,128 +22,201 @@ module Backup
|
|
30
22
|
# 2: All triggers were processed, but some failed.
|
31
23
|
# 3: A fatal error caused Backup to exit.
|
32
24
|
# Some triggers may not have been processed.
|
25
|
+
#
|
26
|
+
# If the --check option is given, `backup check` will be run
|
27
|
+
# and no triggers will be performed.
|
33
28
|
desc 'perform', "Performs the backup for the specified trigger(s)."
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
method_option :
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
|
29
|
+
|
30
|
+
long_desc <<-EOS.gsub(/^ +/, '')
|
31
|
+
Performs the backup for the specified trigger(s).
|
32
|
+
|
33
|
+
You may perform multiple backups by providing multiple triggers,
|
34
|
+
separated by commas. Each will run in the order specified.
|
35
|
+
|
36
|
+
$ backup perform --triggers backup1,backup2,backup3,backup4
|
37
|
+
|
38
|
+
--root-path may be an absolute path or relative to the current directory.
|
39
|
+
|
40
|
+
To use the current directory, use: `--root-path .`
|
41
|
+
|
42
|
+
Relative paths given for --config-file, --data-path, --log-path,
|
43
|
+
--cache-path and --tmp-path will be relative to --root-path.
|
44
|
+
|
45
|
+
Console log output may be forced using --no-quiet.
|
46
|
+
|
47
|
+
Logging to file or syslog may be disabled using --no-logfile or --no-syslog
|
48
|
+
respectively. This will override logging options set in `config.rb`.
|
49
|
+
EOS
|
50
|
+
|
51
|
+
method_option :trigger,
|
52
|
+
:aliases => ['-t', '--triggers'],
|
53
|
+
:required => true,
|
54
|
+
:type => :string,
|
55
|
+
:desc => "Triggers to perform. e.g. 'trigger_a,trigger_b'"
|
56
|
+
|
57
|
+
method_option :config_file,
|
58
|
+
:aliases => '-c',
|
59
|
+
:type => :string,
|
60
|
+
:default => '',
|
61
|
+
:desc => 'Path to your config.rb file.'
|
62
|
+
|
63
|
+
method_option :root_path,
|
64
|
+
:aliases => '-r',
|
65
|
+
:type => :string,
|
66
|
+
:default => '',
|
67
|
+
:desc => 'Root path to base all relative path on.'
|
68
|
+
|
69
|
+
method_option :data_path,
|
70
|
+
:aliases => '-d',
|
71
|
+
:type => :string,
|
72
|
+
:default => '',
|
73
|
+
:desc => 'Path to store storage cycling data.'
|
74
|
+
|
75
|
+
method_option :log_path,
|
76
|
+
:aliases => '-l',
|
77
|
+
:type => :string,
|
78
|
+
:default => '',
|
79
|
+
:desc => "Path to store Backup's log file."
|
80
|
+
|
81
|
+
method_option :cache_path,
|
82
|
+
:type => :string,
|
83
|
+
:default => '',
|
84
|
+
:desc => "Path to store Dropbox's cached authorization."
|
85
|
+
|
86
|
+
method_option :tmp_path,
|
87
|
+
:type => :string,
|
88
|
+
:default => '',
|
89
|
+
:desc => 'Path to store temporary data during the backup.'
|
90
|
+
|
62
91
|
# Note that :quiet, :syslog and :logfile are specified as :string types,
|
63
92
|
# so the --no-<option> usage will set the value to nil instead of false.
|
64
|
-
method_option :quiet,
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
93
|
+
method_option :quiet,
|
94
|
+
:aliases => '-q',
|
95
|
+
:type => :string,
|
96
|
+
:default => false,
|
97
|
+
:banner => '',
|
98
|
+
:desc => 'Disable console log output.'
|
99
|
+
|
100
|
+
method_option :syslog,
|
101
|
+
:type => :string,
|
102
|
+
:default => false,
|
103
|
+
:banner => '',
|
104
|
+
:desc => 'Enable logging to syslog.'
|
105
|
+
|
106
|
+
method_option :logfile,
|
107
|
+
:type => :string,
|
108
|
+
:default => true,
|
109
|
+
:banner => '',
|
110
|
+
:desc => "Enable Backup's log file."
|
111
|
+
|
112
|
+
method_option :check,
|
113
|
+
:type => :boolean,
|
114
|
+
:default => false,
|
115
|
+
:desc => 'Check configuration for errors or warnings.'
|
75
116
|
|
76
117
|
def perform
|
77
|
-
|
78
|
-
|
118
|
+
check if options[:check] # this will exit()
|
119
|
+
|
79
120
|
models = nil
|
80
121
|
begin
|
81
|
-
##
|
82
122
|
# Set logger options
|
83
123
|
opts = options
|
84
124
|
Logger.configure do
|
85
|
-
console.quiet
|
86
|
-
logfile.enabled
|
87
|
-
logfile.log_path
|
88
|
-
syslog.enabled
|
125
|
+
console.quiet = opts[:quiet]
|
126
|
+
logfile.enabled = opts[:logfile]
|
127
|
+
logfile.log_path = opts[:log_path]
|
128
|
+
syslog.enabled = opts[:syslog]
|
89
129
|
end
|
90
130
|
|
91
|
-
##
|
92
131
|
# Update Config variables
|
93
132
|
# (config_file, root_path, data_path, cache_path, tmp_path)
|
94
133
|
Config.update(options)
|
95
134
|
|
96
|
-
##
|
97
|
-
# Ensure the :cache_path and :tmp_path are created
|
98
|
-
# if they do not yet exist
|
99
|
-
[Config.cache_path, Config.tmp_path].each do |path|
|
100
|
-
FileUtils.mkdir_p(path)
|
101
|
-
end
|
102
|
-
|
103
|
-
##
|
104
135
|
# Load the user's +config.rb+ file (and all their Models).
|
105
|
-
# May update Logger options.
|
136
|
+
# May update Logger (and Config) options.
|
106
137
|
Config.load_config!
|
107
138
|
|
108
|
-
##
|
109
139
|
# Identify all Models to be run for the given +triggers+.
|
110
140
|
triggers = options[:trigger].split(',').map(&:strip)
|
111
141
|
models = triggers.map {|trigger|
|
112
142
|
Model.find_by_trigger(trigger)
|
113
143
|
}.flatten.uniq
|
114
144
|
|
115
|
-
|
116
|
-
|
117
|
-
"No Models found for trigger(s) '#{triggers.join(',')}'."
|
118
|
-
end
|
145
|
+
raise Errors::CLIError, "No Models found for trigger(s) " +
|
146
|
+
"'#{ triggers.join(',') }'." if models.empty?
|
119
147
|
|
120
|
-
|
121
|
-
raise Errors::CLIError, 'Configuration Check has warnings.'
|
122
|
-
end
|
123
|
-
|
124
|
-
##
|
125
|
-
# Finalize Logger configuration and begin real-time logging.
|
148
|
+
# Finalize Logger and begin real-time logging.
|
126
149
|
Logger.start!
|
127
150
|
|
128
151
|
rescue Exception => err
|
129
152
|
Logger.error Errors::CLIError.wrap(err)
|
130
|
-
Logger.error 'Configuration Check Failed.' if options[:check]
|
131
153
|
# Logger configuration will be ignored
|
132
154
|
# and messages will be output to the console only.
|
133
155
|
Logger.abort!
|
134
|
-
exit(
|
156
|
+
exit(3)
|
135
157
|
end
|
136
158
|
|
137
|
-
|
138
|
-
|
159
|
+
# Model#perform! handles all exceptions from this point,
|
160
|
+
# as each model may fail and return here to allow others to run.
|
161
|
+
warnings = errors = false
|
162
|
+
models.each do |model|
|
163
|
+
model.perform!
|
164
|
+
warnings ||= Logger.has_warnings?
|
165
|
+
errors ||= Logger.has_errors?
|
166
|
+
Logger.clear!
|
167
|
+
end
|
168
|
+
exit(errors ? 2 : 1) if errors || warnings
|
169
|
+
end
|
170
|
+
|
171
|
+
##
|
172
|
+
# [Check]
|
173
|
+
#
|
174
|
+
# Loads the user's `config.rb` (and all Model files) and reports any Errors
|
175
|
+
# or Warnings. This is primarily for checking for syntax errors, missing
|
176
|
+
# dependencies and deprecation warnings.
|
177
|
+
#
|
178
|
+
# This may also be invoked using the `--check` option to `backup perform`.
|
179
|
+
#
|
180
|
+
# This command only requires `Config.config_file` to be correct.
|
181
|
+
# All other Config paths are irrelevant.
|
182
|
+
#
|
183
|
+
# All output will be sent to the console only.
|
184
|
+
# Logger options will be ignored.
|
185
|
+
#
|
186
|
+
# If successful, this method with exit(0).
|
187
|
+
# If there are Errors or Warnings, it will exit(1).
|
188
|
+
desc 'check', 'Check for configuration errors or warnings'
|
189
|
+
|
190
|
+
long_desc <<-EOS.gsub(/^ +/, '')
|
191
|
+
Loads your 'config.rb' file and all models and reports any
|
192
|
+
errors or warnings with your configuration, including missing
|
193
|
+
dependencies and the use of any deprecated settings.
|
194
|
+
EOS
|
195
|
+
|
196
|
+
method_option :config_file,
|
197
|
+
:aliases => '-c',
|
198
|
+
:type => :string,
|
199
|
+
:default => '',
|
200
|
+
:desc => "Path to your config.rb file."
|
201
|
+
|
202
|
+
def check
|
203
|
+
begin
|
204
|
+
Config.update(options)
|
205
|
+
Config.load_config!
|
206
|
+
rescue Exception => err
|
207
|
+
Logger.error Errors::CLIError.wrap(err)
|
208
|
+
end
|
209
|
+
|
210
|
+
if Logger.has_warnings? || Logger.has_errors?
|
211
|
+
Logger.error 'Configuration Check Failed.'
|
212
|
+
exit_code = 1
|
139
213
|
else
|
140
|
-
|
141
|
-
|
142
|
-
# clearing the Logger after each job.
|
143
|
-
#
|
144
|
-
# Model#perform! handles all exceptions from this point,
|
145
|
-
# as each model may fail and return here to allow others to run.
|
146
|
-
warnings = errors = false
|
147
|
-
models.each do |model|
|
148
|
-
model.perform!
|
149
|
-
warnings ||= Logger.has_warnings?
|
150
|
-
errors ||= Logger.has_errors?
|
151
|
-
Logger.clear!
|
152
|
-
end
|
153
|
-
exit(errors ? 2 : 1) if errors || warnings
|
214
|
+
Logger.info 'Configuration Check Succeeded.'
|
215
|
+
exit_code = 0
|
154
216
|
end
|
217
|
+
|
218
|
+
Logger.abort!
|
219
|
+
exit(exit_code)
|
155
220
|
end
|
156
221
|
|
157
222
|
##
|
@@ -161,14 +226,28 @@ module Backup
|
|
161
226
|
# $ backup generate:model --trigger my_backup --databases='mongodb'
|
162
227
|
# will generate a pre-populated model with a base MongoDB setup
|
163
228
|
desc 'generate:model', "Generates a Backup model file."
|
164
|
-
long_desc "Generates a Backup model file.\n\n" +
|
165
|
-
"\s\sNote: '--config-path' is the path to the directory where 'config.rb' is located.\n\n" +
|
166
|
-
"\s\sThe model file will be created as '<config_path>/models/<trigger>.rb'\n\n" +
|
167
|
-
"\s\sDefault: #{Config.root_path}\n\n"
|
168
229
|
|
169
|
-
|
170
|
-
|
171
|
-
|
230
|
+
long_desc <<-EOS.gsub(/^ +/, '')
|
231
|
+
Generates a Backup model file.
|
232
|
+
|
233
|
+
'--config-path' is the path to the *directory* where 'config.rb' is located.
|
234
|
+
|
235
|
+
The model file will be created as '<config_path>/models/<trigger>.rb'
|
236
|
+
|
237
|
+
The default location would be:
|
238
|
+
|
239
|
+
#{ Config.root_path }/models/
|
240
|
+
EOS
|
241
|
+
|
242
|
+
method_option :trigger,
|
243
|
+
:aliases => '-t',
|
244
|
+
:required => true,
|
245
|
+
:type => :string,
|
246
|
+
:desc => 'Trigger name for the Backup model'
|
247
|
+
|
248
|
+
method_option :config_path,
|
249
|
+
:type => :string,
|
250
|
+
:desc => 'Path to your Backup configuration directory'
|
172
251
|
|
173
252
|
# options with their available values
|
174
253
|
%w{ databases storages syncers
|
@@ -178,9 +257,13 @@ module Backup
|
|
178
257
|
"(#{Dir[path + '/*'].sort.map {|p| File.basename(p) }.join(', ')})"
|
179
258
|
end
|
180
259
|
|
181
|
-
method_option :archives,
|
182
|
-
|
183
|
-
|
260
|
+
method_option :archives,
|
261
|
+
:type => :boolean,
|
262
|
+
:desc => 'Model will include tar archives.'
|
263
|
+
method_option :splitter,
|
264
|
+
:type => :boolean,
|
265
|
+
:default => true,
|
266
|
+
:desc => "Use `--no-splitter` to disable"
|
184
267
|
|
185
268
|
define_method "generate:model" do
|
186
269
|
opts = options.merge(
|
@@ -193,8 +276,12 @@ module Backup
|
|
193
276
|
config = File.join(config_path, "config.rb")
|
194
277
|
model = File.join(models_path, "#{opts[:trigger]}.rb")
|
195
278
|
|
279
|
+
if File.file?(config_path)
|
280
|
+
abort('--config-path should be a directory, not a file.')
|
281
|
+
end
|
282
|
+
|
196
283
|
FileUtils.mkdir_p(models_path)
|
197
|
-
if overwrite?(model)
|
284
|
+
if Helpers.overwrite?(model)
|
198
285
|
File.open(model, 'w') do |file|
|
199
286
|
file.write(
|
200
287
|
Backup::Template.new({:options => opts}).result("cli/model.erb")
|
@@ -203,7 +290,7 @@ module Backup
|
|
203
290
|
puts "Generated model file: '#{ model }'."
|
204
291
|
end
|
205
292
|
|
206
|
-
|
293
|
+
unless File.exist?(config)
|
207
294
|
File.open(config, "w") do |file|
|
208
295
|
file.write(Backup::Template.new.result("cli/config"))
|
209
296
|
end
|
@@ -215,8 +302,18 @@ module Backup
|
|
215
302
|
# [Generate:Config]
|
216
303
|
# Generates the main configuration file
|
217
304
|
desc 'generate:config', 'Generates the main Backup bootstrap/configuration file'
|
218
|
-
|
219
|
-
|
305
|
+
|
306
|
+
long_desc <<-EOS.gsub(/^ +/, '')
|
307
|
+
Path to your Backup configuration directory.
|
308
|
+
|
309
|
+
Default path would be:
|
310
|
+
|
311
|
+
#{ Config.root_path }
|
312
|
+
EOS
|
313
|
+
|
314
|
+
method_option :config_path,
|
315
|
+
:type => :string,
|
316
|
+
:desc => 'Path to your Backup configuration directory.'
|
220
317
|
|
221
318
|
define_method 'generate:config' do
|
222
319
|
config_path = options[:config_path] ?
|
@@ -224,7 +321,7 @@ module Backup
|
|
224
321
|
config = File.join(config_path, "config.rb")
|
225
322
|
|
226
323
|
FileUtils.mkdir_p(config_path)
|
227
|
-
if overwrite?(config)
|
324
|
+
if Helpers.overwrite?(config)
|
228
325
|
File.open(config, "w") do |file|
|
229
326
|
file.write(Backup::Template.new.result("cli/config"))
|
230
327
|
end
|
@@ -247,13 +344,20 @@ module Backup
|
|
247
344
|
case options[:encryptor].downcase
|
248
345
|
when 'openssl'
|
249
346
|
base64 = options[:base64] ? '-base64' : ''
|
250
|
-
password = options[:password_file].empty? ? '' :
|
347
|
+
password = options[:password_file].empty? ? '' :
|
348
|
+
"-pass file:#{ options[:password_file] }"
|
251
349
|
salt = options[:salt] ? '-salt' : ''
|
252
|
-
|
350
|
+
|
351
|
+
Helpers.exec!(
|
352
|
+
"openssl aes-256-cbc -d #{ base64 } #{ password } #{ salt } " +
|
353
|
+
"-in '#{ options[:in] }' -out '#{ options[:out] }'"
|
354
|
+
)
|
253
355
|
when 'gpg'
|
254
|
-
|
356
|
+
Helpers.exec!(
|
357
|
+
"gpg -o '#{ options[:out] }' -d '#{ options[:in] }'"
|
358
|
+
)
|
255
359
|
else
|
256
|
-
puts "Unknown encryptor: #{options[:encryptor]}"
|
360
|
+
puts "Unknown encryptor: #{ options[:encryptor] }"
|
257
361
|
puts "Use either 'openssl' or 'gpg'."
|
258
362
|
end
|
259
363
|
end
|
@@ -262,24 +366,27 @@ module Backup
|
|
262
366
|
# [Dependencies]
|
263
367
|
# Returns a list of Backup's dependencies
|
264
368
|
desc 'dependencies', 'Display, Check or Install Dependencies for Backup.'
|
265
|
-
|
266
|
-
|
369
|
+
|
370
|
+
long_desc <<-EOS.gsub(/^ +/, '')
|
371
|
+
To display a list of available dependencies, run:
|
372
|
+
|
373
|
+
$ backup dependencies --list
|
374
|
+
|
375
|
+
To install one of these dependencies, run:
|
376
|
+
|
377
|
+
$ backup dependencies --install <name>
|
378
|
+
|
379
|
+
To check if a dependency is already installed, run:
|
380
|
+
|
381
|
+
$ backup dependencies --installed <name>
|
382
|
+
EOS
|
383
|
+
|
384
|
+
method_option :install, :type => :string, :banner => 'NAME'
|
267
385
|
method_option :list, :type => :boolean
|
268
|
-
method_option :installed, :type => :string
|
386
|
+
method_option :installed, :type => :string, :banner => 'NAME'
|
269
387
|
|
270
388
|
def dependencies
|
271
|
-
unless options.any?
|
272
|
-
puts
|
273
|
-
puts "To display a list of available dependencies, run:\n\n"
|
274
|
-
puts " backup dependencies --list"
|
275
|
-
puts
|
276
|
-
puts "To install one of these dependencies (with the correct version), run:\n\n"
|
277
|
-
puts " backup dependencies --install <name>"
|
278
|
-
puts
|
279
|
-
puts "To check if a dependency is already installed, run:\n\n"
|
280
|
-
puts " backup dependencies --installed <name>"
|
281
|
-
exit
|
282
|
-
end
|
389
|
+
Helpers.exec!("#{ $0 } help dependencies") unless options.any?
|
283
390
|
|
284
391
|
if options[:list]
|
285
392
|
deps = Dependency.all
|
@@ -361,23 +468,27 @@ module Backup
|
|
361
468
|
puts "Backup #{Backup::Version.current}"
|
362
469
|
end
|
363
470
|
|
364
|
-
private
|
365
|
-
|
366
|
-
##
|
367
|
-
# Helper method for asking the user if he/she wants to overwrite the file
|
368
|
-
def overwrite?(path)
|
369
|
-
if File.exist?(path)
|
370
|
-
return yes? "A file already exists at '#{ path }'. Do you want to overwrite? [y/n]"
|
371
|
-
end
|
372
|
-
true
|
373
|
-
end
|
374
|
-
|
375
471
|
# This is to avoid Thor's warnings when stubbing methods on the Thor class.
|
376
472
|
module Helpers
|
377
473
|
class << self
|
474
|
+
|
475
|
+
def overwrite?(path)
|
476
|
+
return true unless File.exist?(path)
|
477
|
+
|
478
|
+
$stderr.print "A file already exists at '#{ path }'.\n" +
|
479
|
+
"Do you want to overwrite? [y/n] "
|
480
|
+
/^[Yy]/ =~ $stdin.gets
|
481
|
+
end
|
482
|
+
|
483
|
+
def exec!(cmd)
|
484
|
+
puts "Lauching: #{ cmd }"
|
485
|
+
exec(cmd)
|
486
|
+
end
|
487
|
+
|
378
488
|
def bundler_loaded?
|
379
489
|
!ENV['BUNDLE_GEMFILE'].to_s.empty?
|
380
490
|
end
|
491
|
+
|
381
492
|
end
|
382
493
|
end
|
383
494
|
|