kameleon 0.0.9 → 0.2.0.alpha.2

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.
Files changed (81) hide show
  1. data/LICENCE +1 -1
  2. data/README.textile +157 -0
  3. data/lib/kameleon.rb +3 -18
  4. data/lib/kameleon/dsl.rb +98 -0
  5. data/lib/kameleon/dsl/act/form.rb +106 -0
  6. data/lib/kameleon/dsl/act/mouse.rb +59 -0
  7. data/lib/kameleon/dsl/context/scope.rb +95 -0
  8. data/lib/kameleon/dsl/utils/debug.rb +10 -0
  9. data/lib/kameleon/dsl/verify/absence.rb +151 -0
  10. data/lib/kameleon/dsl/verify/presence.rb +327 -0
  11. data/lib/kameleon/ext/active_record/shared_single_connection.rb +42 -0
  12. data/lib/kameleon/ext/capybara/server.rb +21 -0
  13. data/lib/kameleon/ext/capybara/session_pool.rb +63 -0
  14. data/lib/kameleon/ext/rspec/all.rb +4 -0
  15. data/lib/kameleon/ext/rspec/dsl.rb +39 -0
  16. data/lib/kameleon/ext/rspec/garbage_collector.rb +11 -0
  17. data/lib/kameleon/ext/rspec/headless.rb +12 -0
  18. data/lib/kameleon/ext/rspec/pool.rb +7 -0
  19. data/lib/kameleon/ext/rspec/transactional_examples.rb +10 -0
  20. data/{spec/support/deferred_garbage_collection.rb → lib/kameleon/ext/ruby/deferred_garbage_collector.rb} +0 -0
  21. data/lib/kameleon/ext/session/devise.rb +28 -0
  22. data/lib/kameleon/session.rb +23 -0
  23. data/lib/kameleon/utils/configuration.rb +5 -5
  24. data/lib/kameleon/utils/debug_console.rb +31 -0
  25. metadata +73 -77
  26. data/lib/kameleon/dsl/act.rb +0 -107
  27. data/lib/kameleon/dsl/see.rb +0 -155
  28. data/lib/kameleon/session/capybara.rb +0 -33
  29. data/lib/kameleon/session/server.rb +0 -21
  30. data/lib/kameleon/session/session_pool.rb +0 -45
  31. data/lib/kameleon/user/abstract.rb +0 -142
  32. data/lib/kameleon/user/base.rb +0 -36
  33. data/lib/kameleon/user/guest.rb +0 -10
  34. data/lib/kameleon/utils/helpers.rb +0 -11
  35. data/lib/patch/capybara_selenium_driver.rb +0 -7
  36. data/spec/sample_rack_app/hey.rb +0 -24
  37. data/spec/spec_helper.rb +0 -41
  38. data/spec/unit/act/click_spec.rb +0 -52
  39. data/spec/unit/act/fill_in/attach_file_spec.rb +0 -36
  40. data/spec/unit/act/fill_in/checkbox_spec.rb +0 -87
  41. data/spec/unit/act/fill_in/date_ranges_spec.rb +0 -24
  42. data/spec/unit/act/fill_in/multiple_select_spec.rb +0 -42
  43. data/spec/unit/act/fill_in/radio_button_spec.rb +0 -35
  44. data/spec/unit/act/fill_in/select_spec.rb +0 -35
  45. data/spec/unit/act/fill_in/text_area_spec.rb +0 -52
  46. data/spec/unit/act/fill_in/text_input_spec.rb +0 -52
  47. data/spec/unit/act/on_hover_spec.rb +0 -34
  48. data/spec/unit/dsl/not_see/form_elements/fields/empty_spec.rb +0 -38
  49. data/spec/unit/dsl/not_see/form_elements/fields/readonly_spec.rb +0 -38
  50. data/spec/unit/dsl/not_see/form_elements/fields_spec.rb +0 -24
  51. data/spec/unit/dsl/not_see/form_elements/textareas_spec.rb +0 -25
  52. data/spec/unit/dsl/not_see/form_elements/texts_spec.rb +0 -26
  53. data/spec/unit/dsl/not_see/in_scopes_spec.rb +0 -63
  54. data/spec/unit/dsl/not_see/special_elements/buttons_spec.rb +0 -24
  55. data/spec/unit/dsl/not_see/special_elements/error_message_for_spec.rb +0 -24
  56. data/spec/unit/dsl/not_see/special_elements/images_spec.rb +0 -24
  57. data/spec/unit/dsl/not_see/special_elements/links_spec.rb +0 -46
  58. data/spec/unit/dsl/not_see/special_elements/ordered_texts_spec.rb +0 -21
  59. data/spec/unit/dsl/not_see/special_selectors_spec.rb +0 -39
  60. data/spec/unit/dsl/not_see/texts_spec.rb +0 -24
  61. data/spec/unit/dsl/see/counted_elements_spec.rb +0 -26
  62. data/spec/unit/dsl/see/form_elements/checkboxes_spec.rb +0 -45
  63. data/spec/unit/dsl/see/form_elements/fields/disabled_spec.rb +0 -30
  64. data/spec/unit/dsl/see/form_elements/fields/empty_spec.rb +0 -28
  65. data/spec/unit/dsl/see/form_elements/fields/readonly_spec.rb +0 -38
  66. data/spec/unit/dsl/see/form_elements/fields_spec.rb +0 -28
  67. data/spec/unit/dsl/see/form_elements/multiple_selects_spec.rb +0 -47
  68. data/spec/unit/dsl/see/form_elements/radio_buttons_spec.rb +0 -35
  69. data/spec/unit/dsl/see/form_elements/selects_spec.rb +0 -40
  70. data/spec/unit/dsl/see/form_elements/textareas_spec.rb +0 -29
  71. data/spec/unit/dsl/see/form_elements/texts_spec.rb +0 -29
  72. data/spec/unit/dsl/see/in_scopes_spec.rb +0 -85
  73. data/spec/unit/dsl/see/special_elements/buttons_spec.rb +0 -28
  74. data/spec/unit/dsl/see/special_elements/error_message_for_spec.rb +0 -24
  75. data/spec/unit/dsl/see/special_elements/images_spec.rb +0 -28
  76. data/spec/unit/dsl/see/special_elements/links_spec.rb +0 -55
  77. data/spec/unit/dsl/see/special_elements/ordered_texts_spec.rb +0 -21
  78. data/spec/unit/dsl/see/special_selectors_spec.rb +0 -57
  79. data/spec/unit/dsl/see/texts_spec.rb +0 -24
  80. data/spec/unit/guest_spec.rb +0 -46
  81. data/spec/unit/user_base_spec.rb +0 -13
