oats 0.0.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.
- data/.gitignore +6 -0
- data/Gemfile +15 -0
- data/README.txt +165 -0
- data/Rakefile +2 -0
- data/bin/agent +204 -0
- data/bin/oats +10 -0
- data/bin/occ +29 -0
- data/bin/results_cleanup +6 -0
- data/doc/COPYING +55 -0
- data/doc/LICENSE +55 -0
- data/doc/OATS_Framework.doc +0 -0
- data/doc/classes/ApplicationLogs.html +239 -0
- data/doc/classes/Campaign.html +843 -0
- data/doc/classes/CommandlineOptions.html +131 -0
- data/doc/classes/Driver.html +182 -0
- data/doc/classes/Hash.html +137 -0
- data/doc/classes/Ide.html +194 -0
- data/doc/classes/MapSelenium.html +197 -0
- data/doc/classes/Net.html +107 -0
- data/doc/classes/Oats/OatsFilterError.html +119 -0
- data/doc/classes/Oats.html +998 -0
- data/doc/classes/OatsAssertError.html +119 -0
- data/doc/classes/OatsBadInput.html +119 -0
- data/doc/classes/OatsData.html +290 -0
- data/doc/classes/OatsError.html +117 -0
- data/doc/classes/OatsExit.html +117 -0
- data/doc/classes/OatsLock.html +254 -0
- data/doc/classes/OatsMain.html +182 -0
- data/doc/classes/OatsMysqlError.html +113 -0
- data/doc/classes/OatsMysqlMissingInput.html +113 -0
- data/doc/classes/OatsReportError.html +113 -0
- data/doc/classes/OatsSetupError.html +119 -0
- data/doc/classes/OatsTestError.html +119 -0
- data/doc/classes/OatsTestExit.html +119 -0
- data/doc/classes/OatsTestLocateError.html +120 -0
- data/doc/classes/OatsVerifyError.html +119 -0
- data/doc/classes/Ragent.html +397 -0
- data/doc/classes/Rclient.html +236 -0
- data/doc/classes/Report.html +368 -0
- data/doc/classes/Reports.html +244 -0
- data/doc/classes/RestApi.html +333 -0
- data/doc/classes/RhttpClient.html +236 -0
- data/doc/classes/Rimap.html +170 -0
- data/doc/classes/Rmysql.html +176 -0
- data/doc/classes/Roptions.html +131 -0
- data/doc/classes/Rselenium.html +233 -0
- data/doc/classes/Rssh.html +138 -0
- data/doc/classes/Runnable.html +174 -0
- data/doc/classes/SFTriggers.html +206 -0
- data/doc/classes/Selenium/Client/Driver.html +211 -0
- data/doc/classes/Selenium/Client.html +107 -0
- data/doc/classes/Selenium.html +107 -0
- data/doc/classes/SystemCapture.html +304 -0
- data/doc/classes/TestCase.html +418 -0
- data/doc/classes/TestData.html +235 -0
- data/doc/classes/TestList.html +264 -0
- data/doc/classes/Tools.html +244 -0
- data/doc/classes/Util.html +201 -0
- data/doc/classes/Variation.html +206 -0
- data/doc/fr_class_index.html +92 -0
- data/doc/fr_method_index.html +465 -0
- data/doc/index.html +23 -0
- data/doc/oats_httpd.conf +32 -0
- data/doc/oats_user.yml +25 -0
- data/doc/rdoc-style.css +208 -0
- data/lib/deep_merge/.gitignore +2 -0
- data/lib/deep_merge/core.rb +195 -0
- data/lib/deep_merge/deep_merge.rb +1 -0
- data/lib/deep_merge/deep_merge_hash.rb +28 -0
- data/lib/deep_merge/rails_compat.rb +27 -0
- data/lib/oats/application_logs.rb +163 -0
- data/lib/oats/build_id.rb +58 -0
- data/lib/oats/commandline_options.rb +128 -0
- data/lib/oats/diff.rb +278 -0
- data/lib/oats/driver.rb +492 -0
- data/lib/oats/ide.rb +227 -0
- data/lib/oats/keywords.rb +67 -0
- data/lib/oats/log4r_init.rb +14 -0
- data/lib/oats/mysql.rb +97 -0
- data/lib/oats/oats.rb +637 -0
- data/lib/oats/oats_data.rb +400 -0
- data/lib/oats/oats_exceptions.rb +25 -0
- data/lib/oats/oats_lock.rb +261 -0
- data/lib/oats/oats_selenium_api.rb +639 -0
- data/lib/oats/oselenium.rb +189 -0
- data/lib/oats/ossh.rb +36 -0
- data/lib/oats/patches_for_eventmachine_12.10.rb +66 -0
- data/lib/oats/ragent.rb +321 -0
- data/lib/oats/rclient.rb +42 -0
- data/lib/oats/report.rb +207 -0
- data/lib/oats/roptions.rb +88 -0
- data/lib/oats/test_case.rb +510 -0
- data/lib/oats/test_data.rb +98 -0
- data/lib/oats/test_list.rb +141 -0
- data/lib/oats/unixdiff.rb +75 -0
- data/lib/oats/util.rb +125 -0
- data/lib/oats/version.rb +3 -0
- data/lib/oats.rb +36 -0
- data/nbproject/configs/agent.properties +0 -0
- data/nbproject/configs/gr.properties +0 -0
- data/nbproject/project.properties +10 -0
- data/nbproject/project.xml +17 -0
- data/oats.gemspec +42 -0
- data/oats_ini.yml +258 -0
- data/oats_tests/Gemfile +18 -0
- data/oats_tests/aut_ini.yml +30 -0
- data/oats_tests/bin/oats +8 -0
- data/oats_tests/environments/qa.yml +4 -0
- data/oats_tests/environments/qa_chrome.yml +4 -0
- data/oats_tests/examples/core/coreExamples.yml +8 -0
- data/oats_tests/examples/core/expectedException.rb +39 -0
- data/oats_tests/examples/core/ok_verify.rb +2 -0
- data/oats_tests/examples/core/ok_verify.rb_ok/out/myfile.txt +1 -0
- data/oats_tests/examples/core/ok_verify.rb_ok/out/myfile2.txt +1 -0
- data/oats_tests/examples/core/ok_verify.rb_ok/rats_test.log +2 -0
- data/oats_tests/examples/core/unexpectedException.rb +30 -0
- data/oats_tests/examples/examples.yml +13 -0
- data/oats_tests/examples/gui/guiExamples.yml +7 -0
- data/oats_tests/examples/gui/seleniumGoogle.rb +10 -0
- data/oats_tests/examples/gui/webdriverGoogle.rb +9 -0
- data/oats_tests/examples/keywords/SampleXlList-1.xls +0 -0
- data/oats_tests/examples/keywords/SampleXlList-2.xls +0 -0
- data/oats_tests/examples/keywords/SampleXlLists.xls +0 -0
- data/oats_tests/examples/keywords/keywordsDriver.rb +1 -0
- data/oats_tests/examples/keywords/keywordsExamples.yml +8 -0
- data/oats_tests/examples/keywords/keywordsTC1.yml +5 -0
- data/oats_tests/examples/keywords/keywordsTestlist.yml +16 -0
- data/oats_tests/examples/needsWork/addTestDynamically.rb +4 -0
- data/oats_tests/examples/needsWork/emailVerify.rb +34 -0
- data/oats_tests/examples/needsWork/testSql/rtest.sql +6 -0
- data/oats_tests/examples/needsWork/testSql/rtest.yml +11 -0
- data/oats_tests/examples/occTest/occTest.rb +13 -0
- data/oats_tests/examples/occTest/occTest_1.rb +1 -0
- data/oats_tests/examples/occTest/occTest_1_1.rb +1 -0
- data/oats_tests/examples/occTest/occTest_1_2.rb +1 -0
- data/oats_tests/examples/occTest/occTest_1_3.rb +1 -0
- data/oats_tests/examples/occTest/occTest_1_4.rb +1 -0
- data/oats_tests/examples/occTest/occTest_2.rb +1 -0
- data/oats_tests/examples/occTest/occTest_2_1.rb +1 -0
- data/oats_tests/examples/occTest/occTest_2_2.rb +1 -0
- data/oats_tests/examples/occTest/occTest_2_3.rb +1 -0
- data/oats_tests/examples/occTest/occTest_2_4.rb +1 -0
- data/oats_tests/examples/occTest/occTest_3.rb +1 -0
- data/oats_tests/examples/occTest/occTest_3_1.rb +1 -0
- data/oats_tests/examples/occTest/occTest_3_2.rb +1 -0
- data/oats_tests/examples/occTest/occTest_3_3.rb +1 -0
- data/oats_tests/examples/occTest/occTest_3_4.rb +1 -0
- data/oats_tests/examples/occTest/occTest_4.rb +1 -0
- data/oats_tests/examples/occTest/occTestlist.yml +9 -0
- data/oats_tests/examples/occTest/occTestlist_1.yml +9 -0
- data/oats_tests/examples/occTest/occTestlist_2.yml +9 -0
- data/oats_tests/examples/occTest/occTestlist_3.yml +9 -0
- data/oats_tests/examples/occTest/variation1.yml +4 -0
- data/oats_tests/examples/occTest/variation2.yml +4 -0
- data/oats_tests/examples/testFileLocationUnitTests/extn_driver.rb +4 -0
- data/oats_tests/examples/testFileLocationUnitTests/folder/oats.yml +3 -0
- data/oats_tests/examples/testFileLocationUnitTests/folder/t1.rb +2 -0
- data/oats_tests/examples/testFileLocationUnitTests/folder1/t1.yml +2 -0
- data/oats_tests/examples/testFileLocationUnitTests/folder1/t1_1.yml +3 -0
- data/oats_tests/examples/testFileLocationUnitTests/folder2/oats.yml +3 -0
- data/oats_tests/examples/testFileLocationUnitTests/folder2/t1.rb +2 -0
- data/oats_tests/examples/testFileLocationUnitTests/folder2/t1.yml +2 -0
- data/oats_tests/examples/testFileLocationUnitTests/no_yaml.rb +3 -0
- data/oats_tests/examples/testFileLocationUnitTests/post_yaml.rb +1 -0
- data/oats_tests/examples/testFileLocationUnitTests/t1.rb +4 -0
- data/oats_tests/examples/testFileLocationUnitTests/t1.yml +2 -0
- data/oats_tests/examples/testFileLocationUnitTests/t1_1.yml +3 -0
- data/oats_tests/examples/testFileLocationUnitTests/testDir/oats.yml +3 -0
- data/oats_tests/examples/testFileLocationUnitTests/testDir/t1.rb +2 -0
- data/oats_tests/examples/testFileLocationUnitTests/testDir/t1.yml +2 -0
- data/oats_tests/examples/testFileLocationUnitTests/testDir2/t1.rb +2 -0
- data/oats_tests/examples/testFileLocationUnitTests/testDir2/t1.yml +2 -0
- data/oats_tests/examples/testFileLocationUnitTests/unitTestList.yml +36 -0
- data/oats_tests/examples/testFileLocationUnitTests/yml_driver.rb +2 -0
- data/oats_tests/lib/business.rb +28 -0
- data/oats_tests/lib/sample_xl_lists.rb +37 -0
- data/test/common_test_unit_setup.rb +21 -0
- data/test/test_basic.rb +16 -0
- data/test/test_selenium.rb +16 -0
- data/test/test_xl_lists.rb +16 -0
- metadata +291 -0
data/lib/oats/ide.rb
ADDED
|
@@ -0,0 +1,227 @@
|
|
|
1
|
+
# IDE Class to run an IDE based HTML suite after transforming it based on oats_data
|
|
2
|
+
|
|
3
|
+
module Oats
|
|
4
|
+
|
|
5
|
+
# Runs an IDE based HTML suite after transforming it based on current Oats data
|
|
6
|
+
class Ide
|
|
7
|
+
def initialize()
|
|
8
|
+
super
|
|
9
|
+
@suite_base_url_signin_type = nil;
|
|
10
|
+
@first_test_url = nil;
|
|
11
|
+
end
|
|
12
|
+
|
|
13
|
+
# Run input_suite_path while in a TestData.dir . Assumes Oats.data is initialized for TestData.dir
|
|
14
|
+
# input_suite_path:: path to the suite HTML
|
|
15
|
+
# hash:: list from => to values to use for regeneration of the included test cases.
|
|
16
|
+
def run (input_suite_path, hash = nil )
|
|
17
|
+
begin
|
|
18
|
+
run_ide(input_suite_path, hash)
|
|
19
|
+
ensure
|
|
20
|
+
TestData.current_test.collect_downloaded_output
|
|
21
|
+
end
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
private
|
|
25
|
+
|
|
26
|
+
def run_ide (input_suite_path, hash = nil )
|
|
27
|
+
suite_path = get_path(input_suite_path)
|
|
28
|
+
name = File.basename(suite_path)
|
|
29
|
+
doc = open(suite_path ) { |f| Hpricot(f) }
|
|
30
|
+
# FileUtils.rm Dir[File.join(TestData.current_test.dir,'*.gen.*')] # Clean previously generated files
|
|
31
|
+
FileUtils.rm Dir['*.gen.*'] # Clean previously generated files in pwd
|
|
32
|
+
if doc.search("head[@profile='http://selenium-ide.openqa.org/profiles/test-case']").empty?
|
|
33
|
+
regen_suite = nil
|
|
34
|
+
doc.search('a[@href]') do |a|
|
|
35
|
+
if Oats.data['execution']['run_in_dir_results']
|
|
36
|
+
generated_test = regenerate_html(a['href'], test.result, File.dirname(suite_path), hash)
|
|
37
|
+
else
|
|
38
|
+
generated_test = regenerate_html(a['href'], test.dir, File.dirname(suite_path), hash)
|
|
39
|
+
end
|
|
40
|
+
if generated_test
|
|
41
|
+
regen_suite = true
|
|
42
|
+
a.set_attribute(:href,generated_test)
|
|
43
|
+
end
|
|
44
|
+
end
|
|
45
|
+
html_suite_path = File.join(test.dir , File.basename(suite_path,'.*') + '.gen.html')
|
|
46
|
+
regen_suite = true if regen_suite or html_suite_path != suite_path
|
|
47
|
+
html_suite_path = File.join(test.result , File.basename(suite_path,'.*') + '.gen.html') if Oats.data['execution']['run_in_dir_results']
|
|
48
|
+
$log.info "Creating: #{html_suite_path}"
|
|
49
|
+
File.open( html_suite_path, 'w' ) { |out| out.print doc } if regen_suite
|
|
50
|
+
else # A single test HTML, not the suite
|
|
51
|
+
raise OatsTestError, "Input file is not an IDE suite: " + html_suite_path
|
|
52
|
+
end
|
|
53
|
+
|
|
54
|
+
# Execute html_suite_path
|
|
55
|
+
result_file = File.join(test.result, File.basename(name, '.*') + '_results.html')
|
|
56
|
+
if Oats.data['selenium']['ide']['generate']
|
|
57
|
+
$log.warn "Option execution:ide:generate is set. Test will not be executed."
|
|
58
|
+
$log.debug "Target result_file was: #{result_file}"
|
|
59
|
+
return
|
|
60
|
+
end
|
|
61
|
+
rc_jar_file = File.join(Oats.data['_']['vendor'],'selenium-server.jar')
|
|
62
|
+
browser = '*' + Oats.data['selenium']['browser_type'].sub(/ .*/,'')
|
|
63
|
+
url = nil
|
|
64
|
+
if @suite_base_url_signin_type
|
|
65
|
+
url = Oats.data[@suite_base_url_signin_type]["SignIn"]["url"]
|
|
66
|
+
else
|
|
67
|
+
if @first_test_url
|
|
68
|
+
url = @first_test_url
|
|
69
|
+
else
|
|
70
|
+
raise(OatsError, "None of the tests in #{suite_path} specified a base URL.")
|
|
71
|
+
end
|
|
72
|
+
end
|
|
73
|
+
if url
|
|
74
|
+
base_url = url.match('https?://[^/]*/?')
|
|
75
|
+
else
|
|
76
|
+
base_url = nil
|
|
77
|
+
end
|
|
78
|
+
port = Oats.data['selenium']['ide']['port']
|
|
79
|
+
if Oats.data['env']['web']['host']
|
|
80
|
+
base_url = 'http://' + Oats.data['env']['web']['host']
|
|
81
|
+
else
|
|
82
|
+
base_url = base_url[0]
|
|
83
|
+
end
|
|
84
|
+
# if base_url
|
|
85
|
+
# base_url = base_url[0]
|
|
86
|
+
# else
|
|
87
|
+
# base_url = 'http://' + Oats.data['env']['web']['host']
|
|
88
|
+
# $log.warn "Can not determine the base url from [#{url}]. Assuming base url is [#{base_url}]" \
|
|
89
|
+
# unless @suite_base_url_signin_type and Oats.data[@suite_base_url_signin_type]["SignIn"]
|
|
90
|
+
# end
|
|
91
|
+
command = "java -jar \"#{rc_jar_file}\" -port #{port}"
|
|
92
|
+
command += " -timeout #{Oats.data['selenium']['ide']['suite_timeout']}" if Oats.data['selenium']['ide']['suite_timeout']
|
|
93
|
+
# Don't use profiles when using RC in IDE mode
|
|
94
|
+
command += " -firefoxprofileTemplate \"#{$oats_global['firefox_profile_dir']}\"" \
|
|
95
|
+
if Oats.data['selenium']['browser_type'] =~ /firefox/ and $oats_global['firefox_profile_dir']
|
|
96
|
+
command += " -htmlSuite #{browser} #{base_url} \"#{html_suite_path}\" \"#{result_file}\" 2>&1"
|
|
97
|
+
$log.info "Starting Selenium Remote Control: #{command}"
|
|
98
|
+
# return # DEBUG
|
|
99
|
+
first_rc_try = true
|
|
100
|
+
failure_line = nil
|
|
101
|
+
catch :end_rc do
|
|
102
|
+
2.times do
|
|
103
|
+
IO.popen(command) do |io|
|
|
104
|
+
while io.gets do
|
|
105
|
+
$log.info chomp
|
|
106
|
+
if /Selenium is already running on port/ =~ $_
|
|
107
|
+
if first_rc_try
|
|
108
|
+
io.readlines.each {|line|$log.info line.chomp }
|
|
109
|
+
Util.clear_port(Oats.data['selenium']['ide']['port'],$log)
|
|
110
|
+
$log.info "Will attempt to restart Selenium RC..."
|
|
111
|
+
else
|
|
112
|
+
# raise(OatsError, $_, caller[1..3])
|
|
113
|
+
raise(OatsError, $_)
|
|
114
|
+
throw(:end_rc)
|
|
115
|
+
end
|
|
116
|
+
first_rc_try = false
|
|
117
|
+
elsif /fail/i =~ $_ and /Failed to start: SocketListener/ !~ $_
|
|
118
|
+
failure_line = $_
|
|
119
|
+
throw(:end_rc)
|
|
120
|
+
elsif /exception/i =~ $_ # Like server.SeleniumCommandTimedOutException
|
|
121
|
+
failure_line = $_
|
|
122
|
+
end
|
|
123
|
+
end
|
|
124
|
+
end
|
|
125
|
+
throw(:end_rc) if first_rc_try
|
|
126
|
+
end
|
|
127
|
+
end
|
|
128
|
+
# pause_val = Oats.data['execution']['ide']['pause_on_exit']
|
|
129
|
+
seconds = 999999
|
|
130
|
+
pause_val = $oats['selenium']['pause_on_exit']
|
|
131
|
+
if not pause_val.integer? or
|
|
132
|
+
pause_val <= 0
|
|
133
|
+
seconds = nil
|
|
134
|
+
elsif pause_val == 1
|
|
135
|
+
seconds = nil unless failure_line
|
|
136
|
+
elsif pause_val > 0
|
|
137
|
+
seconds = pause_val
|
|
138
|
+
end
|
|
139
|
+
raise(OatsError, "Result file is not readable: #{result_file}") unless File.readable?(result_file)
|
|
140
|
+
if seconds
|
|
141
|
+
# Need to quote browser path for cygwin because it may have spaces.
|
|
142
|
+
begin
|
|
143
|
+
timeout(seconds) do
|
|
144
|
+
# $stderr.puts "Paused because selenium:pause_on_exit is set to [#{pause_val}]"
|
|
145
|
+
# $stderr.puts "PLEASE HIT <ENTER> TO CONTINUE!"
|
|
146
|
+
successful = system( '"' +Oats.data['selenium']['ide']['result_browser'] + '" file://'+result_file)
|
|
147
|
+
$log.error "Error trying to open results file: #{$?}" \
|
|
148
|
+
unless successful or $? == 256
|
|
149
|
+
end
|
|
150
|
+
rescue Timeout::Error
|
|
151
|
+
end
|
|
152
|
+
end
|
|
153
|
+
TestData.pause_after_error = false
|
|
154
|
+
$log.info "Results are at: file://#{result_file}"
|
|
155
|
+
raise(OatsTestError, failure_line) if failure_line
|
|
156
|
+
end
|
|
157
|
+
|
|
158
|
+
# Helper method to replace HTML file contents based on oats and test data mappings.
|
|
159
|
+
def map_file_contents(oats_data, test_data, file_contents,key_path)
|
|
160
|
+
return unless test_data
|
|
161
|
+
# $log.debug key_path
|
|
162
|
+
if @suite_base_url_signin_type.nil?
|
|
163
|
+
@suite_base_url_signin_type = 'Campaign' if key_path == 'root:Campaign:SignIn'
|
|
164
|
+
@suite_base_url_signin_type = 'Admin' if key_path == 'root:Admin:SignIn'
|
|
165
|
+
# $log.debug "Base URL is set to #{baseUrl}"
|
|
166
|
+
end
|
|
167
|
+
test_data.each do |key,val|
|
|
168
|
+
repVal = oats_data[key]
|
|
169
|
+
next if val.nil? or repVal.nil?
|
|
170
|
+
if val.class == Hash
|
|
171
|
+
map_file_contents( repVal, val, file_contents,key_path + ':' + key)
|
|
172
|
+
else
|
|
173
|
+
file_contents.gsub!(val, repVal.to_s)
|
|
174
|
+
test_data[key] = repVal
|
|
175
|
+
end
|
|
176
|
+
end
|
|
177
|
+
end
|
|
178
|
+
|
|
179
|
+
# Updates HTML file contents based on current oats_data into test_dir_out
|
|
180
|
+
# Returns generated file name or nil if no new file is generated
|
|
181
|
+
def regenerate_html(file_in, dir_out, dir_in = dir_out, hash = nil)
|
|
182
|
+
basename = File.basename(file_in,'.*')
|
|
183
|
+
file_in_absolute = File.expand_path(file_in,dir_in) # get absolute path
|
|
184
|
+
unless File.exist?(file_in_absolute)
|
|
185
|
+
file_in_absolute = Dir.glob( File.join( $oats['execution']['dir_tests'],
|
|
186
|
+
'/**/', file_in.sub(/^(\.\.\/)*/, ''))).first
|
|
187
|
+
# file_in = file_in.sub!(/[^\/]*\//,'')
|
|
188
|
+
raise(OatsError,"Can not locate IDE test case file: [#{file_in}]") unless file_in_absolute
|
|
189
|
+
end
|
|
190
|
+
file_in_root = file_in_absolute.sub(/(.*)\..*$/,'\1')
|
|
191
|
+
yaml_in = file_in_root + '.yml'
|
|
192
|
+
file_out_root = File.join(dir_out, basename)
|
|
193
|
+
file_gen = file_out_root +'.gen.html'
|
|
194
|
+
yml_out = file_out_root +'.gen.yml'
|
|
195
|
+
new_base_name = basename
|
|
196
|
+
if File.exist?(file_gen)
|
|
197
|
+
new_base_name = File.basename(File.dirname(file_in)) + '_' + new_base_name
|
|
198
|
+
file_gen = File.join(dir_out, new_base_name ) +'.gen.html'
|
|
199
|
+
yml_out = File.join(dir_out, new_base_name ) +'.gen.yml'
|
|
200
|
+
end
|
|
201
|
+
if @suite_base_url_signin_type.nil? and @first_test_url.nil?
|
|
202
|
+
doc = open(file_in_absolute) { |f| Hpricot(f) }
|
|
203
|
+
link = doc.at("link[@rel='selenium.base']")
|
|
204
|
+
@first_test_url = link['href'] unless link.nil?
|
|
205
|
+
end
|
|
206
|
+
unless File.exist?(yaml_in)
|
|
207
|
+
return nil if file_in_root == file_out_root
|
|
208
|
+
$log.info "Copying [#{file_in_absolute}] to: #{file_gen}]"
|
|
209
|
+
FileUtils.cp(file_in_absolute, file_gen)
|
|
210
|
+
return basename + '.gen.html'
|
|
211
|
+
end
|
|
212
|
+
$log.debug "Regenerating [#{file_in_absolute}] into [#{file_gen}] based on [#{yaml_in}]"
|
|
213
|
+
file_contents = IO.read(file_in_absolute)
|
|
214
|
+
test_data = YAML.load_file(yaml_in)
|
|
215
|
+
map_file_contents(Oats.data, test_data, file_contents, 'root')
|
|
216
|
+
hash.each { |val, rep_val| file_contents.gsub!(val, rep_val) } if hash
|
|
217
|
+
if Oats.data['selenium']['browser_type'] =~ /iexplore/
|
|
218
|
+
file_contents.sub!(/(<\/IE-ONLY>.*-->)/,'<-- \1')
|
|
219
|
+
file_contents.sub!(/(<!--.*<IE-ONLY>)/,'\1 -->')
|
|
220
|
+
end
|
|
221
|
+
File.open( file_gen, 'w' ) { |out| out.print file_contents }
|
|
222
|
+
File.open( yml_out, 'w' ) { |out| YAML.dump( test_data, out ) }
|
|
223
|
+
basename + '.gen.html'
|
|
224
|
+
end
|
|
225
|
+
|
|
226
|
+
end
|
|
227
|
+
end
|
|
@@ -0,0 +1,67 @@
|
|
|
1
|
+
|
|
2
|
+
module Oats
|
|
3
|
+
|
|
4
|
+
# Process keyword driven testing
|
|
5
|
+
class Keywords
|
|
6
|
+
class << self
|
|
7
|
+
|
|
8
|
+
# Same as selenium.wait_and_type, but maps key via OatsX.locator, and uses
|
|
9
|
+
# OatsX.data[key] for value
|
|
10
|
+
def wait_and_type(key, *args)
|
|
11
|
+
selenium.wait_and_type(locator(key), oats_data[key], *args)
|
|
12
|
+
end
|
|
13
|
+
|
|
14
|
+
# Same as selenium.wait_for_element, but maps key via OatsX.locator first
|
|
15
|
+
def wait_and_click(key)
|
|
16
|
+
selenium.wait_and_click(locator(key))
|
|
17
|
+
end
|
|
18
|
+
|
|
19
|
+
# Same as selenium.wait_for_element, maps key via OatsX.locator first
|
|
20
|
+
def wait_and_text(key)
|
|
21
|
+
selenium.wait_for_element(locator(key)).text
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
# Returned the key or mappings if defined in the <class>::LOCATOR_MAP
|
|
25
|
+
def locator(key)
|
|
26
|
+
self::LOCATOR_MAP[key] || key
|
|
27
|
+
end
|
|
28
|
+
|
|
29
|
+
|
|
30
|
+
# Return data from XL spreadsheet entries via Oats.data('xl.data')
|
|
31
|
+
# OatsX.oats_data(key_string) or OatsX.oats_data[key_string]
|
|
32
|
+
def oats_data(cell = nil, clas = self)
|
|
33
|
+
xl_root = $oats[clas.name]
|
|
34
|
+
list = xl_root['list'] || Oats.data('keywords.list')
|
|
35
|
+
if list
|
|
36
|
+
xl_root_list = xl_root[list]
|
|
37
|
+
else
|
|
38
|
+
xl_root_list = xl_root
|
|
39
|
+
end
|
|
40
|
+
# Oats.assert list, "Oats.data keywords.list is not defined."
|
|
41
|
+
val = cell ? xl_root_list[cell] : xl_root_list
|
|
42
|
+
Oats.assert( val, "No keywords are defined for #{clas}" + (list ? ".#{list}" : '') ) if cell == 'keywords'
|
|
43
|
+
Marshal.load(Marshal.dump(val)) # Protect Oats.data from modification
|
|
44
|
+
end
|
|
45
|
+
|
|
46
|
+
# Handles keyword processing.
|
|
47
|
+
# Used by OATS framework to run XL driven test suites.
|
|
48
|
+
# Users can also call this from yaml_handlers.
|
|
49
|
+
def process
|
|
50
|
+
# Class name comes from Oats.data oats_keywords_cleass, or in the case of XL files from TestCase ID
|
|
51
|
+
class_name = Oats.data('keywords.class') || File.basename(File.dirname(File.dirname(Oats.test.id)))
|
|
52
|
+
begin
|
|
53
|
+
keywords_class = Kernel.const_get class_name
|
|
54
|
+
rescue NameError
|
|
55
|
+
raise OatsTestError, "Can not find class: " + class_name
|
|
56
|
+
end
|
|
57
|
+
oats_data('keywords',keywords_class).each do |action|
|
|
58
|
+
Oats.assert keywords_class.respond_to?(action),
|
|
59
|
+
"There is no method defined in #{class_name} to the handle keyword 'a#{action}'."
|
|
60
|
+
Oats.info "Performing " + action
|
|
61
|
+
keywords_class.send action
|
|
62
|
+
end
|
|
63
|
+
end
|
|
64
|
+
|
|
65
|
+
end
|
|
66
|
+
end
|
|
67
|
+
end
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
# Log4r can be configured using YAML. This example uses log4r_yaml.yaml
|
|
2
|
+
require 'log4r'
|
|
3
|
+
require 'log4r/yamlconfigurator'
|
|
4
|
+
# we use various outputters, so require them, otherwise config chokes
|
|
5
|
+
require 'log4r/outputter/datefileoutputter'
|
|
6
|
+
require 'log4r/outputter/emailoutputter'
|
|
7
|
+
include Log4r
|
|
8
|
+
|
|
9
|
+
cfg = YamlConfigurator # shorthand
|
|
10
|
+
cfg['HOME'] = ENV['HOME'] # the only parameter in the YAML, our HOME directory
|
|
11
|
+
|
|
12
|
+
# load the YAML file with this
|
|
13
|
+
cfg.load_yaml_file('log4r.yaml')
|
|
14
|
+
|
data/lib/oats/mysql.rb
ADDED
|
@@ -0,0 +1,97 @@
|
|
|
1
|
+
#require 'mysql' # http://www.tmtm.org/en/ruby/mysql
|
|
2
|
+
require "tempfile"
|
|
3
|
+
require 'oats/oats_exceptions'
|
|
4
|
+
|
|
5
|
+
module Oats
|
|
6
|
+
class OatsMysqlError < OatsTestError ; end
|
|
7
|
+
class OatsMysqlMissingInput < OatsMysqlError ; end
|
|
8
|
+
class OatsMysqlNoConnect < OatsMysqlError ; end
|
|
9
|
+
# Oats.mysql creates an instance of this class to interact with MySQL DBs
|
|
10
|
+
class Mysql
|
|
11
|
+
|
|
12
|
+
# See Oats.mysql for more accurate/detailed documentation
|
|
13
|
+
# sql_input:: Path to a file.sql to execute
|
|
14
|
+
# connect:: Override for Oats.data sql:connect
|
|
15
|
+
# returns array of rows of results. Each row is an array of columns.
|
|
16
|
+
def run(sql_input, connect = nil, sql_out_name = nil)
|
|
17
|
+
raise OatsMysqlNoConnect, "Oats.data sql:connect is null" unless Oats.data['sql']['connect']
|
|
18
|
+
test = TestData.current_test
|
|
19
|
+
unless /\s/ =~ sql_input # If there is space in name, assume it is not a file
|
|
20
|
+
abs_path = File.expand_path(sql_input,test.path)
|
|
21
|
+
end
|
|
22
|
+
if File.exist?(abs_path)
|
|
23
|
+
mysql_input_file = OatsData.regenerate_file(abs_path)
|
|
24
|
+
mysql_input_file = abs_path unless mysql_input_file
|
|
25
|
+
name = File.basename(sql_input,'.*')
|
|
26
|
+
sql_input = IO.read(mysql_input_file)
|
|
27
|
+
sql_input = nil if sql_input.length > 200
|
|
28
|
+
else
|
|
29
|
+
tf = Tempfile.new("OatsMysqlInput")
|
|
30
|
+
tf.puts(sql_input)
|
|
31
|
+
tf.close
|
|
32
|
+
mysql_input_file = Util.expand_path(tf.path)
|
|
33
|
+
name = 'mysql_default'
|
|
34
|
+
end
|
|
35
|
+
sql_out_name = name + '.txt' unless sql_out_name
|
|
36
|
+
sql_out = File.join(test.result, sql_out_name) if sql_out_name
|
|
37
|
+
err_file = sql_out + '.err'
|
|
38
|
+
command = (ENV['OS'] != 'Darwin' ? 'mysql' : '/usr/local/mysql/bin/mysql') +
|
|
39
|
+
" #{parameters(connect)} < #{mysql_input_file} > #{sql_out} 2> #{err_file}"
|
|
40
|
+
# $log.debug "Executing: #{command}"
|
|
41
|
+
$log.info "SQL: #{sql_input}" if sql_input
|
|
42
|
+
FileUtils.mkdir_p(test.out)
|
|
43
|
+
ok = system(command)
|
|
44
|
+
$log.error("MySQL failed with return code: #{$?}") unless ok
|
|
45
|
+
FileUtils.rm_f(err_file) unless File.size?(err_file)
|
|
46
|
+
FileUtils.rm_f(sql_out) unless File.size?(sql_out)
|
|
47
|
+
if File.exist?(err_file)
|
|
48
|
+
errors = IO.readlines(err_file)
|
|
49
|
+
errors.size == 1 or errors[0...-1].each {|line| $log.error line.chomp}
|
|
50
|
+
raise(OatsMysqlError,errors.last.chomp) unless errors.empty?
|
|
51
|
+
end
|
|
52
|
+
rows = IO.readlines(sql_out) if File.exist?(sql_out)
|
|
53
|
+
return [] unless rows
|
|
54
|
+
rows.shift
|
|
55
|
+
if rows[1] =~ /\t/
|
|
56
|
+
return rows.collect{|t| t.chomp.split(/\t/) }
|
|
57
|
+
else
|
|
58
|
+
return rows.collect{|t| t.chomp }
|
|
59
|
+
end
|
|
60
|
+
end
|
|
61
|
+
|
|
62
|
+
|
|
63
|
+
def processlist
|
|
64
|
+
raise OatsMysqlNoConnect, "Oats.data sql:connect is null" unless Oats.data['sql']['connect']
|
|
65
|
+
sql_out = 'mysql_processlist.txt'
|
|
66
|
+
command = "mysqladmin #{parameters('connect',true)} processlist > #{sql_out}"
|
|
67
|
+
success = system(command)
|
|
68
|
+
$log.error("MySQL failed with return code: #{$?}") unless success
|
|
69
|
+
FileUtils.rm_f(sql_out) unless File.size?(sql_out)
|
|
70
|
+
end
|
|
71
|
+
|
|
72
|
+
private
|
|
73
|
+
|
|
74
|
+
def parameters(connect,proc_list=false)
|
|
75
|
+
sql = Oats.data['sql']
|
|
76
|
+
connect ||= sql['connect']
|
|
77
|
+
conn = sql[connect]
|
|
78
|
+
user = conn['user']
|
|
79
|
+
err "Oats MySQL requires input for sql:user" unless user
|
|
80
|
+
password = conn['password']
|
|
81
|
+
err "Oats MySQL requires a string input for sql:password" unless password
|
|
82
|
+
password = " -p#{password}" unless password == ""
|
|
83
|
+
host = conn['host']
|
|
84
|
+
err "Oats MySQL requires input for sql:host" unless host
|
|
85
|
+
params = "-u#{user}#{password} -h#{host}"
|
|
86
|
+
return params if proc_list
|
|
87
|
+
db = conn['database']
|
|
88
|
+
err "Oats MySQL requires input for sql:db" unless db
|
|
89
|
+
"#{params} -D#{db}"
|
|
90
|
+
end
|
|
91
|
+
|
|
92
|
+
def err(inp)
|
|
93
|
+
raise(OatsMysqlMissingInput,inp)
|
|
94
|
+
end
|
|
95
|
+
|
|
96
|
+
end
|
|
97
|
+
end
|