annotate piecrust/data/linker.py @ 238:4dce0e61b48c

internal: Fix bug with the default source when listing `/` path.
author Ludovic Chabant <ludovic@chabant.com>
date Sun, 15 Feb 2015 22:47:46 -0800
parents 879fe1457e48
children f130365568ff
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
172
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
1 import logging
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
2 import collections
212
701591ebfcba data: Improve the Linker and RecursiveLinker features. Add tests.
Ludovic Chabant <ludovic@chabant.com>
parents: 172
diff changeset
3 from piecrust.data.base import PaginationData, IPaginationSource
701591ebfcba data: Improve the Linker and RecursiveLinker features. Add tests.
Ludovic Chabant <ludovic@chabant.com>
parents: 172
diff changeset
4 from piecrust.data.iterators import PageIterator
172
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
5 from piecrust.sources.base import IListableSource, build_pages
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
6
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
7
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
8 logger = logging.getLogger(__name__)
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
9
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
10
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
11 class LinkedPageData(PaginationData):
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
12 """ Class whose instances get returned when iterating on a `Linker`
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
13 or `RecursiveLinker`. It's just like what gets usually returned by
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
14 `Paginator` and other page iterators, but with a few additional data
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
15 like hierarchical data.
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
16 """
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
17 debug_render = ['is_dir', 'is_self'] + PaginationData.debug_render
172
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
18
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
19 def __init__(self, page):
172
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
20 super(LinkedPageData, self).__init__(page)
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
21 self.name = page.config.get('__linker_name')
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
22 self.is_self = page.config.get('__linker_is_self')
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
23 self.children = page.config.get('__linker_child')
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
24 self.is_dir = (self.children is not None)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
25 self.is_page = True
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
26
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
27 self.mapLoader('*', self._linkerChildLoader)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
28
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
29 def _linkerChildLoader(self, name):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
30 return getattr(self.children, name)
172
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
31
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
32
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
33 class LinkedPageDataBuilderIterator(object):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
34 """ Iterator that builds `LinkedPageData` out of pages.
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
35 """
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
36 def __init__(self, it):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
37 self.it = it
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
38
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
39 def __iter__(self):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
40 for item in self.it:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
41 yield LinkedPageData(item)
3
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
42
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
43
227
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
44 class LinkerSource(IPaginationSource):
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
45 """ Source iterator that returns pages given by `Linker`.
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
46 """
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
47 def __init__(self, pages, orig_source):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
48 self._pages = list(pages)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
49 self._orig_source = None
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
50 if isinstance(orig_source, IPaginationSource):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
51 self._orig_source = orig_source
227
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
52
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
53 def getItemsPerPage(self):
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
54 raise NotImplementedError()
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
55
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
56 def getSourceIterator(self):
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
57 return self._pages
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
58
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
59 def getSorterIterator(self, it):
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
60 # We don't want to sort the pages -- we expect the original source
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
61 # to return hierarchical items in the order it wants already.
227
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
62 return None
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
63
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
64 def getTailIterator(self, it):
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
65 return LinkedPageDataBuilderIterator(it)
227
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
66
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
67 def getPaginationFilter(self, page):
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
68 return None
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
69
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
70 def getSettingAccessor(self):
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
71 if self._orig_source:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
72 return self._orig_source.getSettingAccessor()
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
73 return None
212
701591ebfcba data: Improve the Linker and RecursiveLinker features. Add tests.
Ludovic Chabant <ludovic@chabant.com>
parents: 172
diff changeset
74
701591ebfcba data: Improve the Linker and RecursiveLinker features. Add tests.
Ludovic Chabant <ludovic@chabant.com>
parents: 172
diff changeset
75
3
f485ba500df3 Gigantic change to basically make PieCrust 2 vaguely functional.
Ludovic Chabant <ludovic@chabant.com>
parents:
diff changeset
76 class Linker(object):
172
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
77 debug_render_doc = """Provides access to sibling and children pages."""
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
78
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
79 def __init__(self, source, *, name=None, dir_path=None, page_path=None):
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
80 self._source = source
172
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
81 self._name = name
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
82 self._dir_path = dir_path
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
83 self._root_page_path = page_path
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
84 self._items = None
172
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
85
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
86 self.is_dir = True
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
87 self.is_page = False
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
88 self.is_self = False
172
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
89
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
90 def __iter__(self):
227
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
91 return iter(self.pages)
212
701591ebfcba data: Improve the Linker and RecursiveLinker features. Add tests.
Ludovic Chabant <ludovic@chabant.com>
parents: 172
diff changeset
92
227
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
93 def __getattr__(self, name):
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
94 self._load()
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
95 try:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
96 item = self._items[name]
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
97 except KeyError:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
98 raise AttributeError()
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
99
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
100 if isinstance(item, Linker):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
101 return item
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
102
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
103 return LinkedPageData(item)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
104
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
105 @property
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
106 def name(self):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
107 if self._name is None:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
108 self._load()
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
109 return self._name
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
110
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
111 @property
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
112 def children(self):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
113 return self._iterItems(0)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
114
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
115 @property
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
116 def pages(self):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
117 return self._iterItems(0, filter_page_items)
227
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
118
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
119 @property
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
120 def directories(self):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
121 return self._iterItems(0, filter_directory_items)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
122
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
123 @property
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
124 def all(self):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
125 return self._iterItems()
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
126
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
127 @property
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
128 def allpages(self):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
129 return self._iterItems(-1, filter_page_items)
227
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
130
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
131 @property
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
132 def alldirectories(self):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
133 return self._iterItems(-1, filter_directory_items)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
134
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
135 @property
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
136 def root(self):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
137 return self.forpath('/')
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
138
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
139 def forpath(self, rel_path):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
140 return Linker(self._source,
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
141 name='.', dir_path=rel_path,
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
142 page_path=self._root_page_path)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
143
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
144 def _iterItems(self, max_depth=-1, filter_func=None):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
145 items = walk_linkers(self, max_depth=max_depth,
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
146 filter_func=filter_func)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
147 src = LinkerSource(items, self._source)
227
d6d0e4976beb data: Make the `Linekr` use the new `getSettingAccessor` API.
Ludovic Chabant <ludovic@chabant.com>
parents: 212
diff changeset
148 return PageIterator(src)
212
701591ebfcba data: Improve the Linker and RecursiveLinker features. Add tests.
Ludovic Chabant <ludovic@chabant.com>
parents: 172
diff changeset
149
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
150 def _load(self):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
151 if self._items is not None:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
152 return
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
153
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
154 is_listable = isinstance(self._source, IListableSource)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
155 if not is_listable:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
156 raise Exception("Source '%s' can't be listed." % self._source.name)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
157
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
158 if self._root_page_path is not None:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
159 if self._name is None:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
160 self._name = self._source.getBasename(self._root_page_path)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
161 if self._dir_path is None:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
162 self._dir_path = self._source.getDirpath(self._root_page_path)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
163
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
164 if self._dir_path is None:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
165 raise Exception("This linker has no directory to start from.")
212
701591ebfcba data: Improve the Linker and RecursiveLinker features. Add tests.
Ludovic Chabant <ludovic@chabant.com>
parents: 172
diff changeset
166
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
167 items = list(self._source.listPath(self._dir_path))
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
168 self._items = collections.OrderedDict()
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
169 with self._source.app.env.page_repository.startBatchGet():
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
170 for is_dir, name, data in items:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
171 # If `is_dir` is true, `data` will be the directory's source
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
172 # path. If not, it will be a page factory.
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
173 if is_dir:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
174 item = Linker(self._source,
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
175 name=name, dir_path=data)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
176 else:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
177 item = data.buildPage()
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
178 item.config.set('__linker_name', name)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
179 item.config.set('__linker_is_self',
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
180 item.rel_path == self._root_page_path)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
181
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
182 existing = self._items.get(name)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
183 if existing is None:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
184 self._items[name] = item
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
185 elif is_dir:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
186 # The current item is a directory. The existing item
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
187 # should be a page.
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
188 existing.config.set('__linker_child', item)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
189 else:
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
190 # The current item is a page. The existing item should
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
191 # be a directory.
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
192 item.config.set('__linker_child', existing)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
193 self._items[name] = item
172
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
194
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
195
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
196 def filter_page_items(item):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
197 return not isinstance(item, Linker)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
198
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
199
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
200 def filter_directory_items(item):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
201 return isinstance(item, linker)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
202
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
203
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
204 def walk_linkers(linker, depth=0, max_depth=-1, filter_func=None):
172
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
205 linker._load()
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
206 for item in linker._items.values():
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
207 if not filter_func or filter_func(item):
172
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
208 yield item
4fc1d306046b linker: Actually implement the `Linker` class, and use it in the page data.
Ludovic Chabant <ludovic@chabant.com>
parents: 3
diff changeset
209
237
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
210 if (isinstance(item, Linker) and
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
211 (max_depth < 0 or depth + 1 <= max_depth)):
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
212 yield from walk_linkers(item, depth + 1, max_depth)
879fe1457e48 data: `Linker` refactor.
Ludovic Chabant <ludovic@chabant.com>
parents: 227
diff changeset
213