@@ -0,0 +1,95 @@
1
+ module Kameleon
2
+ module DSL
3
+ module Context
4
+ class Scope
5
+
6
+ attr_accessor :params
7
+
8
+ def initialize(params)
9
+ @params = params
10
+ end
11
+
12
+ def selector
13
+ detect_selector(params)
14
+ end
15
+
16
+ private
17
+
18
+ def detect_selector(param)
19
+ case param
20
+ when Hash
21
+ #! add warning when there is more then one element in hash
22
+ Kameleon::DSL::Context::SpecialSelectors.send(*param.first)
23
+ when Symbol
24
+ normalize(defined_areas[param])
25
+ when String
26
+ normalize(param)
27
+ when Array
28
+ param.size == 1 ?
29
+ detect_selector(param.first) :
30
+ normalize(param)
31
+ when nil
32
+ normalize(default_selector)
33
+ else
34
+ raise "type <#{param.class.name}> not implemented"
35
+ end
36
+ end
37
+
38
+ def normalize(params)
39
+ case params
40
+ when String
41
+ [::Capybara.default_selector, params]
42
+ when Array
43
+ if params.empty?
44
+ normalize(default_selector)
45
+ elsif params.size == 1
46
+ [::Capybara.default_selector] + params
47
+ else
48
+ params
49
+ end
50
+ end
51
+ end
52
+
53
+ def default_selector
54
+ defined_areas[:default] || [:xpath, "//body"]
55
+ end
56
+
57
+ def defined_areas
58
+ ::Kameleon::Session.defined_areas
59
+ end
60
+ end
61
+
62
+ #! extending selectors in capybara way https://github.com/jnicklas/capybara/blob/master/lib/capybara.rb#L76
63
+ module SpecialSelectors
64
+ def self.row(param)
65
+ case param
66
+ when String
67
+ [:xpath, "//tr[*='#{param}'][1]"]
68
+ when Fixnum
69
+ [:xpath, "//tbody/tr[#{param}]"]
70
+ else
71
+ raise "not implemented"
72
+ end
73
+ end
74
+
75
+ def self.row_and_column(param)
76
+ value_in_row, value_in_column = *param
77
+ if value_in_row.is_a?(Fixnum) and value_in_column.is_a?(Fixnum)
78
+ [:xpath, "//tbody/tr[#{value_in_row}]/td[#{value_in_column}]"]
79
+ else
80
+ #! on page there might be more then one table
81
+ position = Capybara.current_session.all(:xpath, "//table//th").index { |n| n.text =~ /#{value_in_column}/ }
82
+ [:xpath, "//tr[*='#{value_in_row}'][1]/td[#{position+1}]"]
83
+ end
84
+ end
85
+
86
+ def self.column(param)
87
+ raise "not implemented"
88
+ # position = session.all(:xpath, "//table//th").index { |n| n.text =~ /#{value}/ }
89
+ # return [:xpath, ".//table//th[#{position + 1}] | .//table//td[#{position + 1}]", :select_multiple]
90
+ end
91
+ end
92
+ end
93
+ end
94
+ end
95
+
@@ -0,0 +1,10 @@
1
+ #! it should be package into raw module
2
+ #def page_element(selector)
3
+ # session.find(*get_selector(selector))
4
+ #end
5
+ #
6
+ #def page_elements(selector)
7
+ # session.all(*get_selector(selector))
8
+ #end
9
+
10
+ #! js execution
@@ -0,0 +1,151 @@
1
+ module Kameleon
2
+ module DSL
3
+ module Verify
4
+ class Absence
5
+
6
+ attr_accessor :conditions, :params
7
+
8
+ def initialize(*params)
9
+ @params = params
10
+ @conditions = []
11
+
12
+ parse_conditions
13
+ end
14
+
15
+ private
16
+
17
+ def parse_conditions
18
+ prepare_conditions(params)
19
+ end
20
+
21
+ def prepare_conditions(param)
22
+ case param
23
+ when String
24
+ conditions << Condition.new(:have_no_content, param)
25
+ when Hash
26
+ param.each_pair do |type, values|
27
+ case type
28
+ when :link, :links
29
+ conditions.concat Link.new(values).conditions
30
+ when :image, :images
31
+ conditions.concat Image.new(values).conditions
32
+ when :field, :fields
33
+ conditions.concat Field.new(values).conditions
34
+ else
35
+ raise "not implemented"
36
+ end
37
+ end
38
+ when Array
39
+ params.each { |parameter| prepare_conditions(parameter) }
40
+ else
41
+ raise "not implemented"
42
+ end
43
+ end
44
+
45
+ class Condition
46
+ attr_accessor :method, :params, :block
47
+
48
+ def initialize(method, *params, &block)
49
+ @method = method
50
+ @params = params
51
+ @block = block
52
+ end
53
+ end
54
+
55
+ #! below class need some love - refactoring
56
+
57
+ class Link
58
+ attr_reader :conditions
59
+
60
+ def initialize(params)
61
+ @conditions = []
62
+ parse_params(params)
63
+ end
64
+
65
+ private
66
+
67
+ def parse_params(params)
68
+ case params
69
+ when Hash
70
+ params.each_pair do |text, url|
71
+ conditions << Condition.new(:have_no_link, text, :href => url)
72
+ end
73
+ when String
74
+ conditions << Condition.new(:have_no_link, params)
75
+ when Array
76
+ params.each { |param| parse_params(param) }
77
+ else
78
+ raise 'not implemented'
79
+ end
80
+ end
81
+ end
82
+
83
+ class Image
84
+ attr_reader :conditions
85
+
86
+ def initialize(params)
87
+ @conditions = []
88
+ parse_params(params)
89
+ end
90
+
91
+ private
92
+
93
+ def parse_params(params)
94
+ case params
95
+ when String
96
+ conditions << Condition.new(:have_no_xpath, prepare_xpath(params))
97
+ when Array
98
+ params.each { |param| parse_params(param) }
99
+ else
100
+ raise 'not implemented'
101
+ end
102
+ end
103
+
104
+ def prepare_xpath(alt_or_src)
105
+ "//img[@alt=\"#{alt_or_src}\"] | //img[@src=\"#{alt_or_src}\"]"
106
+ end
107
+ end
108
+
109
+ class Field
110
+ attr_reader :conditions
111
+
112
+ def initialize(params)
113
+ @conditions = []
114
+ parse_params(params)
115
+ end
116
+
117
+ private
118
+
119
+ def parse_params(params)
120
+ case params
121
+ when Hash
122
+ params.each_pair do |text, url|
123
+ conditions << Condition.new(:have_no_field, text, :href => url)
124
+ end
125
+ when String
126
+ conditions << Condition.new(:have_no_field, params)
127
+ when Array
128
+ params.each { |param| parse_params(param) }
129
+ else
130
+ raise 'not implemented'
131
+ end
132
+ end
133
+ end
134
+
135
+ class Condition
136
+ attr_accessor :method, :params, :block
137
+
138
+ def initialize(method, *params, &block)
139
+ @method = method
140
+ @params = params
141
+ @block = block
142
+ end
143
+ end
144
+
145
+
146
+ end
147
+ end
148
+ end
149
+ end
150
+
151
+ #! not_see :button, :buttons -> have_no_button(selector)
@@ -0,0 +1,327 @@
1
+ module Kameleon
2
+ module DSL
3
+ module Verify
4
+ class Presence
5
+
6
+ attr_accessor :conditions, :params
7
+
8
+ def initialize(*params)
9
+ @params = params
10
+ @conditions = []
11
+
12
+ parse_conditions
13
+ end
14
+
15
+ private
16
+
17
+ def parse_conditions
18
+ prepare_conditions(params)
19
+ end
20
+
21
+ def prepare_conditions(param)
22
+ case param
23
+ when String
24
+ conditions << Condition.new(:have_content, param)
25
+ when Hash
26
+ param.each_pair do |type, values|
27
+ case type
28
+ when :link, :links
29
+ conditions.concat Link.new(values).conditions
30
+ when :image, :images
31
+ conditions.concat Image.new(values).conditions
32
+ when :ordered
33
+ conditions.concat Sequence.new(values).conditions
34
+ when Fixnum
35
+ conditions.concat Quantity.new(type, values).conditions
36
+ when String
37
+ if type == ""
38
+ prepare_conditions(:empty => values)
39
+ else
40
+ conditions.concat TextInput.new(type, values).conditions
41
+ end
42
+ when :checked, :unchecked, :check, :uncheck
43
+ conditions.concat CheckBoxInput.new(type, values).conditions
44
+ when :selected, :unselected, :select, :unselect
45
+ conditions.concat SelectInput.new(type, values).conditions
46
+ when :field, :fields
47
+ conditions.concat TextInput.new(nil, values).conditions
48
+ when :empty
49
+ conditions.concat EmptyInput.new(values).conditions
50
+ else
51
+ raise "not implemented"
52
+ end
53
+ end
54
+ when Array
55
+ params.each { |parameter| prepare_conditions(parameter) }
56
+ else
57
+ raise "not implemented"
58
+ end
59
+ end
60
+ end
61
+
62
+ class Condition
63
+ attr_accessor :method, :params, :block
64
+
65
+ def initialize(method, *params, &block)
66
+ @method = method
67
+ @params = params
68
+ @block = block
69
+ end
70
+ end
71
+
72
+ #! below class require some deep refactoring
73
+
74
+ class Link
75
+ attr_reader :conditions
76
+
77
+ def initialize(params)
78
+ @conditions = []
79
+ parse_params(params)
80
+ end
81
+
82
+ private
83
+
84
+ def parse_params(params)
85
+ case params
86
+ when Hash
87
+ params.each_pair do |text, url|
88
+ conditions << Condition.new(:have_link, text, :href => url)
89
+ end
90
+ when String
91
+ conditions << Condition.new(:have_link, params)
92
+ when Array
93
+ params.each { |param| parse_params(param) }
94
+ else
95
+ raise 'not implemented'
96
+ end
97
+ end
98
+ end
99
+
100
+ class Image
101
+ attr_reader :conditions
102
+
103
+ def initialize(params)
104
+ @conditions = []
105
+ parse_params(params)
106
+ end
107
+
108
+ private
109
+
110
+ def parse_params(params)
111
+ case params
112
+ when String
113
+ conditions << Condition.new(:have_xpath, prepare_xpath(params))
114
+ when Array
115
+ params.each { |param| parse_params(param) }
116
+ else
117
+ raise 'not implemented'
118
+ end
119
+ end
120
+
121
+ def prepare_xpath(alt_or_src)
122
+ "//img[@alt=\"#{alt_or_src}\"] | //img[@src=\"#{alt_or_src}\"]"
123
+ end
124
+ end
125
+
126
+ class Quantity
127
+ attr_reader :conditions
128
+ attr_reader :quantity
129
+
130
+ def initialize(quantity, params)
131
+ @conditions = []
132
+ @quantity = quantity
133
+ parse_params(params)
134
+ end
135
+
136
+ private
137
+
138
+ def parse_params(params)
139
+ if params === Array && params.first == Array
140
+ params.each { |param| parse_params(param) }
141
+ else
142
+ #! refactor
143
+ selector = prepare_query(params).selector
144
+ conditions << Condition.new(prepare_method(selector), selector.last, :count => quantity)
145
+ end
146
+ end
147
+
148
+ def prepare_query(selector)
149
+ Context::Scope.new(selector)
150
+ end
151
+
152
+ #! refactor - delagate to Context::Scope class
153
+ def prepare_method(query)
154
+ query.first == :xpath ?
155
+ :have_xpath :
156
+ :have_css
157
+ end
158
+ end
159
+
160
+ class Sequence
161
+ attr_reader :params
162
+
163
+ def initialize(params)
164
+ @params = params
165
+ end
166
+
167
+
168
+ def conditions
169
+ [condition]
170
+ end
171
+
172
+ private
173
+
174
+ def condition
175
+ Condition.new(nil, params, prepare_xpath) do |elements, xpath_query|
176
+ texts = page.all(:xpath, xpath_query).map(&:text)
177
+ texts.should == elements
178
+ end
179
+ end
180
+
181
+ def prepare_xpath
182
+ params.collect { |n| "//node()[text()= \"#{n}\"]" }.join(' | ')
183
+ end
184
+ end
185
+
186
+ class TextInput
187
+ attr_reader :conditions, :value
188
+
189
+ def initialize(value, *params)
190
+ @value = value
191
+ @conditions = []
192
+ parse_params(params)
193
+ end
194
+
195
+ private
196
+
197
+ def parse_params(params)
198
+ case params
199
+ when String
200
+ conditions << Condition.new(:have_field, params, :with => value)
201
+ when Array
202
+ params.each { |param| parse_params(param) }
203
+ else
204
+ raise "not supported"
205
+ end
206
+ end
207
+ end
208
+
209
+
210
+ class EmptyInput
211
+ attr_reader :conditions
212
+
213
+ def initialize(*params)
214
+ @conditions = []
215
+ parse_params(params)
216
+ end
217
+
218
+ private
219
+
220
+ def parse_params(params)
221
+ case params
222
+ when String
223
+ conditions << condition(params)
224
+ when Array
225
+ params.each { |param| parse_params(param) }
226
+ else
227
+ raise "not supported"
228
+ end
229
+ end
230
+
231
+ def condition(params)
232
+ Condition.new(nil, params) do |element|
233
+ page.should have_field(element)
234
+ find_field(element).value.should satisfy do |value|
235
+ value == nil or value == ""
236
+ end
237
+ end
238
+ end
239
+ end
240
+
241
+ class CheckBoxInput
242
+ attr_reader :conditions, :value
243
+
244
+ def initialize(value, *params)
245
+ @value = value
246
+ @conditions = []
247
+ parse_params(params)
248
+ end
249
+
250
+ private
251
+
252
+ def parse_params(params)
253
+ case params
254
+ when String
255
+ conditions << Condition.new(matcher_method, params)
256
+ when Array
257
+ params.each { |param| parse_params(param) }
258
+ else
259
+ raise "not supported"
260
+ end
261
+ end
262
+
263
+ def matcher_method
264
+ case value
265
+ when :checked, :check
266
+ :have_checked_field
267
+ when :unchecked, :uncheck
268
+ :have_unchecked_field
269
+ else
270
+ raise "not supported"
271
+ end
272
+ end
273
+ end
274
+
275
+ class SelectInput
276
+ attr_reader :conditions, :value
277
+
278
+ def initialize(value, *params)
279
+ @value = value
280
+ @conditions = []
281
+ parse_params(params)
282
+ end
283
+
284
+ private
285
+
286
+ def parse_params(params)
287
+ case params
288
+ when Hash
289
+ params.each_pair do |selected_value, identifier|
290
+ case identifier
291
+ when Array
292
+ selected_value.each do |value|
293
+ parse_params(value => identifier)
294
+ end
295
+ when String
296
+ conditions << Condition.new(matcher_method, identifier, :selected => selected_value)
297
+ else
298
+ raise "not supported"
299
+ end
300
+ end
301
+ when Array
302
+ params.each { |param| parse_params(param) }
303
+ else
304
+ raise "not supported"
305
+ end
306
+ end
307
+
308
+
309
+ def matcher_method
310
+ case value
311
+ when :selected, :select
312
+ :have_select
313
+ when :unselected, :unselect
314
+ :have_no_select
315
+ else
316
+ raise "not supported"
317
+ end
318
+ end
319
+ end
320
+
321
+ end
322
+
323
+ end
324
+ end
325
+
326
+ #! see :button, :buttons -> have_button(selector)
327
+ #! see field that is :disabled, :readonly