hgext/largefiles/proto.py
author Mads Kiilerich <madski@unity3d.com>
Mon, 28 Jan 2013 15:19:44 +0100
branchstable
changeset 18488 a977b42df8b3
parent 18298 3598c585e464
child 18922 d2c4d37f7db5
permissions -rw-r--r--
largefiles: don't verify largefile hashes on servers when processing statlfile When changesets referencing largefiles are pushed then the corresponding largefiles will be pushed too - unless the target already has them. The client will use statlfile to make sure it only sends largefiles that the target doesn't have. The server would however on every statlfile check that the content of the largefile had the expected hash. What should be cheap thus became an expensive operation that trashed the disk and the cache. Largefile hashes are already checked by putlfile before being stored on the server. A server should thus be able to keep its largefile store free of errors - even more than it can keep revlogs free of errors. Verification should happen when running 'hg verify' locally on the server. Rehashing every largefile on every remote stat is too expensive. Clients will also stat lfiles before downloading them. When the server verified the hash in stat it meant that it had to read the file twice to serve it. With this change the server will assume its own hashes are ok without checking them on every statlfile. Some consequences of this change: - in case of server side corruption the problem will be detected by the existing check on the client side - not on server side - clients that could upload an uncorrupted largefile when pushing will no longer magically heal the server (and break hardlinks) - a client will now only upload its uncorrupted files after the corrupted file has been removed on the server side - client side verify will no longer report corruption in files it doesn't have (Issue3123 discussed related problems - and how they have been fixed.)
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
     1
# Copyright 2011 Fog Creek Software
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
     2
#
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
     3
# This software may be used and distributed according to the terms of the
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
     4
# GNU General Public License version 2 or any later version.
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
     5
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
     6
import os
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
     7
import urllib2
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
     8
17192
1ac628cd7113 peer: introduce real peer classes
Peter Arrenbrecht <peter.arrenbrecht@gmail.com>
parents: 17127
diff changeset
     9
from mercurial import error, httppeer, util, wireproto
17127
9e1616307c4c largefiles: batch statlfile requests when pushing a largefiles repo (issue3386)
Na'Tosha Bard <natosha@unity3d.com>
parents: 16594
diff changeset
    10
from mercurial.wireproto import batchable, future
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    11
from mercurial.i18n import _
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    12
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    13
import lfutil
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    14
15255
7ab05d752405 largefiles: cosmetics, whitespace, code style
Greg Ward <greg@gerg.ca>
parents: 15252
diff changeset
    15
LARGEFILES_REQUIRED_MSG = ('\nThis repository uses the largefiles extension.'
7ab05d752405 largefiles: cosmetics, whitespace, code style
Greg Ward <greg@gerg.ca>
parents: 15252
diff changeset
    16
                           '\n\nPlease enable it in your Mercurial config '
7ab05d752405 largefiles: cosmetics, whitespace, code style
Greg Ward <greg@gerg.ca>
parents: 15252
diff changeset
    17
                           'file.\n')
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    18
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    19
def putlfile(repo, proto, sha):
15317
41f371150ccb largefiles: make the store primary, and the user cache secondary
Benjamin Pollack <benjamin@bitquabit.com>
parents: 15316
diff changeset
    20
    '''Put a largefile into a repository's local store and into the
41f371150ccb largefiles: make the store primary, and the user cache secondary
Benjamin Pollack <benjamin@bitquabit.com>
parents: 15316
diff changeset
    21
    user cache.'''
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    22
    proto.redirect()
15391
a5a6a9b7f3b9 largefiles: replace tempfile.NamedTemporaryFile with tempfile.mkstemp
Hao Lian <hao@fogcreek.com>
parents: 15317
diff changeset
    23
16594
5516fdf3fe24 largefiles: in putlfile, ensure tempfile's directory exists prior to creation
hlian
parents: 16247
diff changeset
    24
    path = lfutil.storepath(repo, sha)
5516fdf3fe24 largefiles: in putlfile, ensure tempfile's directory exists prior to creation
hlian
parents: 16247
diff changeset
    25
    util.makedirs(os.path.dirname(path))
5516fdf3fe24 largefiles: in putlfile, ensure tempfile's directory exists prior to creation
hlian
parents: 16247
diff changeset
    26
    tmpfp = util.atomictempfile(path, createmode=repo.store.createmode)
5516fdf3fe24 largefiles: in putlfile, ensure tempfile's directory exists prior to creation
hlian
parents: 16247
diff changeset
    27
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    28
    try:
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    29
        try:
15391
a5a6a9b7f3b9 largefiles: replace tempfile.NamedTemporaryFile with tempfile.mkstemp
Hao Lian <hao@fogcreek.com>
parents: 15317
diff changeset
    30
            proto.getfile(tmpfp)
