bluecloth 2.0.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (103) hide show
  1. data/ChangeLog +629 -0
  2. data/LICENSE +27 -0
  3. data/LICENSE.discount +47 -0
  4. data/README +71 -0
  5. data/Rakefile +319 -0
  6. data/Rakefile.local +63 -0
  7. data/bin/bluecloth +84 -0
  8. data/ext/VERSION +1 -0
  9. data/ext/amalloc.h +29 -0
  10. data/ext/bluecloth.c +373 -0
  11. data/ext/config.h +47 -0
  12. data/ext/cstring.h +73 -0
  13. data/ext/docheader.c +43 -0
  14. data/ext/extconf.rb +45 -0
  15. data/ext/generate.c +1387 -0
  16. data/ext/markdown.c +939 -0
  17. data/ext/markdown.h +135 -0
  18. data/ext/mkdio.c +241 -0
  19. data/ext/mkdio.h +66 -0
  20. data/ext/resource.c +169 -0
  21. data/ext/version.c +28 -0
  22. data/lib/bluecloth.rb +148 -0
  23. data/rake/191_compat.rb +26 -0
  24. data/rake/dependencies.rb +76 -0
  25. data/rake/helpers.rb +412 -0
  26. data/rake/manual.rb +782 -0
  27. data/rake/packaging.rb +116 -0
  28. data/rake/publishing.rb +321 -0
  29. data/rake/rdoc.rb +40 -0
  30. data/rake/style.rb +62 -0
  31. data/rake/svn.rb +639 -0
  32. data/rake/testing.rb +204 -0
  33. data/rake/verifytask.rb +64 -0
  34. data/rake/win32.rb +186 -0
  35. data/spec/bluecloth/101_changes_spec.rb +141 -0
  36. data/spec/bluecloth/autolinks_spec.rb +49 -0
  37. data/spec/bluecloth/blockquotes_spec.rb +143 -0
  38. data/spec/bluecloth/code_spans_spec.rb +164 -0
  39. data/spec/bluecloth/emphasis_spec.rb +164 -0
  40. data/spec/bluecloth/entities_spec.rb +65 -0
  41. data/spec/bluecloth/hrules_spec.rb +90 -0
  42. data/spec/bluecloth/images_spec.rb +92 -0
  43. data/spec/bluecloth/inline_html_spec.rb +238 -0
  44. data/spec/bluecloth/links_spec.rb +171 -0
  45. data/spec/bluecloth/lists_spec.rb +294 -0
  46. data/spec/bluecloth/paragraphs_spec.rb +75 -0
  47. data/spec/bluecloth/titles_spec.rb +305 -0
  48. data/spec/bluecloth_spec.rb +209 -0
  49. data/spec/bugfix_spec.rb +123 -0
  50. data/spec/contributions_spec.rb +85 -0
  51. data/spec/data/antsugar.txt +34 -0
  52. data/spec/data/markdowntest/Amps and angle encoding.html +17 -0
  53. data/spec/data/markdowntest/Amps and angle encoding.text +21 -0
  54. data/spec/data/markdowntest/Auto links.html +18 -0
  55. data/spec/data/markdowntest/Auto links.text +13 -0
  56. data/spec/data/markdowntest/Backslash escapes.html +118 -0
  57. data/spec/data/markdowntest/Backslash escapes.text +120 -0
  58. data/spec/data/markdowntest/Blockquotes with code blocks.html +15 -0
  59. data/spec/data/markdowntest/Blockquotes with code blocks.text +11 -0
  60. data/spec/data/markdowntest/Code Blocks.html +18 -0
  61. data/spec/data/markdowntest/Code Blocks.text +14 -0
  62. data/spec/data/markdowntest/Code Spans.html +5 -0
  63. data/spec/data/markdowntest/Code Spans.text +5 -0
  64. data/spec/data/markdowntest/Hard-wrapped paragraphs with list-like lines.html +8 -0
  65. data/spec/data/markdowntest/Hard-wrapped paragraphs with list-like lines.text +8 -0
  66. data/spec/data/markdowntest/Horizontal rules.html +71 -0
  67. data/spec/data/markdowntest/Horizontal rules.text +67 -0
  68. data/spec/data/markdowntest/Inline HTML (Advanced).html +15 -0
  69. data/spec/data/markdowntest/Inline HTML (Advanced).text +15 -0
  70. data/spec/data/markdowntest/Inline HTML (Simple).html +72 -0
  71. data/spec/data/markdowntest/Inline HTML (Simple).text +69 -0
  72. data/spec/data/markdowntest/Inline HTML comments.html +13 -0
  73. data/spec/data/markdowntest/Inline HTML comments.text +13 -0
  74. data/spec/data/markdowntest/Links, inline style.html +11 -0
  75. data/spec/data/markdowntest/Links, inline style.text +12 -0
  76. data/spec/data/markdowntest/Links, reference style.html +52 -0
  77. data/spec/data/markdowntest/Links, reference style.text +71 -0
  78. data/spec/data/markdowntest/Links, shortcut references.html +9 -0
  79. data/spec/data/markdowntest/Links, shortcut references.text +20 -0
  80. data/spec/data/markdowntest/Literal quotes in titles.html +3 -0
  81. data/spec/data/markdowntest/Literal quotes in titles.text +7 -0
  82. data/spec/data/markdowntest/Markdown Documentation - Basics.html +314 -0
  83. data/spec/data/markdowntest/Markdown Documentation - Basics.text +306 -0
  84. data/spec/data/markdowntest/Markdown Documentation - Syntax.html +942 -0
  85. data/spec/data/markdowntest/Markdown Documentation - Syntax.text +888 -0
  86. data/spec/data/markdowntest/Nested blockquotes.html +9 -0
  87. data/spec/data/markdowntest/Nested blockquotes.text +5 -0
  88. data/spec/data/markdowntest/Ordered and unordered lists.html +148 -0
  89. data/spec/data/markdowntest/Ordered and unordered lists.text +131 -0
  90. data/spec/data/markdowntest/Strong and em together.html +7 -0
  91. data/spec/data/markdowntest/Strong and em together.text +7 -0
  92. data/spec/data/markdowntest/Tabs.html +25 -0
  93. data/spec/data/markdowntest/Tabs.text +21 -0
  94. data/spec/data/markdowntest/Tidyness.html +8 -0
  95. data/spec/data/markdowntest/Tidyness.text +5 -0
  96. data/spec/data/ml-announce.txt +17 -0
  97. data/spec/data/re-overflow.txt +67 -0
  98. data/spec/data/re-overflow2.txt +281 -0
  99. data/spec/lib/constants.rb +5 -0
  100. data/spec/lib/helpers.rb +137 -0
  101. data/spec/lib/matchers.rb +235 -0
  102. data/spec/markdowntest_spec.rb +76 -0
  103. metadata +305 -0
