status: use contexts
authorMatt Mackall <mpm@selenic.com>
Fri, 11 Jul 2008 18:46:02 -0500
changeset 6769 97c12b1ed1e0
parent 6768 e3bb005373b1
child 6770 854b907527e5
status: use contexts
mercurial/localrepo.py
--- a/mercurial/localrepo.py	Fri Jul 11 18:46:02 2008 -0500
+++ b/mercurial/localrepo.py	Fri Jul 11 18:46:02 2008 -0500
@@ -943,7 +943,7 @@
         '''
         return self[node].walk(match)
 
-    def status(self, node1=None, node2=None, match=None,
+    def status(self, node1='.', node2=None, match=None,
                ignored=False, clean=False, unknown=False):
         """return status of files between two nodes or node and working directory
 
@@ -951,14 +951,9 @@
         If node2 is None, compare node1 with working directory.
         """
 
-        def fcmp(fn, getnode):
-            t1 = self.wread(fn)
-            return self.file(fn).cmp(getnode(fn), t1)
-
-        def mfmatches(node):
-            change = self.changelog.read(node)
-            mf = self.manifest.read(change[0]).copy()
-            for fn in mf.keys():
+        def mfmatches(ctx):
+            mf = ctx.manifest().copy()
+            for fn in mf:
                 if not match(fn):
                     del mf[fn]
             return mf
@@ -966,35 +961,34 @@
         if not match:
             match = match_.always(self.root, self.getcwd())
 
+        ctx1 = self[node1]
+        ctx2 = self[node2]
+        working = ctx2 == self[None]
+        parentworking = working and ctx1 == self['.']
+
         listignored, listclean, listunknown = ignored, clean, unknown
         modified, added, removed, deleted, unknown = [], [], [], [], []
         ignored, clean = [], []
 
-        compareworking = False
-        if not node1 or (not node2 and node1 == self.dirstate.parents()[0]):
-            compareworking = True
-
-        if not compareworking:
+        if not parentworking:
             # read the manifest from node1 before the manifest from node2,
             # so that we'll hit the manifest cache if we're going through
             # all the revisions in parent->child order.
-            mf1 = mfmatches(node1)
+            mf1 = mfmatches(ctx1)
 
         # are we comparing the working directory?
-        if not node2:
+        if working:
             (lookup, modified, added, removed, deleted, unknown,
              ignored, clean) = self.dirstate.status(match, listignored,
                                                     listclean, listunknown)
             # are we comparing working dir against its parent?
-            if compareworking:
+            if parentworking:
                 if lookup:
                     fixup = []
                     # do a full compare of any files that might have changed
-                    ctx = self['.']
-                    ff = self.dirstate.flagfunc(ctx.flags)
                     for f in lookup:
-                        if (f not in ctx or ff(f) != ctx.flags(f)
-                            or ctx[f].cmp(self.wread(f))):
+                        if (f not in ctx1 or ctx2.flags(f) != ctx1.flags(f)
+                            or ctx1[f].cmp(ctx2[f].read())):
                             modified.append(f)
                         else:
                             fixup.append(f)
@@ -1018,31 +1012,28 @@
                 # we are comparing working dir against non-parent
                 # generate a pseudo-manifest for the working dir
                 # XXX: create it in dirstate.py ?
-                mf2 = mfmatches(self.dirstate.parents()[0])
-                ff = self.dirstate.flagfunc(mf2.flags)
+                mf2 = mfmatches(self['.'])
                 for f in lookup + modified + added:
-                    mf2[f] = ""
-                    mf2.set(f, ff(f))
+                    mf2[f] = None
+                    mf2.set(f, ctx2.flags(f))
                 for f in removed:
                     if f in mf2:
                         del mf2[f]
-
         else:
             # we are comparing two revisions
-            mf2 = mfmatches(node2)
+            mf2 = mfmatches(ctx2)
 
-        if not compareworking:
+        if not parentworking:
             # flush lists from dirstate before comparing manifests
             modified, added, clean = [], [], []
 
             # make sure to sort the files so we talk to the disk in a
             # reasonable order
-            getnode = lambda fn: mf1.get(fn, nullid)
             for fn in util.sort(mf2):
                 if fn in mf1:
                     if (mf1.flags(fn) != mf2.flags(fn) or
                         (mf1[fn] != mf2[fn] and
-                         (mf2[fn] != "" or fcmp(fn, getnode)))):
+                         (mf2[fn] or ctx1[f].cmp(ctx2[f].read())))):
                         modified.append(fn)
                     elif listclean:
                         clean.append(fn)