1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
|
# coding: utf-8
"""
This module provides a Locator class for finding template files.
"""
import os
import re
import sys
DEFAULT_EXTENSION = 'mustache'
class Locator(object):
def __init__(self, extension=None):
"""
Construct a template locator.
Arguments:
extension: the template file extension. Defaults to "mustache".
Pass False for no extension (i.e. extensionless template files).
"""
if extension is None:
extension = DEFAULT_EXTENSION
self.template_extension = extension
def _find_path(self, file_name, search_dirs):
"""
Search for the given file, and return the path.
Returns None if the file is not found.
"""
for dir_path in search_dirs:
file_path = os.path.join(dir_path, file_name)
if os.path.exists(file_path):
return file_path
return None
def make_file_name(self, template_name):
file_name = template_name
if self.template_extension is not False:
file_name += os.path.extsep + self.template_extension
return file_name
def make_template_name(self, obj):
"""
Return the canonical template name for an object instance.
This method converts Python-style class names (PEP 8's recommended
CamelCase, aka CapWords) to lower_case_with_underscords. Here
is an example with code:
>>> class HelloWorld(object):
... pass
>>> hi = HelloWorld()
>>>
>>> locator = Locator()
>>> locator.make_template_name(hi)
'hello_world'
"""
template_name = obj.__class__.__name__
def repl(match):
return '_' + match.group(0).lower()
return re.sub('[A-Z]', repl, template_name)[1:]
def locate_path(self, template_name, search_dirs):
"""
Find and return the path to the template with the given name.
Raises an IOError if the template cannot be found.
Arguments:
search_dirs: the list of directories in which to search for templates.
"""
file_name = self.make_file_name(template_name)
path = self._find_path(file_name, search_dirs)
if path is not None:
return path
# TODO: we should probably raise an exception of our own type.
raise IOError('Template %s not found in directories: %s' %
(repr(template_name), repr(search_dirs)))
|