teuton 0.0.1
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/bin/teuton +4 -0
- data/lib/teuton/application.rb +53 -0
- data/lib/teuton/case_manager/case/builtin/main.rb +24 -0
- data/lib/teuton/case_manager/case/builtin/package.rb +20 -0
- data/lib/teuton/case_manager/case/builtin/service.rb +32 -0
- data/lib/teuton/case_manager/case/builtin/user.rb +20 -0
- data/lib/teuton/case_manager/case/case.rb +114 -0
- data/lib/teuton/case_manager/case/close.rb +29 -0
- data/lib/teuton/case_manager/case/config.rb +76 -0
- data/lib/teuton/case_manager/case/dsl/check.rb +24 -0
- data/lib/teuton/case_manager/case/dsl/deprecated.rb +14 -0
- data/lib/teuton/case_manager/case/dsl/expect.rb +78 -0
- data/lib/teuton/case_manager/case/dsl/getset.rb +22 -0
- data/lib/teuton/case_manager/case/dsl/goto.rb +35 -0
- data/lib/teuton/case_manager/case/dsl/log.rb +14 -0
- data/lib/teuton/case_manager/case/dsl/main.rb +11 -0
- data/lib/teuton/case_manager/case/dsl/missing.rb +12 -0
- data/lib/teuton/case_manager/case/dsl/send.rb +69 -0
- data/lib/teuton/case_manager/case/dsl/target.rb +16 -0
- data/lib/teuton/case_manager/case/dsl/unique.rb +11 -0
- data/lib/teuton/case_manager/case/main.rb +7 -0
- data/lib/teuton/case_manager/case/play.rb +59 -0
- data/lib/teuton/case_manager/case/result/ext_array.rb +43 -0
- data/lib/teuton/case_manager/case/result/ext_compare.rb +147 -0
- data/lib/teuton/case_manager/case/result/ext_filter.rb +68 -0
- data/lib/teuton/case_manager/case/result/result.rb +73 -0
- data/lib/teuton/case_manager/case/runner.rb +134 -0
- data/lib/teuton/case_manager/case_manager.rb +76 -0
- data/lib/teuton/case_manager/check_cases.rb +73 -0
- data/lib/teuton/case_manager/dsl.rb +31 -0
- data/lib/teuton/case_manager/export_manager.rb +20 -0
- data/lib/teuton/case_manager/hall_of_fame.rb +28 -0
- data/lib/teuton/case_manager/main.rb +6 -0
- data/lib/teuton/case_manager/report.rb +52 -0
- data/lib/teuton/case_manager/show.rb +19 -0
- data/lib/teuton/case_manager/utils.rb +57 -0
- data/lib/teuton/command/create.rb +20 -0
- data/lib/teuton/command/download.rb +26 -0
- data/lib/teuton/command/main.rb +9 -0
- data/lib/teuton/command/play.rb +34 -0
- data/lib/teuton/command/readme.rb +23 -0
- data/lib/teuton/command/test.rb +35 -0
- data/lib/teuton/command/update.rb +27 -0
- data/lib/teuton/command/version.rb +13 -0
- data/lib/teuton/files/start.rb +13 -0
- data/lib/teuton/project/configfile_reader.rb +49 -0
- data/lib/teuton/project/laboratory/builtin.rb +23 -0
- data/lib/teuton/project/laboratory/dsl.rb +117 -0
- data/lib/teuton/project/laboratory/laboratory.rb +55 -0
- data/lib/teuton/project/laboratory/show.rb +161 -0
- data/lib/teuton/project/name_file_finder.rb +129 -0
- data/lib/teuton/project/project.rb +62 -0
- data/lib/teuton/project/project_creator.rb +79 -0
- data/lib/teuton/project/readme/dsl.rb +109 -0
- data/lib/teuton/project/readme/lang.rb +30 -0
- data/lib/teuton/project/readme/readme.rb +156 -0
- data/lib/teuton/rake_function/check.rb +39 -0
- data/lib/teuton/rake_function/install.rb +36 -0
- data/lib/teuton/report/close.rb +34 -0
- data/lib/teuton/report/formatter/array_formatter.rb +84 -0
- data/lib/teuton/report/formatter/base_formatter.rb +33 -0
- data/lib/teuton/report/formatter/csv_formatter.rb +31 -0
- data/lib/teuton/report/formatter/formatter_factory.rb +73 -0
- data/lib/teuton/report/formatter/html_formatter.rb +81 -0
- data/lib/teuton/report/formatter/json_formatter.rb +17 -0
- data/lib/teuton/report/formatter/list_formatter.rb +71 -0
- data/lib/teuton/report/formatter/moodle_csv_formatter.rb +28 -0
- data/lib/teuton/report/formatter/resume_array_formatter.rb +49 -0
- data/lib/teuton/report/formatter/resume_json_formatter.rb +16 -0
- data/lib/teuton/report/formatter/resume_list_formatter.rb +62 -0
- data/lib/teuton/report/formatter/resume_txt_formatter.rb +102 -0
- data/lib/teuton/report/formatter/resume_yaml_formatter.rb +16 -0
- data/lib/teuton/report/formatter/txt_formatter.rb +102 -0
- data/lib/teuton/report/formatter/xml_formatter.rb +42 -0
- data/lib/teuton/report/formatter/yaml_formatter.rb +18 -0
- data/lib/teuton/report/report.rb +55 -0
- data/lib/teuton/report/show.rb +111 -0
- data/lib/teuton/utils/verbose.rb +15 -0
- data/lib/teuton.rb +17 -0
- metadata +263 -0
@@ -0,0 +1,161 @@
|
|
1
|
+
require 'terminal-table'
|
2
|
+
require 'rainbow'
|
3
|
+
|
4
|
+
require_relative '../../application'
|
5
|
+
require_relative '../configfile_reader'
|
6
|
+
|
7
|
+
# Laboratory
|
8
|
+
# * show_dsl
|
9
|
+
# * show_stats
|
10
|
+
# * show_config
|
11
|
+
class Laboratory
|
12
|
+
def show_dsl
|
13
|
+
@verbose = true
|
14
|
+
process_content
|
15
|
+
show_stats
|
16
|
+
show_config
|
17
|
+
end
|
18
|
+
|
19
|
+
def show_stats
|
20
|
+
@stats[:hosts] = 0
|
21
|
+
@hosts.each_pair { |_k, v| @stats[:hosts] += v }
|
22
|
+
|
23
|
+
my_screen_table = Terminal::Table.new do |st|
|
24
|
+
st.add_row ['DSL Stats', 'Count']
|
25
|
+
st.add_separator
|
26
|
+
st.add_row ['Groups', @stats[:groups]]
|
27
|
+
st.add_row ['Targets', @stats[:targets]]
|
28
|
+
st.add_row ['Goto', @stats[:hosts]]
|
29
|
+
@hosts.each_pair { |k, v| st.add_row [" * #{k}", v] }
|
30
|
+
st.add_row ['Uniques', @stats[:uniques]]
|
31
|
+
st.add_row ['Logs', @stats[:uniques]]
|
32
|
+
st.add_row [' ', ' ']
|
33
|
+
|
34
|
+
st.add_row ['Gets', @stats[:gets]]
|
35
|
+
if @gets.count > 0
|
36
|
+
list = @gets.sort_by { |_k, v| v }
|
37
|
+
list.reverse_each { |item| st.add_row [" * #{item[0]}", item[1].to_s] }
|
38
|
+
end
|
39
|
+
|
40
|
+
st.add_row ['Sets', @stats[:sets]]
|
41
|
+
if @sets.count > 0
|
42
|
+
@sets.each_pair { |k, v| st.add_row [" * #{k}", v.to_s] }
|
43
|
+
end
|
44
|
+
end
|
45
|
+
verboseln my_screen_table.to_s + "\n"
|
46
|
+
end
|
47
|
+
|
48
|
+
def show_config
|
49
|
+
@verbose = false
|
50
|
+
process_content
|
51
|
+
@verbose = true
|
52
|
+
revise_config_content
|
53
|
+
end
|
54
|
+
|
55
|
+
def show_requests
|
56
|
+
@verbose = false
|
57
|
+
process_content
|
58
|
+
@verbose = true
|
59
|
+
my_screen_table = Terminal::Table.new do |st|
|
60
|
+
st.add_row ['Lines', 'REQUEST description']
|
61
|
+
st.add_separator
|
62
|
+
@requests.each_with_index do |line, index|
|
63
|
+
st.add_row ['%03d' % index, line]
|
64
|
+
end
|
65
|
+
end
|
66
|
+
verboseln my_screen_table
|
67
|
+
end
|
68
|
+
|
69
|
+
private
|
70
|
+
|
71
|
+
def verbose(text)
|
72
|
+
print text if @verbose
|
73
|
+
end
|
74
|
+
|
75
|
+
def verboseln(text)
|
76
|
+
puts text if @verbose
|
77
|
+
end
|
78
|
+
|
79
|
+
def process_content
|
80
|
+
groups = Application.instance.groups
|
81
|
+
verboseln ''
|
82
|
+
groups.each do |t|
|
83
|
+
@stats[:groups] += 1
|
84
|
+
|
85
|
+
msg = "GROUP: #{t[:name]}"
|
86
|
+
my_screen_table = Terminal::Table.new { |st| st.add_row [msg] }
|
87
|
+
verboseln my_screen_table
|
88
|
+
|
89
|
+
instance_eval(&t[:block])
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
def find_script_vars
|
94
|
+
script_vars = [:tt_members]
|
95
|
+
@hosts.each_key do |k|
|
96
|
+
next if k == :localhost
|
97
|
+
|
98
|
+
if k.class == Symbol
|
99
|
+
script_vars << (k.to_s + '_ip').to_sym
|
100
|
+
script_vars << (k.to_s + '_username').to_sym
|
101
|
+
script_vars << (k.to_s + '_password').to_sym
|
102
|
+
else
|
103
|
+
script_vars << k.to_s + '_ip'
|
104
|
+
script_vars << k.to_s + '_username'
|
105
|
+
script_vars << k.to_s + '_password'
|
106
|
+
end
|
107
|
+
end
|
108
|
+
@gets.each_key { |k| script_vars << k }
|
109
|
+
script_vars
|
110
|
+
end
|
111
|
+
|
112
|
+
def recomended_config_content
|
113
|
+
verbose Rainbow('[WARN] File ').yellow
|
114
|
+
verbose Rainbow(@path[:config]).yellow.bright
|
115
|
+
verboseln Rainbow(' not found!').yellow
|
116
|
+
verboseln '[INFO] Recomended content:'
|
117
|
+
output = { global: nil, cases: [] }
|
118
|
+
output[:cases][0] = {}
|
119
|
+
script_vars = find_script_vars
|
120
|
+
script_vars.each { |i| output[:cases][0][i] = 'VALUE' }
|
121
|
+
verboseln YAML.dump(output)
|
122
|
+
end
|
123
|
+
|
124
|
+
def revise_config_content
|
125
|
+
@verbose = true
|
126
|
+
my_screen_table = Terminal::Table.new do |st|
|
127
|
+
st.add_row ['Revising CONFIG file']
|
128
|
+
end
|
129
|
+
verboseln my_screen_table
|
130
|
+
|
131
|
+
unless File.exist?(@path[:config])
|
132
|
+
recomended_config_content
|
133
|
+
return
|
134
|
+
end
|
135
|
+
|
136
|
+
script_vars = find_script_vars
|
137
|
+
config_vars = ConfigFileReader.read(@path[:config])
|
138
|
+
unless config_vars[:global].nil?
|
139
|
+
config_vars[:global].each_key { |k| script_vars.delete(k) }
|
140
|
+
end
|
141
|
+
unless config_vars[:alias].nil?
|
142
|
+
config_vars[:alias].each_key { |k| script_vars.delete(k) }
|
143
|
+
end
|
144
|
+
|
145
|
+
config_vars[:cases].each_with_index do |item, index|
|
146
|
+
next if item[:tt_skip] == true
|
147
|
+
|
148
|
+
script_vars.each do |value|
|
149
|
+
next unless item[value].nil?
|
150
|
+
|
151
|
+
next unless @sets[':' + value.to_s].nil?
|
152
|
+
|
153
|
+
verbose Rainbow(' * Define ').red
|
154
|
+
verbose Rainbow(value).red.bright
|
155
|
+
verbose Rainbow(' value for Case[').red
|
156
|
+
verbose Rainbow(index).red.bright
|
157
|
+
verboseln Rainbow('] or set tt_skip = true').red
|
158
|
+
end
|
159
|
+
end
|
160
|
+
end
|
161
|
+
end
|
@@ -0,0 +1,129 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'rainbow'
|
4
|
+
require_relative '../application'
|
5
|
+
|
6
|
+
# Project:
|
7
|
+
# * find_filenames_for, verbose, verboseln
|
8
|
+
module NameFileFinder
|
9
|
+
def self.find_filenames_for(relpathtofile)
|
10
|
+
pathtofile = File.absolute_path(relpathtofile)
|
11
|
+
|
12
|
+
# Define:
|
13
|
+
# script_path, must contain fullpath to DSL script file
|
14
|
+
# config_path, must contain fullpath to YAML config file
|
15
|
+
if File.directory?(pathtofile)
|
16
|
+
# COMPLEX MODE: We use start.rb as main RB file
|
17
|
+
find_filenames_from_directory(pathtofile)
|
18
|
+
else
|
19
|
+
# SIMPLE MODE: We use pathtofile as main RB file
|
20
|
+
find_filenames_from_rb(pathtofile)
|
21
|
+
end
|
22
|
+
true
|
23
|
+
end
|
24
|
+
|
25
|
+
def self.find_filenames_from_directory(pathtodir)
|
26
|
+
# COMPLEX MODE: We use start.rb as main RB file
|
27
|
+
script_path = File.join(pathtodir, 'start.rb')
|
28
|
+
unless File.exist? script_path
|
29
|
+
print Rainbow('[ERROR] File ').red
|
30
|
+
print Rainbow(script_path).bright.red
|
31
|
+
puts Rainbow(' not found!').red
|
32
|
+
exit 1
|
33
|
+
end
|
34
|
+
|
35
|
+
app = Application.instance
|
36
|
+
app.project_path = pathtodir
|
37
|
+
app.script_path = script_path
|
38
|
+
app.test_name = pathtodir.split(File::SEPARATOR)[-1]
|
39
|
+
|
40
|
+
find_configfilename_from_directory(pathtodir)
|
41
|
+
end
|
42
|
+
|
43
|
+
def self.find_configfilename_from_directory(pathtodir)
|
44
|
+
# COMPLEX MODE: We use config.yaml by default
|
45
|
+
app = Application.instance
|
46
|
+
|
47
|
+
config_path = ''
|
48
|
+
if app.options['cpath'].nil?
|
49
|
+
config_name = 'config'
|
50
|
+
# Config name file is introduced by cname arg option from teuton command
|
51
|
+
config_name = app.options['cname'] unless app.options['cname'].nil?
|
52
|
+
config_path = File.join(pathtodir, "#{config_name}.json")
|
53
|
+
unless File.exist? config_path
|
54
|
+
config_path = File.join(pathtodir, "#{config_name}.yaml")
|
55
|
+
end
|
56
|
+
else
|
57
|
+
# Config path file is introduced by cpath arg option from teuton command
|
58
|
+
config_path = app.options['cpath']
|
59
|
+
end
|
60
|
+
app.config_path = config_path
|
61
|
+
end
|
62
|
+
|
63
|
+
def self.find_filenames_from_rb(script_path)
|
64
|
+
# SIMPLE MODE: We use script_path as main RB file
|
65
|
+
# This must be fullpath to DSL script file
|
66
|
+
if File.extname(script_path) != '.rb'
|
67
|
+
print Rainbow('[ERROR] Script ').red
|
68
|
+
print Rainbow(script_path).bright.red
|
69
|
+
puts Rainbow(' must have rb extension').red
|
70
|
+
exit 1
|
71
|
+
end
|
72
|
+
|
73
|
+
app = Application.instance
|
74
|
+
app.project_path = File.dirname(script_path)
|
75
|
+
app.script_path = script_path
|
76
|
+
app.test_name = File.basename(script_path, '.rb')
|
77
|
+
|
78
|
+
find_configfilenames_from_rb(script_path)
|
79
|
+
end
|
80
|
+
|
81
|
+
def self.find_configfilenames_from_rb(script_path)
|
82
|
+
# SIMPLE MODE: We use script_path as main RB file
|
83
|
+
# This must be fullpath to DSL script file
|
84
|
+
app = Application.instance
|
85
|
+
|
86
|
+
config_path = ''
|
87
|
+
if app.options['cpath'].nil?
|
88
|
+
config_name = File.basename(script_path, '.rb')
|
89
|
+
# Config name file is introduced by cname arg option from teuton command
|
90
|
+
config_name = app.options['cname'] unless app.options['cname'].nil?
|
91
|
+
|
92
|
+
config_path = File.join(app.project_path, config_name + '.json')
|
93
|
+
unless File.exist? config_path
|
94
|
+
config_path = File.join(app.project_path, config_name + '.yaml')
|
95
|
+
end
|
96
|
+
else
|
97
|
+
# Config path file is introduced by cpath arg option from teuton command
|
98
|
+
config_path = app.options['cpath']
|
99
|
+
end
|
100
|
+
app.config_path = config_path
|
101
|
+
end
|
102
|
+
|
103
|
+
def self.puts_input_info_on_screen
|
104
|
+
app = Application.instance
|
105
|
+
|
106
|
+
verbose Rainbow('[INFO] ScriptPath => ').blue
|
107
|
+
verboseln Rainbow(trim(app.script_path)).blue.bright
|
108
|
+
verbose Rainbow('[INFO] ConfigPath => ').blue
|
109
|
+
verboseln Rainbow(trim(app.config_path)).blue.bright
|
110
|
+
verbose Rainbow('[INFO] TestName => ').blue
|
111
|
+
verboseln Rainbow(trim(app.test_name)).blue.bright
|
112
|
+
end
|
113
|
+
|
114
|
+
def self.trim(input)
|
115
|
+
output = input.to_s
|
116
|
+
output = "...#{input[input.size - 50, input.size]}" if output.size > 65
|
117
|
+
output.to_s
|
118
|
+
end
|
119
|
+
|
120
|
+
def self.verboseln(text)
|
121
|
+
verbose(text + "\n")
|
122
|
+
end
|
123
|
+
|
124
|
+
def self.verbose(text)
|
125
|
+
return unless Application.instance.verbose
|
126
|
+
return if Application.instance.options['quiet']
|
127
|
+
print text
|
128
|
+
end
|
129
|
+
end
|
@@ -0,0 +1,62 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require_relative '../application'
|
4
|
+
require_relative 'name_file_finder'
|
5
|
+
|
6
|
+
# Project functions invoked by CLI project tool
|
7
|
+
# * test
|
8
|
+
# * play
|
9
|
+
# * process_input_case_option
|
10
|
+
# * readme
|
11
|
+
# * require_dsl_and_script
|
12
|
+
module Project
|
13
|
+
def self.test(pathtofile, options)
|
14
|
+
Application.instance.options.merge! options
|
15
|
+
NameFileFinder.find_filenames_for(pathtofile)
|
16
|
+
NameFileFinder.puts_input_info_on_screen
|
17
|
+
require_dsl_and_script('laboratory/laboratory') # Define DSL keywords
|
18
|
+
|
19
|
+
app = Application.instance
|
20
|
+
lab = Laboratory.new(app.script_path, app.config_path)
|
21
|
+
# lab.show_requests if options[:r]
|
22
|
+
lab.show_config if options[:c]
|
23
|
+
lab.show_dsl unless options[:r] || options[:c]
|
24
|
+
end
|
25
|
+
|
26
|
+
def self.play(pathtofile, options)
|
27
|
+
Application.instance.options.merge! options
|
28
|
+
process_input_case_option
|
29
|
+
NameFileFinder.find_filenames_for(pathtofile)
|
30
|
+
NameFileFinder.puts_input_info_on_screen
|
31
|
+
require_dsl_and_script('../case_manager/dsl') # Define DSL keywords
|
32
|
+
end
|
33
|
+
|
34
|
+
def self.process_input_case_option
|
35
|
+
options = Application.instance.options
|
36
|
+
unless options['case'].nil?
|
37
|
+
a = options['case'].split(',')
|
38
|
+
options['case'] = a.collect! { |i| i.to_i }
|
39
|
+
end
|
40
|
+
end
|
41
|
+
|
42
|
+
def self.readme(pathtofile, options)
|
43
|
+
Application.instance.options.merge! options
|
44
|
+
NameFileFinder.find_filenames_for(pathtofile)
|
45
|
+
require_dsl_and_script('readme/readme') # Define DSL keywords
|
46
|
+
|
47
|
+
app = Application.instance
|
48
|
+
readme = Readme.new(app.script_path, app.config_path)
|
49
|
+
readme.show
|
50
|
+
end
|
51
|
+
|
52
|
+
def self.require_dsl_and_script(dslpath)
|
53
|
+
app = Application.instance
|
54
|
+
require_relative dslpath
|
55
|
+
begin
|
56
|
+
require_relative app.script_path
|
57
|
+
rescue SyntaxError => e
|
58
|
+
puts e.to_s
|
59
|
+
puts Rainbow.new("[ERROR] SyntaxError into file #{app.script_path}").red
|
60
|
+
end
|
61
|
+
end
|
62
|
+
end
|
@@ -0,0 +1,79 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
require 'fileutils'
|
4
|
+
require 'rainbow'
|
5
|
+
|
6
|
+
# Project#create
|
7
|
+
# * create
|
8
|
+
# * create_main_dir_and_files
|
9
|
+
# * create_assets_dir_and_files
|
10
|
+
# * create_dir
|
11
|
+
# * create_dirs
|
12
|
+
# * copyfile
|
13
|
+
module ProjectCreator
|
14
|
+
def self.create(project_dir)
|
15
|
+
project_name = File.basename(project_dir)
|
16
|
+
puts "\n[INFO] Creating #{Rainbow(project_name).bright} project skeleton"
|
17
|
+
|
18
|
+
source_basedir = File.join(File.dirname(__FILE__), '../..')
|
19
|
+
create_dir project_dir
|
20
|
+
|
21
|
+
create_main_dir_and_files(project_dir, source_basedir)
|
22
|
+
create_assets_dir_and_files(project_dir, source_basedir)
|
23
|
+
end
|
24
|
+
|
25
|
+
def self.create_main_dir_and_files(project_dir, source_basedir)
|
26
|
+
# Directory and files: Ruby script, Configfile, gitignore
|
27
|
+
items = [
|
28
|
+
{ source: 'lib/files/config.yaml', target: 'config.yaml' },
|
29
|
+
{ source: 'lib/files/start.rb', target: 'start.rb' },
|
30
|
+
{ source: 'lib/files/README.md', target: 'README.md' },
|
31
|
+
{ source: 'lib/files/gitignore', target: '.gitignore' }
|
32
|
+
]
|
33
|
+
items.each do |item|
|
34
|
+
source = File.join(source_basedir, item[:source])
|
35
|
+
target = File.join(project_dir, item[:target])
|
36
|
+
copyfile(source, target)
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
def self.create_assets_dir_and_files(project_dir, source_basedir)
|
41
|
+
# Assets Directory and files
|
42
|
+
project_assets_dir = File.join(project_dir, 'assets')
|
43
|
+
create_dir project_assets_dir
|
44
|
+
# source = File.join(source_basedir, 'lib/files/README.md')
|
45
|
+
# target = File.join(project_dir, 'README.md')
|
46
|
+
# copyfile(source, target) # README.md
|
47
|
+
puts ''
|
48
|
+
end
|
49
|
+
|
50
|
+
def self.create_dir(dirpath)
|
51
|
+
if Dir.exist? dirpath
|
52
|
+
puts "* Exists dir! => #{Rainbow(dirpath).yellow}"
|
53
|
+
else
|
54
|
+
begin
|
55
|
+
FileUtils.mkdir_p(dirpath)
|
56
|
+
puts "* Create dir => #{Rainbow(dirpath).green}"
|
57
|
+
rescue StandarError
|
58
|
+
puts "* Create dir ERROR => #{Rainbow(dirpath).red}"
|
59
|
+
end
|
60
|
+
end
|
61
|
+
end
|
62
|
+
|
63
|
+
def self.create_dirs(*args)
|
64
|
+
args.each { |arg| create_dir arg }
|
65
|
+
end
|
66
|
+
|
67
|
+
def self.copyfile(target, dest)
|
68
|
+
if File.exist? dest
|
69
|
+
puts "* Exists file! => #{Rainbow(dest).yellow}"
|
70
|
+
else
|
71
|
+
begin
|
72
|
+
FileUtils.cp(target, dest)
|
73
|
+
puts "* Create file => #{Rainbow(dest).green}"
|
74
|
+
rescue StandarError
|
75
|
+
puts "* Create file ERROR => #{Rainbow(dest).red}"
|
76
|
+
end
|
77
|
+
end
|
78
|
+
end
|
79
|
+
end
|
@@ -0,0 +1,109 @@
|
|
1
|
+
# frozen_string_literal: true
|
2
|
+
|
3
|
+
# Readme
|
4
|
+
# * target
|
5
|
+
# * goto
|
6
|
+
# * run
|
7
|
+
# * expect
|
8
|
+
# * unique
|
9
|
+
# * log
|
10
|
+
class Readme
|
11
|
+
def readme(text)
|
12
|
+
if @action[:target].nil?
|
13
|
+
# It's a group readme
|
14
|
+
@current[:readme] << text
|
15
|
+
else
|
16
|
+
# It's a target readme
|
17
|
+
@action[:readme] << text
|
18
|
+
end
|
19
|
+
end
|
20
|
+
|
21
|
+
def target(desc, args = {})
|
22
|
+
previous_host = @action[:host]
|
23
|
+
@action = { target: desc, host: previous_host, readme: [] }
|
24
|
+
weight = 1.0
|
25
|
+
weight = args[:weight].to_f if args[:weight]
|
26
|
+
@action[:weight] = weight
|
27
|
+
end
|
28
|
+
alias goal target
|
29
|
+
|
30
|
+
def goto(host = :localhost, args = {})
|
31
|
+
unless host == :localhost
|
32
|
+
b = {}
|
33
|
+
a = "#{host}_ip".to_sym
|
34
|
+
if @config[:global][a].nil? && (not @setted_params.include?(a))
|
35
|
+
@cases_params << a
|
36
|
+
end
|
37
|
+
b[:ip] = @config[:global][a] if @config[:global][a]
|
38
|
+
b[:ip] = @setted_params[a] if @setted_params[a]
|
39
|
+
|
40
|
+
a = "#{host}_username".to_sym
|
41
|
+
if @config[:global][a].nil? && (not @setted_params.include?(a))
|
42
|
+
@cases_params << a
|
43
|
+
end
|
44
|
+
b[:username] = @config[:global][a] if @config[:global][a]
|
45
|
+
b[:username] = @setted_params[a] if @setted_params[a]
|
46
|
+
|
47
|
+
a = "#{host}_password".to_sym
|
48
|
+
if @config[:global][a].nil? && (not @setted_params.include?(a))
|
49
|
+
@cases_params << a
|
50
|
+
end
|
51
|
+
b[:password] = @config[:global][a] if @config[:global][a]
|
52
|
+
b[:password] = @setted_params[a] if @setted_params[a]
|
53
|
+
|
54
|
+
@required_hosts[host.to_s] = b
|
55
|
+
end
|
56
|
+
@action[:host] = host
|
57
|
+
@action[:exec] = args[:exec] || 'noexec'
|
58
|
+
end
|
59
|
+
|
60
|
+
def run(command, args = {})
|
61
|
+
args[:exec] = command
|
62
|
+
goto(:localhost, args)
|
63
|
+
end
|
64
|
+
|
65
|
+
def expect(_cond, args = {})
|
66
|
+
@current[:actions] << @action
|
67
|
+
result.reset
|
68
|
+
end
|
69
|
+
alias expect_any expect
|
70
|
+
alias expect_none expect
|
71
|
+
alias expect_one expect
|
72
|
+
|
73
|
+
def get(value)
|
74
|
+
unless @config[:global][value].nil?
|
75
|
+
@global_params[value] = @config[:global][value]
|
76
|
+
return @config[:global][value]
|
77
|
+
end
|
78
|
+
|
79
|
+
return value.to_s.upcase if @setted_params.include? value
|
80
|
+
|
81
|
+
@cases_params << value
|
82
|
+
value.to_s.upcase
|
83
|
+
end
|
84
|
+
|
85
|
+
# If a method call is missing, then delegate to concept parent.
|
86
|
+
def method_missing(method)
|
87
|
+
a = method.to_s
|
88
|
+
instance_eval("get(:#{a[0, a.size - 1]})") if a[a.size - 1] == '?'
|
89
|
+
end
|
90
|
+
|
91
|
+
def gett(value)
|
92
|
+
a = get(value)
|
93
|
+
return "[#{value}](\#required-params)" if @cases_params.include? value
|
94
|
+
return "[#{value}](\#created-params)" if @setted_params[value]
|
95
|
+
"[#{a}](\#global-params)" if @global_params.include? value
|
96
|
+
end
|
97
|
+
|
98
|
+
def set(key, value)
|
99
|
+
@setted_params[key] = value
|
100
|
+
end
|
101
|
+
|
102
|
+
def unique(_key, _value)
|
103
|
+
# don't do nothing
|
104
|
+
end
|
105
|
+
|
106
|
+
def log(text = '', type = :info)
|
107
|
+
@data[:logs] << "[#{type}]: " + text.to_s
|
108
|
+
end
|
109
|
+
end
|
@@ -0,0 +1,30 @@
|
|
1
|
+
|
2
|
+
require_relative '../../application'
|
3
|
+
|
4
|
+
module Lang
|
5
|
+
def self.get(key)
|
6
|
+
lang = {}
|
7
|
+
lang['en'] = {
|
8
|
+
version: 'Teuton version : %s',
|
9
|
+
testname: 'Challenge name : %s',
|
10
|
+
date: 'Date : %s',
|
11
|
+
hosts: "\n\#\#\# Required hosts\n",
|
12
|
+
params: "\n\#\#\# Required params\n",
|
13
|
+
goto: "\nGo to [%s](\#required-hosts) host, and do next:\n",
|
14
|
+
global: "\nGlobal parameters that can be modified:\n",
|
15
|
+
created: "\nParams created during challenge execution:\n"
|
16
|
+
}
|
17
|
+
lang['es'] = {
|
18
|
+
version: 'Versión de Teuton : %s',
|
19
|
+
testname: 'Nombre del reto : %s',
|
20
|
+
date: 'Fecha : %s',
|
21
|
+
hosts: "\n\#\#\# Máquinas que se necesitan\n",
|
22
|
+
params: "\n\#\#\# Parámetros de necesarios\n",
|
23
|
+
goto: "\nIr a la máquina [%s](\#required-hosts), y hacer lo siguiente:\n",
|
24
|
+
global: "\nParámetros globales que pueden ser modificados:\n",
|
25
|
+
created: "\nParámetros creados durante la ejecución del reto:\n"
|
26
|
+
}
|
27
|
+
locale = Application.instance.options['lang'].downcase
|
28
|
+
lang[locale][key]
|
29
|
+
end
|
30
|
+
end
|