testability-driver 1.0.3 → 1.0.4
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/lib/tdriver-devtools/behaviour/xml/rdoc_behaviour_xml_generator.rb +2 -2
- data/lib/tdriver-devtools/tdriver-devtools.rb +1 -1
- data/lib/tdriver-devtools/tests/feature_tests/lib/custom_rdoc_generator.rb +3 -3
- data/lib/tdriver/base/behaviour/behaviours/object_behaviour_composition.rb +6 -1
- data/lib/tdriver/base/behaviour/behaviours/object_behaviour_description.rb +5 -3
- data/lib/tdriver/base/behaviour/behaviours/object_composition.rb +1 -1
- data/lib/tdriver/base/behaviour/factory.rb +225 -225
- data/lib/tdriver/base/errors.rb +1 -1
- data/lib/tdriver/base/state_object.rb +227 -179
- data/lib/tdriver/base/sut/controller.rb +2 -2
- data/lib/tdriver/base/sut/factory.rb +190 -182
- data/lib/tdriver/base/sut/generic/behaviours/application.rb +69 -25
- data/lib/tdriver/base/sut/generic/behaviours/controller.rb +1 -1
- data/lib/tdriver/base/sut/generic/behaviours/find.rb +4 -4
- data/lib/tdriver/base/sut/generic/behaviours/flash_behaviour.rb +3 -3
- data/lib/tdriver/base/sut/generic/behaviours/sut.rb +350 -165
- data/lib/tdriver/base/sut/generic/behaviours/switchbox_behaviour.rb +9 -9
- data/lib/tdriver/base/sut/generic/behaviours/verification.rb +191 -103
- data/lib/tdriver/base/sut/generic/commands/application.rb +1 -1
- data/lib/tdriver/base/sut/generic/commands/key_sequence.rb +1 -1
- data/lib/tdriver/base/sut/generic/commands/screen_capture.rb +1 -1
- data/lib/tdriver/base/sut/generic/plugin.rb +1 -1
- data/lib/tdriver/base/sut/sut.rb +5 -1
- data/lib/tdriver/base/test_object/abstract.rb +136 -151
- data/lib/tdriver/base/test_object/adapter.rb +293 -82
- data/lib/tdriver/base/test_object/behaviours/syncronization.rb +20 -17
- data/lib/tdriver/base/test_object/behaviours/test_object.rb +159 -532
- data/lib/tdriver/base/test_object/cache.rb +1 -1
- data/lib/tdriver/base/test_object/factory.rb +254 -605
- data/lib/tdriver/base/test_object/identificator.rb +1 -1
- data/lib/tdriver/base/test_object/loader.rb +1 -1
- data/lib/tdriver/base/test_object/verification.rb +17 -17
- data/lib/tdriver/loader.rb +20 -9
- data/lib/tdriver/report/report.rb +5 -0
- data/lib/tdriver/report/report_creator.rb +2 -2
- data/lib/tdriver/report/report_cucumber_listener.rb +4 -4
- data/lib/tdriver/report/report_cucumber_reporter.rb +4 -4
- data/lib/tdriver/report/report_execution_statistics.rb +22 -22
- data/lib/tdriver/report/report_grouping.rb +2 -2
- data/lib/tdriver/report/report_javascript.rb +11 -4
- data/lib/tdriver/report/report_test_case_run.rb +2 -2
- data/lib/tdriver/report/report_test_run.rb +5 -5
- data/lib/tdriver/report/report_test_unit.rb +74 -26
- data/lib/tdriver/report/report_writer.rb +70 -13
- data/lib/tdriver/tdriver.rb +17 -8
- data/lib/tdriver/util/common/array.rb +1 -1
- data/lib/tdriver/util/common/crc16.rb +1 -1
- data/lib/tdriver/util/common/environment.rb +1 -1
- data/lib/tdriver/util/common/file.rb +18 -9
- data/lib/tdriver/util/common/gem.rb +1 -1
- data/lib/tdriver/util/common/hash.rb +21 -0
- data/lib/tdriver/util/common/kernel.rb +1 -1
- data/lib/tdriver/util/common/loader.rb +5 -2
- data/lib/tdriver/util/common/numeric.rb +54 -3
- data/lib/tdriver/util/common/retryable.rb +30 -12
- data/lib/tdriver/util/common/stackable.rb +185 -0
- data/lib/tdriver/util/common/string.rb +21 -5
- data/lib/tdriver/util/{dbaccess/dbaccess.rb → database/access.rb} +4 -1
- data/lib/tdriver/util/{dbaccess/dbconnection.rb → database/connection.rb} +3 -0
- data/lib/tdriver/util/{dbaccess → database}/error.rb +0 -1
- data/lib/tdriver/util/{dbaccess → database}/loader.rb +5 -6
- data/lib/tdriver/util/{dynamic_attribute_filter.rb → filters/dynamic_attributes.rb} +1 -1
- data/lib/tdriver/util/hooking/hooking.rb +477 -0
- data/lib/tdriver/util/loader.rb +35 -29
- data/lib/tdriver/util/localisation/error.rb +0 -1
- data/lib/tdriver/util/localisation/loader.rb +1 -4
- data/lib/tdriver/util/localisation/localisation.rb +30 -27
- data/lib/tdriver/util/{common.rb → logger/loader.rb} +2 -4
- data/lib/tdriver/util/logger/logger.rb +574 -0
- data/lib/tdriver/util/operator_data/loader.rb +4 -3
- data/lib/tdriver/util/operator_data/operator_data.rb +5 -5
- data/lib/tdriver/util/parameter/parameter.rb +7 -1
- data/lib/tdriver/util/parameter/parameter_hash.rb +1 -1
- data/lib/tdriver/util/parameter/parameter_template.rb +1 -1
- data/lib/tdriver/util/parameter/parameter_user_api.rb +28 -20
- data/lib/tdriver/util/parameter/parameter_xml.rb +1 -1
- data/lib/tdriver/util/plugin/abstract.rb +1 -1
- data/lib/tdriver/util/plugin/service.rb +1 -1
- data/lib/tdriver/util/{localisation.rb → recorder/loader.rb} +4 -3
- data/lib/tdriver/util/recorder/recorder.rb +66 -0
- data/lib/tdriver/util/recorder/scripter.rb +258 -0
- data/lib/tdriver/util/{stats.rb → statistics/statistics.rb} +7 -8
- data/lib/tdriver/util/user_data/error.rb +0 -1
- data/lib/tdriver/util/user_data/loader.rb +1 -2
- data/lib/tdriver/util/user_data/user_data.rb +6 -6
- data/lib/tdriver/util/video/camera.rb +67 -0
- data/lib/tdriver/util/video/camera_linux.rb +139 -0
- data/lib/tdriver/util/video/camera_windows.rb +174 -0
- data/lib/tdriver/util/video/loader.rb +31 -0
- data/lib/tdriver/util/video/video_utils.rb +139 -0
- data/lib/tdriver/util/xml/abstraction.rb +56 -5
- data/lib/tdriver/util/xml/builder.rb +2 -5
- data/lib/tdriver/util/{parameter.rb → xml/comment.rb} +10 -2
- data/lib/tdriver/util/xml/loader.rb +32 -22
- data/lib/tdriver/util/xml/nil_node.rb +2 -2
- data/lib/tdriver/util/xml/parsers/loader.rb +0 -1
- data/lib/tdriver/util/xml/parsers/nokogiri/abstraction.rb +18 -44
- data/lib/tdriver/util/xml/parsers/nokogiri/attribute.rb +9 -13
- data/lib/tdriver/util/xml/parsers/nokogiri/builder.rb +9 -3
- data/lib/tdriver/util/xml/parsers/nokogiri/comment.rb +39 -0
- data/lib/tdriver/util/xml/parsers/nokogiri/document.rb +6 -11
- data/lib/tdriver/util/xml/parsers/nokogiri/element.rb +2 -122
- data/lib/tdriver/util/xml/parsers/nokogiri/loader.rb +26 -16
- data/lib/tdriver/util/xml/parsers/nokogiri/node.rb +203 -0
- data/lib/tdriver/util/xml/parsers/nokogiri/nodeset.rb +1 -2
- data/lib/tdriver/util/xml/parsers/nokogiri/text.rb +2 -20
- data/lib/tdriver/util/xml/xml.rb +52 -20
- data/lib/tdriver/verify/verify.rb +238 -81
- data/xml/behaviours/generic.xml +12 -10
- metadata +156 -180
- data/lib/tdriver/base/test_object/factory_new.rb +0 -202
- data/lib/tdriver/util/hooking.rb +0 -434
- data/lib/tdriver/util/logger.rb +0 -506
- data/lib/tdriver/util/recorder.rb +0 -297
- data/lib/tdriver/util/video_utils.rb +0 -384
- data/lib/tdriver/util/xml/nil_element.rb +0 -89
|
@@ -27,96 +27,89 @@ module TDriver
|
|
|
27
27
|
private
|
|
28
28
|
|
|
29
29
|
# special cases: allow partial match when value of type and attribute name matches
|
|
30
|
-
@@partial_match_allowed = [ 'list_item', 'text' ], ['application', 'fullname' ]
|
|
30
|
+
@@partial_match_allowed = [ 'list_item', 'text' ], [ 'application', 'fullname' ]
|
|
31
31
|
|
|
32
|
+
# TODO: document me
|
|
32
33
|
def xpath_attributes( attributes, element_attributes, object_type )
|
|
33
|
-
|
|
34
|
+
|
|
35
|
+
# collect attributes
|
|
34
36
|
attributes = attributes.collect{ | key, values |
|
|
35
37
|
|
|
36
|
-
values
|
|
38
|
+
# allow multiple values options for attribute, e.g. object which 'text' attribute value is either '1' or '2'
|
|
39
|
+
( values.kind_of?( Array ) ? values : [ values ] ).collect{ | value |
|
|
37
40
|
|
|
38
41
|
# concatenate string if it contains single and double quotes, otherwise return as is
|
|
39
42
|
value = xpath_literal_string( value )
|
|
40
43
|
|
|
41
44
|
if @@partial_match_allowed.include?( [ object_type, key ] )
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
else
|
|
47
|
-
|
|
48
|
-
# exact match required
|
|
49
|
-
value = "=#{ value }"
|
|
50
|
-
|
|
51
|
-
end
|
|
52
|
-
|
|
53
|
-
if element_attributes
|
|
54
|
-
|
|
55
|
-
prefix = "@#{key}#{value} or "
|
|
45
|
+
|
|
46
|
+
prefix_value = "[contains(.,#{ value })]"
|
|
47
|
+
attribute_value = "contains(value/text(),#{ value })"
|
|
56
48
|
|
|
57
49
|
else
|
|
58
50
|
|
|
59
|
-
|
|
51
|
+
prefix_value = "=#{ value }"
|
|
52
|
+
attribute_value = "value/text()=#{ value }"
|
|
60
53
|
|
|
61
54
|
end
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
55
|
+
|
|
56
|
+
# construct xpath
|
|
57
|
+
"(#{ element_attributes ? "@#{ key }#{ prefix_value } or " : "" }attributes/attribute[translate(@name,'ABCDEFGHIJKLMNOPQRSTUVWXYZ','abcdefghijklmnopqrstuvwxyz')='#{ key }' and #{ attribute_value }])"
|
|
58
|
+
|
|
59
|
+
}.join( ' or ' ) # join attribute alternative values
|
|
66
60
|
|
|
67
|
-
}
|
|
61
|
+
}.join( ' and ' ) # join all required attributes
|
|
62
|
+
|
|
63
|
+
# return created xpath or nil if no attributes given
|
|
64
|
+
if attributes.empty?
|
|
68
65
|
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
if result.empty?
|
|
66
|
+
# no attributes given
|
|
67
|
+
nil
|
|
72
68
|
|
|
73
|
-
result = nil
|
|
74
|
-
|
|
75
69
|
else
|
|
76
|
-
|
|
77
|
-
|
|
70
|
+
|
|
71
|
+
# return result
|
|
72
|
+
attributes
|
|
78
73
|
|
|
79
74
|
end
|
|
80
75
|
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
end
|
|
76
|
+
end # xpath_attributes
|
|
84
77
|
|
|
85
|
-
|
|
86
|
-
end
|
|
78
|
+
end # static
|
|
87
79
|
|
|
88
80
|
# TODO: document me
|
|
89
81
|
def self.xpath_to_object( rules, find_all_children )
|
|
90
82
|
|
|
91
83
|
# convert hash keys to downcased string
|
|
92
|
-
rules = Hash[ rules.collect{ | key, value | [ key.to_s.downcase, value ] } ]
|
|
84
|
+
rules = Hash[ rules.collect{ | key, value | [ key.to_s.downcase, value.to_s ] } ]
|
|
93
85
|
|
|
94
|
-
|
|
86
|
+
# xpath container array
|
|
87
|
+
test_object_xpath_array = []
|
|
95
88
|
|
|
96
89
|
# store and remove object element attributes from hash
|
|
97
|
-
object_element_attributes = rules.delete_keys!(
|
|
90
|
+
object_element_attributes = rules.delete_keys!( 'name', 'type', 'parent', 'id' )
|
|
98
91
|
|
|
99
|
-
# TODO: change "any" to "*"
|
|
100
92
|
# children method may request test objects of any type
|
|
101
|
-
if object_element_attributes[
|
|
93
|
+
if object_element_attributes[ 'type' ] == '*'
|
|
102
94
|
|
|
103
95
|
# test object with any name, type, parent and id is allowed
|
|
104
|
-
|
|
96
|
+
test_object_xpath_array << '@*'
|
|
105
97
|
|
|
106
98
|
else
|
|
107
99
|
|
|
108
100
|
# required attributes
|
|
109
|
-
|
|
101
|
+
test_object_xpath_array << xpath_attributes( object_element_attributes, true, object_element_attributes[ 'type' ] )
|
|
110
102
|
|
|
111
103
|
end
|
|
112
104
|
|
|
113
105
|
# additional attributes, eg. :text, :x, :y etc.
|
|
114
|
-
|
|
106
|
+
test_object_xpath_array << xpath_attributes( rules, false, object_element_attributes[ 'type' ] )
|
|
115
107
|
|
|
116
108
|
# join required and additional attribute strings
|
|
117
|
-
|
|
109
|
+
test_object_xpath_string = test_object_xpath_array.compact.join( ' and ' )
|
|
118
110
|
|
|
119
|
-
|
|
111
|
+
# return any child element under current node or only immediate child element
|
|
112
|
+
find_all_children ? "*//object[#{ test_object_xpath_string }]" : "objects[1]/object[#{ test_object_xpath_string }]"
|
|
120
113
|
|
|
121
114
|
end
|
|
122
115
|
|
|
@@ -183,54 +176,70 @@ module TDriver
|
|
|
183
176
|
# TODO: document me
|
|
184
177
|
def self.get_objects( source_data, rules, find_all_children )
|
|
185
178
|
|
|
186
|
-
rule = xpath_to_object( rules, find_all_children )
|
|
187
|
-
|
|
188
179
|
[
|
|
189
180
|
# perform xpath to source xml data
|
|
190
|
-
source_data.xpath( rule ),
|
|
181
|
+
source_data.xpath( rule = xpath_to_object( rules, find_all_children ) ),
|
|
182
|
+
|
|
183
|
+
# return also created xpath
|
|
191
184
|
rule
|
|
192
185
|
]
|
|
193
186
|
|
|
194
187
|
end
|
|
195
188
|
|
|
189
|
+
# TODO: document me
|
|
196
190
|
def self.test_object_hash( object_id, object_type, object_name )
|
|
197
191
|
|
|
192
|
+
# calculate test object hash
|
|
198
193
|
( ( ( 17 * 37 + object_id ) * 37 + object_type.hash ) * 37 + object_name.hash )
|
|
199
194
|
|
|
200
195
|
end
|
|
201
196
|
|
|
202
197
|
# Sort XML nodeset of test objects with layout direction
|
|
203
|
-
def self.sort_elements( nodeset, layout_direction =
|
|
198
|
+
def self.sort_elements( nodeset, layout_direction = 'LeftToRight' )
|
|
204
199
|
|
|
205
|
-
attribute_pattern =
|
|
200
|
+
attribute_pattern = './attributes/attribute[@name="%s"]/value/text()'
|
|
206
201
|
|
|
207
202
|
# collect only nodes that has x_absolute and y_absolute attributes
|
|
208
203
|
nodeset.collect!{ | node |
|
|
209
204
|
|
|
210
|
-
|
|
211
|
-
|
|
205
|
+
if node.at_xpath( attribute_pattern % 'x_absolute' ).nil? || node.at_xpath( attribute_pattern % 'y_absolute' ).nil?
|
|
206
|
+
|
|
207
|
+
#warn("Warning: Unable to sort object set due to object type of #{ node.attribute( 'type' ).inspect } does not have \"x_absolute\" or \"y_absolute\" attribute")
|
|
208
|
+
|
|
209
|
+
return nodeset
|
|
210
|
+
|
|
211
|
+
else
|
|
212
|
+
|
|
213
|
+
node
|
|
214
|
+
|
|
215
|
+
end
|
|
212
216
|
|
|
213
217
|
}.compact!.sort!{ | element_a, element_b |
|
|
214
218
|
|
|
219
|
+
# retrieve element a's attributes x and y
|
|
215
220
|
element_a_x = element_a.at_xpath( attribute_pattern % 'x_absolute' ).content.to_i
|
|
216
221
|
element_a_y = element_a.at_xpath( attribute_pattern % 'y_absolute' ).content.to_i
|
|
217
222
|
|
|
223
|
+
# retrieve element b's attributes x and y
|
|
218
224
|
element_b_x = element_b.at_xpath( attribute_pattern % 'x_absolute' ).content.to_i
|
|
219
225
|
element_b_y = element_b.at_xpath( attribute_pattern % 'y_absolute' ).content.to_i
|
|
220
226
|
|
|
221
227
|
case layout_direction
|
|
222
228
|
|
|
223
|
-
when
|
|
229
|
+
when 'LeftToRight'
|
|
224
230
|
|
|
231
|
+
# compare elements
|
|
225
232
|
( element_a_y == element_b_y ) ? ( element_a_x <=> element_b_x ) : ( element_a_y <=> element_b_y )
|
|
226
233
|
|
|
227
|
-
when
|
|
234
|
+
when 'RightToLeft'
|
|
228
235
|
|
|
236
|
+
# compare elements
|
|
229
237
|
( element_a_y == element_b_y ) ? ( element_b_x <=> element_a_x ) : ( element_a_y <=> element_b_y )
|
|
230
238
|
|
|
231
239
|
else
|
|
232
240
|
|
|
233
|
-
|
|
241
|
+
# raise exception if layout direction it not supported
|
|
242
|
+
Kernel::raise ArgumentError, "Unsupported layout direction #{ layout_direction.inspect }"
|
|
234
243
|
|
|
235
244
|
end
|
|
236
245
|
|
|
@@ -257,24 +266,32 @@ module TDriver
|
|
|
257
266
|
end
|
|
258
267
|
|
|
259
268
|
# TODO: document me
|
|
260
|
-
def self.test_object_element_attribute( source_data,
|
|
269
|
+
def self.test_object_element_attribute( source_data, attribute_name, *default, &block )
|
|
261
270
|
|
|
262
|
-
result = source_data.attribute(
|
|
271
|
+
result = source_data.attribute( attribute_name )
|
|
263
272
|
|
|
273
|
+
# if no attribute found call optional code block or raise exception
|
|
264
274
|
unless result
|
|
265
275
|
|
|
266
276
|
if block_given?
|
|
267
|
-
|
|
268
|
-
|
|
277
|
+
|
|
278
|
+
# pass return value of block as result
|
|
279
|
+
yield( attribute_name )
|
|
269
280
|
|
|
270
281
|
else
|
|
271
282
|
|
|
272
|
-
# raise exception if no
|
|
273
|
-
|
|
283
|
+
# raise exception if no default value given
|
|
284
|
+
if default.empty?
|
|
285
|
+
|
|
286
|
+
# raise exception if no such attribute found
|
|
287
|
+
Kernel::raise MobyBase::AttributeNotFoundError, "Could not find test object element attribute #{ attribute_name.inspect }"
|
|
288
|
+
|
|
289
|
+
else
|
|
274
290
|
|
|
275
|
-
|
|
276
|
-
|
|
277
|
-
|
|
291
|
+
# pass default value as result
|
|
292
|
+
default.first
|
|
293
|
+
|
|
294
|
+
end
|
|
278
295
|
|
|
279
296
|
end
|
|
280
297
|
|
|
@@ -287,14 +304,14 @@ module TDriver
|
|
|
287
304
|
end
|
|
288
305
|
|
|
289
306
|
# TODO: document me
|
|
290
|
-
def self.test_object_attribute( source_data, attribute_name, &block )
|
|
307
|
+
def self.test_object_attribute( source_data, attribute_name, *default, &block )
|
|
291
308
|
|
|
292
309
|
# TODO: consider using at_xpath and adding /value/text() to query string; however "downside" is that if multiple matches found only first value will be returned as result
|
|
293
310
|
|
|
294
311
|
# retrieve attribute(s) from xml
|
|
295
312
|
nodeset = source_data.xpath(
|
|
296
313
|
|
|
297
|
-
"attributes/attribute[translate(@name,'ABCDEFGHIJKLMNOPQRSTUVWXYZ','abcdefghijklmnopqrstuvwxyz')='#{ attribute_name.downcase }']"
|
|
314
|
+
"attributes/attribute[translate(@name,'ABCDEFGHIJKLMNOPQRSTUVWXYZ','abcdefghijklmnopqrstuvwxyz')='#{ attribute_name.downcase }']"
|
|
298
315
|
|
|
299
316
|
)
|
|
300
317
|
|
|
@@ -304,20 +321,26 @@ module TDriver
|
|
|
304
321
|
if block_given?
|
|
305
322
|
|
|
306
323
|
# pass return value of block as result
|
|
307
|
-
yield
|
|
324
|
+
yield( attribute_name )
|
|
308
325
|
|
|
309
326
|
else
|
|
310
327
|
|
|
311
|
-
# raise exception if no
|
|
312
|
-
|
|
328
|
+
# raise exception if no default value given
|
|
329
|
+
if default.empty?
|
|
313
330
|
|
|
314
|
-
|
|
315
|
-
|
|
316
|
-
|
|
331
|
+
# raise exception if no such attribute found
|
|
332
|
+
Kernel::raise MobyBase::AttributeNotFoundError, "Could not find attribute #{ attribute_name.inspect }" # for test object of type #{ type.to_s }"
|
|
333
|
+
|
|
334
|
+
else
|
|
317
335
|
|
|
318
|
-
|
|
336
|
+
# pass default value as result
|
|
337
|
+
default.first
|
|
338
|
+
|
|
339
|
+
end
|
|
340
|
+
|
|
341
|
+
end # block_given?
|
|
319
342
|
|
|
320
|
-
else
|
|
343
|
+
else # not nodeset.empty?
|
|
321
344
|
|
|
322
345
|
# attribute(s) found
|
|
323
346
|
# Need to disable this for now
|
|
@@ -331,17 +354,33 @@ module TDriver
|
|
|
331
354
|
end
|
|
332
355
|
|
|
333
356
|
# TODO: document me
|
|
334
|
-
def self.test_object_attributes( source_data )
|
|
335
|
-
|
|
357
|
+
def self.test_object_attributes( source_data, inclusive_filter = [] )
|
|
358
|
+
|
|
359
|
+
# convert all keys to lowercase
|
|
360
|
+
inclusive_filter.collect!{ | key | key.to_s.downcase } unless inclusive_filter.empty?
|
|
361
|
+
|
|
336
362
|
# return hash of test object attributes
|
|
337
363
|
Hash[
|
|
338
364
|
|
|
339
365
|
# iterate each attribute and collect name and value
|
|
340
|
-
source_data.xpath( 'attributes/attribute' ).collect{ |
|
|
366
|
+
source_data.xpath( 'attributes/attribute/value' ).collect{ | value |
|
|
341
367
|
|
|
342
|
-
|
|
368
|
+
# retrieve attribute name
|
|
369
|
+
name = value.parent.attribute('name').to_s
|
|
343
370
|
|
|
344
|
-
|
|
371
|
+
# collect attribute elements name and content
|
|
372
|
+
unless inclusive_filter.empty?
|
|
373
|
+
|
|
374
|
+
[ name, value.content ] if inclusive_filter.include?( name.downcase )
|
|
375
|
+
|
|
376
|
+
else
|
|
377
|
+
|
|
378
|
+
# pass the attribute pair - no filtering done
|
|
379
|
+
[ name, value.content ]
|
|
380
|
+
|
|
381
|
+
end
|
|
382
|
+
|
|
383
|
+
}
|
|
345
384
|
|
|
346
385
|
]
|
|
347
386
|
|
|
@@ -372,7 +411,8 @@ module TDriver
|
|
|
372
411
|
# iterate through each child object type attribute and create accessor method
|
|
373
412
|
source_data.xpath( 'objects/object/@type' ).each{ | object_type |
|
|
374
413
|
|
|
375
|
-
|
|
414
|
+
# skip if object type value is nil or empty due to child accessor cannot be created
|
|
415
|
+
next if object_type.nil? || object_type.to_s.empty?
|
|
376
416
|
|
|
377
417
|
# convert attribute node value to string
|
|
378
418
|
object_type = object_type.content
|
|
@@ -383,7 +423,7 @@ module TDriver
|
|
|
383
423
|
# create child accessor method to test object unless already exists
|
|
384
424
|
test_object.instance_eval(
|
|
385
425
|
|
|
386
|
-
"def #{object_type}(rules={}); raise TypeError,'parameter <rules> should be hash' unless rules.kind_of?(Hash); rules[:type]=:#{object_type}; child(rules); end;"
|
|
426
|
+
"def #{ object_type }( rules = {} ); raise TypeError,'parameter <rules> should be hash' unless rules.kind_of?( Hash ); rules[ :type ]=:#{ object_type }; child( rules ); end;"
|
|
387
427
|
|
|
388
428
|
) unless object_type.empty?
|
|
389
429
|
|
|
@@ -391,8 +431,179 @@ module TDriver
|
|
|
391
431
|
|
|
392
432
|
end
|
|
393
433
|
|
|
434
|
+
# TODO: document me
|
|
435
|
+
def self.state_object_xml( source_data, id )
|
|
436
|
+
|
|
437
|
+
# collect each object from source xml
|
|
438
|
+
objects = source_data.xpath( 'tasInfo/object' ).collect{ | element | element.to_s }.join
|
|
439
|
+
|
|
440
|
+
# return xml root element
|
|
441
|
+
MobyUtil::XML.parse_string(
|
|
442
|
+
"<sut name='sut' type='sut' id='#{ id }'><objects>#{ objects }</objects></sut>"
|
|
443
|
+
).root
|
|
444
|
+
|
|
445
|
+
end
|
|
446
|
+
|
|
447
|
+
def self.retrieve_parent_application( xml_source )
|
|
448
|
+
|
|
449
|
+
xml_source_iterator = xml_source.clone
|
|
450
|
+
|
|
451
|
+
while xml_source_iterator.kind_of?( MobyUtil::XML::Element )
|
|
452
|
+
|
|
453
|
+
if ( test_object_element_attribute( xml_source_iterator, 'type' ) == 'application' )
|
|
454
|
+
|
|
455
|
+
return xml_source_iterator
|
|
456
|
+
|
|
457
|
+
end
|
|
458
|
+
|
|
459
|
+
if xml_source_iterator.kind_of?( MobyUtil::XML::Element )
|
|
460
|
+
|
|
461
|
+
xml_source_iterator = xml_source_iterator.parent.parent
|
|
462
|
+
|
|
463
|
+
else
|
|
464
|
+
|
|
465
|
+
# not found from xml tree
|
|
466
|
+
break
|
|
467
|
+
|
|
468
|
+
end
|
|
469
|
+
|
|
470
|
+
end
|
|
471
|
+
|
|
472
|
+
#warn("warning: unable to retrieve parent application")
|
|
473
|
+
|
|
474
|
+
raise MobyBase::TestObjectNotFoundError, "Unable to retrieve parent application"
|
|
475
|
+
|
|
476
|
+
# return application object or nil if no parent found
|
|
477
|
+
# Does is make sense to return nil - shouldn't all test objects belong to an application? Maybe throw exception if application not found
|
|
478
|
+
|
|
479
|
+
#nil
|
|
480
|
+
|
|
481
|
+
#return @sut.child( :type => 'application' ) rescue nil
|
|
482
|
+
|
|
483
|
+
end
|
|
484
|
+
|
|
485
|
+
# TODO: document me
|
|
486
|
+
def self.get_xml_element_for_test_object( test_object )
|
|
487
|
+
|
|
488
|
+
# retrieve nodeset from sut xml_data
|
|
489
|
+
nodeset = test_object.instance_variable_get( :@sut ).xml_data.xpath( test_object.instance_variable_get( :@x_path ) )
|
|
490
|
+
|
|
491
|
+
# raise exception if no test objects found
|
|
492
|
+
Kernel::raise MobyBase::TestObjectNotFoundError if nodeset.empty?
|
|
493
|
+
|
|
494
|
+
# return first test object from the nodeset
|
|
495
|
+
nodeset.first
|
|
496
|
+
|
|
497
|
+
end
|
|
498
|
+
|
|
499
|
+
# TODO: document me
|
|
500
|
+
def self.get_test_object_identifiers( xml_source, test_object = nil )
|
|
501
|
+
|
|
502
|
+
# retrieve parent xpath if test_object given
|
|
503
|
+
parent_xpath = test_object ? test_object.instance_variable_get( :@parent ).x_path : ""
|
|
504
|
+
|
|
505
|
+
# retrieve type attribute
|
|
506
|
+
type = xml_source.attribute( 'type' )
|
|
507
|
+
|
|
508
|
+
# retrieve id attribute
|
|
509
|
+
id = xml_source.attribute( 'id' )
|
|
510
|
+
|
|
511
|
+
# retrieve env attribute
|
|
512
|
+
env = xml_source.attribute( 'env' )
|
|
513
|
+
|
|
514
|
+
# retrieve test object element attributes and return array containting xpath to test object, name, type and id elements
|
|
515
|
+
[
|
|
516
|
+
# x_path to test object
|
|
517
|
+
test_object ? "#{ parent_xpath }/*//object[@type='#{ type }' and @id='#{ id }']" : nil,
|
|
518
|
+
|
|
519
|
+
# test object name
|
|
520
|
+
xml_source.attribute( 'name' ),
|
|
521
|
+
|
|
522
|
+
# test object type
|
|
523
|
+
type,
|
|
524
|
+
|
|
525
|
+
# test object id
|
|
526
|
+
id,
|
|
527
|
+
|
|
528
|
+
env
|
|
529
|
+
|
|
530
|
+
]
|
|
531
|
+
|
|
532
|
+
end
|
|
533
|
+
|
|
534
|
+
# TODO: document me
|
|
535
|
+
def self.hash_to_element_attributes( hash )
|
|
536
|
+
|
|
537
|
+
hash.collect{ | key, value |
|
|
538
|
+
|
|
539
|
+
"#{ key.to_s }=\"#{ value.to_s }\""
|
|
540
|
+
|
|
541
|
+
}.join(' ')
|
|
542
|
+
|
|
543
|
+
end
|
|
544
|
+
|
|
545
|
+
# TODO: document me
|
|
546
|
+
def self.merge_application_elements( xml_string )
|
|
547
|
+
|
|
548
|
+
# parse the ui state xml
|
|
549
|
+
document_root = MobyUtil::XML.parse_string( xml_string ).root
|
|
550
|
+
|
|
551
|
+
# retrieve application objects as nodeset
|
|
552
|
+
nodeset = document_root.xpath('/tasMessage/tasInfo/object')
|
|
553
|
+
|
|
554
|
+
# check if multiple application objects found
|
|
555
|
+
if nodeset.count > 1
|
|
556
|
+
|
|
557
|
+
# new header, apply original element attributes
|
|
558
|
+
new_xml = "<tasMessage #{ hash_to_element_attributes( document_root.attributes ) }><tasInfo #{ hash_to_element_attributes( nodeset.first.parent.attributes ) }>"
|
|
559
|
+
|
|
560
|
+
# flag defining that is application element already created
|
|
561
|
+
application_element_set = false
|
|
562
|
+
|
|
563
|
+
# collect environment values
|
|
564
|
+
environments = document_root.xpath('/tasMessage/tasInfo/object[@type="application"]/@env').collect{ | attribute | attribute.to_s }
|
|
565
|
+
|
|
566
|
+
# iterate through each object found in xml
|
|
567
|
+
nodeset.each{ | object |
|
|
568
|
+
|
|
569
|
+
# only one application element
|
|
570
|
+
unless application_element_set
|
|
571
|
+
|
|
572
|
+
#application_objects << object
|
|
573
|
+
|
|
574
|
+
# retrieve object attributes
|
|
575
|
+
attributes = object.attributes
|
|
576
|
+
|
|
577
|
+
# merge env to attributes hash
|
|
578
|
+
attributes['env'] = environments.join(';')
|
|
579
|
+
|
|
580
|
+
# add application object xml element to new xml string
|
|
581
|
+
new_xml << "<object #{ hash_to_element_attributes( attributes ) }>"
|
|
582
|
+
|
|
583
|
+
# application element is now set, no need to do it again
|
|
584
|
+
application_element_set = true
|
|
585
|
+
|
|
586
|
+
end
|
|
587
|
+
|
|
588
|
+
# append all found elements
|
|
589
|
+
object.xpath('./*').each{ | object | new_xml << object.to_s }
|
|
590
|
+
|
|
591
|
+
}
|
|
592
|
+
|
|
593
|
+
# multiple applications found, return merged application xml
|
|
594
|
+
new_xml << "</object></tasInfo></tasMessage>"
|
|
595
|
+
|
|
596
|
+
else
|
|
597
|
+
|
|
598
|
+
# only one application found, return data as is
|
|
599
|
+
xml_string
|
|
600
|
+
|
|
601
|
+
end
|
|
602
|
+
|
|
603
|
+
end
|
|
604
|
+
|
|
394
605
|
# enable hooking for performance measurement & debug logging
|
|
395
|
-
|
|
606
|
+
TDriver::Hooking.hook_methods( self ) if defined?( TDriver::Hooking )
|
|
396
607
|
|
|
397
608
|
end # TestObjectAdapter
|
|
398
609
|
|