liri 0.3.0 → 0.3.1
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/.gitignore +2 -0
- data/.rubocop.yml +5 -1
- data/Gemfile +3 -0
- data/Gemfile.lock +54 -1
- data/README.md +3 -0
- data/bash_script_examples.sh +3 -1
- data/config/locales/to_duration_es.yml +9 -9
- data/exe/liri +26 -7
- data/lib/agent/agent.rb +66 -87
- data/lib/all_libraries.rb +2 -0
- data/lib/common/benchmarking.rb +10 -9
- data/lib/common/manager_data.rb +4 -4
- data/lib/common/setup.rb +14 -4
- data/lib/common/tests_result.rb +59 -30
- data/lib/common/text_time_parser.rb +47 -0
- data/lib/common/unit_test/rspec.rb +4 -18
- data/lib/common/unit_test/rspec_result_parser.rb +37 -0
- data/lib/hash_extend.rb +8 -6
- data/lib/liri.rb +15 -7
- data/lib/manager/credential.rb +1 -1
- data/lib/manager/manager.rb +176 -112
- data/lib/task.rb +6 -2
- data/template/liri-config.yml +9 -3
- metadata +4 -2
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: b30998dd0b5a8393fd498a7e860a9d7f3a3c61b6b55c7c06d832aa83a5104482
|
4
|
+
data.tar.gz: 41a2b382eb25a400529b236ddba38e81c1ea01cf81bc184e0b8615e66f33657e
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: e4d65b549bc22186954fad36d3d96715335e7513f5aab7e9f429afc657f9945da0be95c20ccb320ca6c213b54bb1e96d58caa1136ae056ba477583c198988cdb
|
7
|
+
data.tar.gz: d421828fefa0c2ef94eaccb857e7095d35d27ffadfafcebe817134cfb4b0e9f93fd4333daf834e46ef03e289f95af2218dbbd2aae194dcca7c25bb0bdc587b75
|
data/.gitignore
CHANGED
data/.rubocop.yml
CHANGED
data/Gemfile
CHANGED
@@ -27,6 +27,9 @@ group :development do
|
|
27
27
|
# Ruby static code analyzer and formatter, based on the community Ruby style guide. https://github.com/rubocop-hq/rubocop
|
28
28
|
gem 'rubocop', '~>1', require: false
|
29
29
|
|
30
|
+
# RubyCritic is a gem that wraps around static analysis gems such as Reek, Flay and Flog to provide a quality report of your Ruby code.
|
31
|
+
gem 'rubycritic', '~>4', require: false
|
32
|
+
|
30
33
|
# A Ruby Documentation Tool. https://github.com/lsegal/yard
|
31
34
|
gem 'yard', '~>0'
|
32
35
|
end
|
data/Gemfile.lock
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
PATH
|
2
2
|
remote: .
|
3
3
|
specs:
|
4
|
-
liri (0.3.
|
4
|
+
liri (0.3.1)
|
5
5
|
commander (~> 4)
|
6
6
|
highline (~> 2)
|
7
7
|
i18n (~> 1)
|
@@ -14,24 +14,55 @@ PATH
|
|
14
14
|
GEM
|
15
15
|
remote: https://rubygems.org/
|
16
16
|
specs:
|
17
|
+
addressable (2.8.0)
|
18
|
+
public_suffix (>= 2.0.2, < 5.0)
|
17
19
|
ast (2.4.2)
|
20
|
+
axiom-types (0.1.1)
|
21
|
+
descendants_tracker (~> 0.0.4)
|
22
|
+
ice_nine (~> 0.11.0)
|
23
|
+
thread_safe (~> 0.3, >= 0.3.1)
|
18
24
|
coderay (1.1.3)
|
25
|
+
coercible (1.0.0)
|
26
|
+
descendants_tracker (~> 0.0.1)
|
19
27
|
commander (4.6.0)
|
20
28
|
highline (~> 2.0.0)
|
21
29
|
concurrent-ruby (1.1.9)
|
30
|
+
descendants_tracker (0.0.4)
|
31
|
+
thread_safe (~> 0.3, >= 0.3.1)
|
22
32
|
diff-lcs (1.4.4)
|
23
33
|
docile (1.4.0)
|
34
|
+
equalizer (0.0.11)
|
35
|
+
erubi (1.10.0)
|
36
|
+
flay (2.13.0)
|
37
|
+
erubi (~> 1.10)
|
38
|
+
path_expander (~> 1.0)
|
39
|
+
ruby_parser (~> 3.0)
|
40
|
+
sexp_processor (~> 4.0)
|
41
|
+
flog (4.6.5)
|
42
|
+
path_expander (~> 1.0)
|
43
|
+
ruby_parser (~> 3.1, > 3.1.0)
|
44
|
+
sexp_processor (~> 4.8)
|
24
45
|
highline (2.0.3)
|
25
46
|
i18n (1.10.0)
|
26
47
|
concurrent-ruby (~> 1.0)
|
48
|
+
ice_nine (0.11.2)
|
49
|
+
kwalify (0.7.2)
|
50
|
+
launchy (2.5.0)
|
51
|
+
addressable (~> 2.7)
|
27
52
|
net-scp (3.0.0)
|
28
53
|
net-ssh (>= 2.6.5, < 7.0.0)
|
29
54
|
net-ssh (6.1.0)
|
30
55
|
parallel (1.22.1)
|
31
56
|
parser (3.1.2.0)
|
32
57
|
ast (~> 2.4.1)
|
58
|
+
path_expander (1.1.0)
|
59
|
+
public_suffix (4.0.7)
|
33
60
|
rainbow (3.1.1)
|
34
61
|
rake (13.0.6)
|
62
|
+
reek (6.1.1)
|
63
|
+
kwalify (~> 0.7.0)
|
64
|
+
parser (~> 3.1.0)
|
65
|
+
rainbow (>= 2.0, < 4.0)
|
35
66
|
regexp_parser (2.4.0)
|
36
67
|
rexml (3.2.5)
|
37
68
|
rspec (3.10.0)
|
@@ -59,7 +90,21 @@ GEM
|
|
59
90
|
rubocop-ast (1.17.0)
|
60
91
|
parser (>= 3.1.1.0)
|
61
92
|
ruby-progressbar (1.11.0)
|
93
|
+
ruby_parser (3.19.1)
|
94
|
+
sexp_processor (~> 4.16)
|
95
|
+
rubycritic (4.7.0)
|
96
|
+
flay (~> 2.8)
|
97
|
+
flog (~> 4.4)
|
98
|
+
launchy (>= 2.0.0)
|
99
|
+
parser (>= 2.6.0)
|
100
|
+
rainbow (~> 3.0)
|
101
|
+
reek (~> 6.0, < 7.0)
|
102
|
+
ruby_parser (~> 3.8)
|
103
|
+
simplecov (>= 0.17.0)
|
104
|
+
tty-which (~> 0.4.0)
|
105
|
+
virtus (~> 1.0)
|
62
106
|
rubyzip (2.3.2)
|
107
|
+
sexp_processor (4.16.1)
|
63
108
|
simplecov (0.21.2)
|
64
109
|
docile (~> 1.1)
|
65
110
|
simplecov-html (~> 0.11)
|
@@ -68,8 +113,15 @@ GEM
|
|
68
113
|
simplecov_json_formatter (0.1.4)
|
69
114
|
terminal-table (3.0.2)
|
70
115
|
unicode-display_width (>= 1.1.1, < 3)
|
116
|
+
thread_safe (0.3.6)
|
71
117
|
to_duration (1.2.1)
|
118
|
+
tty-which (0.4.2)
|
72
119
|
unicode-display_width (2.1.0)
|
120
|
+
virtus (1.0.5)
|
121
|
+
axiom-types (~> 0.1)
|
122
|
+
coercible (~> 1.0)
|
123
|
+
descendants_tracker (~> 0.0, >= 0.0.3)
|
124
|
+
equalizer (~> 0.0, >= 0.0.9)
|
73
125
|
yard (0.9.26)
|
74
126
|
|
75
127
|
PLATFORMS
|
@@ -81,6 +133,7 @@ DEPENDENCIES
|
|
81
133
|
rake (~> 13)
|
82
134
|
rspec (~> 3.10.0)
|
83
135
|
rubocop (~> 1)
|
136
|
+
rubycritic (~> 4)
|
84
137
|
simplecov (~> 0)
|
85
138
|
yard (~> 0)
|
86
139
|
|
data/README.md
CHANGED
@@ -59,6 +59,9 @@ unitarias de una gema X, si esta gema X requiere una versión específica de Rub
|
|
59
59
|
de cosas deben configurarse de manera manual.
|
60
60
|
|
61
61
|
## Desarrollo
|
62
|
+
La rama master siempre debe ser estable.
|
63
|
+
Se debe crear un release cada vez que se llega a una versión estable de algún agregado nuevo.
|
64
|
+
Agregar fixes y mejoras en ramas.
|
62
65
|
|
63
66
|
### Pruebas Unitarias
|
64
67
|
|
data/bash_script_examples.sh
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
es:
|
2
2
|
to_duration:
|
3
3
|
and: y
|
4
|
-
less_than_one_second:
|
4
|
+
less_than_one_second: < 1s
|
5
5
|
year:
|
6
6
|
one: año
|
7
7
|
other: años
|
@@ -12,14 +12,14 @@ es:
|
|
12
12
|
one: semana
|
13
13
|
other: semanas
|
14
14
|
day:
|
15
|
-
one:
|
16
|
-
other:
|
15
|
+
one: d
|
16
|
+
other: d
|
17
17
|
hour:
|
18
|
-
one:
|
19
|
-
other:
|
18
|
+
one: h
|
19
|
+
other: h
|
20
20
|
minute:
|
21
|
-
one:
|
22
|
-
other:
|
21
|
+
one: m
|
22
|
+
other: m
|
23
23
|
second:
|
24
|
-
one:
|
25
|
-
other:
|
24
|
+
one: s
|
25
|
+
other: s
|
data/exe/liri
CHANGED
@@ -26,7 +26,7 @@ command :manager do |c|
|
|
26
26
|
c.option '-o', '--output [filename]', String, 'Especifica donde guardar los resultados de la ejecución de pruebas unitarias'
|
27
27
|
c.action do |args, options|
|
28
28
|
current_folder = Dir.pwd
|
29
|
-
Liri.set_setup(current_folder)
|
29
|
+
Liri.set_setup(current_folder, :manager)
|
30
30
|
Liri::Common::Benchmarking.start(end_msg: "\nFinalizado en: ", stdout: true) do
|
31
31
|
# Metodo que se ejecuta al llamar al comando manager
|
32
32
|
Liri::Manager.run(current_folder)
|
@@ -57,22 +57,41 @@ end
|
|
57
57
|
# Define el alias m para el comando agent
|
58
58
|
alias_command :a, :agent
|
59
59
|
|
60
|
+
# Define el comando y los parámetros para obtener los archivos de tests
|
61
|
+
command :tests_files do |c|
|
62
|
+
c.syntax = 'Liri tests_files [options]'
|
63
|
+
c.summary = 'Retorna los archivos de tests'
|
64
|
+
c.description = 'Ejecuta el comando para obtener la cantidad total de tests del proyecto'
|
65
|
+
c.example 'Ejecuta el comando tests', 'liri tf'
|
66
|
+
c.example 'Ejecuta el comando tests', 'liri tests_files'
|
67
|
+
c.action do |args, options|
|
68
|
+
# Método que se ejecuta al llamar al comando tests
|
69
|
+
current_folder = Dir.pwd
|
70
|
+
Liri.set_setup(current_folder, :manager)
|
71
|
+
tests_count = Liri::Task.tests_files(current_folder)
|
72
|
+
puts tests_count
|
73
|
+
end
|
74
|
+
end
|
75
|
+
|
76
|
+
# Define el alias t para el comando tests
|
77
|
+
alias_command :tf, :tests_files
|
78
|
+
|
60
79
|
# Define el comando y los parámetros para obtener la cantidad de tests
|
61
|
-
command :
|
62
|
-
c.syntax = 'Liri
|
80
|
+
command :tests_count do |c|
|
81
|
+
c.syntax = 'Liri tests_count [options]'
|
63
82
|
c.summary = 'Retorna la cantidad total de tests'
|
64
83
|
c.description = 'Ejecuta el comando para obtener la cantidad total de tests del proyecto'
|
65
|
-
c.example 'Ejecuta el comando tests', 'liri
|
66
|
-
c.example 'Ejecuta el comando tests', 'liri
|
84
|
+
c.example 'Ejecuta el comando tests', 'liri tc'
|
85
|
+
c.example 'Ejecuta el comando tests', 'liri tests_count'
|
67
86
|
c.action do |args, options|
|
68
87
|
# Método que se ejecuta al llamar al comando tests
|
69
88
|
current_folder = Dir.pwd
|
70
|
-
Liri.set_setup(current_folder)
|
89
|
+
Liri.set_setup(current_folder, :manager)
|
71
90
|
tests_count = Liri::Task.tests_count(current_folder)
|
72
91
|
puts tests_count
|
73
92
|
end
|
74
93
|
end
|
75
94
|
|
76
95
|
# Define el alias t para el comando tests
|
77
|
-
alias_command :
|
96
|
+
alias_command :tc, :tests_count
|
78
97
|
|
data/lib/agent/agent.rb
CHANGED
@@ -12,12 +12,12 @@ module Liri
|
|
12
12
|
# Inicia la ejecución del Agent
|
13
13
|
# @param stop [Boolean] el valor true es para que no se ejecute infinitamente el método en el test unitario.
|
14
14
|
def run(work_folder_path, stop = false)
|
15
|
-
setup_manager = Liri.set_setup(work_folder_path)
|
15
|
+
setup_manager = Liri.set_setup(work_folder_path, :agent)
|
16
16
|
agent_folder_path = setup_manager.agent_folder_path
|
17
17
|
|
18
|
-
Liri.set_logger(setup_manager.logs_folder_path, '
|
19
|
-
Liri.logger.info("
|
20
|
-
Liri.logger.info("
|
18
|
+
Liri.set_logger(setup_manager.logs_folder_path, 'liriagent.log')
|
19
|
+
Liri.logger.info("Agent process started")
|
20
|
+
Liri.logger.info("Press Ctrl + c to finish Agent process manually\n", true)
|
21
21
|
|
22
22
|
decompressed_source_code_path = File.join(agent_folder_path, '/', Common::SourceCode::DECOMPRESSED_FOLDER_NAME)
|
23
23
|
source_code = Common::SourceCode.new(decompressed_source_code_path, agent_folder_path, Liri.compression_class, Liri.unit_test_class)
|
@@ -28,9 +28,9 @@ module Liri
|
|
28
28
|
threads << agent.start_server_socket_to_process_manager_connection_request # Esperar y procesar la petición de conexión del Manager
|
29
29
|
|
30
30
|
Liri.init_exit(stop, threads, 'Agent')
|
31
|
-
Liri.logger.info("
|
31
|
+
Liri.logger.info("Agent process finished")
|
32
32
|
rescue SignalException => e
|
33
|
-
Liri.logger.info("Exception(#{e})
|
33
|
+
Liri.logger.info("Exception(#{e}) Agent process finished manually")
|
34
34
|
Liri.kill(threads)
|
35
35
|
end
|
36
36
|
end
|
@@ -60,12 +60,10 @@ module Liri
|
|
60
60
|
begin
|
61
61
|
@udp_socket.bind('0.0.0.0', @udp_port)
|
62
62
|
rescue Errno::EADDRINUSE => e
|
63
|
-
Liri.logger.error("Exception(#{e})
|
63
|
+
Liri.logger.error("Exception(#{e}) Busy UDP port #{@udp_port}")
|
64
64
|
Thread.exit
|
65
65
|
end
|
66
|
-
Liri.logger.info("
|
67
|
-
(Se espera que algún Manager se contacte por primera vez para establecer una conexión TCP)
|
68
|
-
")
|
66
|
+
Liri.logger.info("Waiting managers request in UDP port #{@udp_port}")
|
69
67
|
|
70
68
|
loop do
|
71
69
|
@manager_request = @udp_socket.recvfrom(1024)
|
@@ -79,56 +77,51 @@ module Liri
|
|
79
77
|
# Inicia un cliente tcp para responder a la petición broadcast del Manager para que éste sepa donde enviar las pruebas
|
80
78
|
def start_client_socket_to_process_tests(manager_ip_address, manager_data)
|
81
79
|
tcp_socket = TCPSocket.open(manager_ip_address, @tcp_port)
|
82
|
-
|
83
80
|
agent_ip_address = tcp_socket.addr[2]
|
81
|
+
tcp_socket.puts({ msg: 'get_source_code', hardware_model: get_hardware_model }.to_json)
|
84
82
|
|
85
|
-
tcp_socket.puts({ msg: 'Listo' }) # Se envía un mensaje inicial al Manager
|
86
|
-
|
87
|
-
Liri.logger.info("Se inicia una conexión para procesar pruebas con el Manager: #{manager_ip_address} en el puerto TCP: #{@tcp_port}")
|
88
|
-
Liri.logger.info("\nConexión iniciada con el Manager: #{manager_ip_address}", true)
|
89
|
-
|
90
|
-
# En la siguiente línea se espera un puts desde el Manager, pero el Manager no lo hace
|
91
|
-
response = JSON.parse(tcp_socket.gets)
|
92
|
-
return unless response['exist_tests']
|
93
|
-
|
94
|
-
get_source_code(manager_ip_address, manager_data)
|
95
|
-
|
96
|
-
# Se procesan las pruebas enviadas por el Manager
|
97
83
|
while line = tcp_socket.gets
|
98
|
-
|
99
|
-
|
84
|
+
tcp_socket_data = JSON.parse(line.chop)
|
85
|
+
msg = tcp_socket_data['msg']
|
100
86
|
|
101
|
-
|
102
|
-
|
103
|
-
|
104
|
-
raw_tests_result = @runner.run_tests(tests)
|
87
|
+
if msg == 'already_connected' || msg == 'no_exist_tests' || msg == 'finish_agent'
|
88
|
+
break
|
89
|
+
end
|
105
90
|
|
106
|
-
|
107
|
-
|
108
|
-
|
91
|
+
if msg == 'proceed_get_source_code'
|
92
|
+
result = get_source_code(manager_ip_address, manager_data)
|
93
|
+
tcp_socket.puts({ msg: result }.to_json)
|
94
|
+
end
|
109
95
|
|
110
|
-
|
111
|
-
|
112
|
-
|
96
|
+
if msg == 'process_tests'
|
97
|
+
tests_batch = tcp_socket_data
|
98
|
+
tests = get_tests(tests_batch, manager_ip_address)
|
99
|
+
raw_tests_result = @runner.run_tests(tests)
|
100
|
+
tests_batch_number = tests_batch['tests_batch_number']
|
101
|
+
tests_result_file_name = @tests_result.build_file_name(agent_ip_address, tests_batch_number)
|
102
|
+
tests_result_file_path = @tests_result.save(tests_result_file_name, raw_tests_result)
|
103
|
+
|
104
|
+
send_tests_results_file(manager_ip_address, manager_data, tests_result_file_path)
|
105
|
+
result = { msg: 'processed_tests', tests_batch_number: tests_batch_number, tests_result_file_name: tests_result_file_name, tests_batch_keys_size: tests_batch['tests_batch_keys'].size}
|
106
|
+
tcp_socket.puts(result.to_json) # Envía el número de lote y el nombre del archivo de resultados.
|
107
|
+
end
|
113
108
|
end
|
114
109
|
|
110
|
+
Liri.logger.info("Finish connection with Manager #{manager_ip_address} in TCP port: #{@tcp_port}")
|
115
111
|
tcp_socket.close
|
116
|
-
Liri.logger.info("Se termina la conexión con el Manager #{manager_ip_address} en el puerto TCP: #{@tcp_port}")
|
117
|
-
|
118
112
|
Liri.clean_folder_content(@agent_folder_path)
|
119
113
|
|
120
|
-
start_client_to_close_manager_server(manager_ip_address, 'Conexión Terminada')
|
121
114
|
unregister_manager(manager_ip_address)
|
122
115
|
rescue Errno::EADDRINUSE => e
|
123
|
-
Liri.logger.error("Exception(#{e})
|
116
|
+
Liri.logger.error("Exception(#{e}) Busy UDP port #{@udp_port}")
|
124
117
|
rescue Errno::ECONNRESET => e
|
125
118
|
tcp_socket.close
|
126
|
-
Liri.logger.error("Exception(#{e})
|
127
|
-
Liri.logger.info("
|
119
|
+
Liri.logger.error("Exception(#{e}) Closed connection in TCP port #{@tcp_port}")
|
120
|
+
Liri.logger.info("Finish connection with Manager #{manager_ip_address} in TCP port: #{@tcp_port}")
|
128
121
|
unregister_manager(manager_ip_address)
|
129
122
|
rescue Errno::ECONNREFUSED => e
|
130
|
-
Liri.logger.error("Exception(#{e})
|
131
|
-
Liri.logger.info("
|
123
|
+
Liri.logger.error("Exception(#{e}) Rejected connection in TCP port #{@tcp_port}")
|
124
|
+
Liri.logger.info("Finish connection with Manager #{manager_ip_address} in TCP port: #{@tcp_port}")
|
132
125
|
unregister_manager(manager_ip_address)
|
133
126
|
end
|
134
127
|
|
@@ -140,28 +133,14 @@ module Liri
|
|
140
133
|
def process_manager_connection_request(manager_ip_address, manager_data)
|
141
134
|
unless registered_manager?(manager_ip_address)
|
142
135
|
register_manager(manager_ip_address)
|
143
|
-
Liri.logger.info("
|
144
|
-
|
145
|
-
start_client_socket_to_process_tests(manager_ip_address, manager_data)
|
146
|
-
#else
|
147
|
-
#unregister_manager(manager_ip_address)
|
148
|
-
#end
|
136
|
+
Liri.logger.info("Broadcast request received from Manager: #{manager_ip_address} in UDP port: #{@udp_port}")
|
137
|
+
start_client_socket_to_process_tests(manager_ip_address, manager_data)
|
149
138
|
end
|
150
139
|
end
|
151
140
|
|
152
|
-
# Se establece una nueva comunicación con el servidor TCP del Manager con el único objetivo de cerrar el servidor
|
153
|
-
# Esta conexión permitirá al Manager cerrar sus hilos pendientes con servidores TCP en espera y terminar el proceso
|
154
|
-
def start_client_to_close_manager_server(manager_ip_address, msg)
|
155
|
-
tcp_socket = TCPSocket.open(manager_ip_address, @tcp_port)
|
156
|
-
Liri.logger.info("Se termina cualquier proceso pendiente con el Manager #{manager_ip_address} en el puerto TCP: #{@tcp_port}")
|
157
|
-
tcp_socket.print({ msg: msg }.to_json)
|
158
|
-
tcp_socket.close
|
159
|
-
end
|
160
|
-
|
161
141
|
def get_source_code(manager_ip_address, manager_data)
|
162
|
-
#puts "#{manager_data.to_h}"
|
163
142
|
puts ''
|
164
|
-
Liri::Common::Benchmarking.start(start_msg: "
|
143
|
+
Liri::Common::Benchmarking.start(start_msg: "Getting source code. Wait... ", stdout: true) do
|
165
144
|
puts ''
|
166
145
|
Net::SCP.start(manager_ip_address, manager_data.user, password: manager_data.password) do |scp|
|
167
146
|
scp.download!(manager_data.compressed_file_path, @source_code.compressed_file_folder_path)
|
@@ -172,7 +151,7 @@ module Liri
|
|
172
151
|
downloaded_file_name = manager_data.compressed_file_path.split('/').last
|
173
152
|
downloaded_file_path = File.join(@source_code.compressed_file_folder_path, '/', downloaded_file_name)
|
174
153
|
|
175
|
-
Liri::Common::Benchmarking.start(start_msg: "
|
154
|
+
Liri::Common::Benchmarking.start(start_msg: "Uncompressing source code. Wait... ", stdout: true) do
|
176
155
|
@source_code.decompress_file(downloaded_file_path)
|
177
156
|
@all_tests = @source_code.all_tests
|
178
157
|
end
|
@@ -193,49 +172,44 @@ module Liri
|
|
193
172
|
# Se setea la versión de ruby y el gemset para el código fuente descomprimido
|
194
173
|
# Se especifica el Gemfile del cual se van a instalar los requerimientos
|
195
174
|
# Esto se hace porque por defecto se usa la versión de Ruby de Liri y su Gemset y por ello hay que cambiarlos explicitamente aquí
|
196
|
-
Liri::Common::Benchmarking.start(start_msg: "
|
175
|
+
Liri::Common::Benchmarking.start(start_msg: "Running bundle install. Wait... ", end_msg: "Running bundle install. Duration: ", stdout: true) do
|
197
176
|
puts ''
|
198
177
|
system("bash -lc 'rvm use #{Liri.current_folder_ruby_and_gemset}; BUNDLE_GEMFILE=Gemfile bundle install'")
|
199
178
|
end
|
200
179
|
puts ''
|
201
180
|
|
202
|
-
Liri::Common::Benchmarking.start(start_msg: "
|
181
|
+
Liri::Common::Benchmarking.start(start_msg: "Running rake db:migrate RAILS_ENV=test. Wait... ", end_msg: "Running rake db:migrate RAILS_ENV=test. Duration: ", stdout: true) do
|
203
182
|
puts ''
|
204
183
|
system("bash -lc 'rvm use #{Liri.current_folder_ruby_and_gemset}; rake db:migrate RAILS_ENV=test'")
|
205
184
|
end
|
206
185
|
puts ''
|
207
|
-
|
208
|
-
#Liri::Common::Benchmarking.start(start_msg: "Ejecutando rake db:migrate:reset RAILS_ENV=test. Espere... ", end_msg: "Ejecución de rake db:migrate:reset RAILS_ENV=test. Duración: ", stdout: true) do
|
209
|
-
# puts ''
|
210
|
-
# system("bash -lc 'rvm use #{Liri.current_folder_ruby_and_gemset}; rake db:migrate:reset RAILS_ENV=test'")
|
211
|
-
#end
|
212
|
-
#puts ''
|
213
186
|
end
|
214
|
-
|
187
|
+
'get_tests_files'
|
188
|
+
rescue Liri::FileNotFoundError => e
|
189
|
+
Liri.logger.error("Exception(#{e}) Not found file to decompress in Agent")
|
190
|
+
'get_source_code_fail'
|
215
191
|
rescue Errno::ECONNREFUSED => e
|
216
|
-
Liri.logger.error("Exception(#{e})
|
217
|
-
|
192
|
+
Liri.logger.error("Exception(#{e}) Rejected connection by #{manager_ip_address}. Maybe ssh is not running in #{manager_ip_address}")
|
193
|
+
'get_source_code_fail'
|
218
194
|
rescue Errno::ENOTTY => e
|
219
195
|
# Este rescue es temporal, hay que ver una mejor manera de detectar si la contraseña es incorrecta
|
220
|
-
Liri.logger.error("Exception(#{e})
|
221
|
-
|
222
|
-
false
|
196
|
+
Liri.logger.error("Exception(#{e}) Invalid password received in #{manager_ip_address} for ssh connection")
|
197
|
+
'get_source_code_fail'
|
223
198
|
rescue Net::SSH::AuthenticationFailed => e
|
224
199
|
# Este rescue es temporal, hay que ver una mejor manera de detectar si la contraseña es incorrecta
|
225
|
-
Liri.logger.error("Exception(#{e})
|
226
|
-
|
227
|
-
false
|
200
|
+
Liri.logger.error("Exception(#{e}) Invalid password received in #{manager_ip_address} for ssh connection")
|
201
|
+
'get_source_code_fail'
|
228
202
|
rescue Net::SCP::Error => e
|
229
|
-
Liri.logger.warn("Exception(#{e})
|
230
|
-
|
203
|
+
Liri.logger.warn("Exception(#{e}) File not found in #{manager_ip_address} through scp")
|
204
|
+
'get_source_code_fail'
|
231
205
|
rescue TypeError => e
|
232
|
-
Liri.logger.warn("Exception(#{e})
|
233
|
-
|
206
|
+
Liri.logger.warn("Exception(#{e}) Undetermined error")
|
207
|
+
'get_source_code_fail'
|
234
208
|
end
|
235
209
|
|
236
210
|
def get_manager_data(manager_data_hash)
|
237
211
|
Common::ManagerData.new(
|
238
|
-
|
212
|
+
tests_results_folder_path: manager_data_hash['tests_results_folder_path'],
|
239
213
|
compressed_file_path: manager_data_hash['compressed_file_path'],
|
240
214
|
user: manager_data_hash['user'],
|
241
215
|
password: manager_data_hash['password']
|
@@ -244,9 +218,9 @@ module Liri
|
|
244
218
|
|
245
219
|
def send_tests_results_file(manager_ip_address, manager_data, tests_result_file_path)
|
246
220
|
puts ''
|
247
|
-
Liri::Common::Benchmarking.start(start_msg: "
|
221
|
+
Liri::Common::Benchmarking.start(start_msg: "Sending test files results. Wait... ", stdout: true) do
|
248
222
|
Net::SCP.start(manager_ip_address, manager_data.user, password: manager_data.password) do |scp|
|
249
|
-
scp.upload!(tests_result_file_path, manager_data.
|
223
|
+
scp.upload!(tests_result_file_path, manager_data.tests_results_folder_path)
|
250
224
|
end
|
251
225
|
end
|
252
226
|
puts ''
|
@@ -255,12 +229,17 @@ module Liri
|
|
255
229
|
def get_tests(tests_batch, manager_ip_address)
|
256
230
|
# Se convierte "[5, 9, 13, 1]" a un arreglo [5, 9, 13, 1]
|
257
231
|
tests_keys = tests_batch['tests_batch_keys']
|
258
|
-
Liri.logger.debug("
|
232
|
+
Liri.logger.debug("Tests keys received from Manager #{manager_ip_address}: #{tests_keys}")
|
259
233
|
# Se buscan obtienen los tests que coincidan con las claves recibidas de @all_tests = {1=>"spec/hash_spec.rb:2", 2=>"spec/hash_spec.rb:13", 3=>"spec/hash_spec.rb:24", ..., 29=>"spec/liri_spec.rb:62"}
|
260
234
|
# Se retorna un arreglo con los tests a ejecutar ["spec/liri_spec.rb:4", "spec/hash_spec.rb:5", "spec/hash_spec.rb:59", ..., "spec/hash_spec.rb:37"]
|
261
235
|
tests_keys.map { |test_key| @all_tests[test_key] }
|
262
236
|
end
|
263
237
|
|
238
|
+
def get_hardware_model
|
239
|
+
hardware_model = %x|cat /sys/devices/virtual/dmi/id/product_name|
|
240
|
+
hardware_model.strip[0..14] # remove \n from string
|
241
|
+
end
|
242
|
+
|
264
243
|
def registered_manager?(manager_ip_address)
|
265
244
|
@managers[manager_ip_address]
|
266
245
|
end
|
@@ -273,4 +252,4 @@ module Liri
|
|
273
252
|
@managers.remove!(manager_ip_address)
|
274
253
|
end
|
275
254
|
end
|
276
|
-
end
|
255
|
+
end
|
data/lib/all_libraries.rb
CHANGED
@@ -26,7 +26,9 @@ require 'common/setup'
|
|
26
26
|
require 'common/source_code'
|
27
27
|
require 'common/compressor/zip'
|
28
28
|
require 'common/unit_test/rspec'
|
29
|
+
require 'common/unit_test/rspec_result_parser'
|
29
30
|
require 'common/tests_result'
|
31
|
+
require 'common/text_time_parser'
|
30
32
|
|
31
33
|
require 'manager/manager'
|
32
34
|
require 'manager/credential'
|
data/lib/common/benchmarking.rb
CHANGED
@@ -1,31 +1,32 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
1
3
|
# = benchmarking.rb
|
2
4
|
#
|
3
5
|
# @author Rodrigo Fernández
|
4
|
-
#
|
5
|
-
# == Módulo Benchmarking
|
6
|
-
# Este módulo se encarga de medir el tiempo de ejecución de algunos bloques de código
|
7
6
|
|
8
7
|
require 'benchmark'
|
9
8
|
require 'i18n' # requerimiento de la gema to_duration
|
10
9
|
require 'to_duration'
|
11
10
|
|
12
11
|
# Se configura la ubicación del archivo de internacionalización de la gema to_duration
|
13
|
-
I18n.load_path << Dir[File.join(File.dirname(File.dirname(File.dirname(__FILE__))), 'config/locales')
|
12
|
+
I18n.load_path << Dir["#{File.join(File.dirname(File.dirname(File.dirname(__FILE__))), 'config/locales')}/*.yml"]
|
14
13
|
I18n.default_locale = :es
|
15
14
|
|
16
15
|
module Liri
|
17
16
|
module Common
|
17
|
+
# == Módulo Benchmarking
|
18
|
+
# Este módulo se encarga de medir el tiempo de ejecución de algunos bloques de código
|
18
19
|
module Benchmarking
|
19
20
|
class << self
|
20
|
-
def start(start_msg: nil, end_msg: '
|
21
|
+
def start(start_msg: nil, end_msg: 'Duration: ', stdout: true, &block)
|
21
22
|
Liri.logger.info(start_msg, stdout)
|
22
|
-
|
23
|
-
|
24
|
-
|
23
|
+
|
24
|
+
seconds = Benchmark.realtime(&block)
|
25
|
+
|
25
26
|
Liri.logger.info("#{end_msg}#{seconds.to_duration}", stdout)
|
26
27
|
seconds
|
27
28
|
end
|
28
29
|
end
|
29
30
|
end
|
30
31
|
end
|
31
|
-
end
|
32
|
+
end
|
data/lib/common/manager_data.rb
CHANGED
@@ -8,10 +8,10 @@ module Liri
|
|
8
8
|
module Common
|
9
9
|
# Esta clase guarda los datos del Manager
|
10
10
|
class ManagerData
|
11
|
-
attr_accessor :
|
11
|
+
attr_accessor :tests_results_folder_path, :compressed_file_path, :user, :password
|
12
12
|
|
13
|
-
def initialize(
|
14
|
-
@
|
13
|
+
def initialize(tests_results_folder_path:, compressed_file_path:, user:, password:)
|
14
|
+
@tests_results_folder_path = tests_results_folder_path
|
15
15
|
@compressed_file_path = compressed_file_path
|
16
16
|
@user = user
|
17
17
|
@password = password
|
@@ -19,7 +19,7 @@ module Liri
|
|
19
19
|
|
20
20
|
def to_h
|
21
21
|
{
|
22
|
-
|
22
|
+
tests_results_folder_path: @tests_results_folder_path,
|
23
23
|
compressed_file_path: @compressed_file_path,
|
24
24
|
user: @user,
|
25
25
|
password: @password
|
data/lib/common/setup.rb
CHANGED
@@ -14,21 +14,31 @@ module Liri
|
|
14
14
|
MANAGER_FOLDER_NAME = 'manager'
|
15
15
|
AGENT_FOLDER_NAME = 'agent'
|
16
16
|
|
17
|
-
attr_reader :setup_folder_path, :setup_file_path, :logs_folder_path, :manager_folder_path,
|
17
|
+
attr_reader :setup_folder_path, :setup_file_path, :logs_folder_path, :manager_folder_path,
|
18
|
+
:manager_tests_results_folder_path, :agent_folder_path
|
18
19
|
|
19
|
-
def initialize(destination_folder_path)
|
20
|
+
def initialize(destination_folder_path, program, manager_tests_results_folder_time: nil)
|
20
21
|
@setup_folder_path = File.join(destination_folder_path, '/', SETUP_FOLDER_NAME)
|
21
22
|
@setup_file_path = File.join(@setup_folder_path, '/', SETUP_FILE_NAME)
|
22
23
|
@logs_folder_path = File.join(@setup_folder_path, '/', LOGS_FOLDER_NAME)
|
23
24
|
@manager_folder_path = File.join(@setup_folder_path, '/', MANAGER_FOLDER_NAME)
|
25
|
+
@manager_tests_results_folder_path = File.join(@manager_folder_path, '/', "#{manager_tests_results_folder_time}_tests_results") if manager_tests_results_folder_time
|
24
26
|
@agent_folder_path = File.join(@setup_folder_path, '/', AGENT_FOLDER_NAME)
|
27
|
+
@program = program
|
25
28
|
end
|
26
29
|
|
27
30
|
def init
|
28
31
|
create_folder(@setup_folder_path)
|
29
32
|
create_folder(@logs_folder_path)
|
30
|
-
|
31
|
-
|
33
|
+
|
34
|
+
case @program
|
35
|
+
when :manager
|
36
|
+
create_folder(@manager_folder_path)
|
37
|
+
create_folder(@manager_tests_results_folder_path) if @manager_tests_results_folder_path
|
38
|
+
when :agent
|
39
|
+
create_folder(@agent_folder_path)
|
40
|
+
end
|
41
|
+
|
32
42
|
create_setup_file
|
33
43
|
end
|
34
44
|
|