Ich möchte einen Mercurial-Hook haben, der vor dem Commit einer Transaktion ausgeführt wird, die die Transaktion abbricht, wenn eine binäre Datei größer als 1 Megabyte ist. Ich habe den folgenden Code gefunden, der bis auf ein Problem funktioniert. Wenn mein Changeset das Entfernen einer Datei beinhaltet, löst dieser Hook eine Ausnahme aus.Mercurial-Hook, um die Übertragung großer Binärdateien zu verbieten
Der Haken (Ich verwende pretxncommit = python:checksize.newbinsize
):
from mercurial import context, util
from mercurial.i18n import _
import mercurial.node as dpynode
'''hooks to forbid adding binary file over a given size
Ensure the PYTHONPATH is pointing where hg_checksize.py is and setup your
repo .hg/hgrc like this:
[hooks]
pretxncommit = python:checksize.newbinsize
pretxnchangegroup = python:checksize.newbinsize
preoutgoing = python:checksize.nopull
[limits]
maxnewbinsize = 10240
'''
def newbinsize(ui, repo, node=None, **kwargs):
'''forbid to add binary files over a given size'''
forbid = False
# default limit is 10 MB
limit = int(ui.config('limits', 'maxnewbinsize', 10000000))
tip = context.changectx(repo, 'tip').rev()
ctx = context.changectx(repo, node)
for rev in range(ctx.rev(), tip+1):
ctx = context.changectx(repo, rev)
print ctx.files()
for f in ctx.files():
fctx = ctx.filectx(f)
filecontent = fctx.data()
# check only for new files
if not fctx.parents():
if len(filecontent) > limit and util.binary(filecontent):
msg = 'new binary file %s of %s is too large: %ld > %ld\n'
hname = dpynode.short(ctx.node())
ui.write(_(msg) % (f, hname, len(filecontent), limit))
forbid = True
return forbid
Die Ausnahme:
$ hg commit -m 'commit message'
error: pretxncommit hook raised an exception: apps/helpers/templatetags/[email protected]: not found in manifest
transaction abort!
rollback completed
abort: apps/helpers/templatetags/[email protected]: not found in manifest!
ich mit dem Schreiben Mercurial Haken nicht vertraut bin, so bin ich ziemlich verwirrt über das, was geht weiter. Warum kümmert sich der Haken, dass eine Datei entfernt wurde, wenn hg schon davon weiß? Gibt es eine Möglichkeit, diesen Haken so zu reparieren, dass er immer funktioniert?
Update (gelöst): Ich habe den Hook modifiziert, um Dateien herauszufiltern, die im Änderungsset entfernt wurden.
def newbinsize(ui, repo, node=None, **kwargs):
'''forbid to add binary files over a given size'''
forbid = False
# default limit is 10 MB
limit = int(ui.config('limits', 'maxnewbinsize', 10000000))
ctx = repo[node]
for rev in xrange(ctx.rev(), len(repo)):
ctx = context.changectx(repo, rev)
# do not check the size of files that have been removed
# files that have been removed do not have filecontexts
# to test for whether a file was removed, test for the existence of a filecontext
filecontexts = list(ctx)
def file_was_removed(f):
"""Returns True if the file was removed"""
if f not in filecontexts:
return True
else:
return False
for f in itertools.ifilterfalse(file_was_removed, ctx.files()):
fctx = ctx.filectx(f)
filecontent = fctx.data()
# check only for new files
if not fctx.parents():
if len(filecontent) > limit and util.binary(filecontent):
msg = 'new binary file %s of %s is too large: %ld > %ld\n'
hname = dpynode.short(ctx.node())
ui.write(_(msg) % (f, hname, len(filecontent), limit))
forbid = True
return forbid
Wie filtere ich die entfernten Dateien aus ctx.files()? – hekevintran
Macht nichts, ich konnte es herausfinden. Vielen Dank. – hekevintran
das Abfangen der Ausnahme ist ausreichend;) – tonfa