/brz/remove-bazaar

To get this branch, use:
bzr branch http://gegoxaren.bato24.eu/bzr/brz/remove-bazaar

« back to all changes in this revision

Viewing changes to breezy/workingtree.py

  • Committer: Gustav Hartvigsson
  • Date: 2021-01-11 20:19:38 UTC
  • mfrom: (7526.3.2 work)
  • Revision ID: gustav.hartvigsson@gmail.com-20210111201938-omr9wjz3qdgyxe8k
MergedĀ lp:brz

Show diffs side-by-side

added added

removed removed

Lines of Context:
709
709
 
710
710
    def get_symlink_target(self, path):
711
711
        abspath = self.abspath(path)
712
 
        target = osutils.readlink(abspath)
713
 
        return target
 
712
        try:
 
713
            return osutils.readlink(abspath)
 
714
        except OSError as e:
 
715
            if getattr(e, 'errno', None) == errno.ENOENT:
 
716
                raise errors.NoSuchFile(path)
 
717
            raise
714
718
 
715
719
    def subsume(self, other_tree):
716
720
        raise NotImplementedError(self.subsume)
1049
1053
            if file_id is None:
1050
1054
                raise ValueError(
1051
1055
                    'WorkingTree.set_root_id with fileid=None')
1052
 
            file_id = osutils.safe_file_id(file_id)
1053
1056
            self._set_root_id(file_id)
1054
1057
 
1055
1058
    def _set_root_id(self, file_id):
1072
1075
        """
1073
1076
        raise NotImplementedError(self.unlock)
1074
1077
 
1075
 
    _marker = object()
1076
 
 
1077
1078
    def update(self, change_reporter=None, possible_transports=None,
1078
 
               revision=None, old_tip=_marker, show_base=False):
 
1079
               revision=None, old_tip=None, show_base=False):
1079
1080
        """Update a working tree along its branch.
1080
1081
 
1081
1082
        This will update the branch if its bound too, which means we have
1107
1108
            returned (old tip of the branch or None). _marker is used
1108
1109
            otherwise.
1109
1110
        """
1110
 
        if self.branch.get_bound_location() is not None:
1111
 
            self.lock_write()
1112
 
            update_branch = (old_tip is self._marker)
1113
 
        else:
1114
 
            self.lock_tree_write()
1115
 
            update_branch = False
1116
 
        try:
1117
 
            if update_branch:
1118
 
                old_tip = self.branch.update(possible_transports)
1119
 
            else:
1120
 
                if old_tip is self._marker:
1121
 
                    old_tip = None
1122
 
            return self._update_tree(old_tip, change_reporter, revision, show_base)
1123
 
        finally:
1124
 
            self.unlock()
1125
 
 
1126
 
    def _update_tree(self, old_tip=None, change_reporter=None, revision=None,
1127
 
                     show_base=False):
1128
 
        """Update a tree to the master branch.
1129
 
 
1130
 
        :param old_tip: if supplied, the previous tip revision the branch,
1131
 
            before it was changed to the master branch's tip.
1132
 
        """
1133
 
        # here if old_tip is not None, it is the old tip of the branch before
1134
 
        # it was updated from the master branch. This should become a pending
1135
 
        # merge in the working tree to preserve the user existing work.  we
1136
 
        # cant set that until we update the working trees last revision to be
1137
 
        # one from the new branch, because it will just get absorbed by the
1138
 
        # parent de-duplication logic.
1139
 
        #
1140
 
        # We MUST save it even if an error occurs, because otherwise the users
1141
 
        # local work is unreferenced and will appear to have been lost.
1142
 
        #
1143
 
        with self.lock_tree_write():
1144
 
            nb_conflicts = 0
1145
 
            try:
1146
 
                last_rev = self.get_parent_ids()[0]
1147
 
            except IndexError:
1148
 
                last_rev = _mod_revision.NULL_REVISION
1149
 
            if revision is None:
1150
 
                revision = self.branch.last_revision()
1151
 
 
1152
 
            old_tip = old_tip or _mod_revision.NULL_REVISION
1153
 
 
1154
 
            if not _mod_revision.is_null(old_tip) and old_tip != last_rev:
1155
 
                # the branch we are bound to was updated
1156
 
                # merge those changes in first
1157
 
                base_tree = self.basis_tree()
1158
 
                other_tree = self.branch.repository.revision_tree(old_tip)
1159
 
                nb_conflicts = merge.merge_inner(self.branch, other_tree,
1160
 
                                                 base_tree, this_tree=self,
1161
 
                                                 change_reporter=change_reporter,
1162
 
                                                 show_base=show_base)
1163
 
                if nb_conflicts:
1164
 
                    self.add_parent_tree((old_tip, other_tree))
1165
 
                    note(gettext('Rerun update after fixing the conflicts.'))
1166
 
                    return nb_conflicts
1167
 
 
1168
 
            if last_rev != _mod_revision.ensure_null(revision):
1169
 
                # the working tree is up to date with the branch
1170
 
                # we can merge the specified revision from master
1171
 
                to_tree = self.branch.repository.revision_tree(revision)
1172
 
                to_root_id = to_tree.path2id('')
1173
 
 
1174
 
                basis = self.basis_tree()
1175
 
                with basis.lock_read():
1176
 
                    if (basis.path2id('') is None or basis.path2id('') != to_root_id):
1177
 
                        self.set_root_id(to_root_id)
1178
 
                        self.flush()
1179
 
 
1180
 
                # determine the branch point
1181
 
                graph = self.branch.repository.get_graph()
1182
 
                base_rev_id = graph.find_unique_lca(self.branch.last_revision(),
1183
 
                                                    last_rev)
1184
 
                base_tree = self.branch.repository.revision_tree(base_rev_id)
1185
 
 
1186
 
                nb_conflicts = merge.merge_inner(self.branch, to_tree, base_tree,
1187
 
                                                 this_tree=self,
1188
 
                                                 change_reporter=change_reporter,
1189
 
                                                 show_base=show_base)
1190
 
                self.set_last_revision(revision)
1191
 
                # TODO - dedup parents list with things merged by pull ?
1192
 
                # reuse the tree we've updated to to set the basis:
1193
 
                parent_trees = [(revision, to_tree)]
1194
 
                merges = self.get_parent_ids()[1:]
1195
 
                # Ideally we ask the tree for the trees here, that way the working
1196
 
                # tree can decide whether to give us the entire tree or give us a
1197
 
                # lazy initialised tree. dirstate for instance will have the trees
1198
 
                # in ram already, whereas a last-revision + basis-inventory tree
1199
 
                # will not, but also does not need them when setting parents.
1200
 
                for parent in merges:
1201
 
                    parent_trees.append(
1202
 
                        (parent, self.branch.repository.revision_tree(parent)))
1203
 
                if not _mod_revision.is_null(old_tip):
1204
 
                    parent_trees.append(
1205
 
                        (old_tip, self.branch.repository.revision_tree(old_tip)))
1206
 
                self.set_parent_trees(parent_trees)
1207
 
                last_rev = parent_trees[0][0]
1208
 
            return nb_conflicts
 
1111
        raise NotImplementedError(self.update)
1209
1112
 
1210
1113
    def set_conflicts(self, arg):
1211
1114
        raise errors.UnsupportedOperation(self.set_conflicts, self)
1220
1123
        """Walk the directories of this tree.
1221
1124
 
1222
1125
        returns a generator which yields items in the form:
1223
 
                ((curren_directory_path, fileid),
1224
 
                 [(file1_path, file1_name, file1_kind, (lstat), file1_id,
 
1126
                (current_directory_path,
 
1127
                 [(file1_path, file1_name, file1_kind, (lstat),
1225
1128
                   file1_kind), ... ])
1226
1129
 
1227
1130
        This API returns a generator, which is only valid during the current
1241
1144
        into files that have text conflicts.  The corresponding .THIS .BASE and
1242
1145
        .OTHER files are deleted, as per 'resolve'.
1243
1146
 
1244
 
        :return: a tuple of ConflictLists: (un_resolved, resolved).
 
1147
        :return: a tuple of lists: (un_resolved, resolved).
1245
1148
        """
1246
1149
        with self.lock_tree_write():
1247
 
            un_resolved = _mod_conflicts.ConflictList()
1248
 
            resolved = _mod_conflicts.ConflictList()
 
1150
            un_resolved = []
 
1151
            resolved = []
1249
1152
            for conflict in self.conflicts():
1250
1153
                try:
1251
1154
                    conflict.action_auto(self)