swarm_cluster_cli_ope 0.1.6 → 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.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 4d080e1fbcc49d24e180f7cae13bf99415e85b7ae7a443c175a8251486fd75f5
4
- data.tar.gz: 6b4b0b8ffaf462a4f7ae9e7601276b40cf722860ecd3bfb1270a5734bbb6211d
3
+ metadata.gz: 473cc11423d57b9b40b361184587b1acdda0d14751b12266740eb98e1f1c7caa
4
+ data.tar.gz: 542e14fb88a4d40c34209853678e80fc0d2bddc90745aa9bd6eaee666e7fcf03
5
5
  SHA512:
6
- metadata.gz: fce5856e48f7d73ff31aac4c26fb2d7c0c235f0c36ab8a6fda65e79b7696f48f35faff221d5e97de4bfd8183d704c76ce11b3534b311fcf6697580c88cfeba0d
7
- data.tar.gz: 90c49135edaabb0d3e4f9abcb63880df81279159198429e803abcb96ac606a8ba908d4392375c52cda82ada9bcf95805d920b3e8a3d066525923daed3885c702
6
+ metadata.gz: 90fe0e391b0aa2eb12f1564153905db9fd294aa2817094da62dc1a7da7c3c663f7f94f99996d5f3c1e7818f1d8d214d2c1286fdefbe9eedfb932c3abdf224586
7
+ data.tar.gz: 24e26ab924509fbc0df1d03a67c59ec5d62d544a8cc0709f757012c2dcb6fd8915a049ad82ccec49316f19b4cdb65c1bac9f4c62e3a1c4231f5de7c316bbcbc1
@@ -1,7 +1,7 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- swarm_cluster_cli_ope (0.1.6)
4
+ swarm_cluster_cli_ope (0.2)
5
5
  activesupport
6
6
  open4
7
7
  thor (~> 1.0)
data/README.md CHANGED
@@ -36,6 +36,9 @@ FILE di configurazione base:
36
36
  3 DEBUG
37
37
 
38
38
 
39
+ ### ENV differenti
40
+ Tutti i comandi possono essere accompagnati con -e, per scopparli nel relativo ENVIRONMENT
41
+
39
42
  ### Configuratione di un progetto
40
43
  Si occupa di generare nel progetto il file di configurazione in cui impostare impostazioni specifiche di progetto
41
44
  quali stack_name (.swarm_cluster_project)
@@ -98,11 +101,14 @@ nel file di configurazione creato nella home aggiungere la chiave "dev_mode":1 p
98
101
 
99
102
  ### Abbiamo due tasks swarm di simulazione
100
103
  ```shell script
101
- docker stack deploy -c test_folder/test_1/docker_compose.yml test1
104
+ docker stack deploy -c test_folder/test_1/docker-compose.yml test1
105
+ docker stack deploy -c test_folder/test_1/docker-compose.yml test1_staging
102
106
  docker stack deploy -c test_folder/test_2/docker_compose.yml test2
103
107
  ```
104
108
 
