~bzr-pqm/bzr/bzr.dev

« back to all changes in this revision

Viewing changes to bzrlib/workingtree.py

  • Committer: Martin Pool
  • Date: 2006-03-06 07:11:09 UTC
  • mfrom: (1591 +trunk)
  • mto: This revision was merged to the branch mainline in revision 1593.
  • Revision ID: mbp@sourcefrog.net-20060306071109-6b35534e38610c43
[merge] bzr.dev

Show diffs side-by-side

added added

removed removed

Lines of Context:
64
64
from bzrlib.inventory import InventoryEntry, Inventory
65
65
from bzrlib.lockable_files import LockableFiles, TransportLock
66
66
from bzrlib.merge import merge_inner, transform_tree
67
 
from bzrlib.osutils import (appendpath,
 
67
from bzrlib.osutils import (
 
68
                            abspath,
 
69
                            appendpath,
68
70
                            compact_date,
69
71
                            file_kind,
70
72
                            isdir,
74
76
                            safe_unicode,
75
77
                            splitpath,
76
78
                            rand_bytes,
77
 
                            abspath,
78
79
                            normpath,
79
80
                            realpath,
80
81
                            relpath,
1161
1162
 
1162
1163
    @needs_write_lock
1163
1164
    def update(self):
 
1165
        """Update a working tree along its branch.
 
1166
 
 
1167
        This will update the branch if its bound too, which means we have multiple trees involved:
 
1168
        The new basis tree of the master.
 
1169
        The old basis tree of the branch.
 
1170
        The old basis tree of the working tree.
 
1171
        The current working tree state.
 
1172
        pathologically all three may be different, and non ancestors of each other.
 
1173
        Conceptually we want to:
 
1174
        Preserve the wt.basis->wt.state changes
 
1175
        Transform the wt.basis to the new master basis.
 
1176
        Apply a merge of the old branch basis to get any 'local' changes from it into the tree.
 
1177
        Restore the wt.basis->wt.state changes.
 
1178
 
 
1179
        There isn't a single operation at the moment to do that, so we:
 
1180
        Merge current state -> basis tree of the master w.r.t. the old tree basis.
 
1181
        Do a 'normal' merge of the old branch basis if it is relevant.
 
1182
        """
 
1183
        old_tip = self.branch.update()
 
1184
        if old_tip is not None:
 
1185
            self.add_pending_merge(old_tip)
1164
1186
        self.branch.lock_read()
1165
1187
        try:
1166
 
            if self.last_revision() == self.branch.last_revision():
1167
 
                return
1168
 
            basis = self.basis_tree()
1169
 
            to_tree = self.branch.basis_tree()
1170
 
            result = merge_inner(self.branch,
1171
 
                                 to_tree,
1172
 
                                 basis,
1173
 
                                 this_tree=self)
1174
 
            self.set_last_revision(self.branch.last_revision())
 
1188
            result = 0
 
1189
            if self.last_revision() != self.branch.last_revision():
 
1190
                # merge tree state up to new branch tip.
 
1191
                basis = self.basis_tree()
 
1192
                to_tree = self.branch.basis_tree()
 
1193
                result += merge_inner(self.branch,
 
1194
                                      to_tree,
 
1195
                                      basis,
 
1196
                                      this_tree=self)
 
1197
                self.set_last_revision(self.branch.last_revision())
 
1198
            if old_tip and old_tip != self.last_revision():
 
1199
                # our last revision was not the prior branch last reivison
 
1200
                # and we have converted that last revision to a pending merge.
 
1201
                # base is somewhere between the branch tip now
 
1202
                # and the now pending merge
 
1203
                from bzrlib.revision import common_ancestor
 
1204
                try:
 
1205
                    base_rev_id = common_ancestor(self.branch.last_revision(),
 
1206
                                                  old_tip,
 
1207
                                                  self.branch.repository)
 
1208
                except errors.NoCommonAncestor:
 
1209
                    base_rev_id = None
 
1210
                base_tree = self.branch.repository.revision_tree(base_rev_id)
 
1211
                other_tree = self.branch.repository.revision_tree(old_tip)
 
1212
                result += merge_inner(self.branch,
 
1213
                                      other_tree,
 
1214
                                      base_tree,
 
1215
                                      this_tree=self)
1175
1216
            return result
1176
1217
        finally:
1177
1218
            self.branch.unlock()