swarm_cluster_cli_ope 0.4.2 → 0.5.0.pre.5

Sign up to get free protection for your applications and to get access to all the features.
@@ -0,0 +1,14 @@
1
+ syslog facility = local3
2
+ read only = no
3
+ list = yes
4
+ auth users = root
5
+ secrets file = /tmp/rsyncd.secrets
6
+ hosts allow = 0.0.0.0/0
7
+ uid = 0
8
+ gid = 0
9
+
10
+ [archives]
11
+ comment = archives goes here
12
+ path = /
13
+ uid = root
14
+ gid = root
@@ -0,0 +1,28 @@
1
+ require 'active_support/concern'
2
+ module SwarmClusterCliOpe
3
+ module Kubernetes
4
+ module SyncConfigs
5
+ module BaseDecorator
6
+ extend ActiveSupport::Concern
7
+
8
+ included do
9
+
10
+ delegate :namespace, :context, to: :@stack_cfgs
11
+
12
+ private
13
+
14
+ # @return [SwarmClusterCliOpe::Kubernetes::Pod]
15
+ def container
16
+ return @service if @service.is_a? SwarmClusterCliOpe::Kubernetes::Pod
17
+ @_container ||= Pod.find_by_selector(service, namespace: namespace, context: context)
18
+ end
19
+
20
+ end
21
+
22
+ # module ClassMethods
23
+
24
+ # end
25
+ end
26
+ end
27
+ end
28
+ end
@@ -0,0 +1,127 @@
1
+ module SwarmClusterCliOpe
2
+ module Kubernetes
3
+ module SyncConfigs
4
+ class Rsync < SwarmClusterCliOpe::SyncConfigs::Base
5
+
6
+ include BaseDecorator
7
+
8
+ # @return [String]
9
+ def local_folder
10
+ @configs[:configs][:local]
11
+ end
12
+
13
+ # @return [String]
14
+ def remote_folder
15
+ @configs[:configs][:remote]
16
+ end
17
+
18
+
19
+ # @return [SwarmClusterCliOpe::ShellCommandResponse]
20
+ def push
21
+ execute(direction: :up)
22
+ end
23
+
24
+ # @return [SwarmClusterCliOpe::ShellCommandResponse]
25
+ def pull
26
+ execute(direction: :down)
27
+ end
28
+
29
+
30
+ private
31
+
32
+ def execute(direction: :down)
33
+
34
+ if container.nil?
35
+ say "Container non trovato"
36
+ exit
37
+ end
38
+
39
+
40
+ if yes? "Attenzione, i dati locali o remoti verranno sovrascritti/cancellati?[y,yes]"
41
+
42
+ podname = container.name
43
+
44
+ if namespace.nil?
45
+ say "Mancata configurazione del namespace tramite argomento o .swarm_cluster_project"
46
+ exit
47
+ end
48
+
49
+ cmd = container.exec(['bash -c "apt update && apt install -yq rsync psmisc"'])
50
+ if cmd.execute.failed?
51
+ puts "Problemi nell'installazione di rsync nel pod"
52
+ else
53
+ cmd = container.cp_in(File.expand_path("../../rsync_cfgs/rsyncd.conf", __FILE__), "/tmp/.")
54
+ copy_1 = cmd.execute.failed?
55
+ cmd = container.cp_in(File.expand_path("../../rsync_cfgs/rsyncd.secrets", __FILE__), "/tmp/.")
56
+ copy_2 = cmd.execute.failed?
57
+ cmd = container.exec(['bash -c "chmod 600 /tmp/rsyncd.secrets && chown root /tmp/*"'])
58
+ chmod = cmd.execute.failed?
59
+ if copy_1 or copy_2 or chmod
60
+ puts "problema nella copia dei file di configurazione nel pod"
61
+ else
62
+
63
+ begin
64
+ cmd = container.exec('bash -c "rsync --daemon --config=/tmp/rsyncd.conf --verbose --log-file=/tmp/rsync.log"')
65
+ if cmd.execute.failed?
66
+ say "Rsync non Inizializzato"
67
+ else
68
+ begin
69
+ local_port = rand(30000..40000)
70
+
71
+ p = IO.popen(container.base_cmd("port-forward #{podname} #{local_port}:873").string_command)
72
+ pid = p.pid
73
+ say "PID in execuzione port forward:#{pid}"
74
+
75
+ begin
76
+
77
+ sleep 1
78
+
79
+ # lanciamo il comando quindi per far rsync
80
+ rsync_command = [
81
+ "rsync -az --no-o --no-g",
82
+ "--delete",
83
+ "--password-file=#{ File.expand_path("../../rsync_cfgs/password", __FILE__)}"
84
+ ]
85
+
86
+ if direction == :up
87
+ rsync_command << "#{local_folder}/."
88
+ rsync_command << "rsync://root@0.0.0.0:#{local_port}/archives#{remote_folder}"
89
+ else
90
+ rsync_command << "rsync://root@0.0.0.0:#{local_port}/archives#{remote_folder}/."
91
+ rsync_command << local_folder
92
+ end
93
+ say "Eseguo rsync #{rsync_command.join(" ")}"
94
+
95
+ cmd = ShellCommandExecution.new(rsync_command)
96
+ cmd.execute
97
+
98
+ ensure
99
+ sleep 1
100
+ say "Stoppo porta forwarded"
101
+ Process.kill("INT", pid)
102
+ end
103
+ ensure
104
+ say "Tolgo il servizio di rsyn"
105
+ cmd = container.exec('bash -c "killall rsync"')
106
+ cmd.execute
107
+ end
108
+ end
109
+
110
+ ensure
111
+ say "Eseguo pulizia configurazioni caricate"
112
+ cmd = container.exec('bash -c "rm -fr /tmp/rsyncd*"')
113
+ cmd.execute
114
+ end
115
+
116
+ end
117
+
118
+ end
119
+
120
+ end
121
+
122
+ end
123
+
124
+ end
125
+ end
126
+ end
127
+ end
@@ -0,0 +1,9 @@
1
+ module SwarmClusterCliOpe
2
+ module Kubernetes
3
+ module SyncConfigs
4
+ class Sqlite3 < SwarmClusterCliOpe::SyncConfigs::Sqlite3
5
+ include BaseDecorator
6
+ end
7
+ end
8
+ end
9
+ end
@@ -38,7 +38,7 @@ module SwarmClusterCliOpe
38
38
  pid: nil,