105
- To install this gem onto your local machine, run `bundle exec rake install`. To release a new version, update the version number in `version.rb`, and then run `bundle exec rake release`, which will create a git tag for the version, push git commits and tags, and push the `.gem` file to [rubygems.org](https://rubygems.org).
109
+ To install this gem onto your local machine, run `bundle exec rake install`. To release a new version, update the version
110
+ number in `version.rb`, and then run `bundle exec rake release`, which will create a git tag for the version, push git
111
+ commits and tags, and push the `.gem` file to [rubygems.org](https://rubygems.org).
106
112
 
107
113
 
108
114
  ## License
@@ -11,6 +11,9 @@ module SwarmClusterCliOpe
11
11
  true
12
12
  end
13
13
 
14
+ class_option :environment, required: false, type: :string, aliases: [:e],
15
+ desc: "Esegue tutte le operazioni nell'env scelto, il file di configurazione dovrà avere il nome: #{Configuration.cfgs_project_file_name}.ENV"
16
+
14
17
  desc "install", "Creazione della configurazione base della gemma"
15
18
 
16
19
  def install
@@ -40,7 +43,9 @@ module SwarmClusterCliOpe
40
43
  desc "config", "Visualizza le configurazioni mergiate (HOME + Project configuration[#{Configuration.cfgs_project_file_name}])"
41
44
 
42
45
  def config
43
- puts JSON.pretty_generate(cfgs.class.merged_configurations)
46
+ cfgs.env(options[:environment]) do
47
+ puts JSON.pretty_generate(cfgs.merged_configurations)
48
+ end
44
49
  end
45
50
 
46
51
 
@@ -54,88 +59,93 @@ module SwarmClusterCliOpe
54
59
  end
55
60
 
56
61
  desc "services", "lista dei servizi per uno stack"
57
- option :stack_name, required: false, type: :string, default: cfgs.stack_name
62
+ option :stack_name, required: false, type: :string
58
63
 
59
64
  def services
60
- Models::Service.all(stack_name: options[:stack_name]).each do |s|
61
- puts s.name
65
+ cfgs.env(options[:environment]) do |cfgs|
66
+ stack_name = options[:stack_name] || cfgs.stack_name
67
+ Models::Service.all(stack_name: stack_name).each do |s|
68
+ puts s.name
69
+ end
62
70
  end
63
71
  end
64
72
 
65
73
  desc "mc SERVICE_NAME", "Apre MC tra la cartella attuale e il container (potrebbe dar luogo a degli errori, ma funziona)"
66
- option :stack_name, required: false, type: :string, default: cfgs.stack_name
74
+ option :stack_name, required: false, type: :string
67
75
 
68
76
  def mc(service_name)
69
-
70
- # Disabilito output della libreria
71
- MakeMakefile::Logging.instance_variable_set(:@logfile, File::NULL)
72
- unless find_executable 'mc'
73
- puts "Non hai installato MC"
74
- exit 0
75
- end
76
-
77
- begin
78
- container = Models::Container.find_by_service_name(service_name, stack_name: options[:stack_name])
79
-
80
- server = container.node.hostname
81
-
82
- # Creo container ssh
83
- # DOCKER_HOST=ssh://swarm_node_1 docker run --rm -d -p 12222:22 \
84
- # --volumes-from sistemi-test_swarm_cluster_cli_wordpress.1.zbbz1xxh4vzzccndvs973jnuc \
85
- # sickp/alpine-sshd:7.5
86
- #
87
- cmd = container.docker_command
88
- cmd.base_suffix_command = ''
89
- shell_operation = cmd.command do |c|
90
- c.add("run --rm -d -p 42222:22 --volumes-from #{container.id} sickp/alpine-sshd:7.5")
77
+ cfgs.env(options[:environment]) do |cfgs|
78
+ stack_name = options[:stack_name] || cfgs.stack_name
79
+ # Disabilito output della libreria
80
+ MakeMakefile::Logging.instance_variable_set(:@logfile, File::NULL)
81
+ unless find_executable 'mc'
82
+ puts "Non hai installato MC"
83
+ exit 0
91
84
  end
92
85
 
93
- puts "Creazione container #{shell_operation.string_command}"
94
- id_container = shell_operation.execute.raw_result[:stdout]
95
- puts "Container generato con id:#{id_container}"
96
-
97
- # eseguo tunnel verso nodo e container ssh
98
- socket_ssh_path = "/tmp/socket_ssh_#{id_container}"
99
- # ssh -f -N -T -M -S <path-to-socket> -L 13333:0.0.0.0:42222 <server>
100
- cmd_tunnel = ["ssh", "-f -N -T -M", "-S #{socket_ssh_path}", "-L 13333:0.0.0.0:42222", server].join(" ")
101
- puts "Apro tunnel"
102
- puts cmd_tunnel
103
- system(cmd_tunnel)
104
-
105
- # apro MC
106
- # mc . sftp://root:root@0.0.0.0:13333
107
- mc_cmd = "mc . sftp://root:root@0.0.0.0:13333"
108
- puts "Apro MC"
109
- puts mc_cmd
110
- system(mc_cmd)
111
- ensure
112
- if socket_ssh_path
113
- # chiudo tunnel
114
- # ssh -S <path-to-socket> -O exit <server>
115
- close_tunnel_cmd = "ssh -S #{socket_ssh_path} -O exit #{server}"
116
- puts "Chiudo tunnel"
117
- # say close_tunnel_cmd
118
- ShellCommandExecution.new(close_tunnel_cmd).execute
119
- end
86
+ begin
87
+ container = Models::Container.find_by_service_name(service_name, stack_name: stack_name)
120
88
 
121
- if id_container
122
- # cancello container
123
- # docker stop #{id_container}
124
- puts "Spengo container di appoggio"
125
- puts "docker stop #{id_container}"
89
+ server = container.node.hostname
90
+
91
+ # Creo container ssh
92
+ # DOCKER_HOST=ssh://swarm_node_1 docker run --rm -d -p 12222:22 \
93
+ # --volumes-from sistemi-test_swarm_cluster_cli_wordpress.1.zbbz1xxh4vzzccndvs973jnuc \
94
+ # sickp/alpine-sshd:7.5
95
+ #
126
96
  cmd = container.docker_command
127
97
  cmd.base_suffix_command = ''
128
- stop_ssh_container = cmd.command do |c|
129
- c.add("stop #{id_container}")
98
+ shell_operation = cmd.command do |c|
99
+ c.add("run --rm -d -p 42222:22 --volumes-from #{container.id} sickp/alpine-sshd:7.5")
100
+ end
101
+
102
+ puts "Creazione container #{shell_operation.string_command}"
103
+ id_container = shell_operation.execute.raw_result[:stdout]
104
+ puts "Container generato con id:#{id_container}"
105
+
106
+ # eseguo tunnel verso nodo e container ssh
107
+ socket_ssh_path = "/tmp/socket_ssh_#{id_container}"
108
+ # ssh -f -N -T -M -S <path-to-socket> -L 13333:0.0.0.0:42222 <server>
109
+ cmd_tunnel = ["ssh", "-f -N -T -M", "-S #{socket_ssh_path}", "-L 13333:0.0.0.0:42222", server].join(" ")
110
+ puts "Apro tunnel"
111
+ puts cmd_tunnel
112
+ system(cmd_tunnel)
113
+
114
+ # apro MC
115
+ # mc . sftp://root:root@0.0.0.0:13333
116
+ mc_cmd = "mc . sftp://root:root@0.0.0.0:13333"
117
+ puts "Apro MC"
118
+ puts mc_cmd
119
+ system(mc_cmd)
120
+ ensure
121
+ if socket_ssh_path
122
+ # chiudo tunnel
123
+ # ssh -S <path-to-socket> -O exit <server>
124
+ close_tunnel_cmd = "ssh -S #{socket_ssh_path} -O exit #{server}"
125
+ puts "Chiudo tunnel"
126
+ # say close_tunnel_cmd
127
+ ShellCommandExecution.new(close_tunnel_cmd).execute
130
128
  end
131
- stop_ssh_container.execute
132
- end
133
129
 
130
+ if id_container
131
+ # cancello container
132
+ # docker stop #{id_container}
133
+ puts "Spengo container di appoggio"
134
+ puts "docker stop #{id_container}"
135
+ cmd = container.docker_command
136
+ cmd.base_suffix_command = ''
137
+ stop_ssh_container = cmd.command do |c|
138
+ c.add("stop #{id_container}")
139
+ end
140
+ stop_ssh_container.execute
141
+ end
142
+
143
+ end
134
144
  end
135
145
  end
136
146
 
137
147
  desc "cp SRC DEST", "Copia la sorgente in destinazione"
138
- option :stack_name, required: false, type: :string, default: cfgs.stack_name
148
+ option :stack_name, required: false, type: :string
139
149
  long_desc <<-LONGDESC
140
150
  SRC e DEST possono essere un servizio, solo uno di essi può essere un servizio (TODO)
141
151
  Per identificare che sia un servizio controllo se nella stringa è presete il :
@@ -144,46 +154,73 @@ module SwarmClusterCliOpe
144
154
  LONGDESC
145
155
 
146
156
  def cp(src, dest)
147
- #identifico quale dei due è il servizio e quale la path
148
- if src.match(/^(.*)\:/)
149
- container = Models::Container.find_by_service_name(Regexp.last_match[1], stack_name: options[:stack_name])
150
- ris = container.copy_out(src.match(/\:(.*)$/)[1], dest)
151
- else
152
- container = Models::Container.find_by_service_name(dest.match(/^(.*)\:/)[1], stack_name: options[:stack_name])
153
- ris = container.copy_in(src, dest.match(/\:(.*)$/)[1])
157
+ cfgs.env(options[:environment]) do |cfgs|
158
+
159
+ cfgs.stack_name = options[:stack_name] || cfgs.stack_name
160
+
161
+ #identifico quale dei due è il servizio e quale la path
162
+ if src.match(/^(.*)\:/)
163
+ service_name = Regexp.last_match[1]
164
+ remote = src.match(/\:(.*)$/)[1]
165
+ local = dest
166
+ execute = :pull
167
+ else
168
+ service_name = dest.match(/^(.*)\:/)[1]
169
+ remote = dest.match(/\:(.*)$/)[1]
170
+ local = src
171
+ execute = :push
172
+ end
173
+
174
+
175
+ cmd = SyncConfigs::Copy.new(cfgs, {
176
+ service: service_name,
177
+ how: 'copy',
178
+ configs: {
179
+ local: local,
180
+ remote: remote
181
+ }
182
+ })
183
+
184
+ puts "COMPLETATO" if cmd.send(execute)
185
+
154
186
  end
155
- puts "COMPLETATO" if ris
156
187
  end
157
188
 
158
189
 
159
190
  desc "configure_project STACK_NAME", "Genera il file di configurazione del progetto contenente il nome dello stack"
160
191
 
161
192
  def configure_project(stack_name)
162
- cfgs.stack_name = stack_name
163
- cfgs.save_project_cfgs
193
+ cfgs.env(options[:environment]) do |c|
194
+ c.stack_name = stack_name
195
+ c.save_project_cfgs
196
+ end
164
197
  end
165
198
 
199
+
166
200
  desc "service_shell SERVICE_NAME", "apre una shell [default bash] dentro al container"
167
- option :stack_name, required: false, type: :string, default: cfgs.stack_name
201
+ option :stack_name, required: false, type: :string
168
202
  option :shell, required: false, type: :string, default: 'bash'
169
203
 
170
204
  def service_shell(service_name)
171
- container = Models::Container.find_by_service_name(service_name, stack_name: options[:stack_name])
205
+ cfgs.env(options[:environment]) do |cfgs|
206
+ stack_name = options[:stack_name] || cfgs.stack_name
207
+ container = Models::Container.find_by_service_name(service_name, stack_name: stack_name)
172
208
 
173
- cmd = container.docker_command
174
- cmd.base_suffix_command = ''
175
- shell_operation = cmd.command do |c|
176
- c.add("exec -it #{container.id} #{options[:shell]}")
177
- end
209
+ cmd = container.docker_command
210
+ cmd.base_suffix_command = ''
211
+ shell_operation = cmd.command do |c|
212
+ c.add("exec -it #{container.id} #{options[:shell]}")
213
+ end
178
214
 
179
- say "Stai entrando della shell in #{options[:shell]} del container #{options[:stack_name]}->#{container.name}[#{container.id}]"
180
- system(shell_operation.string_command)
181
- say "Shell chiusa"
215
+ say "Stai entrando della shell in #{options[:shell]} del container #{stack_name}->#{container.name}[#{container.id}]"
216
+ system(shell_operation.string_command)
217
+ say "Shell chiusa"
218
+ end
182
219
  end
183
220
 
184
221
 
185
222
  desc "rsync_binded_from", "esegue un rsync dalla cartella bindata (viene sincronizzato il contenuto)"
186
- option :stack_name, required: false, type: :string, default: cfgs.stack_name
223
+ option :stack_name, required: false, type: :string
187
224
  option :service_name, required: true, type: :string
188
225
  option :binded_container_folders, required: true, type: :string, desc: "path della cartella bindata all'interno del container da sincronizzare"
189
226
  option :local_folder, required: true, type: :string, desc: "path della cartella dove sincronizzare il comando"
@@ -195,7 +232,7 @@ module SwarmClusterCliOpe
195
232
  end
196
233
 
197
234
  desc "rsync_binded_to", "esegue un rsync verso la cartella bindata"
198
- option :stack_name, required: false, type: :string, default: cfgs.stack_name
235
+ option :stack_name, required: false, type: :string
199
236
  option :service_name, required: true, type: :string
200
237
  option :binded_container_folders, required: true, type: :string, desc: "path della cartella bindata all'interno del container da sincronizzare"
201
238
  option :local_folder, required: true, type: :string, desc: "path della cartella dove sincronizzare il comando"
@@ -206,46 +243,54 @@ module SwarmClusterCliOpe
206
243
  end
207
244
  end
208
245
 
246
+ desc "stack_pull", "Si occupa di scaricare,utilizzando le configurazioni presenti, i dati dallo stack remoto"
247
+ long_desc <<-LONGDESC
248
+ le configurazioni sono contenute nell'array: sync_configs. \n
249
+ ogni configurazione è composta da: \n
250
+ { \n
251
+ service:"" \n
252
+ how:"" \n
253
+ configs:{ }\n
254
+ }\n
255
+ - service è il nome del servizio\n
256
+ - how è il come sincronizzare, definendo la tipologia:\n
257
+ - pg -> DB\n TODO
258
+ - mysql -> DB\n TODO
259
+ - sqlite3 -> DB\n
260
+ - rsync -> RSYNC\n
261
+ - configs: è un hash con le configurazioni per ogni tipo di sincronizzazione\n
262
+ LONGDESC
209
263
 
210
- private
211
-
212
- def rsync_binded(direction: :down, options: {})
213
-
214
- # trovo il container del servizio
215
- container = Models::Container.find_by_service_name(options[:service_name], stack_name: options[:stack_name])
216
-
217
- if container.nil?
218
- say "Container non trovato con #{options[:stack_name]}@##{options[:service_name]}"
219
- exit 0
264
+ def stack_pull
265
+ cfgs.env(options[:environment]) do |cfgs|
266
+ cfgs.sync_configurations.each do |sync|
267
+ sync.pull
268
+ end
220
269
  end
270
+ end
221
271
 
272
+ private
222
273
 
223
- # trovo la cartella bindata e la relativa cartella sul nodo
224
- volume = container.mapped_volumes.find { |v| v.destination == options[:binded_container_folders] and v.is_binded? }
225
- if volume.nil?
226
- say "Non ho trovato il volume bindato con questa destinazione all'interno del container #{options[:binded_container_folders]}"
227
- exit 0
228
- end
229
-
230
- #costruisco il comando rsync fra cartella del nodo e cartella sul pc
231
- cmd = ["rsync", "-zr", "--delete"]
232
- if direction == :down
233
- cmd << "#{volume.ssh_connection_path}/."
234
- # creo la cartella in locale se non esiste
235
- FileUtils.mkdir_p(options[:local_folder])
236
- cmd << options[:local_folder]
237
- end
238
- if direction == :up
239
- cmd << "#{options[:local_folder]}/."
240
- cmd << volume.ssh_connection_path
241
- end
274
+ def rsync_binded(direction: :down, options: {})
275
+ cfgs.env(options[:environment]) do |cfgs|
276
+ cfgs.stack_name = options[:stack_name] || cfgs.stack_name
277
+ sync = SyncConfigs::Rsync.new(cfgs, {
278
+ service: options[:service_name],
279
+ how: 'rsync',
280
+ configs: {
281
+ local: options[:local_folder],
282
+ remote: options[:binded_container_folders]
283
+ }
284
+ })
285
+
286
+ if direction == :down
287
+ sync.pull
288
+ end
289
+ if direction == :up
290
+ sync.push
291
+ end
242
292
 
243
- cmd = ShellCommandExecution.new(cmd)
244
293
 
245
- say "Comando da eseguire:"
246
- say " #{cmd.string_command}"
247
- if yes?("Confermare il comando?[y,yes]")
248
- cmd.execute
249
294
  end
250
295
  end
251
296
  end
@@ -15,6 +15,9 @@ module SwarmClusterCliOpe
15
15
  #@return [String] nome dello stack con cui lavoriamo
16
16
  attr_accessor :stack_name
17
17
 
18
+ #@return [String] in che enviroment siamo, altrimenti siamo nel default
19
+ attr_accessor :environment
20
+
18
21
  NoBaseConfigurations = Class.new(Error)
19
22
 
20
23
  ##
@@ -25,6 +28,19 @@ module SwarmClusterCliOpe
25
28
  @_managers = self.nodes.select { |n| read_managers_cache_list.include?(n.name) }.collect { |c| Manager.new(name: c.name.to_s, connection_uri: c.connection_uri) }
26
29
  end
27
30
 
31
+ ##
32
+ # Serve per entrare nell'env corretto.
33
+ # passando l'env, tutto quello eseguito nello yield sarà gestito in quell'env.
34
+ # Verrà controllato quindi che esista il relativo file di configurazion
35
+ def env(enviroment = nil)
36
+ unless enviroment.nil?
37
+ @environment = enviroment.to_s.to_sym
38
+ end
39
+ logger.info { "ENV: #{@environment ? @environment : "BASE"}" }
40
+ yield self
41
+ @environment = nil
42
+ end
43
+
28
44
  ##
29
45
  # Esegue un refresh della lista dei manager, ciclando su tutti i nodi, e scrivendo in /tmp un file temporaneo con
30
46
  # con la lista dei nomi dei managers
@@ -48,8 +64,10 @@ module SwarmClusterCliOpe
48
64
  #
49
65
  # @return [Array<SwarmClusterCliOpe::Node>]
50
66
  def nodes
51
- return @_nodes if @_nodes
52
- @_nodes = self.class.merged_configurations[:connections_maps].collect { |m, c| Node.new(name: m.to_s, connection_uri: c) }
67
+ @_nodes ||= Hash.new do |hash, key|
68
+ hash[key] = self.merged_configurations[:connections_maps].collect { |m, c| Node.new(name: m.to_s, connection_uri: c) }
69
+ end
70
+ @_nodes[environment]
53
71
  end
54
72
 
55
73
  ##
@@ -58,22 +76,31 @@ module SwarmClusterCliOpe
58
76
  # @param [Array<SwarmClusterCliOpe::Node>]
59
77
  # @return [Configuration]
60
78
  def nodes=(objs)
61
- @_nodes = objs
79
+ nodes[environment] = objs
62
80
  self
63
81
  end
64
82
 
65
83
  # @return [String,NilClass] nome dello stack del progetto se configurato
66
84
  def stack_name
67
- return @stack_name if @stack_name
68
85
  return nil unless self.class.exist_base?
69
- @stack_name = self.class.merged_configurations[:stack_name] if self.class.merged_configurations.key?(:stack_name)
86
+ @stack_name ||= Hash.new do |hash, key|
87
+ hash[key] = merged_configurations[:stack_name] if merged_configurations.key?(:stack_name)
88
+ end
89
+ @stack_name[environment]
90
+ end
91
+
92
+ ##
93
+ # Imposta il nome dello stack
94
+ def stack_name=(objs)
95
+ stack_name #lo richiamo per fargli generare la variabile di classe
96
+ @stack_name[environment] = objs
70
97
  end
71
98
 
72
99
  ##
73
100
  # Livello di logging
74
101
  # @return [Integer]
75
102
  def logger_level
76
- self.class.merged_configurations[:log_level].to_s || "0"
103
+ merged_configurations[:log_level].to_s || "0"
77
104
  rescue SwarmClusterCliOpe::Configuration::NoBaseConfigurations
78
105
  # quando andiamo in errore durante l'installazione per avere le informazioni per il logger.
79
106
  # Usiamo lo standard
@@ -85,7 +112,7 @@ module SwarmClusterCliOpe
85
112
  # @return [TrueClass, FalseClass]
86
113
  def development_mode?
87
114
  return false unless self.class.exist_base?
88
- self.class.merged_configurations.key?(:dev_mode)
115
+ merged_configurations.key?(:dev_mode)
89
116
  end
90
117
 
91
118
  ##
@@ -110,8 +137,8 @@ module SwarmClusterCliOpe
110
137
  ##
111
138
  # Si occupa del salvataggio delle configurazioni di progetto, se abbiamo lo stack_name
112
139
  def save_project_cfgs
113
- if @stack_name
114
- File.open(File.join(FileUtils.pwd, self.class.cfgs_project_file_name), "wb") do |f|
140
+ if stack_name
141
+ File.open(File.join(FileUtils.pwd, self.class.cfgs_project_file_name(with_env: @environment)), "wb") do |f|
115
142
  f.write({
116
143
  stack_name: stack_name
117
144
  }.to_json)
@@ -136,13 +163,31 @@ module SwarmClusterCliOpe
136
163
  nodes.find { |c| c.id == node_id }
137
164
  end
138
165
 
166
+ ##
167
+ # Elenco di tutte le configurazioni di sincronizzazione
168
+ def sync_configurations
169
+ merged_configurations[:sync_configs].collect do |c|
170
+
171
+ case c[:how]
172
+ when 'sqlite3'
173
+ SyncConfigs::Sqlite3.new(self, c)
174
+ when 'rsync'
175
+ SyncConfigs::Rsync.new(self, c)
176
+ else
177
+ logger.error { "CONFIGURAIONE NON PREVISTA: #{c[:how]}" }
178
+ end
179
+
180
+ end.compact
181
+ end
182
+
139
183
  private
140
184
 
141
185
  ##
142
186
  # nome del file in cui salvare le configurazioni di progetto
143
187
  # @return [String]
144
- def self.cfgs_project_file_name
145
- '.swarm_cluster_project'
188
+ # @param [nil|String] with_env nome dell'env da cercare
189
+ def self.cfgs_project_file_name(with_env: nil)
190
+ ".swarm_cluster_project#{with_env ? ".#{with_env}" : ""}"
146
191
  end
147
192
 
148
193
  ##
@@ -150,7 +195,7 @@ module SwarmClusterCliOpe
150
195
  # quindi ogni ora si autoripulisce e con un md5 delle configurazioni di base
151
196
  # @return [String]
152
197
  def swarm_manager_cache_path
153
- md5 = Digest::MD5.hexdigest(self.class.merged_configurations.to_json)
198
+ md5 = Digest::MD5.hexdigest(self.merged_configurations.to_json)
154
199
  file_name = Time.now.strftime(".swarm_cluster_cli_manager_cache-%Y%m%d%H-#{md5}")
155
200
  File.join("/tmp", file_name)
156
201
  end
@@ -164,29 +209,51 @@ module SwarmClusterCliOpe
164
209
  JSON.parse(File.read(self.base_cfg_path)).deep_symbolize_keys
165
210
  end
166
211
 
212
+ public
213
+
167
214
  ## Cerca le configurazioni di progetto e le mergia se sono presenti
168
215
  # @return [Hash]
169
- def self.merged_configurations
170
- return @_merged_configurations if @_merged_configurations
216
+ def merged_configurations
217
+ return @_merged_configurations[@environment] if @_merged_configurations
218
+
219
+ @_merged_configurations = Hash.new do |hash, key|
220
+ folder = FileUtils.pwd
221
+ default_file = looped_file(folder, self.class.cfgs_project_file_name)
222
+ enviroment_file = looped_file(folder, self.class.cfgs_project_file_name(with_env: key))
223
+
224
+ project_cfgs = {}
225
+ unless default_file.nil?
226
+ project_cfgs = JSON.parse(File.read(default_file)).deep_symbolize_keys
227
+ end
228
+
229
+ unless enviroment_file.nil?
230
+ project_cfgs.merge!(JSON.parse(File.read(enviroment_file)).deep_symbolize_keys)
231
+ end
232
+
233
+ logger.debug { "CONFIGS[#{@environment}]: #{project_cfgs.inspect}" }
234
+ hash[key] = self.class.read_base.merge(project_cfgs)
235
+ end
236
+
237
+ @_merged_configurations[@environment]
238
+
239
+ end
240
+
241
+ private
242
+
243
+ def looped_file(start_folder, file)
171
244
  project_file = nil
172
- folder = FileUtils.pwd
173
245
  loop do
174
246
 
175
- if File.exist?(File.join(folder, cfgs_project_file_name))
176
- project_file = File.join(folder, cfgs_project_file_name)
247
+ if File.exist?(File.join(start_folder, file))
248
+ project_file = File.join(start_folder, file)
177
249
  end
178
250
 
179
251
  break unless project_file.nil?
180
- break if folder == '/'
181
- folder = File.expand_path("..", folder)
182
- end
183
-
184
- project_cfgs = {}
185
- unless project_file.nil?
186
- project_cfgs = JSON.parse(File.read(project_file)).deep_symbolize_keys
252
+ break if start_folder == '/'
253
+ start_folder = File.expand_path("..", start_folder)
187
254
  end
188
255
 
189
- @_merged_configurations = read_base.merge(project_cfgs)
256
+ project_file
190
257
  end
191
258
 
192
259
  end
@@ -0,0 +1,35 @@
1
+ module SwarmClusterCliOpe
2
+ module SyncConfigs
3
+ class Base < Thor::Shell::Basic
4
+
5
+ #@return [String] nome del servizio dello stack
6
+ attr_accessor :service
7
+
8
+ # @param [Hash] configs
9
+ # @param [Continuation] stack_cfgs
10
+ def initialize(stack_cfgs, configs)
11
+ super()
12
+ @configs = configs
13
+
14
+ @service = configs[:service]
15
+ @stack_cfgs = stack_cfgs
16
+ end
17
+
18
+
19
+ delegate :stack_name, to: :@stack_cfgs
20
+
21
+ ##
22
+ # Funzione che dobbiamo sovrascrivere per identificare cosa fare quando scarichiamo i dati
23
+ def pull
24
+ raise "TO OVERRIDE"
25
+ end
26
+
27
+ ##
28
+ # Funzione che dobbiamo sovrascrivere per identificare cosa fare quando carichiamo i dati
29
+ def push
30
+ raise "TO OVERRIDE"
31
+ end
32
+
33
+ end
34
+ end
35
+ end
@@ -0,0 +1,35 @@
1
+ module SwarmClusterCliOpe
2
+ module SyncConfigs
3
+ class Copy < Base
4
+
5
+ # @return [String]
6
+ def local_folder
7
+ @configs[:configs][:local]
8
+ end
9
+
10
+ # @return [String]
11
+ def remote_folder
12
+ @configs[:configs][:remote]
13
+ end
14
+
15
+ # @return [TrueClass, FalseClass]
16
+ def push
17
+ container.copy_in(local_folder,remote_folder)
18
+ end
19
+
20
+ # @return [TrueClass, FalseClass]
21
+ def pull
22
+ container.copy_out(remote_folder,local_folder)
23
+ end
24
+
25
+
26
+ private
27
+ # @return [SwarmClusterCliOpe::Models::Container]
28
+ def container
29
+ Models::Container.find_by_service_name(service, stack_name: stack_name)
30
+ end
31
+
32
+
33
+ end
34
+ end
35
+ end
@@ -0,0 +1,74 @@
1
+ module SwarmClusterCliOpe
2
+ module SyncConfigs
3
+ class Rsync < Base
4
+
5
+
6
+ # @return [String]
7
+ def local_folder
8
+ @configs[:configs][:local]
9
+ end
10
+
11
+ # @return [String]
12
+ def remote_folder
13
+ @configs[:configs][:remote]
14
+ end
15
+
16
+
17
+ # @return [SwarmClusterCliOpe::ShellCommandResponse]
18
+ def push
19
+ execute(direction: :up)
20
+ end
21
+
22
+ # @return [SwarmClusterCliOpe::ShellCommandResponse]
23
+ def pull
24
+ execute(direction: :down)
25
+ end
26
+
27
+
28
+ private
29
+ def execute(direction: :down)
30
+
31
+ # trovo il container del servizio
32
+ container = Models::Container.find_by_service_name(service, stack_name: stack_name)
33
+
34
+ if container.nil?
35
+ say "Container non trovato con #{stack_name}@##{service}"
36
+ exit 0
37
+ end
38
+
39
+
40
+ # trovo la cartella bindata e la relativa cartella sul nodo
41
+ volume = container.mapped_volumes.find { |v| v.destination == remote_folder and v.is_binded? }
42
+ if volume.nil?
43
+ say "Non ho trovato il volume bindato con questa destinazione all'interno del container #{remote_folder}"
44
+ exit 0
45
+ end
46
+
47
+ #costruisco il comando rsync fra cartella del nodo e cartella sul pc
48
+ cmd = ["rsync", "-zr", "--delete"]
49
+ if direction == :down
50
+ cmd << "#{volume.ssh_connection_path}/."
51
+ # creo la cartella in locale se non esiste
52
+ FileUtils.mkdir_p(local_folder)
53
+ cmd << local_folder
54
+ end
55
+ if direction == :up
56
+ cmd << "#{local_folder}/."
57
+ cmd << volume.ssh_connection_path
58
+ end
59
+
60
+ cmd = ShellCommandExecution.new(cmd)
61
+
62
+ say "Comando da eseguire:"
63
+ say " #{cmd.string_command}"
64
+ if yes?("Confermare il comando?[y,yes]")
65
+ cmd.execute
66
+ end
67
+
68
+
69
+ end
70
+
71
+
72
+ end
73
+ end
74
+ end
@@ -0,0 +1,8 @@
1
+ module SwarmClusterCliOpe
2
+ module SyncConfigs
3
+ class Sqlite3 < Copy
4
+
5
+
6
+ end
7
+ end
8
+ end
@@ -1,3 +1,3 @@
1
1
  module SwarmClusterCliOpe
2
- VERSION = "0.1.6"
2
+ VERSION = "0.2"
3
3
  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.1.6
4
+ version: '0.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-05-12 00:00:00.000000000 Z
11
+ date: 2020-07-03 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: thor
@@ -107,6 +107,10 @@ files:
107
107
  - lib/swarm_cluster_cli_ope/node.rb
108
108
  - lib/swarm_cluster_cli_ope/shell_command_execution.rb
109
109
  - lib/swarm_cluster_cli_ope/shell_command_response.rb
110
+ - lib/swarm_cluster_cli_ope/sync_configs/base.rb
111
+ - lib/swarm_cluster_cli_ope/sync_configs/copy.rb
112
+ - lib/swarm_cluster_cli_ope/sync_configs/rsync.rb
113
+ - lib/swarm_cluster_cli_ope/sync_configs/sqlite3.rb
110
114
  - lib/swarm_cluster_cli_ope/version.rb
111
115
  - lib/swarm_cluster_cli_ope/worker.rb
112
116
  - swarm_cluster_cli_ope.gemspec
@@ -133,7 +137,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
133
137
  - !ruby/object:Gem::Version
134
138
  version: '0'
135
139
  requirements: []
136
- rubygems_version: 3.0.6
140
+ rubygems_version: 3.0.8
137
141
  signing_key:
138
142
  specification_version: 4
139
143
  summary: WIP Gemma per la gestione del cluster swarm