Mercurial > public > mercurial-scm > hg-stable
diff mercurial/bundle2.py @ 20892:6fe95448596d
bundle2: read the whole bundle from stream on abort
When the bundle processing abort on unknown mandatory parts, we now makes sure
all the bundle content is read. This avoid leaving the communication channel in
an unrecoverable state.
author | Pierre-Yves David <pierre-yves.david@fb.com> |
---|---|
date | Mon, 24 Mar 2014 17:20:15 -0700 |
parents | 1c6cd23fc221 |
children | c33d7bf53812 |
line wrap: on
line diff
--- a/mercurial/bundle2.py Mon Mar 24 13:02:02 2014 -0700 +++ b/mercurial/bundle2.py Mon Mar 24 17:20:15 2014 -0700 @@ -130,8 +130,11 @@ part type is used to know if a part is mandatory or advisory. If the Part type contains any uppercase char it is considered mandatory. When no handler is known for a Mandatory part, the process is aborted and an exception is raised. -If the part is advisory and no handler is known, the part is ignored. - +If the part is advisory and no handler is known, the part is ignored. When the +process is aborted, the full bundle is still read from the stream to keep the +channel usable. But none of the part read from an abort are processed. In the +future, dropping the stream may become an option for channel we do not care to +preserve. """ import util @@ -205,23 +208,29 @@ # - replace this is a init function soon. # - exception catching unbundler.params - for part in unbundler: - parttype = part.type - # part key are matched lower case - key = parttype.lower() - try: - handler = parthandlermapping[key] - ui.debug('found an handler for part %r\n' % parttype) - except KeyError: - if key != parttype: # mandatory parts + iterparts = iter(unbundler) + try: + for part in iterparts: + parttype = part.type + # part key are matched lower case + key = parttype.lower() + try: + handler = parthandlermapping[key] + ui.debug('found an handler for part %r\n' % parttype) + except KeyError: + if key != parttype: # mandatory parts + # todo: + # - use a more precise exception + raise + ui.debug('ignoring unknown advisory part %r\n' % key) # todo: - # - use a more precise exception - # - consume the bundle2 stream anyway. - raise - ui.debug('ignoring unknown advisory part %r\n' % key) - # todo: consume the part (once we use streamed parts) - continue - handler(repo, part) + # - consume the part once we use streaming + continue + handler(repo, part) + except Exception: + for part in iterparts: + pass # consume the bundle content + raise class bundle20(object): """represent an outgoing bundle2 container