ruby-web 1.1.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.
Files changed (190) hide show
  1. data/ChangeLog +474 -0
  2. data/INSTALL.txt +9 -0
  3. data/InstalledFiles +180 -0
  4. data/LICENSE.txt +74 -0
  5. data/Rakefile +529 -0
  6. data/TODO +65 -0
  7. data/doc/additional.xml +149 -0
  8. data/doc/core.xml +652 -0
  9. data/doc/credits/index.xml +52 -0
  10. data/doc/credits/php.contributors.xml +118 -0
  11. data/doc/credits/php.language-snippets.ent +622 -0
  12. data/doc/install/index.xml +136 -0
  13. data/doc/install/mac/index.xml +21 -0
  14. data/doc/install/ruby-web.install.rb.instructions.xml +7 -0
  15. data/doc/install/unix/index.xml +46 -0
  16. data/doc/install/win/apache1.xml +166 -0
  17. data/doc/install/win/apache2.xml +141 -0
  18. data/doc/install/win/iis.xml +162 -0
  19. data/doc/install/win/index.xml +24 -0
  20. data/doc/install/win/installer.xml +31 -0
  21. data/doc/install/win/manual.xml +43 -0
  22. data/doc/manual.xml +69 -0
  23. data/doc/old/apache_cgi.txt +23 -0
  24. data/doc/old/fastcgi.txt +23 -0
  25. data/doc/old/mod_ruby.txt +21 -0
  26. data/doc/old/snippets.rdoc +183 -0
  27. data/doc/old/webrick.txt +23 -0
  28. data/doc/old/windows_cgi.txt +9 -0
  29. data/doc/tutorial.xml +14 -0
  30. data/doc/xsl/manual-multi.xsl +10 -0
  31. data/doc/xsl/manual-pdf.xsl +6 -0
  32. data/doc/xsl/manual-single.xsl +6 -0
  33. data/doc/xsl/manual.css +22 -0
  34. data/install.rb +1022 -0
  35. data/lib/formatter.rb +314 -0
  36. data/lib/html-parser.rb +429 -0
  37. data/lib/htmlrepair.rb +113 -0
  38. data/lib/htmlsplit.rb +842 -0
  39. data/lib/sgml-parser.rb +332 -0
  40. data/lib/web.rb +68 -0
  41. data/lib/web/assertinclude.rb +129 -0
  42. data/lib/web/config.rb +50 -0
  43. data/lib/web/connection.rb +1070 -0
  44. data/lib/web/convenience.rb +154 -0
  45. data/lib/web/formreader.rb +318 -0
  46. data/lib/web/htmlparser/html-parser.rb +429 -0
  47. data/lib/web/htmlparser/sgml-parser.rb +332 -0
  48. data/lib/web/htmltools/element.rb +296 -0
  49. data/lib/web/htmltools/stparser.rb +276 -0
  50. data/lib/web/htmltools/tags.rb +286 -0
  51. data/lib/web/htmltools/tree.rb +139 -0
  52. data/lib/web/htmltools/xmltree.rb +160 -0
  53. data/lib/web/htmltools/xpath.rb +71 -0
  54. data/lib/web/info.rb +63 -0
  55. data/lib/web/load.rb +210 -0
  56. data/lib/web/mime.rb +87 -0
  57. data/lib/web/phprb.rb +340 -0
  58. data/lib/web/resources/test/cookie.rb +33 -0
  59. data/lib/web/resources/test/counter.rb +20 -0
  60. data/lib/web/resources/test/multipart.rb +14 -0
  61. data/lib/web/resources/test/redirect.rb +8 -0
  62. data/lib/web/resources/test/stock.rb +33 -0
  63. data/lib/web/sapi/apache.rb +129 -0
  64. data/lib/web/sapi/fastcgi.rb +22 -0
  65. data/lib/web/sapi/install/apache.rb +180 -0
  66. data/lib/web/sapi/install/iis.rb +93 -0
  67. data/lib/web/sapi/install/macosx.rb +90 -0
  68. data/lib/web/sapi/webrick.rb +86 -0
  69. data/lib/web/session.rb +83 -0
  70. data/lib/web/shim/cgi.rb +129 -0
  71. data/lib/web/shim/rails.rb +175 -0
  72. data/lib/web/stringio.rb +78 -0
  73. data/lib/web/strscanparser.rb +24 -0
  74. data/lib/web/tagparser.rb +96 -0
  75. data/lib/web/testing.rb +666 -0
  76. data/lib/web/traceoutput.rb +75 -0
  77. data/lib/web/unit.rb +56 -0
  78. data/lib/web/upload.rb +59 -0
  79. data/lib/web/validate.rb +52 -0
  80. data/lib/web/wiki.rb +557 -0
  81. data/lib/web/wiki/linker.rb +72 -0
  82. data/lib/web/wiki/page.rb +201 -0
  83. data/lib/webunit.rb +27 -0
  84. data/lib/webunit/assert.rb +152 -0
  85. data/lib/webunit/converter.rb +154 -0
  86. data/lib/webunit/cookie.rb +118 -0
  87. data/lib/webunit/domwalker.rb +185 -0
  88. data/lib/webunit/exception.rb +14 -0
  89. data/lib/webunit/form.rb +116 -0
  90. data/lib/webunit/frame.rb +37 -0
  91. data/lib/webunit/htmlelem.rb +122 -0
  92. data/lib/webunit/image.rb +26 -0
  93. data/lib/webunit/jscript.rb +31 -0
  94. data/lib/webunit/link.rb +33 -0
  95. data/lib/webunit/params.rb +321 -0
  96. data/lib/webunit/parser.rb +229 -0
  97. data/lib/webunit/response.rb +464 -0
  98. data/lib/webunit/runtest.rb +41 -0
  99. data/lib/webunit/table.rb +148 -0
  100. data/lib/webunit/testcase.rb +45 -0
  101. data/lib/webunit/ui/cui/testrunner.rb +50 -0
  102. data/lib/webunit/utils.rb +68 -0
  103. data/lib/webunit/webunit.rb +28 -0
  104. data/test/dev/action.rb +83 -0
  105. data/test/dev/forms.rb +104 -0
  106. data/test/dev/forms2.rb +104 -0
  107. data/test/dev/parser.rb +17 -0
  108. data/test/dev/scripts/dump.rb +24 -0
  109. data/test/dev/scripts/makedist.rb +62 -0
  110. data/test/dev/scripts/uri.rb +41 -0
  111. data/test/dev/scripts/uri/common.rb +432 -0
  112. data/test/dev/scripts/uri/ftp.rb +149 -0
  113. data/test/dev/scripts/uri/generic.rb +1106 -0
  114. data/test/dev/scripts/uri/http.rb +76 -0
  115. data/test/dev/scripts/uri/https.rb +26 -0
  116. data/test/dev/scripts/uri/ldap.rb +238 -0
  117. data/test/dev/scripts/uri/mailto.rb +260 -0
  118. data/test/dev/scripts/urireg.rb +174 -0
  119. data/test/dev/simpledispatcher.rb +156 -0
  120. data/test/dev/test.action.rb +146 -0
  121. data/test/dev/test.formreader.rb +463 -0
  122. data/test/dev/test.simpledispatcher.rb +186 -0
  123. data/test/dev/webunit/conv/digit-0.rb +21 -0
  124. data/test/dev/webunit/conv/digit-1.rb +17 -0
  125. data/test/dev/webunit/conv/digit.rb +23 -0
  126. data/test/dev/webunit/conv/test_digit-0.rb +16 -0
  127. data/test/dev/webunit/conv/test_digit-1.rb +19 -0
  128. data/test/dev/webunit/conv/test_digit.rb +26 -0
  129. data/test/dev/webunit/conv/test_digit_view-0.rb +76 -0
  130. data/test/dev/webunit/conv/test_digit_view-1.rb +102 -0
  131. data/test/dev/webunit/conv/test_digit_view.rb +134 -0
  132. data/test/installation/htdocs/cgi_test.rb +296 -0
  133. data/test/installation/htdocs/test_install.rb +4 -0
  134. data/test/installation/runwebtest.rb +5 -0
  135. data/test/installation/test_cookie.rb +128 -0
  136. data/test/installation/test_form.rb +47 -0
  137. data/test/installation/test_multipart.rb +51 -0
  138. data/test/installation/test_request.rb +24 -0
  139. data/test/installation/test_response.rb +35 -0
  140. data/test/unit/htdocs/cookie.rb +32 -0
  141. data/test/unit/htdocs/multipart.rb +28 -0
  142. data/test/unit/htdocs/redirect.rb +12 -0
  143. data/test/unit/htdocs/simple.rb +13 -0
  144. data/test/unit/htdocs/stock.rb +33 -0
  145. data/test/unit/test_assert.rb +162 -0
  146. data/test/unit/test_cookie.rb +114 -0
  147. data/test/unit/test_domwalker.rb +77 -0
  148. data/test/unit/test_form.rb +42 -0
  149. data/test/unit/test_frame.rb +40 -0
  150. data/test/unit/test_htmlelem.rb +74 -0
  151. data/test/unit/test_image.rb +45 -0
  152. data/test/unit/test_jscript.rb +57 -0
  153. data/test/unit/test_link.rb +85 -0
  154. data/test/unit/test_multipart.rb +51 -0
  155. data/test/unit/test_params.rb +210 -0
  156. data/test/unit/test_parser.rb +53 -0
  157. data/test/unit/test_response.rb +150 -0
  158. data/test/unit/test_table.rb +70 -0
  159. data/test/unit/test_utils.rb +106 -0
  160. data/test/unit/test_webunit.rb +28 -0
  161. data/test/web/mod_ruby_stub.rb +39 -0
  162. data/test/web/test.assertinclude.rb +109 -0
  163. data/test/web/test.buffer.rb +182 -0
  164. data/test/web/test.code.loader.rb +78 -0
  165. data/test/web/test.config.rb +31 -0
  166. data/test/web/test.error.handling.rb +91 -0
  167. data/test/web/test.formreader-2.0.rb +352 -0
  168. data/test/web/test.load.rb +125 -0
  169. data/test/web/test.mime-type.rb +23 -0
  170. data/test/web/test.narf.cgi.rb +106 -0
  171. data/test/web/test.phprb.rb +239 -0
  172. data/test/web/test.request.rb +368 -0
  173. data/test/web/test.response.rb +637 -0
  174. data/test/web/test.ruby-web.rb +10 -0
  175. data/test/web/test.session.rb +50 -0
  176. data/test/web/test.shim.cgi.rb +96 -0
  177. data/test/web/test.tagparser.rb +65 -0
  178. data/test/web/test.template2.rb +297 -0
  179. data/test/web/test.testing2.rb +318 -0
  180. data/test/web/test.upload.rb +45 -0
  181. data/test/web/test.validate.rb +46 -0
  182. data/test/web/test.web.test.rb +495 -0
  183. data/test/wiki/test.history.rb +297 -0
  184. data/test/wiki/test.illustration_page.rb +287 -0
  185. data/test/wiki/test.linker.rb +197 -0
  186. data/test/wiki/test.tarpit.rb +56 -0
  187. data/test/wiki/test.wiki.rb +300 -0
  188. data/test/wikitestroot/admin.rb +7 -0
  189. data/test/wikitestroot/wiki.rb +6 -0
  190. metadata +234 -0
@@ -0,0 +1,78 @@
1
+ class TestCodeLoader < Test::Unit::TestCase
2
+ include Web::Testing
3
+
4
+ def setup
5
+ @pwd = Dir.pwd
6
+ if File.exists?( temp_dir + "/test_dir/" )
7
+ rm_rf(temp_dir + "/test_dir")
8
+ end
9
+ Dir.mkdir(temp_dir + "/test_dir/")
10
+ Dir.chdir(temp_dir + "/test_dir/")
11
+ end
12
+
13
+ def teardown
14
+ Dir.chdir(@pwd)
15
+ rm_rf(temp_dir + "/test_dir")
16
+ end
17
+
18
+ def write_file filename, contents
19
+ File.open( temp_dir + "/test_dir/#{filename}" , "w" ) { |f|
20
+ f.write(contents)
21
+ }
22
+ end
23
+
24
+ def test_ruby
25
+ write_file "app.rb", <<-EOF
26
+ print "Hello, World"
27
+ EOF
28
+
29
+ do_request "app.rb"
30
+
31
+ assert_content "Hello, World"
32
+ end
33
+
34
+ def test_phprb
35
+ require 'pp'
36
+ @old_default_handler = Web::config['load_suffix'].default
37
+ Web::config['load_suffix'].default = lambda do |script|
38
+ PHPRB::load(script)
39
+ end
40
+
41
+ write_file "app.rhtml", <<-EOF
42
+ <?= "Hello, World" ?>
43
+ EOF
44
+
45
+ do_request "app.rhtml"
46
+
47
+ assert_equal( "Hello, World", Web::get_content.strip )
48
+ ensure
49
+ Web::config['load_suffix'].default = @old_default_handler
50
+ end
51
+
52
+ def test_erb
53
+ write_file "app.erb", <<-EOF
54
+ <%= "Hello, World" %>
55
+ EOF
56
+
57
+ do_request "app.erb"
58
+
59
+ assert_equal( "Hello, World", Web::get_content.strip )
60
+
61
+ end
62
+
63
+ def test_custom
64
+ Web::config[:load_suffix][:custom] = lambda do |script|
65
+ Web::write script
66
+ end
67
+
68
+ write_file "app.custom", <<-EOF
69
+ this code doesn't matter
70
+ EOF
71
+
72
+ do_request "app.custom"
73
+ assert_match( /app.custom$/, Web::get_content.strip )
74
+ ensure
75
+ Web::config[:load_suffix].delete :custom
76
+ end
77
+
78
+ end
@@ -0,0 +1,31 @@
1
+ class TestWebConfig < Test::Unit::TestCase
2
+ def setup
3
+ @old_config = Web::config
4
+ Web::module_eval do
5
+ @@config = Web::Config.new
6
+ end
7
+ end
8
+
9
+ def teardown
10
+ c = @old_config
11
+ Web::module_eval do
12
+ @@config = c
13
+ end
14
+ end
15
+
16
+ def test_preferences
17
+ Web::config.set("random_pref" => "random value",
18
+ "another_pref" => "another value")
19
+ assert_equal( "random value", Web::config::random_pref )
20
+ assert_equal( "random value", Web::config["random_pref"] )
21
+ assert_equal( "another value", Web::config::another_pref )
22
+ assert_equal( "another value", Web::config["another_pref"] )
23
+ end
24
+
25
+ def test_docs
26
+ assert_equal( nil, Web::config["random_pref"] )
27
+ Web::config::describe( :random_pref => "This is a test" )
28
+ assert_equal( "This is a test", Web::config::docs[:random_pref] )
29
+ end
30
+
31
+ end
@@ -0,0 +1,91 @@
1
+ class TestErrorHandling < Test::Unit::TestCase
2
+ def app
3
+ temp_dir + "/test_dir/app.rb"
4
+ end
5
+
6
+ def setup
7
+ File.delete(app) if File.exists? app
8
+ @stdout, @stderr = $stdout, $stderr
9
+ $stdout, $stderr = StringIO.new, StringIO.new
10
+ Web::setup
11
+ end
12
+
13
+ def teardown
14
+ File.delete(app) if File.exists? app
15
+ Web::teardown
16
+ $stdout, $stderr = @stdout, @stderr
17
+ end
18
+
19
+ def write_file file
20
+ File.open( temp_dir + "/test_dir/app.rb" , "w" ) { |f| f.write(file) }
21
+ end
22
+
23
+ def test_error_handling
24
+ Web::config[:error_style] = :production
25
+
26
+ Web::open do
27
+ Web::filter do
28
+ raise "hell"
29
+ end
30
+ end
31
+ assert_match( /RuntimeError.*hell/m, $stdout.string )
32
+ end
33
+
34
+ def test_production
35
+ Web::config[:error_style] = :production
36
+
37
+ Web::open do
38
+ raise "this is a test error"
39
+ end
40
+
41
+ assert_equal( '500', Web::status )
42
+
43
+ assert_match( /^RuntimeError: this is a test error/,
44
+ $stderr.string,
45
+ "Error printed to stderr" )
46
+ assert_match( /<b style='font-size:20px'>this is a test error<\/b>/,
47
+ $stdout.string,
48
+ "Error printed with html to stdout" )
49
+ assert_no_match( /test.error.handling.rb/,
50
+ $stdout.string,
51
+ "No backtrace should be printed to stdout" )
52
+
53
+ end
54
+
55
+ def test_development
56
+ Web::config[:error_style] = :development
57
+
58
+ Web::open do
59
+ raise "this is a test error"
60
+ end
61
+
62
+ assert_equal( '500', Web::status )
63
+
64
+ assert_match( /^RuntimeError: this is a test error/,
65
+ $stderr.string,
66
+ "Error printed to stderr" )
67
+ assert_match( /<b style='font-size:20px'>this is a test error<\/b>/,
68
+ $stdout.string,
69
+ "Error printed with html to stdout" )
70
+ assert_match( /test.error.handling.rb/,
71
+ $stdout.string,
72
+ "backtrace printed" )
73
+ end
74
+
75
+ def test_content_type
76
+ Web::config[:error_style] = :development
77
+
78
+ Web::open do
79
+ Web::content_type = "application/ms-excel"
80
+ raise "this is a test error"
81
+ end
82
+
83
+ assert_match( /Content-Type: text\/html/,
84
+ $stdout.string,
85
+ "Content-Type Changed back to text/html" )
86
+ end
87
+
88
+
89
+
90
+
91
+ end
@@ -0,0 +1,352 @@
1
+
2
+ class TestFormReader2 < Test::Unit::TestCase
3
+ # for each kind of html element
4
+ # * test the parsed html element handles "assert_include" properly
5
+ # * test submit the html element
6
+ # a few important bits:
7
+ # * handle multiple elements in a form properly.
8
+ # i.e. just because a field isn't name="field[]"
9
+ # doesn't mean that multiple params on a field are lost.
10
+ # also, you should be able to have multiple elements with the
11
+ # same name, but different types
12
+ # this should work exactly the same for simple text elements.
13
+ # this will work very differently for select elements,
14
+ # testing of which IMHO is broken
15
+ #
16
+ # More notes from patrick:
17
+ # There are two dimensions of "multiples" on a form
18
+ # * single or multiple elements in the html
19
+ # * a request by the programmer that elements be returned as a array or as a string
20
+ #
21
+ # I have some simple templating constructs in here to help write the tests.
22
+ # I'm not using Narflates b/c this templating is only to support these tests;
23
+ # the FormReader code works on just html
24
+ #
25
+
26
+ include Web::Testing
27
+
28
+ def setup
29
+ @parser = nil
30
+ end
31
+
32
+ def make_form( content )
33
+ @parser = FormReader.new( "<form name='aForm'>" + content + "</form>" )
34
+ end
35
+
36
+ def get_fields
37
+ @parser.get_fields( "aForm" )
38
+ end
39
+
40
+ def merge_fields( edited_fields={} )
41
+ @parser.merge_fields( "aForm", edited_fields )
42
+ end
43
+
44
+ def get_options
45
+ @parser.get_options( "aForm" )
46
+ end
47
+
48
+ def test_blank_form
49
+ make_form ""
50
+ assert_equal( {}, get_fields )
51
+ assert_equal( {}, merge_fields )
52
+ assert_raises( Web::Testing::FieldNotFoundException ) {
53
+ merge_fields( "missing" => "element" )
54
+ }
55
+ end
56
+
57
+
58
+ # -----------------------------------------
59
+ # the text elements should behave similarly
60
+ # -----------------------------------------
61
+
62
+ def test_plain_input
63
+ do_text_tests <<-HTML
64
+ <input name="{name}" value="{value}">
65
+ HTML
66
+ end
67
+
68
+ def test_text
69
+ do_text_tests <<-HTML
70
+ <input type="text" name="{name}" value="{value}">
71
+ HTML
72
+ end
73
+
74
+ def test_password
75
+ do_text_tests <<-HTML
76
+ <input type="password" name="{name}" value="{value}">
77
+ HTML
78
+ end
79
+
80
+ def test_textarea
81
+ do_text_tests <<-HTML
82
+ <textarea name="{name}">
83
+ {value}
84
+ </textarea>
85
+ HTML
86
+ end
87
+
88
+ def test_hidden
89
+ do_text_tests <<-HTML
90
+ <input type="hidden" name="{name}" value="{value}">
91
+ HTML
92
+ end
93
+
94
+ def make_text_field( pattern, name, value )
95
+ pattern.gsub( /\{name\}/i, name ).gsub( /\{value\}/i, value )
96
+ end
97
+
98
+ def do_text_tests( field_pattern )
99
+ make_form( make_text_field( field_pattern, "atextfield", "avalue" ) )
100
+
101
+ assert_includes( { "atextfield" => "avalue" }, get_fields )
102
+ assert_equal( { "atextfield" => ["avalue"] }, merge_fields )
103
+
104
+ assert_equal( { "atextfield" => ["other"] },
105
+ merge_fields( "atextfield" => "other" ) )
106
+ assert_equal( { "atextfield" => ["other"] },
107
+ merge_fields( :atextfield => "other" ) )
108
+
109
+ assert_raises( FormMergeError ) {
110
+ merge_fields( "atextfield" => [ "one", "two" ] )
111
+ }
112
+
113
+ # multiple elements. Note that it doesn't matters
114
+ # how the programmer wants the cgi to return results,
115
+ # s/he still tests multiple elements the same
116
+ # i.e. "field" and "field[]" behave the same
117
+ # when asserting content on a form or merging elements
118
+ make_form( make_text_field( field_pattern, "atextfield[]", "two" ) +
119
+ make_text_field( field_pattern, "atextfield[]", "one" ) )
120
+
121
+ assert_includes( { "atextfield[]" => ["two", "one"] }, get_fields )
122
+ assert_equal( { "atextfield[]" => ["two", "one"] }, merge_fields )
123
+
124
+ make_form( make_text_field( field_pattern, "atextfield", "two" ) +
125
+ make_text_field( field_pattern, "atextfield", "one" ) )
126
+
127
+ assert_includes( { "atextfield" =>["two", "one"] }, get_fields )
128
+ assert_equal( { "atextfield" => ["two", "one"] }, merge_fields )
129
+
130
+ # if you merge a multiple with a string,
131
+ # the string replaces the first element
132
+ # in the multiple
133
+ assert_equal( { "atextfield" => ["first", "one"] },
134
+ merge_fields( :atextfield => "first" ) )
135
+ assert_equal( { "atextfield" => ["first", "second"] },
136
+ merge_fields( :atextfield => ["first", "second"] ) )
137
+ assert_raises( FormMergeError ) {
138
+ merge_fields( :atextfield => ["first", "second", "third"] )
139
+ }
140
+
141
+ end
142
+
143
+ # -----------------------------------------
144
+ # file uploads may be odd
145
+ # -----------------------------------------
146
+
147
+ def test_file
148
+ make_form( make_file_field( "file" ) )
149
+ assert_includes( { "file" => "" }, get_fields )
150
+ ### do browsers send the file field when
151
+ ### nothing was entered?
152
+ assert_equal( {"file" => [""] }, merge_fields )
153
+
154
+ upload = Web::Upload.new( File.new( "test/web/testfiles/text" ),
155
+ "content-type",
156
+ "original-filename" )
157
+ assert_equal( { "file" => [upload] },
158
+ merge_fields( :file => upload ) )
159
+ end
160
+
161
+ def make_file_field( name )
162
+ "<input type=\"file\" name=\"#{name}\">"
163
+ end
164
+
165
+ # -----------------------------------------
166
+ # use the same api for:
167
+ # single selects and radio buttons
168
+ # multi selects and checkboxes
169
+ # since they more or less are used
170
+ # to say same thing on a form
171
+ # -----------------------------------------
172
+
173
+ def test_select
174
+ do_select_tests <<-HTML
175
+ <select name="{name}">
176
+ {option}<option {checked}selected{endchecked}>{value}</option>{endoption}
177
+ </select>
178
+ HTML
179
+
180
+ do_select_tests <<-HTML
181
+ <select name="{name}">
182
+ {option}<option value="{value}" {checked}selected{endchecked}></option>{endoption}
183
+ </select>
184
+ HTML
185
+ do_multiselect_tests <<-HTML
186
+ <select name="{name}" multiple>
187
+ {option}<option {checked}selected{endchecked}>{value}</option>{endoption}
188
+ </select>
189
+ HTML
190
+
191
+ # select field + select field = two different select fields
192
+
193
+ end
194
+
195
+ def test_radio_and_checkbox
196
+ do_select_tests <<-HTML
197
+ {option}<input type="radio" name="{name}" value="{value}" {checked}checked{endchecked}>{endoption}
198
+ HTML
199
+
200
+ do_select_tests <<-HTML
201
+ <select name="{name}">
202
+ {option}<option value="{value}" {checked}selected{endchecked}></option>{endoption}
203
+ </select>
204
+ HTML
205
+
206
+ do_multiselect_tests <<-HTML
207
+ <select name="{name}" multiple>
208
+ {option}<option {checked}selected{endchecked}>{value}</option>{endoption}
209
+ </select>
210
+ HTML
211
+
212
+ # select field + select field = two different select fields
213
+
214
+ # checkboxes + checkboxes = one big group of checkboxes
215
+ # that can return multiple values
216
+
217
+ # radio buttons + radio buttons = one big group of radio buttons
218
+ # that can return one value
219
+
220
+ # checkboxes + radio buttons = ?????
221
+ end
222
+
223
+ def make_select_field( pattern, name, values )
224
+ pattern.gsub!( /\{NAME\}/i, name )
225
+ pattern =~ /\{OPTION\}(.*)\{ENDOPTION\}/si
226
+ option_pattern = $1
227
+ options = ""
228
+ values.each{ |k,v|
229
+ options += option_pattern.gsub( /\{VALUE\}/i, k ). \
230
+ gsub( if v
231
+ /\{CHECKED\}|\{ENDCHECKED\}/i
232
+ else
233
+ /\{CHECKED\}.*\{ENDCHECKED\}/i
234
+ end, "" )
235
+ }
236
+ pattern.gsub( /\{OPTION\}.*\{ENDOPTION\}/i, options )
237
+ end
238
+
239
+
240
+ def do_select_tests( pattern )
241
+ make_form( make_select_field( pattern,
242
+ "field",
243
+ {"first" => true,
244
+ "second" => false } ) )
245
+
246
+ assert_includes( { "field" => "first" }, get_fields )
247
+ assert_equal( { "field" => ["first"] }, merge_fields )
248
+ assert_equal( { "field" => ["second"] },
249
+ merge_fields( "field" => select("second") ) )
250
+ assert_raises( FormMergeError ) {
251
+ merge_fields( "field" => select("missing value") )
252
+ }
253
+
254
+ assert_raises( FormMergeError ) {
255
+ merge_fields( "field" => select("first", "second") )
256
+ }
257
+
258
+ end
259
+
260
+ def do_multiselect_tests( pattern )
261
+ make_form( make_select_field( pattern,
262
+ "field",
263
+ {"first" => true,
264
+ "second" => false,
265
+ "third" => true } ) )
266
+ assert_includes( { "field" => ["first", "third"] }, get_fields )
267
+ assert_includes( { "field" => ["first", "second", "third"] }, get_options )
268
+ assert_equal( { "field" => ["first", "third"] }, merge_fields )
269
+
270
+ # three cases for merge_fields with selects:
271
+ # using the select function:
272
+ # * a single text value adds to the selected values
273
+ assert_equal( { "field" => ["first", "second", "third" ] },
274
+ merge_fields( "field" => select("second") ) )
275
+ # * an multiples add to the selected values
276
+ assert_equal( { "field" => ["first", "second", "third" ] },
277
+ merge_fields( "field" => select("second","third") ) )
278
+
279
+ # * a hash turns values on and off
280
+ assert_equal( { "field" => ["second", "third"] },
281
+ merge_fields( "field" => {"first" => false,
282
+ "second" => true } ) )
283
+ assert_equal( { "field" => ["second", "third"] },
284
+ merge_fields( "field" => select("first" => false,
285
+ "second" => true ) ) )
286
+
287
+
288
+ assert_raises( FormMergeError ) {
289
+ merge_fields( "field" => "not using select method" )
290
+ }
291
+
292
+ assert_raises( FormMergeError ) {
293
+ merge_fields( "field" => select("missing value") )
294
+ }
295
+
296
+ #assert_raises( FormMergeError ) {
297
+ # merge_fields( "field" => ["first", "second"] )
298
+ #}
299
+
300
+ end
301
+
302
+ # -----------------------------------------
303
+ # test checkboxes as booleans
304
+ # -----------------------------------------
305
+
306
+ def test_boolean_checkbox
307
+ html = ""
308
+
309
+ {"first" => true,
310
+ "second" => false,
311
+ "third" => true }.each{ |k, v|
312
+
313
+ html += "<input type=\"checkbox\" name=\"#{k}\"";
314
+ html += " checked" if (v)
315
+ html += ">";
316
+
317
+ }
318
+
319
+ make_form( html )
320
+
321
+ assert_includes( {"first" => [true ],
322
+ "second" => [false],
323
+ "third" => [true ] }, get_fields )
324
+ assert_equal( {"first" => [true ],
325
+ "third" => [true ] }, merge_fields )
326
+
327
+ # how to check a checkbox...
328
+ assert_equal( {"first" => [true ],
329
+ "second" => [true],
330
+ "third" => [true ] },
331
+ merge_fields( "second" => true ) )
332
+
333
+ # how to uncheck a check box
334
+ assert_equal( {"second" => [true],
335
+ "third" => [true ] },
336
+ merge_fields( "first" => false,
337
+ "second" => true ) )
338
+
339
+ end
340
+
341
+ # -----------------------------------------
342
+ # test blending different kinds
343
+ # of elements into the same
344
+ # "field" or "field[]"
345
+ # -----------------------------------------
346
+
347
+ # -----------------------------------------
348
+ # test fields with narflate style names,
349
+ # i.e. "field[1].name" / etc
350
+ # -----------------------------------------
351
+
352
+ end