merge crew and main

This commit is contained in:
Henrik Stuart 2010-07-14 19:43:31 +02:00
commit c5ab8c0508
18 changed files with 186 additions and 34 deletions

View File

@ -213,7 +213,9 @@ class repowatcher(object):
if time != int(st_mtime):
return 'l'
return 'n'
if type_ == '?' and self.dirstate._ignore(fn):
if type_ == '?' and self.dirstate._dirignore(fn):
# we must check not only if the file is ignored, but if any part
# of its path match an ignore pattern
return 'i'
return type_

View File

@ -476,6 +476,11 @@ class queue(object):
write_list(self.full_series, self.series_path)
if self.guards_dirty:
write_list(self.active_guards, self.guards_path)
if self.added:
qrepo = self.qrepo()
if qrepo:
qrepo[None].add(self.added)
self.added = []
def removeundo(self, repo):
undo = repo.sjoin('undo')
@ -1623,7 +1628,6 @@ class queue(object):
if (len(files) > 1 or len(rev) > 1) and patchname:
raise util.Abort(_('option "-n" not valid when importing multiple '
'patches'))
self.added = []
if rev:
# If mq patches are applied, we can only import revisions
# that form a linear path to qbase.
@ -1810,9 +1814,6 @@ def qimport(ui, repo, *filename, **opts):
git=opts['git'])
finally:
q.save_dirty()
qrepo = q.qrepo()
if qrepo:
qrepo[None].add(q.added)
if opts.get('push') and not opts.get('rev'):
return q.push(repo, None)

View File

@ -271,9 +271,9 @@ def concludenode(repo, rev, p1, p2, commitmsg=None, extrafn=None):
'Commit the changes and store useful information in extra'
try:
repo.dirstate.setparents(repo[p1].node(), repo[p2].node())
if commitmsg is None:
commitmsg = repo[rev].description()
ctx = repo[rev]
if commitmsg is None:
commitmsg = ctx.description()
extra = {'rebase_source': ctx.hex()}
if extrafn:
extrafn(ctx, extra)
@ -347,23 +347,25 @@ def isagitpatch(repo, patchname):
def updatemq(repo, state, skipped, **opts):
'Update rebased mq patches - finalize and then import them'
mqrebase = {}
for p in repo.mq.applied:
if repo[p.node].rev() in state:
mq = repo.mq
for p in mq.applied:
rev = repo[p.node].rev()
if rev in state:
repo.ui.debug('revision %d is an mq patch (%s), finalize it.\n' %
(repo[p.node].rev(), p.name))
mqrebase[repo[p.node].rev()] = (p.name, isagitpatch(repo, p.name))
(rev, p.name))
mqrebase[rev] = (p.name, isagitpatch(repo, p.name))
if mqrebase:
repo.mq.finish(repo, mqrebase.keys())
mq.finish(repo, mqrebase.keys())
# We must start import from the newest revision
for rev in sorted(mqrebase, reverse=True):
if rev not in skipped:
repo.ui.debug('import mq patch %d (%s)\n'
% (state[rev], mqrebase[rev][0]))
repo.mq.qimport(repo, (), patchname=mqrebase[rev][0],
git=mqrebase[rev][1],rev=[str(state[rev])])
repo.mq.save_dirty()
name, isgit = mqrebase[rev]
repo.ui.debug('import mq patch %d (%s)\n' % (state[rev], name))
mq.qimport(repo, (), patchname=name, git=isgit,
rev=[str(state[rev])])
mq.save_dirty()
def storestatus(repo, originalwd, target, state, collapse, keep, keepbranches,
external):

View File

