diff options
author | Shawn O. Pearce <sop@google.com> | 2008-11-06 11:07:14 -0800 |
---|---|---|
committer | Shawn O. Pearce <sop@google.com> | 2008-11-06 11:23:08 -0800 |
commit | 70939e2f73bf118c89cf4af4988dba807c50a0ce (patch) | |
tree | b1849b9a48572876b35cd621192cbb4c712e816e | |
parent | ae6e0949d187c35d79dbc0b21788fdbb2c65bf78 (diff) | |
download | git-repo-70939e2f73bf118c89cf4af4988dba807c50a0ce.tar.gz |
Add <add-remote to-project="..."> to inject additional remotes
This way users can add forks they know about to an existing project
that was already declared in the primary manifest. This is mostly
useful with the Linux kernel project, where multiple forks is quite
common for the main upstream tree (e.g. Linus' tree), a platform
architecture tree (e.g. ARM) and a device specific tree (e.g. the
msm7k tree used by Android).
Signed-off-by: Shawn O. Pearce <sop@google.com>
-rw-r--r-- | docs/manifest-format.txt | 24 | ||||
-rw-r--r-- | manifest.py | 27 |
2 files changed, 43 insertions, 8 deletions
diff --git a/docs/manifest-format.txt b/docs/manifest-format.txt index 2b49d466..5c014d6d 100644 --- a/docs/manifest-format.txt +++ b/docs/manifest-format.txt | |||
@@ -20,7 +20,10 @@ A manifest XML file (e.g. 'default.xml') roughly conforms to the | |||
20 | following DTD: | 20 | following DTD: |
21 | 21 | ||
22 | <!DOCTYPE manifest [ | 22 | <!DOCTYPE manifest [ |
23 | <!ELEMENT manifest (remote*, default?, project*)> | 23 | <!ELEMENT manifest (remote*, |
24 | default?, | ||
25 | project*, | ||
26 | add-remote*)> | ||
24 | 27 | ||
25 | <!ELEMENT remote (EMPTY)> | 28 | <!ELEMENT remote (EMPTY)> |
26 | <!ATTLIST remote name ID #REQUIRED> | 29 | <!ATTLIST remote name ID #REQUIRED> |
@@ -37,6 +40,13 @@ following DTD: | |||
37 | <!ATTLIST project path CDATA #IMPLIED> | 40 | <!ATTLIST project path CDATA #IMPLIED> |
38 | <!ATTLIST project remote IDREF #IMPLIED> | 41 | <!ATTLIST project remote IDREF #IMPLIED> |
39 | <!ATTLIST project revision CDATA #IMPLIED> | 42 | <!ATTLIST project revision CDATA #IMPLIED> |
43 | |||
44 | <!ELEMENT add-remote (EMPTY)> | ||
45 | <!ATTLIST add-remote to-project ID #REQUIRED> | ||
46 | <!ATTLIST add-remote name ID #REQUIRED> | ||
47 | <!ATTLIST add-remote fetch CDATA #REQUIRED> | ||
48 | <!ATTLIST add-remote review CDATA #IMPLIED> | ||
49 | <!ATTLIST add-remote project-name CDATA #IMPLIED> | ||
40 | ]> | 50 | ]> |
41 | 51 | ||
42 | A description of the elements and their attributes follows. | 52 | A description of the elements and their attributes follows. |
@@ -74,6 +84,18 @@ Only permitted when the remote element is nested inside of a project | |||
74 | element (see below). If not given, defaults to the name supplied | 84 | element (see below). If not given, defaults to the name supplied |
75 | in the project's name attribute. | 85 | in the project's name attribute. |
76 | 86 | ||
87 | Element add-remote | ||
88 | ------------------ | ||
89 | |||
90 | Adds a remote to an existing project, whose name is given by the | ||
91 | to-project attribute. This is functionally equivalent to nesting | ||
92 | a remote element under the project, but has the advantage that it | ||
93 | can be specified in the uesr's `local_manifest.xml` to add a remote | ||
94 | to a project declared by the normal manifest. | ||
95 | |||
96 | The element can be used to add a fork of an existing project that | ||
97 | the user needs to work with. | ||
98 | |||
77 | 99 | ||
78 | Element default | 100 | Element default |
79 | --------------- | 101 | --------------- |
diff --git a/manifest.py b/manifest.py index 65455687..2ac1453a 100644 --- a/manifest.py +++ b/manifest.py | |||
@@ -165,6 +165,16 @@ class Manifest(object): | |||
165 | (project.name, self.manifestFile) | 165 | (project.name, self.manifestFile) |
166 | self._projects[project.name] = project | 166 | self._projects[project.name] = project |
167 | 167 | ||
168 | for node in config.childNodes: | ||
169 | if node.nodeName == 'add-remote': | ||
170 | pn = self._reqatt(node, 'to-project') | ||
171 | project = self._projects.get(pn) | ||
172 | if not project: | ||
173 | raise ManifestParseError, \ | ||
174 | 'project %s not defined in %s' % \ | ||
175 | (pn, self.manifestFile) | ||
176 | self._ParseProjectExtraRemote(project, node) | ||
177 | |||
168 | def _AddMetaProjectMirror(self, m): | 178 | def _AddMetaProjectMirror(self, m): |
169 | name = None | 179 | name = None |
170 | m_url = m.GetRemote(m.remote.name).url | 180 | m_url = m.GetRemote(m.remote.name).url |
@@ -281,18 +291,21 @@ class Manifest(object): | |||
281 | 291 | ||
282 | for n in node.childNodes: | 292 | for n in node.childNodes: |
283 | if n.nodeName == 'remote': | 293 | if n.nodeName == 'remote': |
284 | r = self._ParseRemote(n) | 294 | self._ParseProjectExtraRemote(project, n) |
285 | if project.extraRemotes.get(r.name) \ | ||
286 | or project.remote.name == r.name: | ||
287 | raise ManifestParseError, \ | ||
288 | 'duplicate remote %s in project %s in %s' % \ | ||
289 | (r.name, project.name, self.manifestFile) | ||
290 | project.extraRemotes[r.name] = r | ||
291 | elif n.nodeName == 'copyfile': | 295 | elif n.nodeName == 'copyfile': |
292 | self._ParseCopyFile(project, n) | 296 | self._ParseCopyFile(project, n) |
293 | 297 | ||
294 | return project | 298 | return project |
295 | 299 | ||
300 | def _ParseProjectExtraRemote(self, project, n): | ||
301 | r = self._ParseRemote(n) | ||
302 | if project.extraRemotes.get(r.name) \ | ||
303 | or project.remote.name == r.name: | ||
304 | raise ManifestParseError, \ | ||
305 | 'duplicate remote %s in project %s in %s' % \ | ||
306 | (r.name, project.name, self.manifestFile) | ||
307 | project.extraRemotes[r.name] = r | ||
308 | |||
296 | def _ParseCopyFile(self, project, node): | 309 | def _ParseCopyFile(self, project, node): |
297 | src = self._reqatt(node, 'src') | 310 | src = self._reqatt(node, 'src') |
298 | dest = self._reqatt(node, 'dest') | 311 | dest = self._reqatt(node, 'dest') |