1
# -*- coding: iso-8859-1 -*-
3
MoinMoin - MoinMoin.parser.wiki Tests
5
TODO: these are actually parser+formatter tests. We should have
6
parser only tests here.
8
@copyright: 2003-2004 by J�rgen Hermann <jh@web.de>
9
@license: GNU GPL, see COPYING for details.
14
from StringIO import StringIO
15
from MoinMoin._tests import TestConfig
16
from MoinMoin.Page import Page
17
from MoinMoin.parser.wiki import Parser
20
class ParserTestCase(unittest.TestCase):
21
""" Helper class that provide a parsing method """
23
def parse(self, body):
24
"""Parse body and return html
26
Create a page with body, then parse it and format using html formatter
28
assert body is not None
30
page = Page(self.request, 'ThisPageDoesNotExistsAndWillNeverBeReally')
31
page.set_raw_body(body)
32
from MoinMoin.formatter.text_html import Formatter
33
page.formatter = Formatter(self.request)
34
self.request.formatter = page.formatter
35
page.formatter.setPage(page)
39
saved_write = self.request.write
40
self.request.write = output.write
42
Parser(body, self.request).format(page.formatter)
44
self.request.write = saved_write
45
return output.getvalue()
48
class ParagraphsTestCase(ParserTestCase):
49
""" Test paragraphs creating
51
All tests ignoring white space in output
54
def testFirstParagraph(self):
55
""" parser.wiki: first paragraph should be in <p> """
56
result = self.parse('First')
57
expected = re.compile(r'<p>\s*First\s*</p>')
58
self.assert_(expected.search(result),
59
'"%s" not in "%s"' % (expected.pattern, result))
61
def testEmptyLineBetweenParagraphs(self):
62
""" parser.wiki: empty line separates paragraphs """
63
result = self.parse('First\n\nSecond')
64
expected = re.compile(r'<p>\s*Second\s*</p>')
65
self.assert_(expected.search(result),
66
'"%s" not in "%s"' % (expected.pattern, result))
68
def testParagraphAfterBlockMarkup(self):
69
""" parser.wiki: create paragraph after block markup """
77
'=== heading 3 ===\n',
78
'==== heading 4 ====\n',
79
'===== heading 5 =====\n',
82
text = item + 'Paragraph'
83
result = self.parse(text)
84
expected = re.compile(r'<p.*?>\s*Paragraph\s*</p>')
85
self.assert_(expected.search(result),
86
'"%s" not in "%s"' % (expected.pattern, result))
89
class HeadingsTestCase(ParserTestCase):
90
""" Test various heading problems """
93
""" Require show_section_numbers = 0 to workaround counter
94
global state saved in request.
96
self.config = TestConfig(self.request, show_section_numbers=0)
101
def testIgnoreWhiteSpaceAroundHeadingText(self):
102
""" parser.wiki: ignore white space around heading text
104
See bug: TableOfContentsBreakOnExtraSpaces.
106
Does not test mapping of '=' to h number, or valid html markup.
109
'= head =\n', # leading
110
'= head =\n', # trailing
113
expected = self.parse('= head =')
115
result = self.parse(test)
116
self.assertEqual(result, expected,
117
'Expected "%(expected)s" but got "%(result)s"' % locals())
120
class TOCTestCase(ParserTestCase):
123
""" Require show_section_numbers = 0 to workaround counter
124
global state saved in request.
126
self.config = TestConfig(self.request, show_section_numbers=0)
131
def testHeadingWithWhiteSpace(self):
132
""" parser.wiki: TOC links to headings with white space
134
See bug: TableOfContentsBreakOnExtraSpaces.
136
Does not test TOC or heading formating, just verify that spaces
137
around heading text does not matter.
149
expected = self.parse(standard)
150
result = self.parse(withWhitespace)
151
self.assertEqual(result, expected,
152
'Expected "%(expected)s" but got "%(result)s"' % locals())
155
class DateTimeMacroTestCase(ParserTestCase):
156
""" Test DateTime macro
158
Might fail due to libc problems, therefore the fail message warn
161
TODO: when this test fail, does it mean that moin code fail on that
162
machine? - can we fix this?
166
needle = re.compile(text % r'(.+)')
169
('[[DateTime(1970-01-06T00:00:00)]]', '1970-01-06 00:00:00'),
170
('[[DateTime(259200)]]', '1970-01-04 00:00:00'),
171
('[[DateTime(2003-03-03T03:03:03)]]', '2003-03-03 03:03:03'),
172
('[[DateTime(2000-01-01T00:00:00Z)]]', '2000-01-01 00:00:00'),
173
('[[Date(2002-02-02T01:02:03Z)]]', '2002-02-02'),
177
""" Require default date and time format config values """
178
self.config = TestConfig(self.request,
179
defaults=('date_fmt', 'datetime_fmt'))
184
def testDateTimeMacro(self):
185
""" parser.wiki: DateTime macro """
188
If this fails, it is likely a problem in your python / libc,
189
not in moin. See also:
190
<http://sourceforge.net/tracker/index.php?func=detail&
191
aid=902172&group_id=5470&atid=105470>"""
193
for test, expected in self._tests:
194
html = self.parse(self.text % test)
195
result = self.needle.search(html).group(1)
196
self.assertEqual(result, expected,
197
'Expected "%(expected)s" but got "%(result)s"; %(note)s' % locals())
200
class TextFormatingTestCase(ParserTestCase):
201
""" Test wiki markup """
204
needle = re.compile(text % r'(.+)')
207
('no format', 'no format'),
208
("''em''", '<em>em</em>'),
209
("'''bold'''", '<strong>bold</strong>'),
210
("__underline__", '<span class="u">underline</span>'),
211
("'''''Mix''' at start''", '<em><strong>Mix</strong> at start</em>'),
212
("'''''Mix'' at start'''", '<strong><em>Mix</em> at start</strong>'),
213
("'''Mix at ''end'''''", '<strong>Mix at <em>end</em></strong>'),
214
("''Mix at '''end'''''", '<em>Mix at <strong>end</strong></em>'),
217
def testTextFormating(self):
218
""" parser.wiki: text formating """
219
for test, expected in self._tests:
220
html = self.parse(self.text % test)
221
result = self.needle.search(html).group(1)
222
self.assertEqual(result, expected,
223
'Expected "%(expected)s" but got "%(result)s"' % locals())
226
class CloseInlineTestCase(ParserTestCase):
228
def testCloseOneInline(self):
229
""" parser.wiki: close open inline tag when block close """
232
("text'''text\n", r"<p>text<strong>text\s*</strong></p>"),
233
("text''text\n", r"<p>text<em>text\s*</em></p>"),
234
("text__text\n", r"<p>text<span class=\"u\">text\s*</span></p>"),
235
("text ''em '''em strong __em strong underline",
236
r"text <em>em <strong>em strong <span class=\"u\">em strong underline"
237
r"\s*</span></strong></em></p>"),
239
for test, expected in cases:
240
needle = re.compile(expected)
241
result = self.parse(test)
242
self.assert_(needle.search(result),
243
'Expected "%(expected)s" but got "%(result)s"' % locals())
246
class InlineCrossingTestCase(ParserTestCase):
248
This test case fail with current parser/formatter and should be fixed in 2.0
251
def disabled_testInlineCrossing(self):
252
""" parser.wiki: prevent inline crossing <a><b></a></b> """
254
expected = ("<p><em>a<strong>ab</strong></em><strong>b</strong>\s*</p>")
255
test = "''a'''ab''b'''\n"
256
needle = re.compile(expected)
257
result = self.parse(test)
258
self.assert_(needle.search(result),
259
'Expected "%(expected)s" but got "%(result)s"' % locals())
262
class EscapeHTMLTestCase(ParserTestCase):
264
def testEscapeInTT(self):
265
""" parser.wiki: escape html markup in `tt` """
266
test = 'text `<escape-me>` text\n'
269
def testEscapeInTT2(self):
270
""" parser.wiki: escape html markup in {{{tt}}} """
271
test = 'text {{{<escape-me>}}} text\n'
274
def testEscapeInPre(self):
275
""" parser.wiki: escape html markup in pre """
282
def testEscapeInPreHashbang(self):
283
""" parser.wiki: escape html markup in pre with hashbang """
290
def testEscapeInPythonCodeArea(self):
291
""" parser.wiki: escape html markup in python code area """
292
test = '''{{{#!python
298
def testEscapeInGetTextMacro(self):
299
""" parser.wiki: escape html markup in GetText macro """
300
test = "text [[GetText(<escape-me>)]] text"
303
def testEscapeInGetTextFormatted(self):
304
""" parser.wiki: escape html markup in getText formatted call """
305
test = self.request.getText('<escape-me>', formatted=1)
308
def testEscapeInGetTextFormatedLink(self):
309
""" parser.wiki: escape html markup in getText formatted call with link """
310
test = self.request.getText('["<escape-me>"]', formatted=1)
313
def testEscapeInGetTextUnFormatted(self):
314
""" parser.wiki: escape html markup in getText non formatted call """
315
test = self.request.getText('<escape-me>', formatted=0)
318
def _test(self, test):
319
expected = r'<escape-me>'
320
result = self.parse(test)
321
self.assert_(re.search(expected, result),
322
'Expected "%(expected)s" but got "%(result)s"' % locals())
325
class EscapeWikiTableMarkupTestCase(ParserTestCase):
327
def testEscapeInTT(self):
328
""" parser.wiki: escape wiki table markup in `tt` """
329
test = 'text `||<tablewidth="80"> Table ||` text\n'
332
def testEscapeInTT2(self):
333
""" parser.wiki: escape wiki table markup in {{{tt}}} """
334
test = 'text {{{||<tablewidth="80"> Table ||}}} text\n'
337
def testEscapeInPre(self):
338
""" parser.wiki: escape wiki table markup in pre """
340
||<tablewidth="80"> Table ||
345
def testEscapeInPreHashbang(self):
346
""" parser.wiki: escape wiki table markup in pre with hashbang """
348
||<tablewidth="80"> Table ||
353
def testEscapeInPythonCodeArea(self):
354
""" parser.wiki: escape wiki table markup in python code area """
355
test = '''{{{#!python
356
# ||<tablewidth="80"> Table ||
362
expected = r'<tablewidth="80">'
363
result = self.parse(test)
364
self.assert_(re.search(expected, result),
365
'Expected "%(expected)s" but got "%(result)s"' % locals())
368
class RuleTestCase(ParserTestCase):
369
""" Test rules markup """
371
def testNotRule(self):
372
""" parser.wiki: --- is no rule """
373
result = self.parse('---')
374
expected = '---' # inside <p>
375
self.assert_(expected in result,
376
'Expected "%(expected)s" but got "%(result)s"' % locals())
378
def testStandardRule(self):
379
""" parser.wiki: ---- is standard rule """
380
result = self.parse('----')
382
self.assert_(expected in result,
383
'Expected "%(expected)s" but got "%(result)s"' % locals())
385
def testVariableRule(self):
386
""" parser.wiki: ----- rules with size """
388
for size in range(5, 11):
390
result = self.parse(test)
391
expected = '<hr class="hr%d">' % (size - 4)
392
self.assert_(expected in result,
393
'Expected "%(expected)s" but got "%(result)s"' % locals())
395
def testLongRule(self):
396
""" parser.wiki: ------------ long rule shortened to hr6 """
398
result = self.parse(test)
399
expected = '<hr class="hr6">'
400
self.assert_(expected in result,
401
'Expected "%(expected)s" but got "%(result)s"' % locals())
404
class BlockTestCase(ParserTestCase):
408
('= Heading =\n', '<h2'),
409
('{{{\nPre\n}}}\n', '<pre'),
410
('{{{\n#!python\nPre\n}}}\n', '<div'),
411
('|| Table ||', '<div'),
412
(' * unordered list\n', '<ul'),
413
(' 1. ordered list\n', '<ol'),
414
(' indented text\n', '<ul'),
417
def testParagraphBeforeBlock(self):
418
""" parser.wiki: paragraph closed before block element """
422
for test, blockstart in self.cases:
423
# We dont test here formatter white space generation
424
expected = r'<p>XXX\s*</p>\n+%s' % blockstart
425
needle = re.compile(expected, re.MULTILINE)
426
result = self.parse(text % test)
427
match = needle.search(result)
428
self.assert_(match is not None,
429
'Expected "%(expected)s" but got "%(result)s"' % locals())
431
def testEmptyLineBeforeBlock(self):
432
""" parser.wiki: empty lines before block element ignored
434
Empty lines separate paragraphs, but should be ignored if a block
437
Currently an empty paragraph is created, which make no sense but
444
for test, blockstart in self.cases:
445
expected = r'<p>XXX\s*</p>\n+%s' % blockstart
446
needle = re.compile(expected, re.MULTILINE)
447
result = self.parse(text % test)
448
match = needle.search(result)
449
self.assert_(match is not None,
450
'Expected "%(expected)s" but got "%(result)s"' % locals())