16155
1b2b42e866be largefiles: respect store.createmode and avoid extra file copy
Martin Geisler <mg@aragost.com>
parents: 15778
diff changeset
    31
            tmpfp._fp.seek(0)
1b2b42e866be largefiles: respect store.createmode and avoid extra file copy
Martin Geisler <mg@aragost.com>
parents: 15778
diff changeset
    32
            if sha != lfutil.hexsha1(tmpfp._fp):
15778
f15c646bffc7 largefiles: display remote errors from putlfile (issue3123) (issue3149)
Kevin Gessner <kevin@fogcreek.com>
parents: 15391
diff changeset
    33
                raise IOError(0, _('largefile contents do not match hash'))
15391
a5a6a9b7f3b9 largefiles: replace tempfile.NamedTemporaryFile with tempfile.mkstemp
Hao Lian <hao@fogcreek.com>
parents: 15317
diff changeset
    34
            tmpfp.close()
16155
1b2b42e866be largefiles: respect store.createmode and avoid extra file copy
Martin Geisler <mg@aragost.com>
parents: 15778
diff changeset
    35
            lfutil.linktousercache(repo, sha)
15391
a5a6a9b7f3b9 largefiles: replace tempfile.NamedTemporaryFile with tempfile.mkstemp
Hao Lian <hao@fogcreek.com>
parents: 15317
diff changeset
    36
        except IOError, e:
15778
f15c646bffc7 largefiles: display remote errors from putlfile (issue3123) (issue3149)
Kevin Gessner <kevin@fogcreek.com>
parents: 15391
diff changeset
    37
            repo.ui.warn(_('largefiles: failed to put %s into store: %s') %
f15c646bffc7 largefiles: display remote errors from putlfile (issue3123) (issue3149)
Kevin Gessner <kevin@fogcreek.com>
parents: 15391
diff changeset
    38
                         (sha, e.strerror))
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    39
            return wireproto.pushres(1)
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    40
    finally:
16155
1b2b42e866be largefiles: respect store.createmode and avoid extra file copy
Martin Geisler <mg@aragost.com>
parents: 15778
diff changeset
    41
        tmpfp.discard()
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    42
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    43
    return wireproto.pushres(0)
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    44
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    45
def getlfile(repo, proto, sha):
15252
6e809bb4f969 largefiles: improve comments, internal docstrings
Greg Ward <greg@gerg.ca>
parents: 15224
diff changeset
    46
    '''Retrieve a largefile from the repository-local cache or system
6e809bb4f969 largefiles: improve comments, internal docstrings
Greg Ward <greg@gerg.ca>
parents: 15224
diff changeset
    47
    cache.'''
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    48
    filename = lfutil.findfile(repo, sha)
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    49
    if not filename:
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    50
        raise util.Abort(_('requested largefile %s not present in cache') % sha)
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    51
    f = open(filename, 'rb')
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    52
    length = os.fstat(f.fileno())[6]
15252
6e809bb4f969 largefiles: improve comments, internal docstrings
Greg Ward <greg@gerg.ca>
parents: 15224
diff changeset
    53
6e809bb4f969 largefiles: improve comments, internal docstrings
Greg Ward <greg@gerg.ca>
parents: 15224
diff changeset
    54
    # Since we can't set an HTTP content-length header here, and
6e809bb4f969 largefiles: improve comments, internal docstrings
Greg Ward <greg@gerg.ca>
parents: 15224
diff changeset
    55
    # Mercurial core provides no way to give the length of a streamres
6e809bb4f969 largefiles: improve comments, internal docstrings
Greg Ward <greg@gerg.ca>
parents: 15224
diff changeset
    56
    # (and reading the entire file into RAM would be ill-advised), we
6e809bb4f969 largefiles: improve comments, internal docstrings
Greg Ward <greg@gerg.ca>
parents: 15224
diff changeset
    57
    # just send the length on the first line of the response, like the