39
39
  status: nil
40
40
  }
41
- logger.debug { "SHELL: #{string_command}" }
41
+ logger.info { "SHELL: #{string_command}" }
42
42
  result[:status] = Open4::popen4(string_command) do |pid, stdin, stdout, stderr|
43
43
  stdin.close
44
44
 
@@ -1,8 +1,8 @@
1
1
  require 'forwardable'
2
2
 
3
3
  module SwarmClusterCliOpe
4
- ##
5
- # Identifica una risposta dalla shell
4
+ ##
5
+ # Identifica una risposta dalla shell
6
6
  class ShellCommandResponse
7
7
  extend Forwardable
8
8
  include LoggerConcern
@@ -28,9 +28,22 @@ module SwarmClusterCliOpe
28
28
  ##
29
29
  # Risultato, essendo sempre composto da una lista di righe in formato json, ritorniamo un array di json
30
30
  # @param [Object] object_class
31
- # @return [Array<object_class>]
32
- def result(object_class: OpenStruct)
33
- raw_result[:stdout].split("\n").collect { |s| object_class.new(JSON.parse(s)) }
31
+ # @return [Array<object_class>,Object]
32
+ def result(object_class: OpenStruct, single: false)
33
+ #tento prima di estrapolare direttamente da json e sucessivamente come array
34
+ if single
35
+ # questo per k8s, dato che abbiamo come risposta un json vero
36
+ object_class.new(JSON.parse(raw_result[:stdout]))
37
+ else
38
+ # questo nel caso siamo in swarm che ci ritorna un array di json
39
+ raw_result[:stdout].split("\n").collect { |s| object_class.new(JSON.parse(s)) }
40
+ end
41
+ end
42
+
43
+ # @param [Class<OpenStruct>] object_class
44
+ # @return [Object]
45
+ def single_obj(object_class: OpenStruct)
46
+ result(object_class: object_class, single: true)
34
47
  end
