|
1 # Copyright (c) 2008-2010 Nokia Corporation and/or its subsidiary(-ies). |
|
2 # All rights reserved. |
|
3 # This component and the accompanying materials are made available |
|
4 # under the terms of the License "Eclipse Public License v1.0" |
|
5 # which accompanies this distribution, and is available |
|
6 # at the URL "http://www.eclipse.org/legal/epl-v10.html". |
|
7 # |
|
8 # Initial Contributors: |
|
9 # Nokia Corporation - initial contribution. |
|
10 # |
|
11 # Contributors: |
|
12 # |
|
13 from __future__ import with_statement |
|
14 try: |
|
15 from xml.etree import cElementTree as etree |
|
16 except ImportError: |
|
17 from xml.etree import ElementTree as etree |
|
18 from orb.lib import xml_decl |
|
19 import logging |
|
20 import os |
|
21 import copy |
|
22 |
|
23 |
|
24 logger = logging.getLogger('orb.mapcreators.toplevel') |
|
25 |
|
26 |
|
27 def component_map_lookup(rel_dir, mapname): |
|
28 "Checks the file system to see if a component level map exists" |
|
29 exists = os.path.exists(os.path.join(rel_dir, mapname)) |
|
30 if not exists: |
|
31 logger.debug("Asked for a component map for '%s' but it does not exist" % mapname) |
|
32 return exists |
|
33 |
|
34 |
|
35 class TopLevelMapCreator(object): |
|
36 """ |
|
37 Uses the information in a SystemDefinition object to create a top level map that |
|
38 links to all the component level maps together. |
|
39 """ |
|
40 def __init__(self, sysdef, rel_dir, lookupmethod=component_map_lookup): |
|
41 self.sysdef = sysdef |
|
42 self._rel_dir = rel_dir |
|
43 self._lookup = lookupmethod |
|
44 self._root = etree.Element("map", title=sysdef.name, id=sysdef.name) |
|
45 |
|
46 def _add_subelems(self, parent, item): |
|
47 return etree.SubElement(parent, "topichead", navtitle=item.name, id=item.id) |
|
48 |
|
49 def getmap(self): |
|
50 def sort(item): |
|
51 return item.name |
|
52 layers = self.sysdef.layers |
|
53 layers.sort(key=sort) |
|
54 for layer in layers: |
|
55 layer_elem = self._add_subelems(self._root, layer) |
|
56 packages = layer.packages |
|
57 packages.sort(key=sort) |
|
58 for package in packages: |
|
59 pkg_elem = self._add_subelems(layer_elem, package) |
|
60 collections = package.collections |
|
61 collections.sort(key=sort) |
|
62 for collection in collections: |
|
63 col_elem = self._add_subelems(pkg_elem, collection) |
|
64 components = collection.components |
|
65 components.sort(key=sort) |
|
66 for item in components: |
|
67 if self._lookup(self._rel_dir, "cmp_%s.ditamap" % item.id): |
|
68 col_header = self._add_subelems(col_elem, item) |
|
69 etree.SubElement(col_header, "topicref", navtitle=item.name, href="cmp_%s.ditamap" % item.id, format="ditamap") |
|
70 self._remove_empty_headings() |
|
71 return self._root |
|
72 |
|
73 def write(self, path): |
|
74 with open(path, "w") as f: |
|
75 f.write(xml_decl()+"\n") |
|
76 f.write(etree.tostring(self.getmap())) |
|
77 |
|
78 def _remove_empty_headings(self): |
|
79 new_root = copy.deepcopy(self._root) |
|
80 empty_nodes = True |
|
81 nodes_removed = 0 |
|
82 while empty_nodes: |
|
83 nodes_removed = 0 |
|
84 for parent, newparent in zip(self._root.getiterator(), new_root.getiterator()): |
|
85 for child, newchild in zip(parent, newparent): |
|
86 if len(list(child)) == 0 and not 'href' in child.attrib: |
|
87 newparent.remove(newchild) |
|
88 nodes_removed += 1 |
|
89 self._root = copy.deepcopy(new_root) |
|
90 if nodes_removed == 0: |
|
91 empty_nodes = False |
|
92 self._root = new_root |
|
93 |
|
94 |
|
95 ################################################################ |
|
96 # Unit test code |
|
97 ################################################################ |
|
98 import unittest |
|
99 from _shared import StubSysdef |
|
100 |
|
101 |
|
102 def mock_component_map_lookup(mapname, rel_dir): |
|
103 return True |
|
104 |
|
105 |
|
106 class TestTopLevelMapCreator(unittest.TestCase): |
|
107 def setUp(self): |
|
108 self.mc = TopLevelMapCreator(StubSysdef(), ".", mock_component_map_lookup) |
|
109 |
|
110 def test_i_create_a_map_root_from_a_system_definition(self): |
|
111 root = self.mc.getmap() |
|
112 self.assertTrue(root.tag == "map") |
|
113 self.assertTrue(root.attrib['title'] == "Symbian^3") |
|
114 self.assertTrue(root.attrib['id'] == "Symbian^3") |
|
115 |
|
116 def test_i_create_correct_topicheads_from_layers(self): |
|
117 root = self.mc.getmap() |
|
118 self.assertEquals(len(root.findall("topichead")), 1) |
|
119 os_elem = root.findall("topichead")[0] |
|
120 self.assertEqual(os_elem.attrib["navtitle"], "OS") |
|
121 self.assertEqual(os_elem.attrib["id"], "os") |
|
122 |
|
123 def test_i_create_correct_topicheads_from_packages(self): |
|
124 root = self.mc.getmap() |
|
125 os_elem = root.findall("topichead")[0] |
|
126 self.assertEquals(len(os_elem.findall("topichead")), 1) |
|
127 pkg_elem = os_elem.findall("topichead")[0] |
|
128 self.assertEqual(pkg_elem.attrib["navtitle"], "Kernel and Hardware Services") |
|
129 self.assertEqual(pkg_elem.attrib["id"], "kernelhwsrv") |
|
130 |
|
131 def test_i_create_correct_topicheads_from_collections(self): |
|
132 root = self.mc.getmap() |
|
133 os_elem = root.findall("topichead")[0] |
|
134 pkg_elem = os_elem.findall("topichead")[0] |
|
135 self.assertEquals(len(pkg_elem.findall("topichead")), 1) |
|
136 bootldr_elem = pkg_elem.findall("topichead")[0] |
|
137 self.assertEqual(bootldr_elem.attrib["navtitle"], "Board Boot Loader") |
|
138 self.assertEqual(bootldr_elem.attrib["id"], "brdbootldr") |
|
139 |
|
140 def test_i_create_correct_topicheads_for_components(self): |
|
141 root = self.mc.getmap() |
|
142 os_elem = root.findall("topichead")[0] |
|
143 pkg_elem = os_elem.findall("topichead")[0] |
|
144 com_elem = pkg_elem.findall("topichead")[0] |
|
145 comp_elem_header = com_elem.findall("topichead")[0] |
|
146 self.assertEqual(comp_elem_header.attrib["navtitle"], "Boot Loader") |
|
147 self.assertEqual(comp_elem_header.attrib["id"], "ubootldr") |
|
148 |
|
149 def test_i_create_correct_topicrefs_from_components(self): |
|
150 root = self.mc.getmap() |
|
151 os_elem = root.findall("topichead")[0] |
|
152 pkg_elem = os_elem.findall("topichead")[0] |
|
153 comp_elem = pkg_elem.findall("topichead")[0] |
|
154 comp_elem_header = comp_elem.findall("topichead")[0] |
|
155 self.assertEquals(len(comp_elem_header.findall("topicref")), 1) |
|
156 ubootldr_elem = comp_elem_header.findall("topicref")[0] |
|
157 self.assertEqual(ubootldr_elem.attrib["navtitle"], "Boot Loader") |
|
158 self.assertEqual(ubootldr_elem.attrib["href"], "cmp_ubootldr.ditamap") |
|
159 self.assertEqual(ubootldr_elem.attrib["format"], "ditamap") |
|
160 |
|
161 def test_i_can_remove_empty_headings_from_a_top_level_map(self): |
|
162 self.mc._root = etree.fromstring(empty_headings_toc) |
|
163 self.mc._remove_empty_headings() |
|
164 self.assertEquals(etree.tostring(self.mc._root), removed_empty_headings_toc) |
|
165 |
|
166 def test_i_sort_the_map(self): |
|
167 root = self.mc.getmap() |
|
168 os_elem = root.findall("topichead")[0] |
|
169 pkg_elem = os_elem.findall("topichead")[0] |
|
170 com_elem = pkg_elem.findall("topichead")[0] |
|
171 comp_elem_header = com_elem.findall("topichead")[0] |
|
172 self.assertEqual(comp_elem_header.attrib["navtitle"], "Boot Loader") |
|
173 comp_elem_header = com_elem.findall("topichead")[1] |
|
174 self.assertEqual(comp_elem_header.attrib["navtitle"], "Kernel Architecture") |
|
175 |
|
176 |
|
177 empty_headings_toc = """\ |
|
178 <map id="Symbian^3" title="Symbian^3"> |
|
179 <topichead id="os" navtitle="OS" > |
|
180 <topichead id="kernelhwsrv" navtitle="Kernel and Hardware Services"> |
|
181 <topichead id="brdbootldr" navtitle="Board Boot Loader"> |
|
182 <topichead id="ubootldr" navtitle="Boot Loader"/> |
|
183 </topichead> |
|
184 <topichead id="bsptemplate" navtitle="Board Support Package Template"> |
|
185 <topichead id="asspandvariant" navtitle="Template ASSP and Variant"> |
|
186 <topicref format="ditamap" href="cmp_template_variant.ditamap" navtitle="template_variant" /> |
|
187 </topichead> |
|
188 </topichead> |
|
189 </topichead> |
|
190 </topichead> |
|
191 </map>""" |
|
192 |
|
193 |
|
194 removed_empty_headings_toc = """\ |
|
195 <map id="Symbian^3" title="Symbian^3"> |
|
196 <topichead id="os" navtitle="OS"> |
|
197 <topichead id="kernelhwsrv" navtitle="Kernel and Hardware Services"> |
|
198 <topichead id="bsptemplate" navtitle="Board Support Package Template"> |
|
199 <topichead id="asspandvariant" navtitle="Template ASSP and Variant"> |
|
200 <topicref format="ditamap" href="cmp_template_variant.ditamap" navtitle="template_variant" /> |
|
201 </topichead> |
|
202 </topichead> |
|
203 </topichead> |
|
204 </topichead> |
|
205 </map>""" |