@@ -0,0 +1,75 @@
1
+ #!/usr/bin/env ruby
2
+ # encoding: utf-8
3
+
4
+ BEGIN {
5
+ require 'pathname'
6
+ basedir = Pathname.new( __FILE__ ).dirname.parent.parent
7
+
8
+ libdir = basedir + 'lib'
9
+ extdir = basedir + 'ext'
10
+
11
+ $LOAD_PATH.unshift( libdir ) unless $LOAD_PATH.include?( libdir )
12
+ $LOAD_PATH.unshift( extdir ) unless $LOAD_PATH.include?( extdir )
13
+ }
14
+
15
+ require 'spec'
16
+ require 'bluecloth'
17
+
18
+ require 'spec/lib/helpers'
19
+ require 'spec/lib/constants'
20
+ require 'spec/lib/matchers'
21
+
22
+
23
+ #####################################################################
24
+ ### C O N T E X T S
25
+ #####################################################################
26
+
27
+ describe BlueCloth, "document with paragraphs" do
28
+ include BlueCloth::TestConstants,
29
+ BlueCloth::Matchers
30
+
31
+ it "wraps them in P tags" do
32
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
33
+ This is some stuff that should all be
34
+ put in one paragraph
35
+ even though
36
+ it occurs over several lines.
37
+
38
+ And this is a another
39
+ one.
40
+ ---
41
+ <p>This is some stuff that should all be
42
+ put in one paragraph
43
+ even though
44
+ it occurs over several lines.</p>
45
+
46
+ <p>And this is a another
47
+ one.</p>
48
+ ---
49
+ end
50
+
51
+ it "transforms trailing double spaces to line breaks" do
52
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
53
+ Mostly the same kind of thing
54
+ with two spaces at the end
55
+ of each line
56
+ should result in
57
+ line breaks, though.
58
+
59
+ And this is a another
60
+ one.
61
+ ---
62
+ <p>Mostly the same kind of thing<br/>
63
+ with two spaces at the end<br/>
64
+ of each line<br/>
65
+ should result in<br/>
66
+ line breaks, though.</p>
67
+
68
+ <p>And this is a another<br/>
69
+ one.</p>
70
+ ---
71
+ end
72
+
73
+ end
74
+
75
+
@@ -0,0 +1,305 @@
1
+ #!/usr/bin/env ruby
2
+ # encoding: utf-8
3
+
4
+ BEGIN {
5
+ require 'pathname'
6
+ basedir = Pathname.new( __FILE__ ).dirname.parent.parent
7
+
8
+ libdir = basedir + 'lib'
9
+ extdir = basedir + 'ext'
10
+
11
+ $LOAD_PATH.unshift( libdir ) unless $LOAD_PATH.include?( libdir )
12
+ $LOAD_PATH.unshift( extdir ) unless $LOAD_PATH.include?( extdir )
13
+ }
14
+
15
+ require 'spec'
16
+ require 'bluecloth'
17
+
18
+ require 'spec/lib/helpers'
19
+ require 'spec/lib/constants'
20
+ require 'spec/lib/matchers'
21
+
22
+
23
+ #####################################################################
24
+ ### C O N T E X T S
25
+ #####################################################################
26
+
27
+ describe BlueCloth, "titles" do
28
+ include BlueCloth::TestConstants,
29
+ BlueCloth::Matchers
30
+
31
+ # setext-style h1 -- three characters
32
+ it "transforms Setext-style level-one headers (three equals) into an H1" do
33
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
34
+ Title Text
35
+ ===
36
+ ---
37
+ <h1>Title Text</h1>
38
+ ---
39
+ end
40
+
41
+ # setext-style h1 -- match title width
42
+ it "transforms Setext-style level-one headers (more than three equals) into an H1" do
43
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
44
+ Title Text
45
+ ==========
46
+ ---
47
+ <h1>Title Text</h1>
48
+ ---
49
+ end
50
+
51
+
52
+ # setext-style h2 -- one character
53
+ it "transforms Setext-style level-two headers (one dash) into an H2" do
54
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
55
+ Title Text
56
+ -
57
+ ---
58
+ <h2>Title Text</h2>
59
+ ---
60
+ end
61
+
62
+ # setext-style h2 -- three characters
63
+ it "transforms Setext-style level-two headers (three dashes) into an H2" do
64
+ the_indented_markdown( <<-"..." ).should be_transformed_into(<<-"...").without_indentation
65
+ Title Text
66
+ ---
67
+ ...
68
+ <h2>Title Text</h2>
69
+ ...
70
+ end
71
+
72
+ # setext-style h2 -- match title width
73
+ it "transforms Setext-style level-two headers (more than three dashes) into an H2" do
74
+ the_indented_markdown( <<-"..." ).should be_transformed_into(<<-"...").without_indentation
75
+ Title Text
76
+ ----------
77
+ ...
78
+ <h2>Title Text</h2>
79
+ ...
80
+ end
81
+
82
+ # ATX-style h1 -- Left side only
83
+ it "makes a header out of an ATX-style h1 -- Left side only" do
84
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
85
+ # Title Text
86
+ ---
87
+ <h1>Title Text</h1>
88
+ ---
89
+ end
90
+
91
+ # ATX-style h1 -- both sides
92
+ it "makes a header out of an ATX-style h1 -- both sides" do
93
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
94
+ # Title Text #
95
+ ---
96
+ <h1>Title Text</h1>
97
+ ---
98
+ end
99
+
100
+ # ATX-style h1 -- both sides, right side with three characters
101
+ it "makes a header out of an ATX-style h1 -- both sides, right side with three characters" do
102
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
103
+ # Title Text ###
104
+ ---
105
+ <h1>Title Text</h1>
106
+ ---
107
+ end
108
+
109
+ # ATX-style h1 -- both sides, right side with five characters
110
+ it "makes a header out of an ATX-style h1 -- both sides, right side with five characters" do
111
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
112
+ # Title Text #####
113
+ ---
114
+ <h1>Title Text</h1>
115
+ ---
116
+ end
117
+
118
+
119
+ # ATX-style h2 -- left side only
120
+ it "makes a header out of an ATX-style h2 -- left side only" do
121
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
122
+ ## Title Text
123
+ ---
124
+ <h2>Title Text</h2>
125
+ ---
126
+ end
127
+
128
+ # ATX-style h2 -- both sides
129
+ it "makes a header out of an ATX-style h2 -- both sides" do
130
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
131
+ ## Title Text #
132
+ ---
133
+ <h2>Title Text</h2>
134
+ ---
135
+ end
136
+
137
+ # ATX-style h2 -- both sides, right side with three characters
138
+ it "makes a header out of an ATX-style h2 -- both sides, right side with three characters" do
139
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
140
+ ## Title Text ###
141
+ ---
142
+ <h2>Title Text</h2>
143
+ ---
144
+ end
145
+
146
+ # ATX-style h2 -- both sides, right side with five characters
147
+ it "makes a header out of an ATX-style h2 -- both sides, right side with five characters" do
148
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
149
+ ## Title Text #####
150
+ ---
151
+ <h2>Title Text</h2>
152
+ ---
153
+ end
154
+
155
+
156
+ # ATX-style h3 -- left side only
157
+ it "makes a header out of an ATX-style h3 -- left side only" do
158
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
159
+ ### Title Text
160
+ ---
161
+ <h3>Title Text</h3>
162
+ ---
163
+ end
164
+
165
+ # ATX-style h3 -- both sides, right side with one character
166
+ it "makes a header out of an ATX-style h3 -- both sides, right side with one character" do
167
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
168
+ ### Title Text #
169
+ ---
170
+ <h3>Title Text</h3>
171
+ ---
172
+ end
173
+
174
+ # ATX-style h3 -- both sides, right side with three characters
175
+ it "makes a header out of an ATX-style h3 -- both sides, right side with three characters" do
176
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
177
+ ### Title Text ###
178
+ ---
179
+ <h3>Title Text</h3>
180
+ ---
181
+ end
182
+
183
+ # ATX-style h3 -- both sides, right side with five characters
184
+ it "makes a header out of an ATX-style h3 -- both sides, right side with five characters" do
185
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
186
+ ### Title Text #####
187
+ ---
188
+ <h3>Title Text</h3>
189
+ ---
190
+ end
191
+
192
+
193
+ # ATX-style h4 -- left side only
194
+ it "makes a header out of an ATX-style h4 -- left side only" do
195
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
196
+ #### Title Text
197
+ ---
198
+ <h4>Title Text</h4>
199
+ ---
200
+ end
201
+
202
+ # ATX-style h4 -- both sides, right side with one character
203
+ it "makes a header out of an ATX-style h4 -- both sides, right side with one character" do
204
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
205
+ #### Title Text #
206
+ ---
207
+ <h4>Title Text</h4>
208
+ ---
209
+ end
210
+
211
+ # ATX-style h4 -- both sides, right side with three characters
212
+ it "makes a header out of an ATX-style h4 -- both sides, right side with three characters" do
213
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
214
+ #### Title Text ###
215
+ ---
216
+ <h4>Title Text</h4>
217
+ ---
218
+ end
219
+
220
+ # ATX-style h4 -- both sides, right side with five characters
221
+ it "makes a header out of an ATX-style h4 -- both sides, right side with five characters" do
222
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
223
+ #### Title Text #####
224
+ ---
225
+ <h4>Title Text</h4>
226
+ ---
227
+ end
228
+
229
+
230
+ # ATX-style h5 -- left side only
231
+ it "makes a header out of an ATX-style h5 -- left side only" do
232
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
233
+ ##### Title Text
234
+ ---
235
+ <h5>Title Text</h5>
236
+ ---
237
+ end
238
+
239
+ # ATX-style h5 -- both sides, right side with one character
240
+ it "makes a header out of an ATX-style h5 -- both sides, right side with one character" do
241
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
242
+ ##### Title Text #
243
+ ---
244
+ <h5>Title Text</h5>
245
+ ---
246
+ end
247
+
248
+ # ATX-style h5 -- both sides, right side with three characters
249
+ it "makes a header out of an ATX-style h5 -- both sides, right side with three characters" do
250
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
251
+ ##### Title Text ###
252
+ ---
253
+ <h5>Title Text</h5>
254
+ ---
255
+ end
256
+
257
+ # ATX-style h5 -- both sides, right side with five characters
258
+ it "makes a header out of an ATX-style h5 -- both sides, right side with five characters" do
259
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
260
+ ##### Title Text #####
261
+ ---
262
+ <h5>Title Text</h5>
263
+ ---
264
+ end
265
+
266
+
267
+ # ATX-style h6 -- left side only
268
+ it "makes a header out of an ATX-style h6 -- left side only" do
269
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
270
+ ###### Title Text
271
+ ---
272
+ <h6>Title Text</h6>
273
+ ---
274
+ end
275
+
276
+ # ATX-style h6 -- both sides, right side with one character
277
+ it "makes a header out of an ATX-style h6 -- both sides, right side with one character" do
278
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
279
+ ###### Title Text #
280
+ ---
281
+ <h6>Title Text</h6>
282
+ ---
283
+ end
284
+
285
+ # ATX-style h6 -- both sides, right side with three characters
286
+ it "makes a header out of an ATX-style h6 -- both sides, right side with three characters" do
287
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
288
+ ###### Title Text ###
289
+ ---
290
+ <h6>Title Text</h6>
291
+ ---
292
+ end
293
+
294
+ # ATX-style h6 -- both sides, right side with five characters
295
+ it "makes a header out of an ATX-style h6 -- both sides, right side with five characters" do
296
+ the_indented_markdown( <<-"---" ).should be_transformed_into(<<-"---").without_indentation
297
+ ###### Title Text #####
298
+ ---
299
+ <h6>Title Text</h6>
300
+ ---
301
+ end
302
+
303
+ end
304
+
305
+
@@ -0,0 +1,209 @@
1
+ #!/usr/bin/env ruby
2
+ # encoding: utf-8
3
+
4
+ BEGIN {
5
+ require 'pathname'
6
+ basedir = Pathname.new( __FILE__ ).dirname.parent
7
+
8
+ libdir = basedir + 'lib'
9
+ extdir = basedir + 'ext'
10
+
11
+ $LOAD_PATH.unshift( libdir ) unless $LOAD_PATH.include?( libdir )
12
+ $LOAD_PATH.unshift( extdir ) unless $LOAD_PATH.include?( extdir )
13
+ }
14
+
15
+ require 'spec'
16
+ require 'bluecloth'
17
+
18
+ require 'spec/lib/helpers'
19
+ require 'spec/lib/constants'
20
+ require 'spec/lib/matchers'
21
+
22
+
23
+ ### Output some debugging if $DEBUG is true
24
+ def debug_msg( *args )
25
+ $stderr.puts( *args ) if $DEBUG
26
+ end
27
+
28
+
29
+
30
+ #####################################################################
31
+ ### C O N T E X T S
32
+ #####################################################################
33
+
34
+ describe BlueCloth do
35
+ include BlueCloth::TestConstants,
36
+ BlueCloth::Matchers
37
+
38
+
39
+ it "knows what version of Discount was used to build it" do
40
+ BlueCloth.discount_version.should =~ /^\d+\.\d+\.\d+.*RELAXED/
41
+ end
42
+
43
+ it "can build a flags bitmask out of an options hash" do
44
+ flags = BlueCloth.flags_from_opthash(
45
+ :remove_links => true,
46
+ :header_labels => true,
47
+ :pandoc_headers => false
48
+ )
49
+
50
+ ( flags & BlueCloth::MKD_NOLINKS ).should be_nonzero()
51
+ ( flags & BlueCloth::MKD_TOC ).should be_nonzero()
52
+ ( flags & BlueCloth::MKD_NOHEADER ).should be_nonzero()
53
+ end
54
+
55
+
56
+ it "allows output to be rendered several times" do
57
+ bc = BlueCloth.new( "Some text" )
58
+ bc.to_html.should == bc.to_html
59
+ end
60
+
61
+
62
+ it "correctly applies the :remove_links option to the output" do
63
+ input = "An [example](http://url.com/). A <a href='http://example.com/'>link</a>."
64
+ expected = "<p>An [example](http://url.com/). A &lt;a href='http://example.com/'>link</a>.</p>"
65
+
66
+ the_markdown( input, :remove_links => true ).should be_transformed_into( expected )
67
+ end
68
+
69
+ it "correctly applies the :remove_images option to the output" do
70
+ input = %{An ![alt text](/path/img.jpg "Title"). An <img href='http://example.com/1.jpg' />.}
71
+ expected = %{<p>An ![alt text](/path/img.jpg "Title"). An &lt;img href='http://example.com/1.jpg' />.</p>}
72
+
73
+ the_markdown( input, :remove_images => true ).should be_transformed_into( expected )
74
+ end
75
+
76
+ it "correctly applies the :smartypants option to the output" do
77
+ input = %{He was known to frequent that "other establishment"...}
78
+ expected = %{<p>He was known to frequent that &ldquo;other establishment&rdquo;&hellip;</p>}
79
+
80
+ the_markdown( input, :smartypants => true ).should be_transformed_into( expected )
81
+ end
82
+
83
+
84
+ describe "Discount extensions" do
85
+
86
+ it "correctly applies the :pandoc_headers option" do
87
+ input = "% title\n% author1, author2\n% date\n\nStuff."
88
+
89
+ bc = BlueCloth.new( input, :pandoc_headers => true )
90
+ bc.header.should == {
91
+ :title => 'title',
92
+ :author => 'author1, author2',
93
+ :date => 'date'
94
+ }
95
+ bc.to_html.should == '<p>Stuff.</p>'
96
+ end
97
+
98
+ it "correctly expands id: links when :pseudoprotocols are enabled" do
99
+ input = "It was [just as he said](id:foo) it would be."
100
+ expected = %{<p>It was <a id="foo">just as he said</a> it would be.</p>}
101
+
102
+ the_markdown( input, :pseudoprotocols => true ).should be_transformed_into( expected )
103
+ end
104
+
105
+ it "correctly expands class: links when :pseudoprotocols are enabled" do
106
+ input = "It was [just as he said](class:foo) it would be."
107
+ expected = %{<p>It was <span class="foo">just as he said</span> it would be.</p>}
108
+
109
+ the_markdown( input, :pseudoprotocols => true ).should be_transformed_into( expected )
110
+ end
111
+
112
+ it "correctly expands raw: links when :pseudoprotocols are enabled" do
113
+ input = %{I have node idea [what this is for](raw:really "but") it's here.}
114
+ expected = %{<p>I have node idea really it's here.</p>}
115
+
116
+ the_markdown( input, :pseudoprotocols => true ).should be_transformed_into( expected )
117
+ end
118
+
119
+ it "correctly adds IDs to headers when :header_labels is enabled" do
120
+ input = %{# A header\n\nSome stuff\n\n## Another header\n\nMore stuff.\n\n}
121
+ expected = %{<h1 id=\"A+header\">A header</h1>\n\n<p>Some stuff</p>\n\n} +
122
+ %{<h2 id=\"Another+header\">Another header</h2>\n\n<p>More stuff.</p>}
123
+
124
+ the_markdown( input, :header_labels => true ).should be_transformed_into( expected )
125
+ end
126
+
127
+ it "expands superscripts when :strict_mode is disabled" do
128
+ input = %{It used to be that E = mc^2 used to be the province of physicists.}
129
+ expected = %{<p>It used to be that E = mc<sup>2</sup> used to be the province} +
130
+ %{ of physicists.</p>}
131
+ strict = %{<p>It used to be that E = mc^2 used to be the province} +
132
+ %{ of physicists.</p>}
133
+
134
+ the_markdown( input, :strict_mode => false ).should be_transformed_into( expected )
135
+ the_markdown( input, :strict_mode => true ).should be_transformed_into( strict )
136
+ end
137
+
138
+ it "uses relaxed emphasis when :strict_mode is disabled" do
139
+ input = %{If you use size_t instead, you _won't_ have to worry as much about portability.}
140
+ expected = %{<p>If you use size_t instead, you <em>won't</em> have to worry as much about portability.</p>}
141
+ strict = %{<p>If you use size<em>t instead, you </em>won't_ have to worry as much about portability.</p>}
142
+
143
+ the_markdown( input, :strict_mode => false ).should be_transformed_into( expected )
144
+ the_markdown( input, :strict_mode => true ).should be_transformed_into( strict )
145
+ end
146
+
147
+ end
148
+
149
+ ### Test email address output
150
+ describe " email obfuscation" do
151
+ TESTING_EMAILS = %w[
152
+ address@example.com
153
+ foo-list-admin@bar.com
154
+ fu@bar.COM
155
+ baz@ruby-lang.org
156
+ foo-tim-bazzle@bar-hop.co.uk
157
+ littlestar@twinkle.twinkle.band.CO.ZA
158
+ ll@lll.lllll.ll
159
+ Ull@Ulll.Ulllll.ll
160
+ UUUU1@UU1.UU1UUU.UU
161
+ l@ll.ll
162
+ Ull.Ullll@llll.ll
163
+ Ulll-Ull.Ulllll@ll.ll
164
+ 1@111.ll
165
+ ]
166
+ # I can't see a way to handle IDNs clearly yet, so these will have to wait.
167
+ # info@öko.de
168
+ # jemand@büro.de
169
+ # irgendwo-interreßant@dÅgta.se
170
+ #]
171
+
172
+ def decode( str )
173
+ str.gsub( /&#(x[a-f0-9]+|\d{1,3});/i ) do |match|
174
+ code = $1
175
+ debug_msg "Decoding &##{code};"
176
+
177
+ case code
178
+ when /^x([a-f0-9]+)/i
179
+ debug_msg "-> #{$1.to_i(16).chr}"
180
+ $1.to_i(16).chr
181
+ when /^\d+$/
182
+ debug_msg "-> #{code.to_i.chr}"
183
+ code.to_i.chr
184
+ else
185
+ raise "Hmmm... malformed entity %p" % code
186
+ end
187
+ end
188
+ end
189
+
190
+ TESTING_EMAILS.each do |addr|
191
+ it( "obfuscates the email address %p" % addr ) do
192
+ html = BlueCloth.new( "<#{addr}>" ).to_html
193
+
194
+ expected_output = %r{<p><a href="([^"]+)">[^<]+</a></p>}
195
+ match = expected_output.match( html )
196
+ match.should be_an_instance_of( MatchData )
197
+
198
+ match[1].should_not == addr
199
+
200
+ decoded_href = decode( match[1] )
201
+ debug_msg "Unencoded href = %p" % [ decoded_href ]
202
+ decoded_href.should == "mailto:#{addr}"
203
+ end
204
+ end
205
+ end
206
+
207
+ end
208
+
209
+ # vim: set nosta noet ts=4 sw=4: