summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorDoug Anderson <dianders@google.com>2010-11-01 15:08:06 -0700
committerDoug Anderson <dianders@google.com>2010-11-01 15:08:06 -0700
commit2b8db3ce3e7344b9f3b5216637c5af0d54be5656 (patch)
tree10f0c759efdade6a556eac16b46160b4843135d5
parent5df6de075e5fb674368d38f858419425bc8d8d07 (diff)
downloadgit-repo-2b8db3ce3e7344b9f3b5216637c5af0d54be5656.tar.gz
Added feature to print a <notice> from manifest at the end of a sync.v1.7.1
This feature is used to convey information on a when a branch has ceased development or if it is an experimental branch with a few gotchas, etc. You add it to your manifest XML by doing something like this: <manifest> <notice> NOTE TO DEVELOPERS: If you checkin code, you have to pinky-swear that it contains no bugs. Anyone who breaks their promise will have tomatoes thrown at them in the team meeting. Be sure to bring an extra set of clothes. </notice> <remote ... /> ... </manifest> Carriage returns and indentation are relevant for the text in this tag. This feature was requested by Anush Elangovan on the ChromiumOS team.
-rw-r--r--docs/manifest-format.txt5
-rw-r--r--manifest_xml.py62
-rw-r--r--subcmds/sync.py5
3 files changed, 71 insertions, 1 deletions
diff --git a/docs/manifest-format.txt b/docs/manifest-format.txt
index 211344ee..2e1c8c35 100644
--- a/docs/manifest-format.txt
+++ b/docs/manifest-format.txt
@@ -20,12 +20,15 @@ A manifest XML file (e.g. 'default.xml') roughly conforms to the
20following DTD: 20following DTD:
21 21
22 <!DOCTYPE manifest [ 22 <!DOCTYPE manifest [
23 <!ELEMENT manifest (remote*, 23 <!ELEMENT manifest (notice?,
24 remote*,
24 default?, 25 default?,
25 manifest-server?, 26 manifest-server?,
26 remove-project*, 27 remove-project*,
27 project*)> 28 project*)>
28 29
30 <!ELEMENT notice (#PCDATA)>
31
29 <!ELEMENT remote (EMPTY)> 32 <!ELEMENT remote (EMPTY)>
30 <!ATTLIST remote name ID #REQUIRED> 33 <!ATTLIST remote name ID #REQUIRED>
31 <!ATTLIST remote fetch CDATA #REQUIRED> 34 <!ATTLIST remote fetch CDATA #REQUIRED>
diff --git a/manifest_xml.py b/manifest_xml.py
index d0c9debe..9d68f09f 100644
--- a/manifest_xml.py
+++ b/manifest_xml.py
@@ -107,6 +107,15 @@ class XmlManifest(object):
107 root = doc.createElement('manifest') 107 root = doc.createElement('manifest')
108 doc.appendChild(root) 108 doc.appendChild(root)
109 109
110 # Save out the notice. There's a little bit of work here to give it the
111 # right whitespace, which assumes that the notice is automatically indented
112 # by 4 by minidom.
113 if self.notice:
114 notice_element = root.appendChild(doc.createElement('notice'))
115 notice_lines = self.notice.splitlines()
116 indented_notice = ('\n'.join(" "*4 + line for line in notice_lines))[4:]
117 notice_element.appendChild(doc.createTextNode(indented_notice))
118
110 d = self.default 119 d = self.default
111 sort_remotes = list(self.remotes.keys()) 120 sort_remotes = list(self.remotes.keys())
112 sort_remotes.sort() 121 sort_remotes.sort()
@@ -180,6 +189,11 @@ class XmlManifest(object):
180 return self._default 189 return self._default
181 190
182 @property 191 @property
192 def notice(self):
193 self._Load()
194 return self._notice
195
196 @property
183 def manifest_server(self): 197 def manifest_server(self):
184 self._Load() 198 self._Load()
185 return self._manifest_server 199 return self._manifest_server
@@ -193,6 +207,7 @@ class XmlManifest(object):
193 self._projects = {} 207 self._projects = {}
194 self._remotes = {} 208 self._remotes = {}
195 self._default = None 209 self._default = None
210 self._notice = None
196 self.branch = None 211 self.branch = None
197 self._manifest_server = None 212 self._manifest_server = None
198 213
@@ -264,6 +279,14 @@ class XmlManifest(object):
264 self._default = _Default() 279 self._default = _Default()
265 280
266 for node in config.childNodes: 281 for node in config.childNodes:
282 if node.nodeName == 'notice':
283 if self._notice is not None:
284 raise ManifestParseError, \
285 'duplicate notice in %s' % \
286 (self.manifestFile)
287 self._notice = self._ParseNotice(node)
288
289 for node in config.childNodes:
267 if node.nodeName == 'manifest-server': 290 if node.nodeName == 'manifest-server':
268 url = self._reqatt(node, 'url') 291 url = self._reqatt(node, 'url')
269 if self._manifest_server is not None: 292 if self._manifest_server is not None:
@@ -338,6 +361,45 @@ class XmlManifest(object):
338 d.revisionExpr = None 361 d.revisionExpr = None
339 return d 362 return d
340 363
364 def _ParseNotice(self, node):
365 """
366 reads a <notice> element from the manifest file
367
368 The <notice> element is distinct from other tags in the XML in that the
369 data is conveyed between the start and end tag (it's not an empty-element
370 tag).
371
372 The white space (carriage returns, indentation) for the notice element is
373 relevant and is parsed in a way that is based on how python docstrings work.
374 In fact, the code is remarkably similar to here:
375 http://www.python.org/dev/peps/pep-0257/
376 """
377 # Get the data out of the node...
378 notice = node.childNodes[0].data
379
380 # Figure out minimum indentation, skipping the first line (the same line
381 # as the <notice> tag)...
382 minIndent = sys.maxint
383 lines = notice.splitlines()
384 for line in lines[1:]:
385 lstrippedLine = line.lstrip()
386 if lstrippedLine:
387 indent = len(line) - len(lstrippedLine)
388 minIndent = min(indent, minIndent)
389
390 # Strip leading / trailing blank lines and also indentation.
391 cleanLines = [lines[0].strip()]
392 for line in lines[1:]:
393 cleanLines.append(line[minIndent:].rstrip())
394
395 # Clear completely blank lines from front and back...
396 while cleanLines and not cleanLines[0]:
397 del cleanLines[0]
398 while cleanLines and not cleanLines[-1]:
399 del cleanLines[-1]
400
401 return '\n'.join(cleanLines)
402
341 def _ParseProject(self, node): 403 def _ParseProject(self, node):
342 """ 404 """
343 reads a <project> element from the manifest file 405 reads a <project> element from the manifest file
diff --git a/subcmds/sync.py b/subcmds/sync.py
index ca78467b..d6ea442a 100644
--- a/subcmds/sync.py
+++ b/subcmds/sync.py
@@ -361,6 +361,11 @@ uncommitted changes are present' % project.relpath
361 if not syncbuf.Finish(): 361 if not syncbuf.Finish():
362 sys.exit(1) 362 sys.exit(1)
363 363
364 # If there's a notice that's supposed to print at the end of the sync, print
365 # it now...
366 if self.manifest.notice:
367 print self.manifest.notice
368
364def _PostRepoUpgrade(manifest): 369def _PostRepoUpgrade(manifest):
365 for project in manifest.projects.values(): 370 for project in manifest.projects.values():
366 if project.Exists: 371 if project.Exists: