# HG changeset patch # User Gregory Szorc # Date 1517448885 28800 # Node ID 98a00aa0288d83afb92d83cf32554b39b3715acc # Parent e69e65b2b4a98dd206498bf34aafab8a39299fd1 wireprotoserver: move error response handling out of hgweb The exception handler for ErrorResponse has more to do with the wire protocol than the generic HTTP server. Move the code so it lives alongside other wire protocol code. Differential Revision: https://phab.mercurial-scm.org/D2021 diff -r e69e65b2b4a9 -r 98a00aa0288d mercurial/hgweb/hgweb_mod.py --- a/mercurial/hgweb/hgweb_mod.py Wed Jan 31 16:43:46 2018 -0800 +++ b/mercurial/hgweb/hgweb_mod.py Wed Jan 31 17:34:45 2018 -0800 @@ -369,18 +369,7 @@ if cmd in perms: self.check_perm(rctx, req, perms[cmd]) except ErrorResponse as inst: - # A client that sends unbundle without 100-continue will - # break if we respond early. - if (cmd == 'unbundle' and - (req.env.get('HTTP_EXPECT', - '').lower() != '100-continue') or - req.env.get('X-HgHttp2', '')): - req.drain() - else: - req.headers.append((r'Connection', r'Close')) - req.respond(inst, wireprotoserver.HGTYPE, - body='0\n%s\n' % inst) - return '' + return protohandler['handleerror'](inst) return protohandler['dispatch']() diff -r e69e65b2b4a9 -r 98a00aa0288d mercurial/wireprotoserver.py --- a/mercurial/wireprotoserver.py Wed Jan 31 16:43:46 2018 -0800 +++ b/mercurial/wireprotoserver.py Wed Jan 31 17:34:45 2018 -0800 @@ -242,6 +242,7 @@ 'cmd': cmd, 'proto': proto, 'dispatch': lambda: _callhttp(repo, req, proto, cmd), + 'handleerror': lambda ex: _handlehttperror(ex, req, cmd), } def _callhttp(repo, req, proto, cmd): @@ -303,6 +304,22 @@ return [] raise error.ProgrammingError('hgweb.protocol internal failure', rsp) +def _handlehttperror(e, req, cmd): + """Called when an ErrorResponse is raised during HTTP request processing.""" + # A client that sends unbundle without 100-continue will + # break if we respond early. + if (cmd == 'unbundle' and + (req.env.get('HTTP_EXPECT', + '').lower() != '100-continue') or + req.env.get('X-HgHttp2', '')): + req.drain() + else: + req.headers.append((r'Connection', r'Close')) + + req.respond(e, HGTYPE, body='0\n%s\n' % e) + + return '' + class sshserver(abstractserverproto): def __init__(self, ui, repo): self._ui = ui