capistrano-ops 0.2.3 → 0.2.4
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.
- checksums.yaml +4 -4
- data/.rubocop.yml +21 -0
- data/README.md +58 -19
- data/capistrano-ops.gemspec +5 -5
- data/lib/capistrano/ops/backup/api.rb +35 -33
- data/lib/capistrano/ops/backup/s3.rb +47 -44
- data/lib/capistrano/ops/backup.rb +4 -3
- data/lib/capistrano/ops/capistrano/v3/tasks/backup/backup_helper.rb +50 -0
- data/lib/capistrano/ops/capistrano/v3/tasks/backup/database/create.rake +18 -0
- data/lib/capistrano/ops/capistrano/v3/tasks/backup/database/pull.rake +28 -0
- data/lib/capistrano/ops/capistrano/v3/tasks/backup/storage/create.rake +18 -0
- data/lib/capistrano/ops/capistrano/v3/tasks/backup/storage/pull.rake +30 -0
- data/lib/capistrano/ops/capistrano/v3/tasks/backup.rake +10 -14
- data/lib/capistrano/ops/capistrano/v3/tasks/figaro_yml.rake +59 -60
- data/lib/capistrano/ops/capistrano/v3/tasks/invoke.rake +16 -17
- data/lib/capistrano/ops/capistrano.rb +2 -0
- data/lib/capistrano/ops/notification/api.rb +29 -25
- data/lib/capistrano/ops/notification/slack.rb +65 -59
- data/lib/capistrano/ops/notification/webhook.rb +43 -36
- data/lib/capistrano/ops/notification.rb +4 -2
- data/lib/capistrano/ops/railtie.rb +1 -1
- data/lib/capistrano/ops/tasks/pg/dump.rake +16 -19
- data/lib/capistrano/ops/tasks/pg/remove_old_dumps.rake +30 -10
- data/lib/capistrano/ops/tasks/storage/backup.rake +56 -61
- data/lib/capistrano/ops/tasks/storage/remove_old_backups.rake +48 -31
- data/lib/capistrano/ops/version.rb +2 -1
- data/lib/capistrano/ops.rb +19 -19
- metadata +30 -13
@@ -1,38 +1,58 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
2
|
|
3
|
+
require 'rake'
|
3
4
|
namespace :pg do
|
4
5
|
@backup_path = Rails.root.join(Rails.env.development? ? 'tmp/backups' : '../../shared/backups').to_s
|
5
6
|
@database = Rails.configuration.database_configuration[Rails.env]['database']
|
6
|
-
@
|
7
|
+
@env_local_no = ENV['NUMBER_OF_LOCAL_BACKUPS']
|
8
|
+
@env_external_no = ENV['NUMBER_OF_EXTERNAL_BACKUPS']
|
9
|
+
@total_local_backups_no = (@env_local_no || ENV['NUMBER_OF_BACKUPS'] || 7).to_i
|
10
|
+
@total_external_backups_no = (@env_external_no || ENV['NUMBER_OF_BACKUPS'] || 7).to_i
|
7
11
|
backups_enabled = Rails.env.production? || ENV['BACKUPS_ENABLED'] == 'true'
|
12
|
+
external_backup = Rails.env.production? || ENV['EXTERNAL_BACKUP_ENABLED'] == 'true'
|
8
13
|
|
9
14
|
task :remove_old_dumps do
|
10
15
|
bash_regex = "'#{@database}.{0,}\.dump'"
|
11
16
|
|
12
|
-
unless backups_enabled
|
13
|
-
|
17
|
+
unless backups_enabled
|
18
|
+
puts 'remove_old_dumps: Backups are disabled'
|
14
19
|
exit(0)
|
15
20
|
end
|
21
|
+
unless @total_local_backups_no.positive?
|
22
|
+
puts "remove_old_dumps: No local cleanup because option '#{if @env_local_no
|
23
|
+
'NUMBER_OF_LOCAL_BACKUPS='
|
24
|
+
else
|
25
|
+
'NUMBER_OF_BACKUPS='
|
26
|
+
end}#{@total_local_backups_no}' sets unlimited backups"
|
27
|
+
|
28
|
+
end
|
16
29
|
|
17
|
-
|
18
30
|
commandlist = [
|
19
31
|
"cd #{@backup_path} && ls -lt ",
|
20
32
|
"grep -E -i #{bash_regex} ",
|
21
|
-
"tail -n +#{@
|
33
|
+
"tail -n +#{@total_local_backups_no + 1} ",
|
22
34
|
"awk '{print $9}' ",
|
23
|
-
|
35
|
+
'xargs rm -rf'
|
24
36
|
]
|
25
37
|
|
26
38
|
system(commandlist.join(' | '))
|
27
39
|
|
28
|
-
if ENV['BACKUP_PROVIDER'].present?
|
40
|
+
if ENV['BACKUP_PROVIDER'].present? && external_backup
|
41
|
+
unless @total_external_backups_no.positive?
|
42
|
+
puts "remove_old_dumps: No external cleanup because option '#{if @env_external_no
|
43
|
+
'NUMBER_OF_EXTERNAL_BACKUPS='
|
44
|
+
else
|
45
|
+
'NUMBER_OF_BACKUPS='
|
46
|
+
end}#{@total_external_backups_no}' sets unlimited backups"
|
47
|
+
exit(0)
|
48
|
+
end
|
29
49
|
provider = Backup::Api.new
|
30
50
|
begin
|
31
|
-
result = provider.remove_old_backups(@database, @
|
51
|
+
result = provider.remove_old_backups(@database, @total_external_backups_no)
|
32
52
|
rescue StandardError => e
|
33
|
-
|
53
|
+
puts "remove_old_dumps failed: #{e.message}"
|
34
54
|
end
|
35
|
-
|
55
|
+
puts 'remove_old_dumps finished' if result
|
36
56
|
end
|
37
57
|
end
|
38
58
|
end
|
@@ -1,71 +1,66 @@
|
|
1
|
+
# frozen_string_literal: true
|
1
2
|
|
3
|
+
# rubocop:disable Metrics/BlockLength
|
2
4
|
namespace :storage do
|
3
|
-
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
desc 'backup storage'
|
8
|
-
task :backup do
|
9
|
-
unless backups_enabled
|
10
|
-
puts 'storage: Backups are disabled'
|
11
|
-
exit(0)
|
12
|
-
end
|
13
|
-
notification = Notification::Api.new
|
5
|
+
@backup_path = Rails.root.join(Rails.env.development? ? 'tmp/backups' : '../../shared/backups').to_s
|
6
|
+
@storage_path = Rails.root.join(Rails.env.development? ? 'storage' : '../../shared/storage').to_s
|
7
|
+
backups_enabled = Rails.env.production? || ENV['BACKUPS_ENABLED'] == 'true'
|
8
|
+
external_backup = Rails.env.production? || ENV['EXTERNAL_BACKUP_ENABLED'] == 'true'
|
14
9
|
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
FileUtils.rm_rf("#{@backup_path}/#{filename}") unless result
|
21
|
-
|
22
|
-
|
23
|
-
filesize = size_str(File.size("#{@backup_path}/#{@filename}"))
|
24
|
-
|
25
|
-
p result ? "Backup created: #{@backup_path}/#{@filename} (#{filesize})" : "Backup failed removing dump file"
|
26
|
-
|
27
|
-
if ENV["BACKUP_PROVIDER"].present? && result
|
28
|
-
puts "Uploading #{@filename} to #{ENV["BACKUP_PROVIDER"]}..."
|
29
|
-
provider = Backup::Api.new
|
30
|
-
begin
|
31
|
-
provider.upload("#{@backup_path}/#{@filename}", "#{@filename}")
|
32
|
-
puts "#{@filename} uploaded to #{ENV["BACKUP_PROVIDER"]}"
|
33
|
-
rescue => e
|
34
|
-
puts "#{@filename} upload failed: #{e.message}"
|
35
|
-
end
|
36
|
-
end
|
37
|
-
notification.send_backup_notification(result,title,message(result))
|
38
|
-
|
10
|
+
desc 'backup storage'
|
11
|
+
task :backup do
|
12
|
+
unless backups_enabled
|
13
|
+
puts 'storage: Backups are disabled'
|
14
|
+
exit(0)
|
39
15
|
end
|
16
|
+
notification = Notification::Api.new
|
40
17
|
|
18
|
+
date = Time.now.to_i
|
19
|
+
@filename = "storage_#{date}.tar.gz"
|
20
|
+
FileUtils.mkdir_p(@backup_path) unless Dir.exist?(@backup_path)
|
21
|
+
result = system "tar -zcf #{@backup_path}/#{@filename} -C #{@storage_path} ."
|
22
|
+
FileUtils.rm_rf("#{@backup_path}/#{filename}") unless result
|
23
|
+
puts result ? "Backup created: #{@backup_path}/#{@filename} (#{size_str(File.size("#{@backup_path}/#{@filename}"))})" : 'Backup failed removing dump file'
|
41
24
|
|
42
|
-
|
43
|
-
|
44
|
-
|
25
|
+
if ENV['BACKUP_PROVIDER'].present? && external_backup && result
|
26
|
+
puts "Uploading #{@filename} to #{ENV['BACKUP_PROVIDER']}..."
|
27
|
+
provider = Backup::Api.new
|
28
|
+
begin
|
29
|
+
provider.upload("#{@backup_path}/#{@filename}", @filename.to_s)
|
30
|
+
puts "#{@filename} uploaded to #{ENV['BACKUP_PROVIDER']}"
|
31
|
+
rescue StandardError => e
|
32
|
+
puts "#{@filename} upload failed: #{e.message}"
|
33
|
+
end
|
45
34
|
end
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
35
|
+
notification.send_backup_notification(result, title, message(result), { date: date, backup_path: @backup_path, database: 'storage' })
|
36
|
+
end
|
37
|
+
|
38
|
+
def title
|
39
|
+
ENV['DEFAULT_URL'] || "#{Rails.env} Backup"
|
40
|
+
end
|
41
|
+
|
42
|
+
def message(result)
|
43
|
+
messages = []
|
44
|
+
if result
|
45
|
+
messages << "Backup of storage folder successfully finished at #{Time.now}"
|
46
|
+
messages << "Backup path:\`#{@backup_path}/#{@filename}\`"
|
47
|
+
else
|
48
|
+
messages << "Backup of storage folder failed at #{Time.now}"
|
57
49
|
end
|
50
|
+
messages.join("\n")
|
51
|
+
end
|
58
52
|
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
end
|
53
|
+
def size_str(size)
|
54
|
+
case size
|
55
|
+
when 0..1024
|
56
|
+
"#{size} B"
|
57
|
+
when 1024..1024 * 1024
|
58
|
+
"#{size / 1024} KB"
|
59
|
+
when 1024 * 1024..1024 * 1024 * 1024
|
60
|
+
"#{size / 1024 / 1024} MB"
|
61
|
+
when 1024 * 1024 * 1024..1024 * 1024 * 1024 * 1024
|
62
|
+
"#{size / 1024 / 1024 / 1024} GB"
|
70
63
|
end
|
71
|
-
end
|
64
|
+
end
|
65
|
+
end
|
66
|
+
# rubocop:enable Metrics/BlockLength
|
@@ -1,41 +1,58 @@
|
|
1
1
|
# frozen_string_literal: true
|
2
|
+
|
2
3
|
require 'rake'
|
3
4
|
namespace :storage do
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
5
|
+
backup_path = Rails.root.join(Rails.env.development? ? 'tmp/backups' : '../../shared/backups').to_s
|
6
|
+
backups_enabled = Rails.env.production? || ENV['BACKUPS_ENABLED'] == 'true'
|
7
|
+
external_backup = Rails.env.production? || ENV['EXTERNAL_BACKUP_ENABLED'] == 'true'
|
8
8
|
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
9
|
+
@env_local_no = ENV['NUMBER_OF_LOCAL_BACKUPS']
|
10
|
+
@env_external_no = ENV['NUMBER_OF_EXTERNAL_BACKUPS']
|
11
|
+
@total_local_backups_no = (@env_local_no || ENV['NUMBER_OF_BACKUPS'] || 7).to_i
|
12
|
+
@total_external_backups_no = (@env_external_no || ENV['NUMBER_OF_BACKUPS'] || 7).to_i
|
13
|
+
desc 'remove old storage backups'
|
14
|
+
task :remove_old_backups do
|
15
|
+
bash_regex = "'storage_.{0,}\.tar.gz'"
|
16
|
+
|
17
|
+
unless backups_enabled
|
18
|
+
puts 'remove_old_backups: Backups are disabled'
|
19
|
+
exit(0)
|
20
|
+
end
|
18
21
|
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
]
|
22
|
+
unless @total_local_backups_no.positive?
|
23
|
+
puts "remove_old_backups: No local cleanup because option '#{if @env_local_no
|
24
|
+
'NUMBER_OF_LOCAL_BACKUPS='
|
25
|
+
else
|
26
|
+
'NUMBER_OF_BACKUPS='
|
27
|
+
end}#{@total_local_backups_no}' sets unlimited backups"
|
28
|
+
end
|
27
29
|
|
28
|
-
|
30
|
+
commandlist = [
|
31
|
+
"cd #{backup_path} && ls -lt ",
|
32
|
+
"grep -E -i #{bash_regex} ",
|
33
|
+
"tail -n +#{@total_local_backups_no + 1} ",
|
34
|
+
"awk '{print $9}' ",
|
35
|
+
'xargs rm -rf'
|
36
|
+
]
|
29
37
|
|
30
|
-
|
31
|
-
provider = Backup::Api.new
|
32
|
-
begin
|
33
|
-
result = provider.remove_old_backups('storage_', total_backups_no)
|
34
|
-
rescue StandardError => e
|
35
|
-
p "remove_old_backups failed: #{e.message}"
|
36
|
-
end
|
37
|
-
p 'remove_old_backups finished' if result
|
38
|
-
end
|
38
|
+
system(commandlist.join(' | '))
|
39
39
|
|
40
|
+
if ENV['BACKUP_PROVIDER'].present? && external_backup
|
41
|
+
unless @total_external_backups_no.positive?
|
42
|
+
puts "remove_old_backups: No external cleanup because option '#{if @env_external_no
|
43
|
+
'NUMBER_OF_EXTERNAL_BACKUPS='
|
44
|
+
else
|
45
|
+
'NUMBER_OF_BACKUPS='
|
46
|
+
end}#{@total_external_backups_no}' sets unlimited backups"
|
47
|
+
exit(0)
|
48
|
+
end
|
49
|
+
provider = Backup::Api.new
|
50
|
+
begin
|
51
|
+
result = provider.remove_old_backups('storage_', @total_external_backups_no)
|
52
|
+
rescue StandardError => e
|
53
|
+
puts "remove_old_backups failed: #{e.message}"
|
54
|
+
end
|
55
|
+
puts 'remove_old_backups finished' if result
|
40
56
|
end
|
57
|
+
end
|
41
58
|
end
|
data/lib/capistrano/ops.rb
CHANGED
@@ -1,25 +1,25 @@
|
|
1
|
-
|
1
|
+
# frozen_string_literal: true
|
2
2
|
|
3
3
|
module Capistrano
|
4
|
-
|
5
|
-
|
6
|
-
|
7
|
-
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
4
|
+
module Ops
|
5
|
+
require 'capistrano/ops/backup'
|
6
|
+
require 'capistrano/ops/notification'
|
7
|
+
require 'capistrano/ops/railtie' if defined?(Rails)
|
8
|
+
require 'capistrano/ops/capistrano' if defined?(Capistrano::VERSION)
|
9
|
+
def self.path
|
10
|
+
Dir.pwd
|
11
|
+
end
|
12
12
|
|
13
|
-
|
14
|
-
|
15
|
-
|
13
|
+
def self.bin_rails?
|
14
|
+
File.exist?(File.join(path, 'bin', 'rails'))
|
15
|
+
end
|
16
16
|
|
17
|
-
|
18
|
-
|
19
|
-
|
17
|
+
def self.script_rails?
|
18
|
+
File.exist?(File.join(path, 'script', 'rails'))
|
19
|
+
end
|
20
20
|
|
21
|
-
|
22
|
-
|
23
|
-
end
|
21
|
+
def self.bundler?
|
22
|
+
File.exist?(File.join(path, 'Gemfile'))
|
24
23
|
end
|
25
|
-
end
|
24
|
+
end
|
25
|
+
end
|
metadata
CHANGED
@@ -1,17 +1,31 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: capistrano-ops
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.2.
|
4
|
+
version: 0.2.4
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Florian Crusius
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2023-
|
11
|
+
date: 2023-08-13 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
|
-
name:
|
14
|
+
name: aws-sdk-s3
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - "~>"
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '1.128'
|
20
|
+
type: :runtime
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - "~>"
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: '1.128'
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: faraday
|
15
29
|
requirement: !ruby/object:Gem::Requirement
|
16
30
|
requirements:
|
17
31
|
- - ">="
|
@@ -39,19 +53,19 @@ dependencies:
|
|
39
53
|
- !ruby/object:Gem::Version
|
40
54
|
version: '0'
|
41
55
|
- !ruby/object:Gem::Dependency
|
42
|
-
name:
|
56
|
+
name: rails
|
43
57
|
requirement: !ruby/object:Gem::Requirement
|
44
58
|
requirements:
|
45
|
-
- - "
|
59
|
+
- - ">="
|
46
60
|
- !ruby/object:Gem::Version
|
47
|
-
version: '
|
61
|
+
version: '0'
|
48
62
|
type: :runtime
|
49
63
|
prerelease: false
|
50
64
|
version_requirements: !ruby/object:Gem::Requirement
|
51
65
|
requirements:
|
52
|
-
- - "
|
66
|
+
- - ">="
|
53
67
|
- !ruby/object:Gem::Version
|
54
|
-
version: '
|
68
|
+
version: '0'
|
55
69
|
- !ruby/object:Gem::Dependency
|
56
70
|
name: bundler
|
57
71
|
requirement: !ruby/object:Gem::Requirement
|
@@ -90,6 +104,7 @@ extensions: []
|
|
90
104
|
extra_rdoc_files: []
|
91
105
|
files:
|
92
106
|
- ".gitignore"
|
107
|
+
- ".rubocop.yml"
|
93
108
|
- ".ruby-version"
|
94
109
|
- ".travis.yml"
|
95
110
|
- Gemfile
|
@@ -105,6 +120,11 @@ files:
|
|
105
120
|
- lib/capistrano/ops/backup/s3.rb
|
106
121
|
- lib/capistrano/ops/capistrano.rb
|
107
122
|
- lib/capistrano/ops/capistrano/v3/tasks/backup.rake
|
123
|
+
- lib/capistrano/ops/capistrano/v3/tasks/backup/backup_helper.rb
|
124
|
+
- lib/capistrano/ops/capistrano/v3/tasks/backup/database/create.rake
|
125
|
+
- lib/capistrano/ops/capistrano/v3/tasks/backup/database/pull.rake
|
126
|
+
- lib/capistrano/ops/capistrano/v3/tasks/backup/storage/create.rake
|
127
|
+
- lib/capistrano/ops/capistrano/v3/tasks/backup/storage/pull.rake
|
108
128
|
- lib/capistrano/ops/capistrano/v3/tasks/figaro_yml.rake
|
109
129
|
- lib/capistrano/ops/capistrano/v3/tasks/invoke.rake
|
110
130
|
- lib/capistrano/ops/capistrano/v3/tasks/logs.rake
|
@@ -129,12 +149,9 @@ require_paths:
|
|
129
149
|
- lib
|
130
150
|
required_ruby_version: !ruby/object:Gem::Requirement
|
131
151
|
requirements:
|
132
|
-
- - "
|
133
|
-
- !ruby/object:Gem::Version
|
134
|
-
version: 2.5.0
|
135
|
-
- - "<"
|
152
|
+
- - "~>"
|
136
153
|
- !ruby/object:Gem::Version
|
137
|
-
version:
|
154
|
+
version: 2.7.0
|
138
155
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
139
156
|
requirements:
|
140
157
|
- - ">="
|