swarm_cluster_cli_ope 0.3.2 → 0.5.0.pre.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.
- checksums.yaml +4 -4
- data/CHANGELOG.md +4 -0
- data/Gemfile.lock +48 -4
- data/README.md +27 -4
- data/lib/swarm_cluster_cli_ope/cli.rb +44 -11
- data/lib/swarm_cluster_cli_ope/configuration.rb +9 -0
- data/lib/swarm_cluster_cli_ope/k8s.rb +114 -0
- data/lib/swarm_cluster_cli_ope/k8s_rsync/password +1 -0
- data/lib/swarm_cluster_cli_ope/k8s_rsync/rsyncd.conf +14 -0
- data/lib/swarm_cluster_cli_ope/k8s_rsync/rsyncd.secrets +1 -0
- data/lib/swarm_cluster_cli_ope/shell_command_execution.rb +1 -1
- data/lib/swarm_cluster_cli_ope/sync_configs/base_database.rb +51 -0
- data/lib/swarm_cluster_cli_ope/sync_configs/env_configs.rb +4 -3
- data/lib/swarm_cluster_cli_ope/sync_configs/mysql.rb +9 -43
- data/lib/swarm_cluster_cli_ope/sync_configs/post_gres.rb +159 -0
- data/lib/swarm_cluster_cli_ope/version.rb +1 -1
- data/swarm_cluster_cli_ope.gemspec +1 -0
- metadata +24 -4
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 5be802511060e36dbd846cb15b77de3c8fe5ab58a4cce3e7dd2eee4c33e9a06e
|
4
|
+
data.tar.gz: 58ba7bf7b7eee469c7af8a933901aad85844ed77fe4951cf6de956e2eb08b27a
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: d9995e3a19c00defea55c7d692eb8e01bf52d431323d687b51fa39b26bba11f0ddc2a1fb1dfc63f45c07af475b777aa0f8aa655f6b080e8b7c7076ba2e0b5f14
|
7
|
+
data.tar.gz: 8b3c230e483f066492295c56d4904a30d4e186fad2481e86d654d9de7802d683bb61e6f0fdba2756443367290195d2567e03b4c3f4332c4482c64e821cffd045
|
data/CHANGELOG.md
CHANGED
data/Gemfile.lock
CHANGED
@@ -1,8 +1,9 @@
|
|
1
1
|
PATH
|
2
2
|
remote: .
|
3
3
|
specs:
|
4
|
-
swarm_cluster_cli_ope (0.
|
4
|
+
swarm_cluster_cli_ope (0.5.0.pre.2)
|
5
5
|
activesupport
|
6
|
+
kubeclient (~> 4.9)
|
6
7
|
open4
|
7
8
|
thor (~> 1.0)
|
8
9
|
zeitwerk (~> 2.3)
|
@@ -10,23 +11,66 @@ PATH
|
|
10
11
|
GEM
|
11
12
|
remote: https://rubygems.org/
|
12
13
|
specs:
|
13
|
-
activesupport (6.0.3.
|
14
|
+
activesupport (6.0.3.4)
|
14
15
|
concurrent-ruby (~> 1.0, >= 1.0.2)
|
15
16
|
i18n (>= 0.7, < 2)
|
16
17
|
minitest (~> 5.1)
|
17
18
|
tzinfo (~> 1.1)
|
18
19
|
zeitwerk (~> 2.2, >= 2.2.2)
|
20
|
+
addressable (2.7.0)
|
21
|
+
public_suffix (>= 2.0.2, < 5.0)
|
19
22
|
concurrent-ruby (1.1.7)
|
23
|
+
domain_name (0.5.20190701)
|
24
|
+
unf (>= 0.0.5, < 1.0.0)
|
25
|
+
ffi (1.13.1)
|
26
|
+
ffi-compiler (1.0.1)
|
27
|
+
ffi (>= 1.0.0)
|
28
|
+
rake
|
29
|
+
http (4.4.1)
|
30
|
+
addressable (~> 2.3)
|
31
|
+
http-cookie (~> 1.0)
|
32
|
+
http-form_data (~> 2.2)
|
33
|
+
http-parser (~> 1.2.0)
|
34
|
+
http-accept (1.7.0)
|
35
|
+
http-cookie (1.0.3)
|
36
|
+
domain_name (~> 0.5)
|
37
|
+
http-form_data (2.3.0)
|
38
|
+
http-parser (1.2.1)
|
39
|
+
ffi-compiler (>= 1.0, < 2.0)
|
20
40
|
i18n (1.8.5)
|
21
41
|
concurrent-ruby (~> 1.0)
|
42
|
+
jsonpath (1.0.5)
|
43
|
+
multi_json
|
44
|
+
to_regexp (~> 0.2.1)
|
45
|
+
kubeclient (4.9.1)
|
46
|
+
http (>= 3.0, < 5.0)
|
47
|
+
jsonpath (~> 1.0)
|
48
|
+
recursive-open-struct (~> 1.1, >= 1.1.1)
|
49
|
+
rest-client (~> 2.0)
|
50
|
+
mime-types (3.3.1)
|
51
|
+
mime-types-data (~> 3.2015)
|
52
|
+
mime-types-data (3.2020.1104)
|
22
53
|
minitest (5.14.2)
|
54
|
+
multi_json (1.15.0)
|
55
|
+
netrc (0.11.0)
|
23
56
|
open4 (1.3.4)
|
57
|
+
public_suffix (4.0.6)
|
24
58
|
rake (12.3.3)
|
59
|
+
recursive-open-struct (1.1.3)
|
60
|
+
rest-client (2.1.0)
|
61
|
+
http-accept (>= 1.7.0, < 2.0)
|
62
|
+
http-cookie (>= 1.0.2, < 2.0)
|
63
|
+
mime-types (>= 1.16, < 4.0)
|
64
|
+
netrc (~> 0.8)
|
25
65
|
thor (1.0.1)
|
26
66
|
thread_safe (0.3.6)
|
27
|
-
|
67
|
+
to_regexp (0.2.1)
|
68
|
+
tzinfo (1.2.8)
|
28
69
|
thread_safe (~> 0.1)
|
29
|
-
|
70
|
+
unf (0.1.4)
|
71
|
+
unf_ext
|
72
|
+
unf_ext (0.0.7.7)
|
73
|
+
zeitwerk (2.4.1)
|
30
74
|
|
31
75
|
PLATFORMS
|
32
76
|
ruby
|
data/README.md
CHANGED
@@ -130,13 +130,36 @@ Possibili CFGS per tipologia:
|
|
130
130
|
- local: -> hash di configurazioni per il DB locale
|
131
131
|
- service: "db" -> nome del servizio nel compose locale, DEFAULT: quello definito sopra
|
132
132
|
- mysql_password_env: "MYSQL_PASSWORD" -> variabile ambiente interna al servizio contenente PASSWORD, DEFAULT: MYSQL_PASSWORD
|
133
|
+
- mysql_password: "root" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: root
|
133
134
|
- mysql_user_env: "MYSQL_USER" -> variabile ambiente interna al servizio contenente USERNAME, DEFAULT: MYSQL_USER
|
135
|
+
- mysql_user: "root" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: root
|
136
|
+
- database_name_env: "MYSQL_DATABASE" -> variabile ambiente interna al servizio contenente NOME DB, DEFAULT: MYSQL_DATABASE
|
137
|
+
- database_name: "nome_db" -> valore in chiaro, in sostituzione della variabile ambiente
|
138
|
+
- remote: -> hash di configurazioni per il DB remoto
|
139
|
+
- service: "db" -> nome del servizio nel compose locale, DEFAULT: quello definito sopra
|
140
|
+
- mysql_password_env: "MYSQL_PASSWORD" -> variabile ambiente interna al servizio contenente PASSWORD, DEFAULT: MYSQL_PASSWORD
|
141
|
+
- mysql_password: "root" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: root
|
142
|
+
- mysql_user_env: "MYSQL_USER" -> variabile ambiente interna al servizio contenente USERNAME, DEFAULT: MYSQL_USER
|
143
|
+
- mysql_user: "root" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: root
|
134
144
|
- database_name_env: "MYSQL_DATABASE" -> variabile ambiente interna al servizio contenente NOME DB, DEFAULT: MYSQL_DATABASE
|
145
|
+
- database_name: "MYSQL_DATABASE" -> valore in chiaro, in sostituzione della variabile ambiente
|
146
|
+
- pg:
|
147
|
+
- local: -> hash di configurazioni per il DB locale
|
148
|
+
- service: "db" -> nome del servizio nel compose locale, DEFAULT: quello definito sopra
|
149
|
+
- pg_password_env: "POSTGRES_USER" -> variabile ambiente interna al servizio contenente PASSWORD, DEFAULT: POSTGRES_PASSWORD
|
150
|
+
- pg_password: "" -> valore in chiaro, in sostituzione della variabile ambiente
|
151
|
+
- pg_user_env: "POSTGRES_USER" -> variabile ambiente interna al servizio contenente USERNAME, DEFAULT: POSTGRES_USER
|
152
|
+
- pg_user: "postgres" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: postgres
|
153
|
+
- database_name_env: "POSTGRES_DB" -> variabile ambiente interna al servizio contenente NOME DB, DEFAULT: POSTGRES_DB
|
154
|
+
- database_name: "nome_db" -> valore in chiaro, in sostituzione della variabile ambiente
|
135
155
|
- remote: -> hash di configurazioni per il DB remoto
|
136
156
|
- service: "db" -> nome del servizio nel compose locale, DEFAULT: quello definito sopra
|
137
|
-
-
|
138
|
-
-
|
139
|
-
-
|
157
|
+
- pg_password_env: "POSTGRES_USER" -> variabile ambiente interna al servizio contenente PASSWORD, DEFAULT: POSTGRES_PASSWORD
|
158
|
+
- pg_password: "" -> valore in chiaro, in sostituzione della variabile ambiente
|
159
|
+
- pg_user_env: "POSTGRES_USER" -> variabile ambiente interna al servizio contenente USERNAME, DEFAULT: POSTGRES_USER
|
160
|
+
- pg_user: "postgres" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: postgres
|
161
|
+
- database_name_env: "POSTGRES_DB" -> variabile ambiente interna al servizio contenente NOME DB, DEFAULT: POSTGRES_DB
|
162
|
+
- database_name: "nome_db" -> valore in chiaro, in sostituzione della variabile ambiente
|
140
163
|
|
141
164
|
#### EXAMPLE:
|
142
165
|
Esempio di sincronizzazione di un file sqlite3 e una cartella
|
@@ -180,7 +203,7 @@ docker stack deploy -c test_folder/test_2/docker_compose.yml test2
|
|
180
203
|
Per simulare una sincronizzazione fra locale e remoto di un mysql, lanciamo lo stesso stack anche come compose, in modo
|
181
204
|
da trovarci sulla stessa macchina con tutte e due le situazioni
|
182
205
|
```shell script
|
183
|
-
docker-compose
|
206
|
+
docker-compose -f test_folder/test_1/docker-compose-local.yml up -d
|
184
207
|
```
|
185
208
|
|
186
209
|
|
@@ -14,6 +14,10 @@ module SwarmClusterCliOpe
|
|
14
14
|
class_option :environment, required: false, type: :string, aliases: [:e],
|
15
15
|
desc: "Esegue tutte le operazioni nell'env scelto, il file di configurazione dovrà avere il nome: #{Configuration.cfgs_project_file_name}.ENV"
|
16
16
|
|
17
|
+
|
18
|
+
desc "k8s SUBCOMMAND ...ARGS", "Gestisce un set di comandi specifici per K8s"
|
19
|
+
subcommand "k8s", K8s
|
20
|
+
|
17
21
|
desc "install", "Creazione della configurazione base della gemma"
|
18
22
|
|
19
23
|
def install
|
@@ -243,6 +247,11 @@ module SwarmClusterCliOpe
|
|
243
247
|
end
|
244
248
|
end
|
245
249
|
|
250
|
+
desc "version", "versione della cli"
|
251
|
+
def version
|
252
|
+
say VERSION
|
253
|
+
end
|
254
|
+
|
246
255
|
desc "stacksync [DIRECTION:pull|push]", "Si occupa di scaricare|caricare,utilizzando le configurazioni presenti, i dati dallo stack remoto"
|
247
256
|
long_desc <<-LONGDESC.gsub("\n", "\x5")
|
248
257
|
le configurazioni sono contenute nell'array: sync_configs.
|
@@ -270,17 +279,40 @@ module SwarmClusterCliOpe
|
|
270
279
|
--remote: -> path al file remoto (contesto del container)
|
271
280
|
|
272
281
|
mysql:
|
273
|
-
--
|
274
|
-
|
275
|
-
|
276
|
-
|
277
|
-
|
278
|
-
|
279
|
-
|
280
|
-
|
281
|
-
|
282
|
-
|
283
|
-
|
282
|
+
--local: -> hash di configurazioni per il DB locale
|
283
|
+
- service: "db" -> nome del servizio nel compose locale, DEFAULT: quello definito sopra
|
284
|
+
- mysql_password_env: "MYSQL_PASSWORD" -> variabile ambiente interna al servizio contenente PASSWORD, DEFAULT: MYSQL_PASSWORD
|
285
|
+
- mysql_password: "root" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: root
|
286
|
+
- mysql_user_env: "MYSQL_USER" -> variabile ambiente interna al servizio contenente USERNAME, DEFAULT: MYSQL_USER
|
287
|
+
- mysql_user: "root" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: root
|
288
|
+
- database_name_env: "MYSQL_DATABASE" -> variabile ambiente interna al servizio contenente NOME DB, DEFAULT: MYSQL_DATABASE
|
289
|
+
- database_name: "nome_db" -> valore in chiaro, in sostituzione della variabile ambiente
|
290
|
+
--remote: -> hash di configurazioni per il DB remoto
|
291
|
+
- service: "db" -> nome del servizio nel compose locale, DEFAULT: quello definito sopra
|
292
|
+
- mysql_password_env: "MYSQL_PASSWORD" -> variabile ambiente interna al servizio contenente PASSWORD, DEFAULT: MYSQL_PASSWORD
|
293
|
+
- mysql_password: "root" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: root
|
294
|
+
- mysql_user_env: "MYSQL_USER" -> variabile ambiente interna al servizio contenente USERNAME, DEFAULT: MYSQL_USER
|
295
|
+
- mysql_user: "root" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: root
|
296
|
+
- database_name_env: "MYSQL_DATABASE" -> variabile ambiente interna al servizio contenente NOME DB, DEFAULT: MYSQL_DATABASE
|
297
|
+
- database_name: "MYSQL_DATABASE" -> valore in chiaro, in sostituzione della variabile ambiente
|
298
|
+
pg:
|
299
|
+
--local: -> hash di configurazioni per il DB locale
|
300
|
+
- service: "db" -> nome del servizio nel compose locale, DEFAULT: quello definito sopra
|
301
|
+
- pg_password_env: "POSTGRES_USER" -> variabile ambiente interna al servizio contenente PASSWORD, DEFAULT: POSTGRES_PASSWORD
|
302
|
+
- pg_password: "" -> valore in chiaro, in sostituzione della variabile ambiente
|
303
|
+
- pg_user_env: "POSTGRES_USER" -> variabile ambiente interna al servizio contenente USERNAME, DEFAULT: POSTGRES_USER
|
304
|
+
- pg_user: "postgres" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: postgres
|
305
|
+
- database_name_env: "POSTGRES_DB" -> variabile ambiente interna al servizio contenente NOME DB, DEFAULT: POSTGRES_DB
|
306
|
+
- database_name: "nome_db" -> valore in chiaro, in sostituzione della variabile ambiente
|
307
|
+
--remote: -> hash di configurazioni per il DB remoto
|
308
|
+
- service: "db" -> nome del servizio nel compose locale, DEFAULT: quello definito sopra
|
309
|
+
- pg_password_env: "POSTGRES_USER" -> variabile ambiente interna al servizio contenente PASSWORD, DEFAULT: POSTGRES_PASSWORD
|
310
|
+
- pg_password: "" -> valore in chiaro, in sostituzione della variabile ambiente
|
311
|
+
- pg_user_env: "POSTGRES_USER" -> variabile ambiente interna al servizio contenente USERNAME, DEFAULT: POSTGRES_USER
|
312
|
+
- pg_user: "postgres" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: postgres
|
313
|
+
- database_name_env: "POSTGRES_DB" -> variabile ambiente interna al servizio contenente NOME DB, DEFAULT: POSTGRES_DB
|
314
|
+
- database_name: "nome_db" -> valore in chiaro, in sostituzione della variabile ambiente
|
315
|
+
|
284
316
|
|
285
317
|
EXAMPLE:
|
286
318
|
Esempio di sincronizzazione di un file sqlite3 e una cartella
|
@@ -325,6 +357,7 @@ module SwarmClusterCliOpe
|
|
325
357
|
say "----------->>>>>>"
|
326
358
|
say "[ #{sync.class.name} ]"
|
327
359
|
sync.send(direction)
|
360
|
+
say "COMPLETE"
|
328
361
|
say "<<<<<<-----------"
|
329
362
|
end
|
330
363
|
end
|
@@ -188,6 +188,8 @@ module SwarmClusterCliOpe
|
|
188
188
|
SyncConfigs::Rsync.new(self, c)
|
189
189
|
when 'mysql'
|
190
190
|
SyncConfigs::Mysql.new(self, c)
|
191
|
+
when 'pg'
|
192
|
+
SyncConfigs::PostGres.new(self, c)
|
191
193
|
else
|
192
194
|
logger.error { "CONFIGURAIONE NON PREVISTA: #{c[:how]}" }
|
193
195
|
nil
|
@@ -249,6 +251,13 @@ module SwarmClusterCliOpe
|
|
249
251
|
hash[key] = self.class.read_base.merge(project_cfgs)
|
250
252
|
end
|
251
253
|
|
254
|
+
configuration_version = @_merged_configurations[@environment][:version]
|
255
|
+
if Gem::Version.new(configuration_version) > Gem::Version.new(VERSION)
|
256
|
+
puts "WARNING: Versione del file di configurazione [#{configuration_version}] più aggiornata della gemma [#{VERSION}], eseguire upgrade
|
257
|
+
gem update swarm_cluster_cli_ope"
|
258
|
+
exit
|
259
|
+
end
|
260
|
+
|
252
261
|
@_merged_configurations[@environment]
|
253
262
|
|
254
263
|
end
|
@@ -0,0 +1,114 @@
|
|
1
|
+
require 'kubeclient'
|
2
|
+
module SwarmClusterCliOpe
|
3
|
+
class K8s < Thor
|
4
|
+
include LoggerConcern
|
5
|
+
include ConfigurationConcern
|
6
|
+
include Thor::Actions
|
7
|
+
|
8
|
+
def self.exit_on_failure?
|
9
|
+
true
|
10
|
+
end
|
11
|
+
|
12
|
+
|
13
|
+
desc "rsync <src> <dst>", "esegue un rsync dalla cartella (viene sincronizzato il contenuto)"
|
14
|
+
|
15
|
+
|
16
|
+
def rsync(src, dst)
|
17
|
+
if yes? "Attenzione, i dati locali o remoti verranno sovrascritti/cancellati?[y,yes]"
|
18
|
+
|
19
|
+
reg_exp = /(?<pod_name>.*)\:(?<path>.*)/
|
20
|
+
if File.exist?(src)
|
21
|
+
# il src é la cartella, quindi la destizione è il pod
|
22
|
+
direction = :upload
|
23
|
+
local_path = src
|
24
|
+
podname = dst.match(reg_exp)[:pod_name]
|
25
|
+
podpath = dst.match(reg_exp)[:path]
|
26
|
+
else
|
27
|
+
direction = :download
|
28
|
+
podname = src.match(reg_exp)[:pod_name]
|
29
|
+
podpath = src.match(reg_exp)[:path]
|
30
|
+
local_path = dst
|
31
|
+
end
|
32
|
+
|
33
|
+
puts "#{src} #{direction} #{dst}"
|
34
|
+
|
35
|
+
cfgs.env(options[:environment]) do |cfgs|
|
36
|
+
config = Kubeclient::Config.read(ENV['KUBECONFIG'] || "#{Dir.home}/.kube/config")
|
37
|
+
|
38
|
+
context = config.context # attuale contesto
|
39
|
+
|
40
|
+
puts "Stiamo utilizzando il contesto: #{context.api_endpoint}"
|
41
|
+
|
42
|
+
base_cmd = ["kubectl", "-n #{cfgs.stack_name}"]
|
43
|
+
|
44
|
+
cmd = ShellCommandExecution.new([*base_cmd, "exec #{podname}", "--", 'bash -c "apt update && apt install -yq rsync psmisc"'])
|
45
|
+
if cmd.execute.failed?
|
46
|
+
puts "Problemi nell'installazione di rsync nel pod"
|
47
|
+
else
|
48
|
+
cmd = ShellCommandExecution.new([*base_cmd, "cp", File.expand_path("../k8s_rsync/rsyncd.conf", __FILE__), "#{podname}:/tmp/."])
|
49
|
+
copy_1 = cmd.execute.failed?
|
50
|
+
cmd = ShellCommandExecution.new([*base_cmd, "cp", File.expand_path("../k8s_rsync/rsyncd.secrets", __FILE__), "#{podname}:/tmp/."])
|
51
|
+
copy_2 = cmd.execute.failed?
|
52
|
+
cmd = ShellCommandExecution.new([*base_cmd, "exec #{podname}", "--", 'bash -c "chmod 600 /tmp/rsyncd.secrets && chown root /tmp/*"'])
|
53
|
+
chmod = cmd.execute.failed?
|
54
|
+
if copy_1 or copy_2 or chmod
|
55
|
+
puts "problema nella copia dei file di configurazione nel pod"
|
56
|
+
else
|
57
|
+
|
58
|
+
|
59
|
+
cmd = ShellCommandExecution.new([*base_cmd, "exec -i #{podname}", "--", 'bash -c "rsync --daemon --config=/tmp/rsyncd.conf --verbose --log-file=/tmp/rsync.log"'])
|
60
|
+
if cmd.execute.failed?
|
61
|
+
puts "Rsync non startato"
|
62
|
+
else
|
63
|
+
local_port = rand(30000..40000)
|
64
|
+
|
65
|
+
p = IO.popen([*base_cmd, "port-forward #{podname} #{local_port}:873"].join(" "))
|
66
|
+
pid = p.pid
|
67
|
+
puts "PID in execuzione port forward:#{pid}"
|
68
|
+
|
69
|
+
sleep 1
|
70
|
+
|
71
|
+
# lanciamo il comando quindi per far rsync
|
72
|
+
rsync_command = [
|
73
|
+
"rsync -az --no-o --no-g",
|
74
|
+
"--delete",
|
75
|
+
"--password-file=#{ File.expand_path("../k8s_rsync/password", __FILE__)}"
|
76
|
+
]
|
77
|
+
|
78
|
+
if direction == :upload
|
79
|
+
rsync_command << local_path
|
80
|
+
rsync_command << "rsync://root@0.0.0.0:#{local_port}/archives#{podpath}"
|
81
|
+
else
|
82
|
+
rsync_command << "rsync://root@0.0.0.0:#{local_port}/archives#{podpath}"
|
83
|
+
rsync_command << local_path
|
84
|
+
end
|
85
|
+
|
86
|
+
|
87
|
+
cmd = ShellCommandExecution.new(rsync_command)
|
88
|
+
cmd.execute
|
89
|
+
|
90
|
+
sleep 1
|
91
|
+
Process.kill("INT", pid)
|
92
|
+
|
93
|
+
|
94
|
+
puts "Eseguo pulizia"
|
95
|
+
cmd = ShellCommandExecution.new([*base_cmd, "exec -i #{podname}", "--", 'bash -c "killall rsync"'])
|
96
|
+
cmd.execute
|
97
|
+
cmd = ShellCommandExecution.new([*base_cmd, "exec -i #{podname}", "--", 'bash -c "rm -fr /tmp/rsyncd*"'])
|
98
|
+
cmd.execute
|
99
|
+
|
100
|
+
end
|
101
|
+
|
102
|
+
end
|
103
|
+
|
104
|
+
end
|
105
|
+
|
106
|
+
end
|
107
|
+
|
108
|
+
|
109
|
+
end
|
110
|
+
end
|
111
|
+
|
112
|
+
|
113
|
+
end
|
114
|
+
end
|
@@ -0,0 +1 @@
|
|
1
|
+
root
|
@@ -0,0 +1 @@
|
|
1
|
+
root:root
|
@@ -0,0 +1,51 @@
|
|
1
|
+
module SwarmClusterCliOpe
|
2
|
+
module SyncConfigs
|
3
|
+
class BaseDatabase < Base
|
4
|
+
|
5
|
+
# @return [SwarmClusterCliOpe::SyncConfigs::EnvConfigs]
|
6
|
+
def remote
|
7
|
+
self.class::EnvConfigs.new(self, @configs.dig(:configs, :remote) || {}, -> { container })
|
8
|
+
end
|
9
|
+
|
10
|
+
# @return [SwarmClusterCliOpe::SyncConfigs::EnvConfigs]
|
11
|
+
def local
|
12
|
+
self.class::EnvConfigs.new(self, @configs.dig(:configs, :local) || {}, -> { local_container })
|
13
|
+
end
|
14
|
+
|
15
|
+
##
|
16
|
+
# Classe interna che rappresenta le configurazioni del DB
|
17
|
+
class EnvConfigs < SwarmClusterCliOpe::SyncConfigs::EnvConfigs
|
18
|
+
|
19
|
+
end
|
20
|
+
|
21
|
+
##
|
22
|
+
# Funzione che ricapitola le informazioni utilizzate per eseguire l'operazione
|
23
|
+
def resume(direction)
|
24
|
+
puts "RESUME - #{direction}
|
25
|
+
service: #{service}
|
26
|
+
local:
|
27
|
+
service_name: #{local.service_name}
|
28
|
+
database_name: #{local.database_name}
|
29
|
+
username: #{local.username}
|
30
|
+
password: #{local.password}
|
31
|
+
version: #{local.database_version}
|
32
|
+
remote:
|
33
|
+
service_name: #{remote.service_name}
|
34
|
+
database_name: #{remote.database_name}
|
35
|
+
username: #{remote.username}
|
36
|
+
password: #{remote.password}
|
37
|
+
version: #{remote.database_version}"
|
38
|
+
|
39
|
+
end
|
40
|
+
|
41
|
+
private
|
42
|
+
|
43
|
+
def local_container
|
44
|
+
# il nome dello stack del compose usiamo come standard il nome della cartella, come lo fà già composer di default
|
45
|
+
Models::ComposeContainer.find_by_service_name(local.service_name, stack_name: @stack_cfgs.local_compose_project_name)
|
46
|
+
end
|
47
|
+
|
48
|
+
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
@@ -35,7 +35,8 @@ module SwarmClusterCliOpe
|
|
35
35
|
# @param [String,Symbol] configuration_name -> nome della configurazione da utilizzare per estrapolare la configurazione
|
36
36
|
# in automatico viene tenuto conto se cercare per la versione
|
37
37
|
# con _env o senza....precedenza SENZA
|
38
|
-
|
38
|
+
# @param [nil,String] default_value se non è estrapolato nessun valore, viene utilizzato il valore di default
|
39
|
+
def self.define_cfgs(name, default_env:, configuration_name:,default_value:nil)
|
39
40
|
configuration_name ||= name
|
40
41
|
|
41
42
|
define_method(name) do
|
@@ -43,10 +44,10 @@ module SwarmClusterCliOpe
|
|
43
44
|
|
44
45
|
#valore restituito direttamente dalla configurazione
|
45
46
|
if @configs.key?(configuration_name)
|
46
|
-
value = @configs["#{configuration_name}".to_sym]
|
47
|
+
value = @configs["#{configuration_name}".to_sym] || default_value
|
47
48
|
else
|
48
49
|
env_var = @configs["#{configuration_name}_env".to_sym] || default_env
|
49
|
-
value = find_env_file_variable(env_var)
|
50
|
+
value = find_env_file_variable(env_var) || default_value
|
50
51
|
end
|
51
52
|
self.instance_variable_set("@#{name}", value)
|
52
53
|
end
|
@@ -1,15 +1,15 @@
|
|
1
1
|
module SwarmClusterCliOpe
|
2
2
|
module SyncConfigs
|
3
|
-
class Mysql <
|
3
|
+
class Mysql < BaseDatabase
|
4
4
|
|
5
5
|
# @return [TrueClass, FalseClass]
|
6
6
|
def pull
|
7
7
|
resume('pull')
|
8
8
|
if yes?("Confermare il comando?[y,yes]")
|
9
9
|
tmp_file = "/tmp/#{Time.now.to_i}.sql.gz"
|
10
|
-
container.exec("bash -c 'mysqldump -u #{remote.
|
10
|
+
container.exec("bash -c 'mysqldump -u #{remote.username} --password=#{remote.password} #{remote.database_name} | gzip -c -f' > #{tmp_file}")
|
11
11
|
local_container.copy_in(tmp_file, tmp_file)
|
12
|
-
local_container.exec("bash -c 'zcat #{tmp_file} | mysql -u #{local.
|
12
|
+
local_container.exec("bash -c 'zcat #{tmp_file} | mysql -u #{local.username} --password=#{local.password} #{local.database_name}'")
|
13
13
|
end
|
14
14
|
true
|
15
15
|
end
|
@@ -19,59 +19,25 @@ module SwarmClusterCliOpe
|
|
19
19
|
resume('PUSH')
|
20
20
|
if yes?("ATTENZIONE !!!!!!PUSH!!!!! - Confermare il comando?[y,yes]")
|
21
21
|
tmp_file = "/tmp/#{Time.now.to_i}.sql.gz"
|
22
|
-
local_container.exec("bash -c 'mysqldump -u #{local.
|
22
|
+
local_container.exec("bash -c 'mysqldump -u #{local.username} --password=#{local.password} #{local.database_name} | gzip -c -f' > #{tmp_file}")
|
23
23
|
container.copy_in(tmp_file, tmp_file)
|
24
|
-
container.exec("bash -c 'zcat #{tmp_file} | mysql -u #{remote.
|
24
|
+
container.exec("bash -c 'zcat #{tmp_file} | mysql -u #{remote.username} --password=#{remote.password} #{remote.database_name}'")
|
25
25
|
end
|
26
26
|
true
|
27
27
|
end
|
28
28
|
|
29
|
-
# @return [SwarmClusterCliOpe::SyncConfigs::Mysql::EnvConfigs]
|
30
|
-
def remote
|
31
|
-
EnvConfigs.new(self, @configs[:configs][:remote] || {}, -> { container })
|
32
|
-
end
|
33
|
-
|
34
|
-
# @return [SwarmClusterCliOpe::SyncConfigs::Mysql::EnvConfigs]
|
35
|
-
def local
|
36
|
-
EnvConfigs.new(self, @configs[:configs][:local] || {}, -> { local_container })
|
37
|
-
end
|
38
|
-
|
39
|
-
|
40
29
|
##
|
41
30
|
# Classe interna che rappresenta le configurazioni del DB
|
42
|
-
class EnvConfigs <
|
31
|
+
class EnvConfigs < BaseDatabase::EnvConfigs
|
43
32
|
|
44
33
|
define_cfgs :database_name, default_env: "MYSQL_DATABASE", configuration_name: :database_name
|
45
|
-
define_cfgs :
|
46
|
-
define_cfgs :
|
34
|
+
define_cfgs :username, default_env: "MYSQL_USER", configuration_name: :mysql_user, default_value: 'root'
|
35
|
+
define_cfgs :password, default_env: "MYSQL_PASSWORD", configuration_name: :mysql_password, default_value: 'root'
|
47
36
|
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
##
|
52
|
-
# Funzione che ricapitola le informazioni utilizzate per eseguire l'operazione
|
53
|
-
def resume(direction)
|
54
|
-
puts "RESUME - #{direction}
|
55
|
-
service: #{service}
|
56
|
-
local:
|
57
|
-
service_name: #{local.service_name}
|
58
|
-
database_name: #{local.database_name}
|
59
|
-
mysql_user: #{local.mysql_user}
|
60
|
-
mysql_password: #{local.mysql_password}
|
61
|
-
remote:
|
62
|
-
service_name: #{remote.service_name}
|
63
|
-
database_name: #{remote.database_name}
|
64
|
-
mysql_user: #{remote.mysql_user}
|
65
|
-
mysql_password: #{remote.mysql_password}"
|
37
|
+
define_cfgs :database_version, default_env: "MYSQL_MAJOR", configuration_name: :mysql_version
|
66
38
|
|
67
39
|
end
|
68
40
|
|
69
|
-
private
|
70
|
-
|
71
|
-
def local_container
|
72
|
-
# il nome dello stack del compose usiamo come standard il nome della cartella, come lo fà già composer di default
|
73
|
-
Models::ComposeContainer.find_by_service_name(local.service_name, stack_name: @stack_cfgs.local_compose_project_name)
|
74
|
-
end
|
75
41
|
|
76
42
|
end
|
77
43
|
end
|
@@ -0,0 +1,159 @@
|
|
1
|
+
module SwarmClusterCliOpe
|
2
|
+
module SyncConfigs
|
3
|
+
class PostGres < BaseDatabase
|
4
|
+
|
5
|
+
|
6
|
+
def pull
|
7
|
+
resume('pull')
|
8
|
+
|
9
|
+
if yes?("Confermare il comando?[y,yes]")
|
10
|
+
|
11
|
+
tmp_file = "/tmp/#{Time.now.to_i}.sql.gz"
|
12
|
+
dump_cmd(remote, tmp_file)
|
13
|
+
local.container.copy_in(tmp_file, tmp_file)
|
14
|
+
|
15
|
+
# drop old db and recreate
|
16
|
+
if Gem::Version.new(local.database_version) <= Gem::Version.new("12")
|
17
|
+
close_connections_and_drop_cmd(local)
|
18
|
+
else
|
19
|
+
raise "DA ANALIZZARE QUANDO LA 13 disponibile....dropdb ha un force come parametro"
|
20
|
+
end
|
21
|
+
|
22
|
+
create_cmd(local)
|
23
|
+
|
24
|
+
restore_cmd(local, tmp_file)
|
25
|
+
|
26
|
+
end
|
27
|
+
true
|
28
|
+
end
|
29
|
+
|
30
|
+
# @return [TrueClass, FalseClass]
|
31
|
+
def push
|
32
|
+
resume('PUSH')
|
33
|
+
|
34
|
+
if yes?("ATTENZIONE !!!!!!PUSH!!!!! - Confermare il comando?[y,yes]")
|
35
|
+
|
36
|
+
tmp_file = "/tmp/#{Time.now.to_i}.sql.gz"
|
37
|
+
dump_cmd(local, tmp_file)
|
38
|
+
remote.container.copy_in(tmp_file, tmp_file)
|
39
|
+
|
40
|
+
# drop old db and recreate
|
41
|
+
if Gem::Version.new(local.database_version) <= Gem::Version.new("12")
|
42
|
+
close_connections_and_drop_cmd(remote)
|
43
|
+
else
|
44
|
+
raise "DA ANALIZZARE QUANDO LA 13 disponibile....dropdb ha un force come parametro"
|
45
|
+
end
|
46
|
+
create_cmd(remote)
|
47
|
+
|
48
|
+
restore_cmd(remote, tmp_file)
|
49
|
+
|
50
|
+
end
|
51
|
+
true
|
52
|
+
end
|
53
|
+
|
54
|
+
##
|
55
|
+
# Classe interna che rappresenta le configurazioni del DB
|
56
|
+
class EnvConfigs < BaseDatabase::EnvConfigs
|
57
|
+
|
58
|
+
define_cfgs :database_name, default_env: "POSTGRES_DB", configuration_name: :database_name
|
59
|
+
define_cfgs :username, default_env: "POSTGRES_USER", configuration_name: :pg_user, default_value: 'postgres'
|
60
|
+
define_cfgs :password, default_env: "POSTGRES_PASSWORD", configuration_name: :pg_password
|
61
|
+
|
62
|
+
define_cfgs :database_version, default_env: "PG_MAJOR", configuration_name: :pg_version
|
63
|
+
|
64
|
+
end
|
65
|
+
|
66
|
+
private
|
67
|
+
|
68
|
+
# @param [EnvConfigs] config
|
69
|
+
def create_cmd(config)
|
70
|
+
create_cmd = []
|
71
|
+
create_cmd << "PGPASSWORD=\"#{config.password}\""
|
72
|
+
create_cmd << 'createdb'
|
73
|
+
create_cmd << "--username=#{config.username}"
|
74
|
+
create_cmd << config.database_name
|
75
|
+
|
76
|
+
logger.info { "CREATE COMMAND: #{create_cmd.join(' ')}" }
|
77
|
+
config.container.exec("bash -c '#{create_cmd.join(' ')} || true'")
|
78
|
+
end
|
79
|
+
|
80
|
+
# @param [EnvConfigs] config
|
81
|
+
# def drop_cmd(config)
|
82
|
+
# drop_cmd = []
|
83
|
+
# drop_cmd << "PGPASSWORD=\"#{config.password}\""
|
84
|
+
# drop_cmd << 'dropdb'
|
85
|
+
# drop_cmd << '--if-exists'
|
86
|
+
# drop_cmd << "--username=#{config.username}"
|
87
|
+
# drop_cmd << config.database_name
|
88
|
+
# drop_cmd
|
89
|
+
#
|
90
|
+
# logger.info { "DROP COMMAND: #{drop_cmd.join(' ')}" }
|
91
|
+
# config.container.exec("bash -c '#{drop_cmd.join(' ')}'")
|
92
|
+
# end
|
93
|
+
|
94
|
+
# @param [EnvConfigs] config
|
95
|
+
def restore_cmd(config, tmp_file)
|
96
|
+
restore_cmd = []
|
97
|
+
restore_cmd << "PGPASSWORD=\"#{config.password}\""
|
98
|
+
restore_cmd << 'pg_restore'
|
99
|
+
restore_cmd << '--no-acl'
|
100
|
+
restore_cmd << '--no-owner'
|
101
|
+
restore_cmd << "--username=#{config.username}"
|
102
|
+
restore_cmd << "--dbname=#{config.database_name}"
|
103
|
+
restore_cmd << tmp_file
|
104
|
+
restore_cmd
|
105
|
+
|
106
|
+
logger.info { "RESTORE COMMAND: #{restore_cmd.join(' ')}" }
|
107
|
+
config.container.exec("bash -c '#{restore_cmd.join(' ')}'")
|
108
|
+
end
|
109
|
+
|
110
|
+
# @param [EnvConfigs] config
|
111
|
+
def dump_cmd(config, file)
|
112
|
+
dump_cmd = []
|
113
|
+
dump_cmd << "PGPASSWORD=\"#{config.password}\""
|
114
|
+
dump_cmd << 'pg_dump'
|
115
|
+
dump_cmd << '--no-acl'
|
116
|
+
dump_cmd << '--no-owner'
|
117
|
+
dump_cmd << "--username=#{config.username}"
|
118
|
+
dump_cmd << '--format=custom'
|
119
|
+
dump_cmd << '--compress=9'
|
120
|
+
dump_cmd << config.database_name
|
121
|
+
dump_cmd
|
122
|
+
|
123
|
+
logger.info { "DUMP COMMAND: #{dump_cmd.join(' ')}" }
|
124
|
+
config.container.exec("bash -c '#{dump_cmd.join(' ')}' > #{file}")
|
125
|
+
|
126
|
+
end
|
127
|
+
|
128
|
+
|
129
|
+
# @param [EnvConfigs] config
|
130
|
+
def close_connections_and_drop_cmd(config)
|
131
|
+
cmd = []
|
132
|
+
cmd << "PGPASSWORD=\"#{config.password}\""
|
133
|
+
|
134
|
+
sql = []
|
135
|
+
sql << "SELECT pg_terminate_backend(pg_stat_activity.pid) FROM pg_stat_activity WHERE pg_stat_activity.datname = '\"'\"'#{config.database_name}'\"'\"' AND pid <> pg_backend_pid();;"
|
136
|
+
sql << "DROP DATABASE IF EXISTS #{config.database_name};"
|
137
|
+
|
138
|
+
cmd << "echo \"#{sql.join(" ")}\" "
|
139
|
+
cmd << '|'
|
140
|
+
cmd << 'psql'
|
141
|
+
cmd << "-U #{config.username}"
|
142
|
+
cmd << "postgres"
|
143
|
+
cmd
|
144
|
+
|
145
|
+
logger.info { "CLOSE CONNECTIONS COMMAND: #{cmd.join(' ')}" }
|
146
|
+
config.container.exec("bash -c '#{cmd.join(' ')}'")
|
147
|
+
end
|
148
|
+
|
149
|
+
# quello che fa capistrano quando copia in locale - utenze inventate
|
150
|
+
# gzip -d cortobio_production_new_2020-09-10-171742.sql.gz &&
|
151
|
+
# PGPASSWORD='root' psql -c "SELECT pg_terminate_backend(pg_stat_activity.pid) FROM pg_stat_activity WHERE pg_stat_activity.datname = 'development' AND pid <> pg_backend_pid();;" -U root -h 0.0.0.0 -p 32790 development;
|
152
|
+
# PGPASSWORD='root' dropdb -U root -h 0.0.0.0 -p 32790 development;
|
153
|
+
# PGPASSWORD='root' createdb -U root -h 0.0.0.0 -p 32790 development;
|
154
|
+
# PGPASSWORD='root' psql -U root -h 0.0.0.0 -p 32790 -d development < ./cortobio_production_new_2020-09-10-171742.sql
|
155
|
+
|
156
|
+
|
157
|
+
end
|
158
|
+
end
|
159
|
+
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: swarm_cluster_cli_ope
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.5.0.pre.2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Marino Bonetti
|
8
8
|
autorequire:
|
9
9
|
bindir: exe
|
10
10
|
cert_chain: []
|
11
|
-
date: 2020-09
|
11
|
+
date: 2020-11-09 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: thor
|
@@ -66,6 +66,20 @@ dependencies:
|
|
66
66
|
- - ">="
|
67
67
|
- !ruby/object:Gem::Version
|
68
68
|
version: '0'
|
69
|
+
- !ruby/object:Gem::Dependency
|
70
|
+
name: kubeclient
|
71
|
+
requirement: !ruby/object:Gem::Requirement
|
72
|
+
requirements:
|
73
|
+
- - "~>"
|
74
|
+
- !ruby/object:Gem::Version
|
75
|
+
version: '4.9'
|
76
|
+
type: :runtime
|
77
|
+
prerelease: false
|
78
|
+
version_requirements: !ruby/object:Gem::Requirement
|
79
|
+
requirements:
|
80
|
+
- - "~>"
|
81
|
+
- !ruby/object:Gem::Version
|
82
|
+
version: '4.9'
|
69
83
|
description: |-
|
70
84
|
Gestione di varie operazioni come sincronia con le cartelle bindate dei container (rsync) up o
|
71
85
|
down e possibilità di scaricare/caricare i file direttamente all'interno del cluster, in
|
@@ -97,6 +111,10 @@ files:
|
|
97
111
|
- lib/swarm_cluster_cli_ope/commands/task.rb
|
98
112
|
- lib/swarm_cluster_cli_ope/configuration.rb
|
99
113
|
- lib/swarm_cluster_cli_ope/configuration_concern.rb
|
114
|
+
- lib/swarm_cluster_cli_ope/k8s.rb
|
115
|
+
- lib/swarm_cluster_cli_ope/k8s_rsync/password
|
116
|
+
- lib/swarm_cluster_cli_ope/k8s_rsync/rsyncd.conf
|
117
|
+
- lib/swarm_cluster_cli_ope/k8s_rsync/rsyncd.secrets
|
100
118
|
- lib/swarm_cluster_cli_ope/logger_concern.rb
|
101
119
|
- lib/swarm_cluster_cli_ope/manager.rb
|
102
120
|
- lib/swarm_cluster_cli_ope/models/base.rb
|
@@ -110,9 +128,11 @@ files:
|
|
110
128
|
- lib/swarm_cluster_cli_ope/shell_command_execution.rb
|
111
129
|
- lib/swarm_cluster_cli_ope/shell_command_response.rb
|
112
130
|
- lib/swarm_cluster_cli_ope/sync_configs/base.rb
|
131
|
+
- lib/swarm_cluster_cli_ope/sync_configs/base_database.rb
|
113
132
|
- lib/swarm_cluster_cli_ope/sync_configs/copy.rb
|
114
133
|
- lib/swarm_cluster_cli_ope/sync_configs/env_configs.rb
|
115
134
|
- lib/swarm_cluster_cli_ope/sync_configs/mysql.rb
|
135
|
+
- lib/swarm_cluster_cli_ope/sync_configs/post_gres.rb
|
116
136
|
- lib/swarm_cluster_cli_ope/sync_configs/rsync.rb
|
117
137
|
- lib/swarm_cluster_cli_ope/sync_configs/sqlite3.rb
|
118
138
|
- lib/swarm_cluster_cli_ope/version.rb
|
@@ -137,9 +157,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
137
157
|
version: 2.3.0
|
138
158
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
139
159
|
requirements:
|
140
|
-
- - "
|
160
|
+
- - ">"
|
141
161
|
- !ruby/object:Gem::Version
|
142
|
-
version:
|
162
|
+
version: 1.3.1
|
143
163
|
requirements: []
|
144
164
|
rubygems_version: 3.0.8
|
145
165
|
signing_key:
|