35
48
 
36
49
  #
@@ -0,0 +1,128 @@
1
+ require 'active_support/concern'
2
+
3
+ module SwarmClusterCliOpe
4
+ module StackSyncConcern
5
+ extend ActiveSupport::Concern
6
+
7
+ included do
8
+
9
+ desc "stacksync [DIRECTION:pull|push]", "Si occupa di scaricare|caricare,utilizzando le configurazioni presenti, i dati dallo stack remoto"
10
+ long_desc <<-LONGDESC.gsub("\n", "\x5")
11
+ le configurazioni sono contenute nell'array: sync_configs.
12
+ ogni configurazione è composta da:
13
+ {
14
+ service:""
15
+ how:""
16
+ configs:{ }
17
+ }
18
+ - service è il nome del servizio (o nel caso di k8s una stringa da utilizzare come selettore labels)
19
+ - how è il come sincronizzare, definendo la tipologia:
20
+ ---- pg -> DB TODO
21
+ ---- mysql -> DB dump con mysql
22
+ ---- sqlite3 -> DB: viene eseguita una copia del file
23
+ ---- rsync -> RSYNC
24
+ - configs: è un hash con le configurazioni per ogni tipo di sincronizzazione
25
+
26
+ Possibili CFGS per tipologia:
27
+ rsync:
28
+ --local: -> path cartella locale
29
+ --remote: -> path cartella remota (contesto del container)
30
+
31
+ sqlite3:
32
+ --local: -> path al file
33
+ --remote: -> path al file remoto (contesto del container)
34
+
35
+ mysql:
36
+ --local: -> hash di configurazioni per il DB locale
37
+ - service: "db" -> nome del servizio nel compose locale, DEFAULT: quello definito sopra
38
+ - mysql_password_env: "MYSQL_PASSWORD" -> variabile ambiente interna al servizio contenente PASSWORD, DEFAULT: MYSQL_PASSWORD
39
+ - mysql_password: "root" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: root
40
+ - mysql_user_env: "MYSQL_USER" -> variabile ambiente interna al servizio contenente USERNAME, DEFAULT: MYSQL_USER
41
+ - mysql_user: "root" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: root
42
+ - database_name_env: "MYSQL_DATABASE" -> variabile ambiente interna al servizio contenente NOME DB, DEFAULT: MYSQL_DATABASE
43
+ - database_name: "nome_db" -> valore in chiaro, in sostituzione della variabile ambiente
44
+ --remote: -> hash di configurazioni per il DB remoto
45
+ - service: "db" -> nome del servizio nel compose locale, DEFAULT: quello definito sopra
46
+ - mysql_password_env: "MYSQL_PASSWORD" -> variabile ambiente interna al servizio contenente PASSWORD, DEFAULT: MYSQL_PASSWORD
47
+ - mysql_password: "root" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: root
48
+ - mysql_user_env: "MYSQL_USER" -> variabile ambiente interna al servizio contenente USERNAME, DEFAULT: MYSQL_USER
49
+ - mysql_user: "root" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: root
50
+ - database_name_env: "MYSQL_DATABASE" -> variabile ambiente interna al servizio contenente NOME DB, DEFAULT: MYSQL_DATABASE
51
+ - database_name: "MYSQL_DATABASE" -> valore in chiaro, in sostituzione della variabile ambiente
52
+ pg:
53
+ --local: -> hash di configurazioni per il DB locale
54
+ - service: "db" -> nome del servizio nel compose locale, DEFAULT: quello definito sopra
55
+ - pg_password_env: "POSTGRES_USER" -> variabile ambiente interna al servizio contenente PASSWORD, DEFAULT: POSTGRES_PASSWORD
56
+ - pg_password: "" -> valore in chiaro, in sostituzione della variabile ambiente
57
+ - pg_user_env: "POSTGRES_USER" -> variabile ambiente interna al servizio contenente USERNAME, DEFAULT: POSTGRES_USER
58
+ - pg_user: "postgres" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: postgres
59
+ - database_name_env: "POSTGRES_DB" -> variabile ambiente interna al servizio contenente NOME DB, DEFAULT: POSTGRES_DB
60
+ - database_name: "nome_db" -> valore in chiaro, in sostituzione della variabile ambiente
61
+ --remote: -> hash di configurazioni per il DB remoto
62
+ - service: "db" -> nome del servizio nel compose locale, DEFAULT: quello definito sopra
63
+ - pg_password_env: "POSTGRES_USER" -> variabile ambiente interna al servizio contenente PASSWORD, DEFAULT: POSTGRES_PASSWORD
64
+ - pg_password: "" -> valore in chiaro, in sostituzione della variabile ambiente
65
+ - pg_user_env: "POSTGRES_USER" -> variabile ambiente interna al servizio contenente USERNAME, DEFAULT: POSTGRES_USER
66
+ - pg_user: "postgres" -> valore in chiaro, in sostituzione della variabile ambiente, DEFAULT: postgres
67
+ - database_name_env: "POSTGRES_DB" -> variabile ambiente interna al servizio contenente NOME DB, DEFAULT: POSTGRES_DB
68
+ - database_name: "nome_db" -> valore in chiaro, in sostituzione della variabile ambiente
69
+
70
+
71
+ EXAMPLE:
72
+ Esempio di sincronizzazione di un file sqlite3 e una cartella
73
+ {
74
+ "stack_name": "test1",
75
+ "sync_configs": [
76
+ {
77
+ "service": "second",
78
+ "how": "rsync",
79
+ "configs": {
80
+ "remote": "/test_bind",
81
+ "local": "./uploads"
82
+ }
83
+ },
84
+ {
85
+ "service": "test_sqlite3",
86
+ "how": "sqlite3",
87
+ "configs": {
88
+ "remote": "/cartella_sqlite3/esempio.sqlite3",
89
+ "local": "./development.sqlite3"
90
+ }
91
+ }
92
+ ]
93
+ }
94
+ LONGDESC
95
+
96
+ def stacksync(direction)
97
+ direction = case direction
98
+ when 'push'
99
+ :push
100
+ when 'pull'
101
+ :pull
102
+ else
103
+ raise "ONLY [push|pull] action accepted"
104
+ end
105
+ cfgs.env(options[:environment]) do |cfgs|
106
+ sync_cfgs = cfgs.sync_configurations
107
+ if sync_cfgs.empty?
108
+ say "Attenzione, configurazioni di sincronizzazione vuoto. Leggere la documentazione"
109
+ else
110
+ sync_cfgs.each do |sync|
111
+ say "----------->>>>>>"
112
+ say "[ #{sync.class.name} ]"
113
+ sync.send(direction)
114
+ say "COMPLETE"
115
+ say "<<<<<<-----------"
116
+ end
117
+ end
118
+ end
119
+ end
120
+
121
+
122
+ end
123
+
124
+ # module ClassMethods
125
+
126
+ # end
127
+ end
128
+ end
@@ -9,7 +9,7 @@ module SwarmClusterCliOpe
9
9
  attr_accessor :configs
