annotate mercurial/templater.py @ 12709:4147a292c508

filectx: use ctx.size comparisons to speed up ctx.cmp Comparing sizes is cheaper than comparing file contents, as it does not involve reading the file on disk or from the filelog. It is however not always possible: some extensions, or encode filters, change data when extracting it to the working directory.
author Nicolas Dumazet <nicdumz.commits@gmail.com>
date Tue, 27 Jul 2010 23:07:30 +0900
parents b014f998959d
children ea3bada953d3
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
1909
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
1 # templater.py - template expansion for output
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
2 #
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
3 # Copyright 2005, 2006 Matt Mackall <mpm@selenic.com>
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
4 #
8225
46293a0c7e9f updated license to be explicit about GPL version 2
Martin Geisler <mg@lazybytes.net>
parents: 8223
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: 9842
diff changeset
6 # GNU General Public License version 2 or any later version.
1909
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
7
3891
6b4127c7d52a Simplify i18n imports
Matt Mackall <mpm@selenic.com>
parents: 3877
diff changeset
8 from i18n import _
10843
b91c1804008e templater: directly parse templates, no regexes
Matt Mackall <mpm@selenic.com>
parents: 10339
diff changeset
9 import sys, os
8360
acc202b71619 templater: provide the standard template filters by default
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8312
diff changeset
10 import util, config, templatefilters
1901
c64bef3d7043 use safer string parser for template engine.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1900
diff changeset
11
7107
125c8fedcbe0 Allow hgweb to search for templates in more than one path.
Brendan Cully <brendan@kublai.com>
parents: 6783
diff changeset
12 path = ['templates', '../templates']
8360
acc202b71619 templater: provide the standard template filters by default
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8312
diff changeset
13 stringify = templatefilters.stringify
7107
125c8fedcbe0 Allow hgweb to search for templates in more than one path.
Brendan Cully <brendan@kublai.com>
parents: 6783
diff changeset
14
10850
a63391e26284 templater: use recursive flattening
Matt Mackall <mpm@selenic.com>
parents: 10849
diff changeset
15 def _flatten(thing):
a63391e26284 templater: use recursive flattening
Matt Mackall <mpm@selenic.com>
parents: 10849
diff changeset
16 '''yield a single stream from a possibly nested set of iterators'''
a63391e26284 templater: use recursive flattening
Matt Mackall <mpm@selenic.com>
parents: 10849
diff changeset
17 if isinstance(thing, str):
a63391e26284 templater: use recursive flattening
Matt Mackall <mpm@selenic.com>
parents: 10849
diff changeset
18 yield thing
a63391e26284 templater: use recursive flattening
Matt Mackall <mpm@selenic.com>
parents: 10849
diff changeset
19 elif not hasattr(thing, '__iter__'):
11305
d4cafcb63f77 cleanups: undefined variables
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 10855
diff changeset
20 if thing is not None:
10852
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
21 yield str(thing)
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
22 else:
10850
a63391e26284 templater: use recursive flattening
Matt Mackall <mpm@selenic.com>
parents: 10849
diff changeset
23 for i in thing:
a63391e26284 templater: use recursive flattening
Matt Mackall <mpm@selenic.com>
parents: 10849
diff changeset
24 if isinstance(i, str):
a63391e26284 templater: use recursive flattening
Matt Mackall <mpm@selenic.com>
parents: 10849
diff changeset
25 yield i
a63391e26284 templater: use recursive flattening
Matt Mackall <mpm@selenic.com>
parents: 10849
diff changeset
26 elif not hasattr(i, '__iter__'):
10852
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
27 if i is not None:
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
28 yield str(i)
10850
a63391e26284 templater: use recursive flattening
Matt Mackall <mpm@selenic.com>
parents: 10849
diff changeset
29 elif i is not None:
a63391e26284 templater: use recursive flattening
Matt Mackall <mpm@selenic.com>
parents: 10849
diff changeset
30 for j in _flatten(i):
a63391e26284 templater: use recursive flattening
Matt Mackall <mpm@selenic.com>
parents: 10849
diff changeset
31 yield j
a63391e26284 templater: use recursive flattening
Matt Mackall <mpm@selenic.com>
parents: 10849
diff changeset
32
1902
1cc5f25653a3 make parsestring work with strings that do not have quotes.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1901
diff changeset
33 def parsestring(s, quoted=True):
1909
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
34 '''parse a string using simple c-like syntax.
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
35 string must be in quotes if quoted is True.'''
1902
1cc5f25653a3 make parsestring work with strings that do not have quotes.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1901
diff changeset
36 if quoted:
3639
5c9a36210662 templater: simplify parsestring
Matt Mackall <mpm@selenic.com>
parents: 3638
diff changeset
37 if len(s) < 2 or s[0] != s[-1]:
5c9a36210662 templater: simplify parsestring
Matt Mackall <mpm@selenic.com>
parents: 3638
diff changeset
38 raise SyntaxError(_('unmatched quotes'))
5c9a36210662 templater: simplify parsestring
Matt Mackall <mpm@selenic.com>
parents: 3638
diff changeset
39 return s[1:-1].decode('string_escape')
3632
231393b7316f templater: use str.decode in parse_string
Matt Mackall <mpm@selenic.com>
parents: 3462
diff changeset
40
231393b7316f templater: use str.decode in parse_string
Matt Mackall <mpm@selenic.com>
parents: 3462
diff changeset
41 return s.decode('string_escape')
1896
f8f818a04f5b move hgweb template code out to templater
Vadim Gelfer <vadim.gelfer@gmail.com>
parents:
diff changeset
42
8218
e61cb2813d2a templater: separate template management and actual string processing
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8198
diff changeset
43 class engine(object):
1909
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
44 '''template expansion engine.
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
45
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
46 template expansion works like this. a map file contains key=value
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
47 pairs. if value is quoted, it is treated as string. otherwise, it
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
48 is treated as name of template file.
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
49
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
50 templater is asked to expand a key in map. it looks up key, and
4334
66a3fe30f9fc minor typo fix in templater's docstring
TK Soh <teekaysoh@yahoo.com>
parents: 3904
diff changeset
51 looks for strings like this: {foo}. it expands {foo} by looking up
1909
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
52 foo in map, and substituting it. expansion is recursive: it stops
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
53 when there is no more {foo} to replace.
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
54
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
55 expansion also allows formatting and filtering.
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
56
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
57 format uses key to expand each item in list. syntax is
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
58 {key%format}.
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
59
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
60 filter uses function to transform value. syntax is
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
61 {key|filter1|filter2|...}.'''
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
62
8218
e61cb2813d2a templater: separate template management and actual string processing
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8198
diff changeset
63 def __init__(self, loader, filters={}, defaults={}):
10848
01346cea5485 templater: privatize class variables
Matt Mackall <mpm@selenic.com>
parents: 10847
diff changeset
64 self._loader = loader
01346cea5485 templater: privatize class variables
Matt Mackall <mpm@selenic.com>
parents: 10847
diff changeset
65 self._filters = filters
01346cea5485 templater: privatize class variables
Matt Mackall <mpm@selenic.com>
parents: 10847
diff changeset
66 self._defaults = defaults
01346cea5485 templater: privatize class variables
Matt Mackall <mpm@selenic.com>
parents: 10847
diff changeset
67 self._cache = {}
8218
e61cb2813d2a templater: separate template management and actual string processing
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8198
diff changeset
68
10853
b6f6d9fd53d6 templater: drop raw method
Matt Mackall <mpm@selenic.com>
parents: 10852
diff changeset
69 def process(self, t, mapping):
b6f6d9fd53d6 templater: drop raw method
Matt Mackall <mpm@selenic.com>
parents: 10852
diff changeset
70 '''Perform expansion. t is name of map element to expand.
b6f6d9fd53d6 templater: drop raw method
Matt Mackall <mpm@selenic.com>
parents: 10852
diff changeset
71 mapping contains added elements for use during expansion. Is a
b6f6d9fd53d6 templater: drop raw method
Matt Mackall <mpm@selenic.com>
parents: 10852
diff changeset
72 generator.'''
b6f6d9fd53d6 templater: drop raw method
Matt Mackall <mpm@selenic.com>
parents: 10852
diff changeset
73 return _flatten(self._process(self._load(t), mapping))
b6f6d9fd53d6 templater: drop raw method
Matt Mackall <mpm@selenic.com>
parents: 10852
diff changeset
74
10852
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
75 def _load(self, t):
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
76 '''load, parse, and cache a template'''
10848
01346cea5485 templater: privatize class variables
Matt Mackall <mpm@selenic.com>
parents: 10847
diff changeset
77 if t not in self._cache:
01346cea5485 templater: privatize class variables
Matt Mackall <mpm@selenic.com>
parents: 10847
diff changeset
78 self._cache[t] = self._parse(self._loader(t))
10852
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
79 return self._cache[t]
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
80
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
81 def _get(self, mapping, key):
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
82 v = mapping.get(key)
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
83 if v is None:
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
84 v = self._defaults.get(key, '')
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
85 if hasattr(v, '__call__'):
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
86 v = v(**mapping)
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
87 return v
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
88
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
89 def _filter(self, mapping, parts):
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
90 filters, val = parts
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
91 x = self._get(mapping, val)
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
92 for f in filters:
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
93 x = f(x)
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
94 return x
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
95
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
96 def _format(self, mapping, args):
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
97 key, parsed = args
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
98 v = self._get(mapping, key)
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
99 if not hasattr(v, '__iter__'):
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
100 raise SyntaxError(_("error expanding '%s%%%s'")
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
101 % (key, format))
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
102 lm = mapping.copy()
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
103 for i in v:
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
104 if isinstance(i, dict):
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
105 lm.update(i)
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
106 yield self._process(parsed, lm)
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
107 else:
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
108 # v is not an iterable of dicts, this happen when 'key'
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
109 # has been fully expanded already and format is useless.
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
110 # If so, return the expanded value.
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
111 yield i
8218
e61cb2813d2a templater: separate template management and actual string processing
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8198
diff changeset
112
10845
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
113 def _parse(self, tmpl):
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
114 '''preparse a template'''
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
115 parsed = []
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
116 pos, stop = 0, len(tmpl)
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
117 while pos < stop:
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
118 n = tmpl.find('{', pos)
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
119 if n < 0:
10853
b6f6d9fd53d6 templater: drop raw method
Matt Mackall <mpm@selenic.com>
parents: 10852
diff changeset
120 parsed.append((None, tmpl[pos:stop]))
10845
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
121 break
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
122 if n > 0 and tmpl[n - 1] == '\\':
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
123 # escaped
10855
62216faed067 templater: drop \ when handling escaped {
Matt Mackall <mpm@selenic.com>
parents: 10854
diff changeset
124 parsed.append((None, tmpl[pos:n - 1] + "{"))
10845
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
125 pos = n + 1
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
126 continue
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
127 if n > pos:
10853
b6f6d9fd53d6 templater: drop raw method
Matt Mackall <mpm@selenic.com>
parents: 10852
diff changeset
128 parsed.append((None, tmpl[pos:n]))
10845
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
129
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
130 pos = n
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
131 n = tmpl.find('}', pos)
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
132 if n < 0:
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
133 # no closing
10853
b6f6d9fd53d6 templater: drop raw method
Matt Mackall <mpm@selenic.com>
parents: 10852
diff changeset
134 parsed.append((None, tmpl[pos:stop]))
10845
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
135 break
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
136
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
137 expr = tmpl[pos + 1:n]
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
138 pos = n + 1
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
139
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
140 if '%' in expr:
12402
b014f998959d templater: add a few comments.
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents: 11305
diff changeset
141 # the keyword should be formatted with a template
10852
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
142 key, t = expr.split('%')
10854
4036634560d6 templater: strip whitespace inside template methods
Matt Mackall <mpm@selenic.com>
parents: 10853
diff changeset
143 parsed.append((self._format, (key.strip(),
4036634560d6 templater: strip whitespace inside template methods
Matt Mackall <mpm@selenic.com>
parents: 10853
diff changeset
144 self._load(t.strip()))))
10845
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
145 elif '|' in expr:
12402
b014f998959d templater: add a few comments.
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents: 11305
diff changeset
146 # process the keyword value with one or more filters
10846
594140b1e12d templater: extend preparsing
Matt Mackall <mpm@selenic.com>
parents: 10845
diff changeset
147 parts = expr.split('|')
10854
4036634560d6 templater: strip whitespace inside template methods
Matt Mackall <mpm@selenic.com>
parents: 10853
diff changeset
148 val = parts[0].strip()
10846
594140b1e12d templater: extend preparsing
Matt Mackall <mpm@selenic.com>
parents: 10845
diff changeset
149 try:
10854
4036634560d6 templater: strip whitespace inside template methods
Matt Mackall <mpm@selenic.com>
parents: 10853
diff changeset
150 filters = [self._filters[f.strip()] for f in parts[1:]]
10846
594140b1e12d templater: extend preparsing
Matt Mackall <mpm@selenic.com>
parents: 10845
diff changeset
151 except KeyError, i:
594140b1e12d templater: extend preparsing
Matt Mackall <mpm@selenic.com>
parents: 10845
diff changeset
152 raise SyntaxError(_("unknown filter '%s'") % i[0])
10852
0d50586a9d31 templater: raise nested functions
Matt Mackall <mpm@selenic.com>
parents: 10850
diff changeset
153 parsed.append((self._filter, (filters, val)))
10845
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
154 else:
12402
b014f998959d templater: add a few comments.
Dan Villiom Podlaski Christiansen <danchr@gmail.com>
parents: 11305
diff changeset
155 # just get the keyword
10854
4036634560d6 templater: strip whitespace inside template methods
Matt Mackall <mpm@selenic.com>
parents: 10853
diff changeset
156 parsed.append((self._get, expr.strip()))
10845
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
157
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
158 return parsed
9d8194c2fcbd templater: preparse templates and cache
Matt Mackall <mpm@selenic.com>
parents: 10843
diff changeset
159
10846
594140b1e12d templater: extend preparsing
Matt Mackall <mpm@selenic.com>
parents: 10845
diff changeset
160 def _process(self, parsed, mapping):
8218
e61cb2813d2a templater: separate template management and actual string processing
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8198
diff changeset
161 '''Render a template. Returns a generator.'''
10846
594140b1e12d templater: extend preparsing
Matt Mackall <mpm@selenic.com>
parents: 10845
diff changeset
162 for f, e in parsed:
10853
b6f6d9fd53d6 templater: drop raw method
Matt Mackall <mpm@selenic.com>
parents: 10852
diff changeset
163 if f:
b6f6d9fd53d6 templater: drop raw method
Matt Mackall <mpm@selenic.com>
parents: 10852
diff changeset
164 yield f(mapping, e)
b6f6d9fd53d6 templater: drop raw method
Matt Mackall <mpm@selenic.com>
parents: 10852
diff changeset
165 else:
b6f6d9fd53d6 templater: drop raw method
Matt Mackall <mpm@selenic.com>
parents: 10852
diff changeset
166 yield e
8218
e61cb2813d2a templater: separate template management and actual string processing
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8198
diff changeset
167
8361
d8c5a7f25a40 templater: make the templating engine pluggable to some extent
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8360
diff changeset
168 engines = {'default': engine}
d8c5a7f25a40 templater: make the templating engine pluggable to some extent
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8360
diff changeset
169
8218
e61cb2813d2a templater: separate template management and actual string processing
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8198
diff changeset
170 class templater(object):
e61cb2813d2a templater: separate template management and actual string processing
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8198
diff changeset
171
7396
526c40a74bd0 templater: return data in increasing chunk sizes
Brendan Cully <brendan@kublai.com>
parents: 7107
diff changeset
172 def __init__(self, mapfile, filters={}, defaults={}, cache={},
526c40a74bd0 templater: return data in increasing chunk sizes
Brendan Cully <brendan@kublai.com>
parents: 7107
diff changeset
173 minchunk=1024, maxchunk=65536):
1909
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
174 '''set up template engine.
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
175 mapfile is name of file to read map definitions from.
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
176 filters is dict of functions. each transforms a value into another.
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
177 defaults is dict of default map definitions.'''
1905
0c760737b996 improve template errors when something is wrong.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1904
diff changeset
178 self.mapfile = mapfile or 'template'
1975
6e1a8ea5d717 Duplicate cache when creating templater.
Shun-ichi Goto <shunichi.goto@gmail.com>
parents: 1964
diff changeset
179 self.cache = cache.copy()
1896
f8f818a04f5b move hgweb template code out to templater
Vadim Gelfer <vadim.gelfer@gmail.com>
parents:
diff changeset
180 self.map = {}
1905
0c760737b996 improve template errors when something is wrong.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1904
diff changeset
181 self.base = (mapfile and os.path.dirname(mapfile)) or ''
8360
acc202b71619 templater: provide the standard template filters by default
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8312
diff changeset
182 self.filters = templatefilters.filters.copy()
acc202b71619 templater: provide the standard template filters by default
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8312
diff changeset
183 self.filters.update(filters)
1964
778281d46bb2 fix template bug that made hgweb break.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1955
diff changeset
184 self.defaults = defaults
7396
526c40a74bd0 templater: return data in increasing chunk sizes
Brendan Cully <brendan@kublai.com>
parents: 7107
diff changeset
185 self.minchunk, self.maxchunk = minchunk, maxchunk
8361
d8c5a7f25a40 templater: make the templating engine pluggable to some extent
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8360
diff changeset
186 self.engines = {}
1896
f8f818a04f5b move hgweb template code out to templater
Vadim Gelfer <vadim.gelfer@gmail.com>
parents:
diff changeset
187
1905
0c760737b996 improve template errors when something is wrong.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1904
diff changeset
188 if not mapfile:
0c760737b996 improve template errors when something is wrong.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1904
diff changeset
189 return
6337
d2713d902524 give better error message on non-existent mapfile (issue813)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 5976
diff changeset
190 if not os.path.exists(mapfile):
d2713d902524 give better error message on non-existent mapfile (issue813)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 5976
diff changeset
191 raise util.Abort(_('style not found: %s') % mapfile)
d2713d902524 give better error message on non-existent mapfile (issue813)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 5976
diff changeset
192
8194
63c47e4ac617 templater: use new config parser
Matt Mackall <mpm@selenic.com>
parents: 8015
diff changeset
193 conf = config.config()
63c47e4ac617 templater: use new config parser
Matt Mackall <mpm@selenic.com>
parents: 8015
diff changeset
194 conf.read(mapfile)
63c47e4ac617 templater: use new config parser
Matt Mackall <mpm@selenic.com>
parents: 8015
diff changeset
195
63c47e4ac617 templater: use new config parser
Matt Mackall <mpm@selenic.com>
parents: 8015
diff changeset
196 for key, val in conf[''].items():
63c47e4ac617 templater: use new config parser
Matt Mackall <mpm@selenic.com>
parents: 8015
diff changeset
197 if val[0] in "'\"":
63c47e4ac617 templater: use new config parser
Matt Mackall <mpm@selenic.com>
parents: 8015
diff changeset
198 try:
63c47e4ac617 templater: use new config parser
Matt Mackall <mpm@selenic.com>
parents: 8015
diff changeset
199 self.cache[key] = parsestring(val)
63c47e4ac617 templater: use new config parser
Matt Mackall <mpm@selenic.com>
parents: 8015
diff changeset
200 except SyntaxError, inst:
63c47e4ac617 templater: use new config parser
Matt Mackall <mpm@selenic.com>
parents: 8015
diff changeset
201 raise SyntaxError('%s: %s' %
8198
cf9accffd0b3 config: getsource -> source
Matt Mackall <mpm@selenic.com>
parents: 8194
diff changeset
202 (conf.source('', key), inst.args[0]))
1896
f8f818a04f5b move hgweb template code out to templater
Vadim Gelfer <vadim.gelfer@gmail.com>
parents:
diff changeset
203 else:
8361
d8c5a7f25a40 templater: make the templating engine pluggable to some extent
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8360
diff changeset
204 val = 'default', val
d8c5a7f25a40 templater: make the templating engine pluggable to some extent
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8360
diff changeset
205 if ':' in val[1]:
d8c5a7f25a40 templater: make the templating engine pluggable to some extent
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8360
diff changeset
206 val = val[1].split(':', 1)
d8c5a7f25a40 templater: make the templating engine pluggable to some extent
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8360
diff changeset
207 self.map[key] = val[0], os.path.join(self.base, val[1])
1896
f8f818a04f5b move hgweb template code out to templater
Vadim Gelfer <vadim.gelfer@gmail.com>
parents:
diff changeset
208
1899
888d298ddb91 many small changes to templater.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1897
diff changeset
209 def __contains__(self, key):
3637
e7639888bb2f templater: simplify cache and remove filter argument in __call__
Matt Mackall <mpm@selenic.com>
parents: 3636
diff changeset
210 return key in self.cache or key in self.map
1899
888d298ddb91 many small changes to templater.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1897
diff changeset
211
8218
e61cb2813d2a templater: separate template management and actual string processing
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8198
diff changeset
212 def load(self, t):
6783
6d824dc86907 templater: make a template a string-only iterator
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 6434
diff changeset
213 '''Get the template for the given template name. Use a local cache.'''
5915
d0576d065993 Prefer i in d over d.has_key(i)
Christian Ebert <blacktrash@gmx.net>
parents: 5269
diff changeset
214 if not t in self.cache:
1905
0c760737b996 improve template errors when something is wrong.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1904
diff changeset
215 try:
8361
d8c5a7f25a40 templater: make the templating engine pluggable to some extent
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8360
diff changeset
216 self.cache[t] = open(self.map[t][1]).read()
1905
0c760737b996 improve template errors when something is wrong.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1904
diff changeset
217 except IOError, inst:
0c760737b996 improve template errors when something is wrong.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1904
diff changeset
218 raise IOError(inst.args[0], _('template file %s: %s') %
8361
d8c5a7f25a40 templater: make the templating engine pluggable to some extent
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8360
diff changeset
219 (self.map[t][1], inst.args[1]))
6783
6d824dc86907 templater: make a template a string-only iterator
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 6434
diff changeset
220 return self.cache[t]
1896
f8f818a04f5b move hgweb template code out to templater
Vadim Gelfer <vadim.gelfer@gmail.com>
parents:
diff changeset
221
10847
90f4367535a5 templater: map -> mapping
Matt Mackall <mpm@selenic.com>
parents: 10846
diff changeset
222 def __call__(self, t, **mapping):
8361
d8c5a7f25a40 templater: make the templating engine pluggable to some extent
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8360
diff changeset
223 ttype = t in self.map and self.map[t][0] or 'default'
d8c5a7f25a40 templater: make the templating engine pluggable to some extent
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8360
diff changeset
224 proc = self.engines.get(ttype)
d8c5a7f25a40 templater: make the templating engine pluggable to some extent
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8360
diff changeset
225 if proc is None:
d8c5a7f25a40 templater: make the templating engine pluggable to some extent
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8360
diff changeset
226 proc = engines[ttype](self.load, self.filters, self.defaults)
d8c5a7f25a40 templater: make the templating engine pluggable to some extent
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8360
diff changeset
227 self.engines[ttype] = proc
d8c5a7f25a40 templater: make the templating engine pluggable to some extent
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8360
diff changeset
228
10847
90f4367535a5 templater: map -> mapping
Matt Mackall <mpm@selenic.com>
parents: 10846
diff changeset
229 stream = proc.process(t, mapping)
7396
526c40a74bd0 templater: return data in increasing chunk sizes
Brendan Cully <brendan@kublai.com>
parents: 7107
diff changeset
230 if self.minchunk:
526c40a74bd0 templater: return data in increasing chunk sizes
Brendan Cully <brendan@kublai.com>
parents: 7107
diff changeset
231 stream = util.increasingchunks(stream, min=self.minchunk,
526c40a74bd0 templater: return data in increasing chunk sizes
Brendan Cully <brendan@kublai.com>
parents: 7107
diff changeset
232 max=self.maxchunk)
526c40a74bd0 templater: return data in increasing chunk sizes
Brendan Cully <brendan@kublai.com>
parents: 7107
diff changeset
233 return stream
7434
cf7741aa1e96 kill some trailing spaces
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7396
diff changeset
234
1899
888d298ddb91 many small changes to templater.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1897
diff changeset
235 def templatepath(name=None):
1909
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
236 '''return location of template file or directory (if no name).
37b9f80a5fbb add doc comments to template code.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1906
diff changeset
237 returns None if not found.'''
7107
125c8fedcbe0 Allow hgweb to search for templates in more than one path.
Brendan Cully <brendan@kublai.com>
parents: 6783
diff changeset
238 normpaths = []
2189
e3eba577a0ae move changeset_templater into templater module.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 2001
diff changeset
239
2001
a439b7b51530 Windows py2exe version didn't handle names given to templatepath() correctly
Lee Cantey <lcantey@gmail.com>
parents: 1987
diff changeset
240 # executable version (py2exe) doesn't support __file__
a439b7b51530 Windows py2exe version didn't handle names given to templatepath() correctly
Lee Cantey <lcantey@gmail.com>
parents: 1987
diff changeset
241 if hasattr(sys, 'frozen'):
a439b7b51530 Windows py2exe version didn't handle names given to templatepath() correctly
Lee Cantey <lcantey@gmail.com>
parents: 1987
diff changeset
242 module = sys.executable
a439b7b51530 Windows py2exe version didn't handle names given to templatepath() correctly
Lee Cantey <lcantey@gmail.com>
parents: 1987
diff changeset
243 else:
a439b7b51530 Windows py2exe version didn't handle names given to templatepath() correctly
Lee Cantey <lcantey@gmail.com>
parents: 1987
diff changeset
244 module = __file__
7107
125c8fedcbe0 Allow hgweb to search for templates in more than one path.
Brendan Cully <brendan@kublai.com>
parents: 6783
diff changeset
245 for f in path:
125c8fedcbe0 Allow hgweb to search for templates in more than one path.
Brendan Cully <brendan@kublai.com>
parents: 6783
diff changeset
246 if f.startswith('/'):
125c8fedcbe0 Allow hgweb to search for templates in more than one path.
Brendan Cully <brendan@kublai.com>
parents: 6783
diff changeset
247 p = f
125c8fedcbe0 Allow hgweb to search for templates in more than one path.
Brendan Cully <brendan@kublai.com>
parents: 6783
diff changeset
248 else:
125c8fedcbe0 Allow hgweb to search for templates in more than one path.
Brendan Cully <brendan@kublai.com>
parents: 6783
diff changeset
249 fl = f.split('/')
125c8fedcbe0 Allow hgweb to search for templates in more than one path.
Brendan Cully <brendan@kublai.com>
parents: 6783
diff changeset
250 p = os.path.join(os.path.dirname(module), *fl)
125c8fedcbe0 Allow hgweb to search for templates in more than one path.
Brendan Cully <brendan@kublai.com>
parents: 6783
diff changeset
251 if name:
125c8fedcbe0 Allow hgweb to search for templates in more than one path.
Brendan Cully <brendan@kublai.com>
parents: 6783
diff changeset
252 p = os.path.join(p, name)
125c8fedcbe0 Allow hgweb to search for templates in more than one path.
Brendan Cully <brendan@kublai.com>
parents: 6783
diff changeset
253 if name and os.path.exists(p):
1897
58b6784cf9f1 move hgweb.templatepath into templater
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 1896
diff changeset
254 return os.path.normpath(p)
7107
125c8fedcbe0 Allow hgweb to search for templates in more than one path.
Brendan Cully <brendan@kublai.com>
parents: 6783
diff changeset
255 elif os.path.isdir(p):
125c8fedcbe0 Allow hgweb to search for templates in more than one path.
Brendan Cully <brendan@kublai.com>
parents: 6783
diff changeset
256 normpaths.append(os.path.normpath(p))
125c8fedcbe0 Allow hgweb to search for templates in more than one path.
Brendan Cully <brendan@kublai.com>
parents: 6783
diff changeset
257
125c8fedcbe0 Allow hgweb to search for templates in more than one path.
Brendan Cully <brendan@kublai.com>
parents: 6783
diff changeset
258 return normpaths
2189
e3eba577a0ae move changeset_templater into templater module.
Vadim Gelfer <vadim.gelfer@gmail.com>
parents: 2001
diff changeset
259
9842
d3dbdca92458 hgweb: don't choke when an inexistent style is requested (issue1901)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 9372
diff changeset
260 def stylemap(styles, paths=None):
7966
aa983c3d94a9 templater: move stylemap function from hgweb to templater
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7434
diff changeset
261 """Return path to mapfile for a given style.
aa983c3d94a9 templater: move stylemap function from hgweb to templater
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7434
diff changeset
262
aa983c3d94a9 templater: move stylemap function from hgweb to templater
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7434
diff changeset
263 Searches mapfile in the following locations:
aa983c3d94a9 templater: move stylemap function from hgweb to templater
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7434
diff changeset
264 1. templatepath/style/map
aa983c3d94a9 templater: move stylemap function from hgweb to templater
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7434
diff changeset
265 2. templatepath/map-style
aa983c3d94a9 templater: move stylemap function from hgweb to templater
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7434
diff changeset
266 3. templatepath/map
aa983c3d94a9 templater: move stylemap function from hgweb to templater
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7434
diff changeset
267 """
aa983c3d94a9 templater: move stylemap function from hgweb to templater
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7434
diff changeset
268
aa983c3d94a9 templater: move stylemap function from hgweb to templater
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7434
diff changeset
269 if paths is None:
aa983c3d94a9 templater: move stylemap function from hgweb to templater
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7434
diff changeset
270 paths = templatepath()
aa983c3d94a9 templater: move stylemap function from hgweb to templater
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7434
diff changeset
271 elif isinstance(paths, str):
8223
02145b700fe4 templater: fix little problem from stylemap() changes
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 8218
diff changeset
272 paths = [paths]
7966
aa983c3d94a9 templater: move stylemap function from hgweb to templater
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7434
diff changeset
273
9842
d3dbdca92458 hgweb: don't choke when an inexistent style is requested (issue1901)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 9372
diff changeset
274 if isinstance(styles, str):
d3dbdca92458 hgweb: don't choke when an inexistent style is requested (issue1901)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 9372
diff changeset
275 styles = [styles]
d3dbdca92458 hgweb: don't choke when an inexistent style is requested (issue1901)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 9372
diff changeset
276
d3dbdca92458 hgweb: don't choke when an inexistent style is requested (issue1901)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 9372
diff changeset
277 for style in styles:
d3dbdca92458 hgweb: don't choke when an inexistent style is requested (issue1901)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 9372
diff changeset
278 if not style:
d3dbdca92458 hgweb: don't choke when an inexistent style is requested (issue1901)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 9372
diff changeset
279 continue
d3dbdca92458 hgweb: don't choke when an inexistent style is requested (issue1901)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 9372
diff changeset
280 locations = [os.path.join(style, 'map'), 'map-' + style]
d3dbdca92458 hgweb: don't choke when an inexistent style is requested (issue1901)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 9372
diff changeset
281 locations.append('map')
d3dbdca92458 hgweb: don't choke when an inexistent style is requested (issue1901)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 9372
diff changeset
282
d3dbdca92458 hgweb: don't choke when an inexistent style is requested (issue1901)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 9372
diff changeset
283 for path in paths:
d3dbdca92458 hgweb: don't choke when an inexistent style is requested (issue1901)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 9372
diff changeset
284 for location in locations:
d3dbdca92458 hgweb: don't choke when an inexistent style is requested (issue1901)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 9372
diff changeset
285 mapfile = os.path.join(path, location)
d3dbdca92458 hgweb: don't choke when an inexistent style is requested (issue1901)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 9372
diff changeset
286 if os.path.isfile(mapfile):
d3dbdca92458 hgweb: don't choke when an inexistent style is requested (issue1901)
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 9372
diff changeset
287 return style, mapfile
7966
aa983c3d94a9 templater: move stylemap function from hgweb to templater
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7434
diff changeset
288
aa983c3d94a9 templater: move stylemap function from hgweb to templater
Dirkjan Ochtman <dirkjan@ochtman.nl>
parents: 7434
diff changeset
289 raise RuntimeError("No hgweb templates found in %r" % paths)