6e809bb4f969 largefiles: improve comments, internal docstrings
Greg Ward <greg@gerg.ca>
parents: 15224
diff changeset
    58
    # ssh proto does for string responses.
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    59
    def generator():
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    60
        yield '%d\n' % length
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    61
        for chunk in f:
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    62
            yield chunk
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    63
    return wireproto.streamres(generator())
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    64
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    65
def statlfile(repo, proto, sha):
18488
a977b42df8b3 largefiles: don't verify largefile hashes on servers when processing statlfile
Mads Kiilerich <madski@unity3d.com>
parents: 18298
diff changeset
    66
    '''Return '2\n' if the largefile is missing, '0\n' if it seems to be in
a977b42df8b3 largefiles: don't verify largefile hashes on servers when processing statlfile
Mads Kiilerich <madski@unity3d.com>
parents: 18298
diff changeset
    67
    good condition.
a977b42df8b3 largefiles: don't verify largefile hashes on servers when processing statlfile
Mads Kiilerich <madski@unity3d.com>
parents: 18298
diff changeset
    68
a977b42df8b3 largefiles: don't verify largefile hashes on servers when processing statlfile
Mads Kiilerich <madski@unity3d.com>
parents: 18298
diff changeset
    69
    The value 1 is reserved for mismatched checksum, but that is too expensive
a977b42df8b3 largefiles: don't verify largefile hashes on servers when processing statlfile
Mads Kiilerich <madski@unity3d.com>
parents: 18298
diff changeset
    70
    to be verified on every stat and must be caught be running 'hg verify'
a977b42df8b3 largefiles: don't verify largefile hashes on servers when processing statlfile
Mads Kiilerich <madski@unity3d.com>
parents: 18298
diff changeset
    71
    server side.'''
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    72
    filename = lfutil.findfile(repo, sha)
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    73
    if not filename:
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    74
        return '2\n'
18488
a977b42df8b3 largefiles: don't verify largefile hashes on servers when processing statlfile
Mads Kiilerich <madski@unity3d.com>
parents: 18298
diff changeset
    75
    return '0\n'
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    76
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    77
def wirereposetup(ui, repo):
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    78
    class lfileswirerepository(repo.__class__):
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    79
        def putlfile(self, sha, fd):
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    80
            # unfortunately, httprepository._callpush tries to convert its
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    81
            # input file-like into a bundle before sending it, so we can't use
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    82
            # it ...
17192
1ac628cd7113 peer: introduce real peer classes
Peter Arrenbrecht <peter.arrenbrecht@gmail.com>
parents: 17127
diff changeset
    83
            if issubclass(self.__class__, httppeer.httppeer):
15778
f15c646bffc7 largefiles: display remote errors from putlfile (issue3123) (issue3149)
Kevin Gessner <kevin@fogcreek.com>
parents: 15391
diff changeset
    84
                res = None
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    85
                try:
15778
f15c646bffc7 largefiles: display remote errors from putlfile (issue3123) (issue3149)
Kevin Gessner <kevin@fogcreek.com>
parents: 15391
diff changeset
    86
                    res = self._call('putlfile', data=fd, sha=sha,
f15c646bffc7 largefiles: display remote errors from putlfile (issue3123) (issue3149)
Kevin Gessner <kevin@fogcreek.com>
parents: 15391
diff changeset
    87
                        headers={'content-type':'application/mercurial-0.1'})
f15c646bffc7 largefiles: display remote errors from putlfile (issue3123) (issue3149)
Kevin Gessner <kevin@fogcreek.com>
parents: 15391
diff changeset
    88
                    d, output = res.split('\n', 1)
f15c646bffc7 largefiles: display remote errors from putlfile (issue3123) (issue3149)
Kevin Gessner <kevin@fogcreek.com>
parents: 15391
diff changeset
    89
                    for l in output.splitlines(True):
f15c646bffc7 largefiles: display remote errors from putlfile (issue3123) (issue3149)
Kevin Gessner <kevin@fogcreek.com>
parents: 15391
diff changeset
    90
                        self.ui.warn(_('remote: '), l, '\n')
f15c646bffc7 largefiles: display remote errors from putlfile (issue3123) (issue3149)
Kevin Gessner <kevin@fogcreek.com>
parents: 15391
diff changeset
    91
                    return int(d)
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    92
                except (ValueError, urllib2.HTTPError):
15778
f15c646bffc7 largefiles: display remote errors from putlfile (issue3123) (issue3149)
Kevin Gessner <kevin@fogcreek.com>
parents: 15391
diff changeset
    93
                    self.ui.warn(_('unexpected putlfile response: %s') % res)
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    94
                    return 1
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    95
            # ... but we can't use sshrepository._call because the data=
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    96
            # argument won't get sent, and _callpush does exactly what we want
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    97
            # in this case: send the data straight through
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    98
            else:
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
    99
                try:
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   100
                    ret, output = self._callpush("putlfile", fd, sha=sha)
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   101
                    if ret == "":
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   102
                        raise error.ResponseError(_('putlfile failed:'),
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   103
                                output)
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   104
                    return int(ret)
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   105
                except IOError:
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   106
                    return 1
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   107
                except ValueError:
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   108
                    raise error.ResponseError(
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   109
                        _('putlfile failed (unexpected response):'), ret)
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   110
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   111
        def getlfile(self, sha):
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   112
            stream = self._callstream("getlfile", sha=sha)
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   113
            length = stream.readline()
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   114
            try:
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   115
                length = int(length)
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   116
            except ValueError:
15170
c1a4a3220711 largefiles: fix over-long lines
Matt Mackall <mpm@selenic.com>
parents: 15168
diff changeset
   117
                self._abort(error.ResponseError(_("unexpected response:"),
c1a4a3220711 largefiles: fix over-long lines
Matt Mackall <mpm@selenic.com>
parents: 15168
diff changeset
   118
                                                length))
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   119
            return (length, stream)
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   120
17127
9e1616307c4c largefiles: batch statlfile requests when pushing a largefiles repo (issue3386)
Na'Tosha Bard <natosha@unity3d.com>
parents: 16594
diff changeset
   121
        @batchable
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   122
        def statlfile(self, sha):
17127
9e1616307c4c largefiles: batch statlfile requests when pushing a largefiles repo (issue3386)
Na'Tosha Bard <natosha@unity3d.com>
parents: 16594
diff changeset
   123
            f = future()
9e1616307c4c largefiles: batch statlfile requests when pushing a largefiles repo (issue3386)
Na'Tosha Bard <natosha@unity3d.com>
parents: 16594
diff changeset
   124
            result = {'sha': sha}
9e1616307c4c largefiles: batch statlfile requests when pushing a largefiles repo (issue3386)
Na'Tosha Bard <natosha@unity3d.com>
parents: 16594
diff changeset
   125
            yield result, f
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   126
            try:
17127
9e1616307c4c largefiles: batch statlfile requests when pushing a largefiles repo (issue3386)
Na'Tosha Bard <natosha@unity3d.com>
parents: 16594
diff changeset
   127
                yield int(f.value)
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   128
            except (ValueError, urllib2.HTTPError):
15252
6e809bb4f969 largefiles: improve comments, internal docstrings
Greg Ward <greg@gerg.ca>
parents: 15224
diff changeset
   129
                # If the server returns anything but an integer followed by a
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   130
                # newline, newline, it's not speaking our language; if we get
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   131
                # an HTTP error, we can't be sure the largefile is present;
15252
6e809bb4f969 largefiles: improve comments, internal docstrings
Greg Ward <greg@gerg.ca>
parents: 15224
diff changeset
   132
                # either way, consider it missing.
17127
9e1616307c4c largefiles: batch statlfile requests when pushing a largefiles repo (issue3386)
Na'Tosha Bard <natosha@unity3d.com>
parents: 16594
diff changeset
   133
                yield 2
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   134
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   135
    repo.__class__ = lfileswirerepository
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   136
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   137
# advertise the largefiles=serve capability
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   138
def capabilities(repo, proto):
16247
d87d9d8a8e03 largefiles: remove use of underscores that breaks coding convention
Na'Tosha Bard <natosha@unity3d.com>
parents: 16155
diff changeset
   139
    return capabilitiesorig(repo, proto) + ' largefiles=serve'
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   140
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   141
def heads(repo, proto):
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   142
    if lfutil.islfilesrepo(repo):
15224
7c604d8c7e83 largefiles: remove pre-1.9 code from extension first bundled with 1.9
Na'Tosha Bard <natosha@unity3d.com>
parents: 15170
diff changeset
   143
        return wireproto.ooberror(LARGEFILES_REQUIRED_MSG)
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   144
    return wireproto.heads(repo, proto)
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   145
16247
d87d9d8a8e03 largefiles: remove use of underscores that breaks coding convention
Na'Tosha Bard <natosha@unity3d.com>
parents: 16155
diff changeset
   146
def sshrepocallstream(self, cmd, **args):
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   147
    if cmd == 'heads' and self.capable('largefiles'):
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   148
        cmd = 'lheads'
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   149
    if cmd == 'batch' and self.capable('largefiles'):
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   150
        args['cmds'] = args['cmds'].replace('heads ', 'lheads ')
16247
d87d9d8a8e03 largefiles: remove use of underscores that breaks coding convention
Na'Tosha Bard <natosha@unity3d.com>
parents: 16155
diff changeset
   151
    return ssholdcallstream(self, cmd, **args)
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   152
16247
d87d9d8a8e03 largefiles: remove use of underscores that breaks coding convention
Na'Tosha Bard <natosha@unity3d.com>
parents: 16155
diff changeset
   153
def httprepocallstream(self, cmd, **args):
15168
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   154
    if cmd == 'heads' and self.capable('largefiles'):
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   155
        cmd = 'lheads'
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   156
    if cmd == 'batch' and self.capable('largefiles'):
cfccd3bee7b3 hgext: add largefiles extension
various
parents:
diff changeset
   157
        args['cmds'] = args['cmds'].replace('heads ', 'lheads ')
16247
d87d9d8a8e03 largefiles: remove use of underscores that breaks coding convention
Na'Tosha Bard <natosha@unity3d.com>
parents: 16155
diff changeset
   158
    return httpoldcallstream(self, cmd, **args)