10
10
 
11
11
  # @param [Hash] configs
12
- # @param [Continuation] stack_cfgs
12
+ # @param [Configuration] stack_cfgs
13
13
  def initialize(stack_cfgs, configs)
14
14
  super()
15
15
  @configs = configs
@@ -0,0 +1,29 @@
1
+ require 'active_support/concern'
2
+
3
+ module SwarmClusterCliOpe
4
+ module ThorConfigurationConcern
5
+ extend ActiveSupport::Concern
6
+
7
+ included do
8
+
9
+ desc "config", "Visualizza le configurazioni mergiate (HOME + Project configuration[#{Configuration.cfgs_project_file_name}])"
10
+
11
+ def config
12
+ cfgs.env(options[:environment]) do
13
+ puts JSON.pretty_generate(cfgs.merged_configurations)
14
+ end
15
+ end
16
+
17
+ desc "configure_project STACK_NAME", "Genera il file di configurazione del progetto contenente il nome dello stack"
18
+
19
+ def configure_project(stack_name)
20
+ cfgs.env(options[:environment]) do |c|
21
+ c.stack_name = stack_name
22
+ c.save_project_cfgs
23
+ end
24
+ end
25
+
26
+ end
27
+
28
+ end
29
+ end
@@ -1,3 +1,3 @@
1
1
  module SwarmClusterCliOpe