@ -353,6 +353,10 @@ class filectx(object):
return self._filelog.size(self._filerev)
def cmp(self, text):
"""compare text with stored file revision
returns True if text is different than what is stored.
"""
return self._filelog.cmp(self._filenode, text)
def renamed(self):
@ -932,7 +936,11 @@ class workingfilectx(filectx):
return (t, tz)
def cmp(self, text):
return self._repo.wread(self._path) == text
"""compare text with disk content
returns True if text is different than what is on disk.
"""
return self._repo.wread(self._path) != text
class memctx(object):
"""Use memctx to perform in-memory commits via localrepo.commitctx().

View File

@ -53,14 +53,27 @@ class filelog(revlog.revlog):
if self.renamed(node):
return len(self.read(node))
# XXX if self.read(node).startswith("\1\n"), this returns (size+4)
return revlog.revlog.size(self, rev)
def cmp(self, node, text):
"""compare text with a given file revision"""
"""compare text with a given file revision
# for renames, we have to go the slow way
if text.startswith('\1\n') or self.renamed(node):
returns True if text is different than what is stored.
"""
t = text
if text.startswith('\1\n'):
t = '\1\n\1\n' + text
samehashes = not revlog.revlog.cmp(self, node, t)
if samehashes:
return False
# renaming a file produces a different hash, even if the data
# remains unchanged. Check if it's the case (slow):
if self.renamed(node):
t2 = self.read(node)
return t2 != text
return revlog.revlog.cmp(self, node, text)
return True

View File

@ -221,7 +221,7 @@ def clone(ui, source, dest=None, pull=False, rev=None, update=True,
src_repo = repository(ui, source)
else:
src_repo = source
branch = None
branch = (None, [])
origsource = source = src_repo.url()
rev, checkout = addbranchrevs(src_repo, src_repo, branch, rev)

View File

@ -10,6 +10,26 @@ import util, encoding
import os, smtplib, socket, quopri
import email.Header, email.MIMEText, email.Utils
_oldheaderinit = email.Header.Header.__init__
def _unifiedheaderinit(self, *args, **kw):
"""
Python2.7 introduces a backwards incompatible change
(Python issue1974, r70772) in email.Generator.Generator code:
pre-2.7 code passed "continuation_ws='\t'" to the Header
constructor, and 2.7 removed this parameter.
Default argument is continuation_ws=' ', which means that the
behaviour is different in <2.7 and 2.7
We consider the 2.7 behaviour to be preferable, but need
to have an unified behaviour for versions 2.4 to 2.7
"""
# override continuation_ws
kw['continuation_ws'] = ' '
_oldheaderinit(self, *args, **kw)
email.Header.Header.__dict__['__init__'] = _unifiedheaderinit
def _smtp(ui):
'''build an smtp connection and return a function to send mail'''
local_hostname = ui.config('smtp', 'local_hostname')

View File

@ -943,7 +943,10 @@ class revlog(object):
raise LookupError(id, self.indexfile, _('no match found'))
def cmp(self, node, text):
"""compare text with a given file revision"""
"""compare text with a given file revision
returns True if text is different than what is stored.
"""
p1, p2 = self.parents(node)
return hash(text, p1, p2) != node

View File

@ -137,21 +137,21 @@ hg ci -m "b3 (HN)"
echo '% case NN: msg'
hg up -q null
hg branch -f b
echo 1 > B
echo 1 > bb
hg ci -Am "b4 (NN): new topo root for branch b"
echo '% case HN: no msg'
echo 2 >> B
echo 2 >> bb
hg ci -m "b5 (HN)"
echo '% case BN: msg'
hg branch -f default
echo 1 > A
echo 1 > aa
hg ci -Am "a6 (BN): new branch root"
echo '% case CN: msg'
hg up -q 4
echo 3 >> BB
echo 3 >> bbb
hg ci -Am "b7 (CN): regular new head"
echo '% case BB: msg'

View File

@ -187,15 +187,15 @@ marked working directory as branch b
adding b
% case NN: msg
marked working directory as branch b
adding B
adding bb
created new head
% case HN: no msg
% case BN: msg
marked working directory as branch default
adding A
adding aa
created new head
% case CN: msg
adding BB
adding bbb
created new head
% case BB: msg
marked working directory as branch default

View File

@ -199,4 +199,14 @@ hg -R a parents --template "{node|short}\n"
hg -R ua parents --template "{node|short}\n"
rm -r ua
cat <<EOF > simpleclone.py
from mercurial import ui, hg
myui = ui.ui()
repo = hg.repository(myui, 'a')
hg.clone(myui, repo, dest="ua")
EOF
python simpleclone.py
rm -r ua
exit 0

View File

@ -312,3 +312,5 @@ summary: hacked default
% same revision checked out in repo a and ua
e8ece76546a6
e8ece76546a6
updating to branch default
3 files updated, 0 files merged, 0 files removed, 0 files unresolved

50
tests/test-filelog Normal file
View File

@ -0,0 +1,50 @@
#!/usr/bin/env python
"""
Tests the behaviour of filelog w.r.t. data starting with '\1\n'
"""
from mercurial import ui, hg
from mercurial.node import nullid, hex
myui = ui.ui()
repo = hg.repository(myui, path='.', create=True)
fl = repo.file('foobar')
def addrev(text, renamed=False):
if renamed:
# data doesnt matter. Just make sure filelog.renamed() returns True
meta = dict(copyrev=hex(nullid), copy='bar')
else:
meta = {}
t = repo.transaction('commit')
try:
node = fl.add(text, meta, t, 0, nullid, nullid)
return node
finally:
t.close()
def error(text):
print 'ERROR: ' + text
textwith = '\1\nfoo'
without = 'foo'
node = addrev(textwith)
if not textwith == fl.read(node):
error('filelog.read for data starting with \\1\\n')
if fl.cmp(node, textwith) or not fl.cmp(node, without):
error('filelog.cmp for data starting with \\1\\n')
if fl.size(0) != len(textwith):
error('FIXME: This is a known failure of filelog.size for data starting '
'with \\1\\n')
node = addrev(textwith, renamed=True)
if not textwith == fl.read(node):
error('filelog.read for a renaming + data starting with \\1\\n')
if fl.cmp(node, textwith) or not fl.cmp(node, without):
error('filelog.cmp for a renaming + data starting with \\1\\n')
if fl.size(1) != len(textwith):
error('filelog.size for a renaming + data starting with \\1\\n')
print 'OK.'

2
tests/test-filelog.out Normal file
View File

@ -0,0 +1,2 @@
ERROR: FIXME: This is a known failure of filelog.size for data starting with \1\n
OK.

View File

@ -97,4 +97,17 @@ hg ci -m 'working'
echo b >> 1844/foo
hg ci 1844 -m 'broken'
# Test for issue884: "Build products not ignored until .hgignore is touched"
echo '^build$' > .hgignore
hg add .hgignore
hg ci .hgignore -m 'ignorelist'
# Now, lets add some build products...
mkdir build
touch build/x
touch build/y
# build/x & build/y shouldn't appear in "hg st"
hg st
kill `cat hg.pid`

View File

@ -101,6 +101,11 @@ hg qref --git -m 'P0 (git)'
hg qnew f.patch
echo 'mq2' > p
hg qref -m 'P1'
hg qcommit -m 'save patch state'
echo '% patch series step 1/2'
hg qseries -s
echo '% patch queue manifest step 1/2'
hg -R .hg/patches manifest
echo '% Git patch'
cat .hg/patches/f_git.patch | filterpatch
@ -112,6 +117,11 @@ cat .hg/patches/f.patch | filterpatch
echo
echo '% Rebase the applied mq patches'
hg rebase -s 2 -d 1 --quiet
hg qcommit -m 'save patch state'
echo '% patch series step 2/2'
hg qseries -s
echo '% patch queue manifest step 2/2'
hg -R .hg/patches manifest
echo '% And the patches are correct'
echo '% Git patch'

View File

@ -80,6 +80,14 @@ popping f2.patch
popping f.patch
patch queue now empty
1 files updated, 0 files merged, 0 files removed, 0 files unresolved
% patch series step 1/2
f_git.patch: P0 (git)
f.patch: P1
% patch queue manifest step 1/2
.hgignore
f.patch
f_git.patch
series
% Git patch
P0 (git)
@ -101,6 +109,14 @@ diff -r x p
+mq2
% Rebase the applied mq patches
% patch series step 2/2
f_git.patch: P0 (git)
f.patch: P1
% patch queue manifest step 2/2
.hgignore
f.patch
f_git.patch
series
% And the patches are correct
% Git patch
# HG changeset patch