annotate mercurial/minirst.py @ 15078:193e7018dc8c

hg: extract copying the store out of clone
author Simon Heimberg <simohe@besonet.ch>
date Thu, 11 Aug 2011 00:03:16 +0200
parents c981f4a9ea74
children a7e375d087f6
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
1 # minirst.py - minimal reStructuredText parser
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
2 #
10443
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
3 # Copyright 2009, 2010 Matt Mackall <mpm@selenic.com> and others
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
4 #
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
5 # This software may be used and distributed according to the terms of the
10263
25e572394f5c Update license to GPLv2+
Matt Mackall <mpm@selenic.com>
parents: 9741
diff changeset
6 # GNU General Public License version 2 or any later version.
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
7
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
8 """simplified reStructuredText parser.
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
9
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
10 This parser knows just enough about reStructuredText to parse the
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
11 Mercurial docstrings.
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
12
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
13 It cheats in a major way: nested blocks are not really nested. They
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
14 are just indented blocks that look like they are nested. This relies
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
15 on the user to keep the right indentation for the blocks.
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
16
12958
8957c39867f6 minirst: link to HelpStyleGuide in docstring
Martin Geisler <mg@aragost.com>
parents: 12867
diff changeset
17 Remember to update http://mercurial.selenic.com/wiki/HelpStyleGuide
8957c39867f6 minirst: link to HelpStyleGuide in docstring
Martin Geisler <mg@aragost.com>
parents: 12867
diff changeset
18 when adding support for new constructs.
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
19 """
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
20
15038
3f4d337cb80a minirst: drop debug code
Matt Mackall <mpm@selenic.com>
parents: 15037
diff changeset
21 import re
11464
521c8e0c93bf minirst: use unicode string as intermediate form for replacement
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11297
diff changeset
22 import util, encoding
12388
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
23 from i18n import _
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
24
11464
521c8e0c93bf minirst: use unicode string as intermediate form for replacement
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11297
diff changeset
25
521c8e0c93bf minirst: use unicode string as intermediate form for replacement
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11297
diff changeset
26 def replace(text, substs):
521c8e0c93bf minirst: use unicode string as intermediate form for replacement
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11297
diff changeset
27 utext = text.decode(encoding.encoding)
521c8e0c93bf minirst: use unicode string as intermediate form for replacement
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11297
diff changeset
28 for f, t in substs:
521c8e0c93bf minirst: use unicode string as intermediate form for replacement
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11297
diff changeset
29 utext = utext.replace(f, t)
521c8e0c93bf minirst: use unicode string as intermediate form for replacement
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11297
diff changeset
30 return utext.encode(encoding.encoding)
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
31
12651
17f28de168a4 minirst: refactor/simplify findblocks
Martin Geisler <mg@lazybytes.net>
parents: 12620
diff changeset
32
17f28de168a4 minirst: refactor/simplify findblocks
Martin Geisler <mg@lazybytes.net>
parents: 12620
diff changeset
33 _blockre = re.compile(r"\n(?:\s*\n)+")
17f28de168a4 minirst: refactor/simplify findblocks
Martin Geisler <mg@lazybytes.net>
parents: 12620
diff changeset
34
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
35 def findblocks(text):
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
36 """Find continuous blocks of lines in text.
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
37
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
38 Returns a list of dictionaries representing the blocks. Each block
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
39 has an 'indent' field and a 'lines' field.
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
40 """
12651
17f28de168a4 minirst: refactor/simplify findblocks
Martin Geisler <mg@lazybytes.net>
parents: 12620
diff changeset
41 blocks = []
15036
bb96e12a3242 minirst: only strip leading newlines, not indentation
Matt Mackall <mpm@selenic.com>
parents: 15015
diff changeset
42 for b in _blockre.split(text.lstrip('\n').rstrip()):
12651
17f28de168a4 minirst: refactor/simplify findblocks
Martin Geisler <mg@lazybytes.net>
parents: 12620
diff changeset
43 lines = b.splitlines()
17f28de168a4 minirst: refactor/simplify findblocks
Martin Geisler <mg@lazybytes.net>
parents: 12620
diff changeset
44 indent = min((len(l) - len(l.lstrip())) for l in lines)
17f28de168a4 minirst: refactor/simplify findblocks
Martin Geisler <mg@lazybytes.net>
parents: 12620
diff changeset
45 lines = [l[indent:] for l in lines]
17f28de168a4 minirst: refactor/simplify findblocks
Martin Geisler <mg@lazybytes.net>
parents: 12620
diff changeset
46 blocks.append(dict(indent=indent, lines=lines))
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
47 return blocks
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
48
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
49
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
50 def findliteralblocks(blocks):
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
51 """Finds literal blocks and adds a 'type' field to the blocks.
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
52
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
53 Literal blocks are given the type 'literal', all other blocks are
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
54 given type the 'paragraph'.
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
55 """
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
56 i = 0
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
57 while i < len(blocks):
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
58 # Searching for a block that looks like this:
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
59 #
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
60 # +------------------------------+
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
61 # | paragraph |
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
62 # | (ends with "::") |
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
63 # +------------------------------+
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
64 # +---------------------------+
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
65 # | indented literal block |
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
66 # +---------------------------+
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
67 blocks[i]['type'] = 'paragraph'
10282
08a0f04b56bd many, many trivial check-code fixups
Matt Mackall <mpm@selenic.com>
parents: 10264
diff changeset
68 if blocks[i]['lines'][-1].endswith('::') and i + 1 < len(blocks):
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
69 indent = blocks[i]['indent']
10282
08a0f04b56bd many, many trivial check-code fixups
Matt Mackall <mpm@selenic.com>
parents: 10264
diff changeset
70 adjustment = blocks[i + 1]['indent'] - indent
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
71
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
72 if blocks[i]['lines'] == ['::']:
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
73 # Expanded form: remove block
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
74 del blocks[i]
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
75 i -= 1
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
76 elif blocks[i]['lines'][-1].endswith(' ::'):
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
77 # Partially minimized form: remove space and both
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
78 # colons.
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
79 blocks[i]['lines'][-1] = blocks[i]['lines'][-1][:-3]
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
80 else:
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
81 # Fully minimized form: remove just one colon.
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
82 blocks[i]['lines'][-1] = blocks[i]['lines'][-1][:-1]
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
83
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
84 # List items are formatted with a hanging indent. We must
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
85 # correct for this here while we still have the original
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
86 # information on the indentation of the subsequent literal
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
87 # blocks available.
9738
f52c4f7a4732 minirst: prepare for general types of bullet lists
Martin Geisler <mg@lazybytes.net>
parents: 9737
diff changeset
88 m = _bulletre.match(blocks[i]['lines'][0])
f52c4f7a4732 minirst: prepare for general types of bullet lists
Martin Geisler <mg@lazybytes.net>
parents: 9737
diff changeset
89 if m:
f52c4f7a4732 minirst: prepare for general types of bullet lists
Martin Geisler <mg@lazybytes.net>
parents: 9737
diff changeset
90 indent += m.end()
f52c4f7a4732 minirst: prepare for general types of bullet lists
Martin Geisler <mg@lazybytes.net>
parents: 9737
diff changeset
91 adjustment -= m.end()
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
92
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
93 # Mark the following indented blocks.
10282
08a0f04b56bd many, many trivial check-code fixups
Matt Mackall <mpm@selenic.com>
parents: 10264
diff changeset
94 while i + 1 < len(blocks) and blocks[i + 1]['indent'] > indent:
08a0f04b56bd many, many trivial check-code fixups
Matt Mackall <mpm@selenic.com>
parents: 10264
diff changeset
95 blocks[i + 1]['type'] = 'literal'
08a0f04b56bd many, many trivial check-code fixups
Matt Mackall <mpm@selenic.com>
parents: 10264
diff changeset
96 blocks[i + 1]['indent'] -= adjustment
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
97 i += 1
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
98 i += 1
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
99 return blocks
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
100
10447
e957cc7cbd14 minirst: support line blocks
Martin Geisler <mg@lazybytes.net>
parents: 10444
diff changeset
101 _bulletre = re.compile(r'(-|[0-9A-Za-z]+\.|\(?[0-9A-Za-z]+\)|\|) ')
13011
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
102 _optionre = re.compile(r'^(-([a-zA-Z0-9]), )?(--[a-z0-9-]+)'
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
103 r'((.*) +)(.*)$')
10065
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
104 _fieldre = re.compile(r':(?![: ])([^:]*)(?<! ):[ ]+(.*)')
9737
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
105 _definitionre = re.compile(r'[^ ]')
15037
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
106 _tablere = re.compile(r'(=+\s+)*=+')
9737
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
107
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
108 def splitparagraphs(blocks):
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
109 """Split paragraphs into lists."""
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
110 # Tuples with (list type, item regexp, single line items?). Order
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
111 # matters: definition lists has the least specific regexp and must
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
112 # come last.
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
113 listtypes = [('bullet', _bulletre, True),
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
114 ('option', _optionre, True),
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
115 ('field', _fieldre, True),
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
116 ('definition', _definitionre, False)]
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
117
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
118 def match(lines, i, itemre, singleline):
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
119 """Does itemre match an item at line i?
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
120
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
121 A list item can be followed by an idented line or another list
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
122 item (but only if singleline is True).
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
123 """
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
124 line1 = lines[i]
10282
08a0f04b56bd many, many trivial check-code fixups
Matt Mackall <mpm@selenic.com>
parents: 10264
diff changeset
125 line2 = i + 1 < len(lines) and lines[i + 1] or ''
9737
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
126 if not itemre.match(line1):
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
127 return False
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
128 if singleline:
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
129 return line2 == '' or line2[0] == ' ' or itemre.match(line2)
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
130 else:
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
131 return line2.startswith(' ')
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
132
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
133 i = 0
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
134 while i < len(blocks):
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
135 if blocks[i]['type'] == 'paragraph':
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
136 lines = blocks[i]['lines']
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
137 for type, itemre, singleline in listtypes:
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
138 if match(lines, 0, itemre, singleline):
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
139 items = []
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
140 for j, line in enumerate(lines):
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
141 if match(lines, j, itemre, singleline):
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
142 items.append(dict(type=type, lines=[],
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
143 indent=blocks[i]['indent']))
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
144 items[-1]['lines'].append(line)
10282
08a0f04b56bd many, many trivial check-code fixups
Matt Mackall <mpm@selenic.com>
parents: 10264
diff changeset
145 blocks[i:i + 1] = items
9737
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
146 break
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
147 i += 1
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
148 return blocks
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
149
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
150
10065
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
151 _fieldwidth = 12
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
152
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
153 def updatefieldlists(blocks):
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
154 """Find key and maximum key width for field lists."""
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
155 i = 0
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
156 while i < len(blocks):
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
157 if blocks[i]['type'] != 'field':
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
158 i += 1
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
159 continue
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
160
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
161 keywidth = 0
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
162 j = i
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
163 while j < len(blocks) and blocks[j]['type'] == 'field':
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
164 m = _fieldre.match(blocks[j]['lines'][0])
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
165 key, rest = m.groups()
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
166 blocks[j]['lines'][0] = rest
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
167 blocks[j]['key'] = key
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
168 keywidth = max(keywidth, len(key))
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
169 j += 1
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
170
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
171 for block in blocks[i:j]:
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
172 block['keywidth'] = keywidth
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
173 i = j + 1
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
174
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
175 return blocks
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
176
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
177
13011
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
178 def updateoptionlists(blocks):
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
179 i = 0
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
180 while i < len(blocks):
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
181 if blocks[i]['type'] != 'option':
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
182 i += 1
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
183 continue
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
184
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
185 optstrwidth = 0
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
186 j = i
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
187 while j < len(blocks) and blocks[j]['type'] == 'option':
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
188 m = _optionre.match(blocks[j]['lines'][0])
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
189
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
190 shortoption = m.group(2)
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
191 group3 = m.group(3)
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
192 longoption = group3[2:].strip()
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
193 desc = m.group(6).strip()
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
194 longoptionarg = m.group(5).strip()
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
195 blocks[j]['lines'][0] = desc
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
196
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
197 noshortop = ''
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
198 if not shortoption:
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
199 noshortop = ' '
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
200
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
201 opt = "%s%s" % (shortoption and "-%s " % shortoption or '',
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
202 ("%s--%s %s") % (noshortop, longoption,
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
203 longoptionarg))
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
204 opt = opt.rstrip()
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
205 blocks[j]['optstr'] = opt
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
206 optstrwidth = max(optstrwidth, encoding.colwidth(opt))
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
207 j += 1
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
208
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
209 for block in blocks[i:j]:
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
210 block['optstrwidth'] = optstrwidth
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
211 i = j + 1
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
212 return blocks
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
213
10443
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
214 def prunecontainers(blocks, keep):
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
215 """Prune unwanted containers.
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
216
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
217 The blocks must have a 'type' field, i.e., they should have been
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
218 run through findliteralblocks first.
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
219 """
10444
e99e0e077bc4 minirst: report pruned container types
Martin Geisler <mg@lazybytes.net>
parents: 10443
diff changeset
220 pruned = []
10443
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
221 i = 0
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
222 while i + 1 < len(blocks):
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
223 # Searching for a block that looks like this:
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
224 #
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
225 # +-------+---------------------------+
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
226 # | ".. container ::" type |
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
227 # +---+ |
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
228 # | blocks |
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
229 # +-------------------------------+
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
230 if (blocks[i]['type'] == 'paragraph' and
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
231 blocks[i]['lines'][0].startswith('.. container::')):
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
232 indent = blocks[i]['indent']
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
233 adjustment = blocks[i + 1]['indent'] - indent
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
234 containertype = blocks[i]['lines'][0][15:]
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
235 prune = containertype not in keep
10444
e99e0e077bc4 minirst: report pruned container types
Martin Geisler <mg@lazybytes.net>
parents: 10443
diff changeset
236 if prune:
e99e0e077bc4 minirst: report pruned container types
Martin Geisler <mg@lazybytes.net>
parents: 10443
diff changeset
237 pruned.append(containertype)
10443
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
238
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
239 # Always delete "..container:: type" block
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
240 del blocks[i]
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
241 j = i
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
242 while j < len(blocks) and blocks[j]['indent'] > indent:
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
243 if prune:
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
244 del blocks[j]
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
245 i -= 1 # adjust outer index
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
246 else:
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
247 blocks[j]['indent'] -= adjustment
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
248 j += 1
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
249 i += 1
10444
e99e0e077bc4 minirst: report pruned container types
Martin Geisler <mg@lazybytes.net>
parents: 10443
diff changeset
250 return blocks, pruned
10443
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
251
62d484a81dfe minirst: support containers
Martin Geisler <mg@lazybytes.net>
parents: 10282
diff changeset
252
10984
68b7d2d668ce minirst: support all recommended title adornments
Martin Geisler <mg@lazybytes.net>
parents: 10983
diff changeset
253 _sectionre = re.compile(r"""^([-=`:.'"~^_*+#])\1+$""")
68b7d2d668ce minirst: support all recommended title adornments
Martin Geisler <mg@lazybytes.net>
parents: 10983
diff changeset
254
15037
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
255 def findtables(blocks):
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
256 '''Find simple tables
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
257
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
258 Only simple one-line table elements are supported
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
259 '''
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
260
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
261 for block in blocks:
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
262 # Searching for a block that looks like this:
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
263 #
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
264 # === ==== ===
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
265 # A B C
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
266 # === ==== === <- optional
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
267 # 1 2 3
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
268 # x y z
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
269 # === ==== ===
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
270 if (block['type'] == 'paragraph' and
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
271 len(block['lines']) > 4 and
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
272 _tablere.match(block['lines'][0]) and
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
273 block['lines'][0] == block['lines'][-1]):
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
274 block['type'] = 'table'
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
275 block['header'] = False
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
276 div = block['lines'][0]
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
277 columns = [x for x in xrange(len(div))
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
278 if div[x] == '=' and (x == 0 or div[x - 1] == ' ')]
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
279 rows = []
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
280 for l in block['lines'][1:-1]:
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
281 if l == div:
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
282 block['header'] = True
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
283 continue
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
284 row = []
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
285 for n, start in enumerate(columns):
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
286 if n + 1 < len(columns):
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
287 row.append(l[start:columns[n + 1]].strip())
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
288 else:
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
289 row.append(l[start:].strip())
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
290 rows.append(row)
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
291 block['table'] = rows
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
292
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
293 return blocks
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
294
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
295 def findsections(blocks):
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
296 """Finds sections.
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
297
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
298 The blocks must have a 'type' field, i.e., they should have been
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
299 run through findliteralblocks first.
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
300 """
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
301 for block in blocks:
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
302 # Searching for a block that looks like this:
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
303 #
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
304 # +------------------------------+
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
305 # | Section title |
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
306 # | ------------- |
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
307 # +------------------------------+
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
308 if (block['type'] == 'paragraph' and
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
309 len(block['lines']) == 2 and
12867
eda77c3e246a minirst: use colwidth to match title lengths (issue2455)
Matt Mackall <mpm@selenic.com>
parents: 12819
diff changeset
310 encoding.colwidth(block['lines'][0]) == len(block['lines'][1]) and
10984
68b7d2d668ce minirst: support all recommended title adornments
Martin Geisler <mg@lazybytes.net>
parents: 10983
diff changeset
311 _sectionre.match(block['lines'][1])):
10983
287a5cdf7743 minirst: correctly format sections containing inline markup
Martin Geisler <mg@lazybytes.net>
parents: 10972
diff changeset
312 block['underline'] = block['lines'][1][0]
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
313 block['type'] = 'section'
10983
287a5cdf7743 minirst: correctly format sections containing inline markup
Martin Geisler <mg@lazybytes.net>
parents: 10972
diff changeset
314 del block['lines'][1]
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
315 return blocks
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
316
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
317
9623
32727ce029de minirst: convert ``foo`` into "foo" upon display
Martin Geisler <mg@lazybytes.net>
parents: 9540
diff changeset
318 def inlineliterals(blocks):
11464
521c8e0c93bf minirst: use unicode string as intermediate form for replacement
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11297
diff changeset
319 substs = [('``', '"')]
9623
32727ce029de minirst: convert ``foo`` into "foo" upon display
Martin Geisler <mg@lazybytes.net>
parents: 9540
diff changeset
320 for b in blocks:
10983
287a5cdf7743 minirst: correctly format sections containing inline markup
Martin Geisler <mg@lazybytes.net>
parents: 10972
diff changeset
321 if b['type'] in ('paragraph', 'section'):
11464
521c8e0c93bf minirst: use unicode string as intermediate form for replacement
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11297
diff changeset
322 b['lines'] = [replace(l, substs) for l in b['lines']]
9623
32727ce029de minirst: convert ``foo`` into "foo" upon display
Martin Geisler <mg@lazybytes.net>
parents: 9540
diff changeset
323 return blocks
32727ce029de minirst: convert ``foo`` into "foo" upon display
Martin Geisler <mg@lazybytes.net>
parents: 9540
diff changeset
324
32727ce029de minirst: convert ``foo`` into "foo" upon display
Martin Geisler <mg@lazybytes.net>
parents: 9540
diff changeset
325
10972
0a2c6948f5f4 doc, minirst: support hg interpreted text role
Martin Geisler <mg@aragost.com>
parents: 10937
diff changeset
326 def hgrole(blocks):
11464
521c8e0c93bf minirst: use unicode string as intermediate form for replacement
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11297
diff changeset
327 substs = [(':hg:`', '"hg '), ('`', '"')]
10972
0a2c6948f5f4 doc, minirst: support hg interpreted text role
Martin Geisler <mg@aragost.com>
parents: 10937
diff changeset
328 for b in blocks:
10983
287a5cdf7743 minirst: correctly format sections containing inline markup
Martin Geisler <mg@lazybytes.net>
parents: 10972
diff changeset
329 if b['type'] in ('paragraph', 'section'):
11192
babf9a5f5528 minirst: handle line breaks in hg role
Martin Geisler <mg@aragost.com>
parents: 11189
diff changeset
330 # Turn :hg:`command` into "hg command". This also works
babf9a5f5528 minirst: handle line breaks in hg role
Martin Geisler <mg@aragost.com>
parents: 11189
diff changeset
331 # when there is a line break in the command and relies on
babf9a5f5528 minirst: handle line breaks in hg role
Martin Geisler <mg@aragost.com>
parents: 11189
diff changeset
332 # the fact that we have no stray back-quotes in the input
babf9a5f5528 minirst: handle line breaks in hg role
Martin Geisler <mg@aragost.com>
parents: 11189
diff changeset
333 # (run the blocks through inlineliterals first).
11464
521c8e0c93bf minirst: use unicode string as intermediate form for replacement
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11297
diff changeset
334 b['lines'] = [replace(l, substs) for l in b['lines']]
10972
0a2c6948f5f4 doc, minirst: support hg interpreted text role
Martin Geisler <mg@aragost.com>
parents: 10937
diff changeset
335 return blocks
0a2c6948f5f4 doc, minirst: support hg interpreted text role
Martin Geisler <mg@aragost.com>
parents: 10937
diff changeset
336
0a2c6948f5f4 doc, minirst: support hg interpreted text role
Martin Geisler <mg@aragost.com>
parents: 10937
diff changeset
337
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
338 def addmargins(blocks):
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
339 """Adds empty blocks for vertical spacing.
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
340
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
341 This groups bullets, options, and definitions together with no vertical
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
342 space between them, and adds an empty block between all other blocks.
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
343 """
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
344 i = 1
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
345 while i < len(blocks):
10282
08a0f04b56bd many, many trivial check-code fixups
Matt Mackall <mpm@selenic.com>
parents: 10264
diff changeset
346 if (blocks[i]['type'] == blocks[i - 1]['type'] and
10936
2853c891ac41 minirst: add margin around definition items
Martin Geisler <mg@lazybytes.net>
parents: 10447
diff changeset
347 blocks[i]['type'] in ('bullet', 'option', 'field')):
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
348 i += 1
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
349 else:
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
350 blocks.insert(i, dict(lines=[''], indent=0, type='margin'))
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
351 i += 2
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
352 return blocks
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
353
12819
5082e2f3f8e0 minirst: ignore comments
Martin Geisler <mg@lazybytes.net>
parents: 12652
diff changeset
354 def prunecomments(blocks):
5082e2f3f8e0 minirst: ignore comments
Martin Geisler <mg@lazybytes.net>
parents: 12652
diff changeset
355 """Remove comments."""
5082e2f3f8e0 minirst: ignore comments
Martin Geisler <mg@lazybytes.net>
parents: 12652
diff changeset
356 i = 0
5082e2f3f8e0 minirst: ignore comments
Martin Geisler <mg@lazybytes.net>
parents: 12652
diff changeset
357 while i < len(blocks):
5082e2f3f8e0 minirst: ignore comments
Martin Geisler <mg@lazybytes.net>
parents: 12652
diff changeset
358 b = blocks[i]
13009
54be08fa4d1d minirst: modified minirst to also recognize empty comments.
Erik Zielke <ez@aragost.com>
parents: 13003
diff changeset
359 if b['type'] == 'paragraph' and (b['lines'][0].startswith('.. ') or
54be08fa4d1d minirst: modified minirst to also recognize empty comments.
Erik Zielke <ez@aragost.com>
parents: 13003
diff changeset
360 b['lines'] == ['..']):
12819
5082e2f3f8e0 minirst: ignore comments
Martin Geisler <mg@lazybytes.net>
parents: 12652
diff changeset
361 del blocks[i]
13003
876a931dd230 minirst: better interaction between comments and margins
Martin Geisler <mg@aragost.com>
parents: 12958
diff changeset
362 if i < len(blocks) and blocks[i]['type'] == 'margin':
876a931dd230 minirst: better interaction between comments and margins
Martin Geisler <mg@aragost.com>
parents: 12958
diff changeset
363 del blocks[i]
12819
5082e2f3f8e0 minirst: ignore comments
Martin Geisler <mg@lazybytes.net>
parents: 12652
diff changeset
364 else:
5082e2f3f8e0 minirst: ignore comments
Martin Geisler <mg@lazybytes.net>
parents: 12652
diff changeset
365 i += 1
5082e2f3f8e0 minirst: ignore comments
Martin Geisler <mg@lazybytes.net>
parents: 12652
diff changeset
366 return blocks
5082e2f3f8e0 minirst: ignore comments
Martin Geisler <mg@lazybytes.net>
parents: 12652
diff changeset
367
12620
9a9312e84e4e minirst: small code cleanup
Martin Geisler <mg@lazybytes.net>
parents: 12388
diff changeset
368 _admonitionre = re.compile(r"\.\. (admonition|attention|caution|danger|"
9a9312e84e4e minirst: small code cleanup
Martin Geisler <mg@lazybytes.net>
parents: 12388
diff changeset
369 r"error|hint|important|note|tip|warning)::",
9a9312e84e4e minirst: small code cleanup
Martin Geisler <mg@lazybytes.net>
parents: 12388
diff changeset
370 flags=re.IGNORECASE)
9a9312e84e4e minirst: small code cleanup
Martin Geisler <mg@lazybytes.net>
parents: 12388
diff changeset
371
12388
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
372 def findadmonitions(blocks):
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
373 """
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
374 Makes the type of the block an admonition block if
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
375 the first line is an admonition directive
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
376 """
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
377 i = 0
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
378 while i < len(blocks):
12620
9a9312e84e4e minirst: small code cleanup
Martin Geisler <mg@lazybytes.net>
parents: 12388
diff changeset
379 m = _admonitionre.match(blocks[i]['lines'][0])
12388
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
380 if m:
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
381 blocks[i]['type'] = 'admonition'
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
382 admonitiontitle = blocks[i]['lines'][0][3:m.end() - 2].lower()
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
383
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
384 firstline = blocks[i]['lines'][0][m.end() + 1:]
12620
9a9312e84e4e minirst: small code cleanup
Martin Geisler <mg@lazybytes.net>
parents: 12388
diff changeset
385 if firstline:
9a9312e84e4e minirst: small code cleanup
Martin Geisler <mg@lazybytes.net>
parents: 12388
diff changeset
386 blocks[i]['lines'].insert(1, ' ' + firstline)
12388
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
387
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
388 blocks[i]['admonitiontitle'] = admonitiontitle
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
389 del blocks[i]['lines'][0]
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
390 i = i + 1
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
391 return blocks
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
392
12652
3c31c0e42b11 minirst: pull admonition titles out formatblock function
Martin Geisler <mg@lazybytes.net>
parents: 12651
diff changeset
393 _admonitiontitles = {'attention': _('Attention:'),
3c31c0e42b11 minirst: pull admonition titles out formatblock function
Martin Geisler <mg@lazybytes.net>
parents: 12651
diff changeset
394 'caution': _('Caution:'),
3c31c0e42b11 minirst: pull admonition titles out formatblock function
Martin Geisler <mg@lazybytes.net>
parents: 12651
diff changeset
395 'danger': _('!Danger!') ,
3c31c0e42b11 minirst: pull admonition titles out formatblock function
Martin Geisler <mg@lazybytes.net>
parents: 12651
diff changeset
396 'error': _('Error:'),
3c31c0e42b11 minirst: pull admonition titles out formatblock function
Martin Geisler <mg@lazybytes.net>
parents: 12651
diff changeset
397 'hint': _('Hint:'),
3c31c0e42b11 minirst: pull admonition titles out formatblock function
Martin Geisler <mg@lazybytes.net>
parents: 12651
diff changeset
398 'important': _('Important:'),
3c31c0e42b11 minirst: pull admonition titles out formatblock function
Martin Geisler <mg@lazybytes.net>
parents: 12651
diff changeset
399 'note': _('Note:'),
3c31c0e42b11 minirst: pull admonition titles out formatblock function
Martin Geisler <mg@lazybytes.net>
parents: 12651
diff changeset
400 'tip': _('Tip:'),
3c31c0e42b11 minirst: pull admonition titles out formatblock function
Martin Geisler <mg@lazybytes.net>
parents: 12651
diff changeset
401 'warning': _('Warning!')}
3c31c0e42b11 minirst: pull admonition titles out formatblock function
Martin Geisler <mg@lazybytes.net>
parents: 12651
diff changeset
402
13011
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
403 def formatoption(block, width):
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
404 desc = ' '.join(map(str.strip, block['lines']))
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
405 colwidth = encoding.colwidth(block['optstr'])
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
406 usablewidth = width - 1
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
407 hanging = block['optstrwidth']
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
408 initindent = '%s%s ' % (block['optstr'], ' ' * ((hanging - colwidth)))
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
409 hangindent = ' ' * (encoding.colwidth(initindent) + 1)
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
410 return ' %s' % (util.wrap(desc, usablewidth,
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
411 initindent=initindent,
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
412 hangindent=hangindent))
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
413
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
414 def formatblock(block, width):
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
415 """Format a block according to width."""
9417
4c3fb45123e5 util, minirst: do not crash with COLUMNS=0
Martin Geisler <mg@lazybytes.net>
parents: 9293
diff changeset
416 if width <= 0:
4c3fb45123e5 util, minirst: do not crash with COLUMNS=0
Martin Geisler <mg@lazybytes.net>
parents: 9293
diff changeset
417 width = 78
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
418 indent = ' ' * block['indent']
12388
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
419 if block['type'] == 'admonition':
12652
3c31c0e42b11 minirst: pull admonition titles out formatblock function
Martin Geisler <mg@lazybytes.net>
parents: 12651
diff changeset
420 admonition = _admonitiontitles[block['admonitiontitle']]
12388
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
421 hang = len(block['lines'][-1]) - len(block['lines'][-1].lstrip())
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
422
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
423 defindent = indent + hang * ' '
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
424 text = ' '.join(map(str.strip, block['lines']))
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
425 return '%s\n%s' % (indent + admonition, util.wrap(text, width=width,
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
426 initindent=defindent,
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
427 hangindent=defindent))
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
428 if block['type'] == 'margin':
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
429 return ''
9735
97d0d910fa5d minirst: remove unnecessary "elif:" statements
Martin Geisler <mg@lazybytes.net>
parents: 9623
diff changeset
430 if block['type'] == 'literal':
9291
cd5b6a11b607 minirst: indent literal blocks with two spaces
Martin Geisler <mg@lazybytes.net>
parents: 9156
diff changeset
431 indent += ' '
cd5b6a11b607 minirst: indent literal blocks with two spaces
Martin Geisler <mg@lazybytes.net>
parents: 9156
diff changeset
432 return indent + ('\n' + indent).join(block['lines'])
9735
97d0d910fa5d minirst: remove unnecessary "elif:" statements
Martin Geisler <mg@lazybytes.net>
parents: 9623
diff changeset
433 if block['type'] == 'section':
12867
eda77c3e246a minirst: use colwidth to match title lengths (issue2455)
Matt Mackall <mpm@selenic.com>
parents: 12819
diff changeset
434 underline = encoding.colwidth(block['lines'][0]) * block['underline']
10983
287a5cdf7743 minirst: correctly format sections containing inline markup
Martin Geisler <mg@lazybytes.net>
parents: 10972
diff changeset
435 return "%s%s\n%s%s" % (indent, block['lines'][0],indent, underline)
15037
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
436 if block['type'] == 'table':
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
437 table = block['table']
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
438 # compute column widths
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
439 widths = [max([encoding.colwidth(e) for e in c]) for c in zip(*table)]
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
440 text = ''
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
441 span = sum(widths) + len(widths) - 1
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
442 indent = ' ' * block['indent']
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
443 hang = ' ' * (len(indent) + span - widths[-1])
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
444 f = ' '.join('%%-%ds' % n for n in widths)
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
445
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
446 for row in table:
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
447 l = f % tuple(row)
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
448 l = util.wrap(l, width=width, initindent=indent, hangindent=hang)
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
449 if not text and block['header']:
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
450 text = l + '\n' + indent + '-' * (min(width, span)) + '\n'
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
451 else:
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
452 text += l + "\n"
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
453 return text
9735
97d0d910fa5d minirst: remove unnecessary "elif:" statements
Martin Geisler <mg@lazybytes.net>
parents: 9623
diff changeset
454 if block['type'] == 'definition':
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
455 term = indent + block['lines'][0]
9737
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
456 hang = len(block['lines'][-1]) - len(block['lines'][-1].lstrip())
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
457 defindent = indent + hang * ' '
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
458 text = ' '.join(map(str.strip, block['lines'][1:]))
11297
d320e70442a5 replace Python standard textwrap by MBCS sensitive one for i18n text
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11192
diff changeset
459 return '%s\n%s' % (term, util.wrap(text, width=width,
d320e70442a5 replace Python standard textwrap by MBCS sensitive one for i18n text
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11192
diff changeset
460 initindent=defindent,
d320e70442a5 replace Python standard textwrap by MBCS sensitive one for i18n text
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11192
diff changeset
461 hangindent=defindent))
10937
a9d5943d2a30 minirst: removed unnecessary initindent variable
Martin Geisler <mg@lazybytes.net>
parents: 10936
diff changeset
462 subindent = indent
9735
97d0d910fa5d minirst: remove unnecessary "elif:" statements
Martin Geisler <mg@lazybytes.net>
parents: 9623
diff changeset
463 if block['type'] == 'bullet':
10447
e957cc7cbd14 minirst: support line blocks
Martin Geisler <mg@lazybytes.net>
parents: 10444
diff changeset
464 if block['lines'][0].startswith('| '):
e957cc7cbd14 minirst: support line blocks
Martin Geisler <mg@lazybytes.net>
parents: 10444
diff changeset
465 # Remove bullet for line blocks and add no extra
e957cc7cbd14 minirst: support line blocks
Martin Geisler <mg@lazybytes.net>
parents: 10444
diff changeset
466 # indention.
e957cc7cbd14 minirst: support line blocks
Martin Geisler <mg@lazybytes.net>
parents: 10444
diff changeset
467 block['lines'][0] = block['lines'][0][2:]
e957cc7cbd14 minirst: support line blocks
Martin Geisler <mg@lazybytes.net>
parents: 10444
diff changeset
468 else:
e957cc7cbd14 minirst: support line blocks
Martin Geisler <mg@lazybytes.net>
parents: 10444
diff changeset
469 m = _bulletre.match(block['lines'][0])
e957cc7cbd14 minirst: support line blocks
Martin Geisler <mg@lazybytes.net>
parents: 10444
diff changeset
470 subindent = indent + m.end() * ' '
9737
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
471 elif block['type'] == 'field':
10065
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
472 keywidth = block['keywidth']
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
473 key = block['key']
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
474
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
475 subindent = indent + _fieldwidth * ' '
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
476 if len(key) + 2 > _fieldwidth:
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
477 # key too large, use full line width
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
478 key = key.ljust(width)
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
479 elif keywidth + 2 < _fieldwidth:
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
480 # all keys are small, add only two spaces
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
481 key = key.ljust(keywidth + 2)
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
482 subindent = indent + (keywidth + 2) * ' '
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
483 else:
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
484 # mixed sizes, use fieldwidth for this one
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
485 key = key.ljust(_fieldwidth)
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
486 block['lines'][0] = key + block['lines'][0]
9737
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
487 elif block['type'] == 'option':
13011
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
488 return formatoption(block, width)
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
489
9737
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
490 text = ' '.join(map(str.strip, block['lines']))
11297
d320e70442a5 replace Python standard textwrap by MBCS sensitive one for i18n text
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11192
diff changeset
491 return util.wrap(text, width=width,
d320e70442a5 replace Python standard textwrap by MBCS sensitive one for i18n text
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11192
diff changeset
492 initindent=indent,
d320e70442a5 replace Python standard textwrap by MBCS sensitive one for i18n text
FUJIWARA Katsunori <foozy@lares.dti.ne.jp>
parents: 11192
diff changeset
493 hangindent=subindent)
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
494
15012
ee766af457ed minirst: add parse method to get document structure
Matt Mackall <mpm@selenic.com>
parents: 14433
diff changeset
495 def parse(text, indent=0, keep=None):
ee766af457ed minirst: add parse method to get document structure
Matt Mackall <mpm@selenic.com>
parents: 14433
diff changeset
496 """Parse text into a list of blocks"""
ee766af457ed minirst: add parse method to get document structure
Matt Mackall <mpm@selenic.com>
parents: 14433
diff changeset
497 pruned = []
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
498 blocks = findblocks(text)
9540
cad36e496640 help: un-indent help topics
Martin Geisler <mg@lazybytes.net>
parents: 9417
diff changeset
499 for b in blocks:
cad36e496640 help: un-indent help topics
Martin Geisler <mg@lazybytes.net>
parents: 9417
diff changeset
500 b['indent'] += indent
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
501 blocks = findliteralblocks(blocks)
15037
df47381b41d6 minirst: add simple table support
Matt Mackall <mpm@selenic.com>
parents: 15036
diff changeset
502 blocks = findtables(blocks)
10444
e99e0e077bc4 minirst: report pruned container types
Martin Geisler <mg@lazybytes.net>
parents: 10443
diff changeset
503 blocks, pruned = prunecontainers(blocks, keep or [])
10983
287a5cdf7743 minirst: correctly format sections containing inline markup
Martin Geisler <mg@lazybytes.net>
parents: 10972
diff changeset
504 blocks = findsections(blocks)
9623
32727ce029de minirst: convert ``foo`` into "foo" upon display
Martin Geisler <mg@lazybytes.net>
parents: 9540
diff changeset
505 blocks = inlineliterals(blocks)
10972
0a2c6948f5f4 doc, minirst: support hg interpreted text role
Martin Geisler <mg@aragost.com>
parents: 10937
diff changeset
506 blocks = hgrole(blocks)
9737
5f101af4a921 minirst: combine list parsing in one function
Martin Geisler <mg@lazybytes.net>
parents: 9735
diff changeset
507 blocks = splitparagraphs(blocks)
10065
a1ae0ed78d1a minirst: improve layout of field lists
Martin Geisler <mg@lazybytes.net>
parents: 10064
diff changeset
508 blocks = updatefieldlists(blocks)
13011
4936a04b6792 minirst: improved support for option lists.
Erik Zielke <ez@aragost.com>
parents: 13009
diff changeset
509 blocks = updateoptionlists(blocks)
13003
876a931dd230 minirst: better interaction between comments and margins
Martin Geisler <mg@aragost.com>
parents: 12958
diff changeset
510 blocks = addmargins(blocks)
12819
5082e2f3f8e0 minirst: ignore comments
Martin Geisler <mg@lazybytes.net>
parents: 12652
diff changeset
511 blocks = prunecomments(blocks)
12388
75f044d4dbf5 minirst: Support for admonitions
Erik Zielke <ez@aragost.com>
parents: 11464
diff changeset
512 blocks = findadmonitions(blocks)
15012
ee766af457ed minirst: add parse method to get document structure
Matt Mackall <mpm@selenic.com>
parents: 14433
diff changeset
513 return blocks, pruned
ee766af457ed minirst: add parse method to get document structure
Matt Mackall <mpm@selenic.com>
parents: 14433
diff changeset
514
15013
4a1e3c761ec7 minirst: add formatblocks helper
Matt Mackall <mpm@selenic.com>
parents: 15012
diff changeset
515 def formatblocks(blocks, width):
4a1e3c761ec7 minirst: add formatblocks helper
Matt Mackall <mpm@selenic.com>
parents: 15012
diff changeset
516 text = '\n'.join(formatblock(b, width) for b in blocks)
4a1e3c761ec7 minirst: add formatblocks helper
Matt Mackall <mpm@selenic.com>
parents: 15012
diff changeset
517 return text
4a1e3c761ec7 minirst: add formatblocks helper
Matt Mackall <mpm@selenic.com>
parents: 15012
diff changeset
518
15012
ee766af457ed minirst: add parse method to get document structure
Matt Mackall <mpm@selenic.com>
parents: 14433
diff changeset
519 def format(text, width, indent=0, keep=None):
ee766af457ed minirst: add parse method to get document structure
Matt Mackall <mpm@selenic.com>
parents: 14433
diff changeset
520 """Parse and format the text according to width."""
ee766af457ed minirst: add parse method to get document structure
Matt Mackall <mpm@selenic.com>
parents: 14433
diff changeset
521 blocks, pruned = parse(text, indent, keep or [])
10444
e99e0e077bc4 minirst: report pruned container types
Martin Geisler <mg@lazybytes.net>
parents: 10443
diff changeset
522 text = '\n'.join(formatblock(b, width) for b in blocks)
e99e0e077bc4 minirst: report pruned container types
Martin Geisler <mg@lazybytes.net>
parents: 10443
diff changeset
523 if keep is None:
e99e0e077bc4 minirst: report pruned container types
Martin Geisler <mg@lazybytes.net>
parents: 10443
diff changeset
524 return text
e99e0e077bc4 minirst: report pruned container types
Martin Geisler <mg@lazybytes.net>
parents: 10443
diff changeset
525 else:
e99e0e077bc4 minirst: report pruned container types
Martin Geisler <mg@lazybytes.net>
parents: 10443
diff changeset
526 return text, pruned
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
527
15014
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
528 def getsections(blocks):
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
529 '''return a list of (section name, nesting level, blocks) tuples'''
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
530 nest = ""
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
531 level = 0
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
532 secs = []
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
533 for b in blocks:
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
534 if b['type'] == 'section':
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
535 i = b['underline']
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
536 if i not in nest:
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
537 nest += i
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
538 level = nest.index(i) + 1
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
539 nest = nest[:level]
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
540 secs.append((b['lines'][0], level, [b]))
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
541 else:
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
542 if not secs:
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
543 # add an initial empty section
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
544 secs = [('', 0, [])]
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
545 secs[-1][2].append(b)
a814e986859f minirst: add getsections helper
Matt Mackall <mpm@selenic.com>
parents: 15013
diff changeset
546 return secs
9156
c9c7e8cdac9c minimal reStructuredText parser
Martin Geisler <mg@lazybytes.net>
parents:
diff changeset
547
15015
ee6988aea74e minirst: add decorateblocks search helper
Matt Mackall <mpm@selenic.com>
parents: 15014
diff changeset
548 def decorateblocks(blocks, width):
ee6988aea74e minirst: add decorateblocks search helper
Matt Mackall <mpm@selenic.com>
parents: 15014
diff changeset
549 '''generate a list of (section name, line text) pairs for search'''
ee6988aea74e minirst: add decorateblocks search helper
Matt Mackall <mpm@selenic.com>
parents: 15014
diff changeset
550 lines = []
ee6988aea74e minirst: add decorateblocks search helper
Matt Mackall <mpm@selenic.com>
parents: 15014
diff changeset
551 for s in getsections(blocks):
ee6988aea74e minirst: add decorateblocks search helper
Matt Mackall <mpm@selenic.com>
parents: 15014
diff changeset
552 section = s[0]
ee6988aea74e minirst: add decorateblocks search helper
Matt Mackall <mpm@selenic.com>
parents: 15014
diff changeset
553 text = formatblocks(s[2], width)
ee6988aea74e minirst: add decorateblocks search helper
Matt Mackall <mpm@selenic.com>
parents: 15014
diff changeset
554 lines.append([(section, l) for l in text.splitlines(True)])
ee6988aea74e minirst: add decorateblocks search helper
Matt Mackall <mpm@selenic.com>
parents: 15014
diff changeset
555 return lines
15039
c981f4a9ea74 minirst: add a helper function to build an RST table from an array
Matt Mackall <mpm@selenic.com>
parents: 15038
diff changeset
556
c981f4a9ea74 minirst: add a helper function to build an RST table from an array
Matt Mackall <mpm@selenic.com>
parents: 15038
diff changeset
557 def maketable(data, indent=0, header=False):
c981f4a9ea74 minirst: add a helper function to build an RST table from an array
Matt Mackall <mpm@selenic.com>
parents: 15038
diff changeset
558 '''Generate an RST table for the given table data'''
c981f4a9ea74 minirst: add a helper function to build an RST table from an array
Matt Mackall <mpm@selenic.com>
parents: 15038
diff changeset
559
c981f4a9ea74 minirst: add a helper function to build an RST table from an array
Matt Mackall <mpm@selenic.com>
parents: 15038
diff changeset
560 widths = [max(encoding.colwidth(e) for e in c) for c in zip(*data)]
c981f4a9ea74 minirst: add a helper function to build an RST table from an array
Matt Mackall <mpm@selenic.com>
parents: 15038
diff changeset
561 indent = ' ' * indent
c981f4a9ea74 minirst: add a helper function to build an RST table from an array
Matt Mackall <mpm@selenic.com>
parents: 15038
diff changeset
562 f = indent + ' '.join('%%-%ds' % w for w in widths) + '\n'
c981f4a9ea74 minirst: add a helper function to build an RST table from an array
Matt Mackall <mpm@selenic.com>
parents: 15038
diff changeset
563 div = indent + ' '.join('=' * w for w in widths) + '\n'
c981f4a9ea74 minirst: add a helper function to build an RST table from an array
Matt Mackall <mpm@selenic.com>
parents: 15038
diff changeset
564
c981f4a9ea74 minirst: add a helper function to build an RST table from an array
Matt Mackall <mpm@selenic.com>
parents: 15038
diff changeset
565 out = [div]
c981f4a9ea74 minirst: add a helper function to build an RST table from an array
Matt Mackall <mpm@selenic.com>
parents: 15038
diff changeset
566 for row in data:
c981f4a9ea74 minirst: add a helper function to build an RST table from an array
Matt Mackall <mpm@selenic.com>
parents: 15038
diff changeset
567 out.append(f % tuple(row))
c981f4a9ea74 minirst: add a helper function to build an RST table from an array
Matt Mackall <mpm@selenic.com>
parents: 15038
diff changeset
568 if header and len(data) > 1:
c981f4a9ea74 minirst: add a helper function to build an RST table from an array
Matt Mackall <mpm@selenic.com>
parents: 15038
diff changeset
569 out.insert(2, div)
c981f4a9ea74 minirst: add a helper function to build an RST table from an array
Matt Mackall <mpm@selenic.com>
parents: 15038
diff changeset
570 out.append(div)
c981f4a9ea74 minirst: add a helper function to build an RST table from an array
Matt Mackall <mpm@selenic.com>
parents: 15038
diff changeset
571 return ''.join(out)