2
- VERSION = "0.4.2"
2
+ VERSION = "0.5.0.pre.5"
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.4.2
4
+ version: 0.5.0.pre.5
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-10 00:00:00.000000000 Z
11
+ date: 2020-11-12 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: thor
@@ -88,6 +88,7 @@ files:
88
88
  - Rakefile
89
89
  - exe/swarm_cli_ope
90
90
  - lib/swarm_cluster_cli_ope.rb
91
+ - lib/swarm_cluster_cli_ope/base_configuration.rb
91
92
  - lib/swarm_cluster_cli_ope/cli.rb
92
93
  - lib/swarm_cluster_cli_ope/commands/base.rb
93
94
  - lib/swarm_cluster_cli_ope/commands/compose_container.rb
@@ -97,6 +98,15 @@ files:
97
98
  - lib/swarm_cluster_cli_ope/commands/task.rb
98
99
  - lib/swarm_cluster_cli_ope/configuration.rb
99
100
  - lib/swarm_cluster_cli_ope/configuration_concern.rb
101
+ - lib/swarm_cluster_cli_ope/k8s.rb
102
+ - lib/swarm_cluster_cli_ope/kubernetes/configuration.rb
103
+ - lib/swarm_cluster_cli_ope/kubernetes/pod.rb
104
+ - lib/swarm_cluster_cli_ope/kubernetes/rsync_cfgs/password
105
+ - lib/swarm_cluster_cli_ope/kubernetes/rsync_cfgs/rsyncd.conf
106
+ - lib/swarm_cluster_cli_ope/kubernetes/rsync_cfgs/rsyncd.secrets
107
+ - lib/swarm_cluster_cli_ope/kubernetes/sync_configs/base_decorator.rb
108
+ - lib/swarm_cluster_cli_ope/kubernetes/sync_configs/rsync.rb
109
+ - lib/swarm_cluster_cli_ope/kubernetes/sync_configs/sqlite3.rb
100
110
  - lib/swarm_cluster_cli_ope/logger_concern.rb
101
111
  - lib/swarm_cluster_cli_ope/manager.rb
102
112
  - lib/swarm_cluster_cli_ope/models/base.rb
@@ -109,6 +119,7 @@ files:
109
119
  - lib/swarm_cluster_cli_ope/node.rb
110
120
  - lib/swarm_cluster_cli_ope/shell_command_execution.rb
111
121
  - lib/swarm_cluster_cli_ope/shell_command_response.rb
122
+ - lib/swarm_cluster_cli_ope/stack_sync_concern.rb
112
123
  - lib/swarm_cluster_cli_ope/sync_configs/base.rb
113
124
  - lib/swarm_cluster_cli_ope/sync_configs/base_database.rb
114
125
  - lib/swarm_cluster_cli_ope/sync_configs/copy.rb
@@ -117,6 +128,7 @@ files:
117
128
  - lib/swarm_cluster_cli_ope/sync_configs/post_gres.rb
118
129
  - lib/swarm_cluster_cli_ope/sync_configs/rsync.rb
119
130
  - lib/swarm_cluster_cli_ope/sync_configs/sqlite3.rb
131
+ - lib/swarm_cluster_cli_ope/thor_configuration_concern.rb
120
132
  - lib/swarm_cluster_cli_ope/version.rb
121
133
  - lib/swarm_cluster_cli_ope/worker.rb
122
134
  - swarm_cluster_cli_ope.gemspec
@@ -139,9 +151,9 @@ required_ruby_version: !ruby/object:Gem::Requirement
139
151
  version: 2.3.0
140
152
  required_rubygems_version: !ruby/object:Gem::Requirement
141
153
  requirements:
142
- - - ">="
154
+ - - ">"
143
155
  - !ruby/object:Gem::Version
144
- version: '0'
156
+ version: 1.3.1
145
157
  requirements: []
146
158
  rubygems_version: 3.0.8
147
159
  signing_key: