Ben Collins-Sussman wrote:
> 2008/2/29 Stephen Butler <sbutler_at_elego.de>:
>> If an item has been modified or deleted in the repository since
>> the item was last updated in the working copy, Subversion should
>> disallow committing that item. This is a prerequisite for tree
>> conflict detection. The user should have to update in order to
>> integrate the repo changes, possibly revealing tree conflicts.
>> I had assumed that Subversion would block a commit that includes an
>> item that has been modified or deleted on the repo. But that's not
>> true in all cases:
>> WC State Repo State Blocked?
>> ======== ========== ========
>> Modified Modified Yes
>> Modified Deleted Yes
>> Deleted Modified Yes
>> Deleted Deleted No
>> We'd like to plug that gap.
> Let's back up a moment. Why is that a 'gap'? That's a very
> deliberate design decision, IIRC. The 'auto merging' loop that's part
> of commit finalization considers some changes to be mergeable, and
> some not. If two people are in a commit race and change the same
> file, that's not auto-mergeable: somebody wins the race, the other
> person's commit outright fails. But if the only 'conflict' is that
> they both happened to delete the same file, that's a perfectly safe
> auto-mergeable change: the overlapping changes are in agreement.
> Nobody will be destroying or overwriting somebody else's change by
> allowing the changes to be merged.
> In theory, if the two commits made absolutely identical textual
> changes to the same file, that would also be an example of a 'safe'
> auto-mergeable thing; we just never made the commit-finalization loop
> sophisticated enough to notice that case.
> In any case, I certainly don't consider this a loophole or oversight;
> it's a deliberate feature. Is this behavior presenting a real problem
> for your model of tree-conflict resolution?
Yes, I acknowledge that was a deliberate policy. We decided that it's usually
what the user wants, and pretty safe, so we'd just do it.
However, this is a policy which is not right for every situation. Our approach
in this designs was to decide what we think is the best compromise between
safety and usability, and hard-code our heuristics into the algorithm.
I'm pretty sure the particular big problem with this is the fact that two
conflicting renames of the same file can only be detected at the moment by the
two conflicting "delete" halves of those renames. But if our policy says that
two deletes of the same thing are not in conflict and are always to be silently
merge (rename A B) with (rename A C)
=> there are now two files, B and C.
I'd like to reexamine the way in which this and similar policy decisions are
embedded into the code. I would like the merge code to act according to a
caller-specified policy, or raise all conflicts like this to a "conflict
resolver" callback in which the client can enact whatever policy it likes -
auto-merge deletes, or don't, for example.
I'm seeing the same kind of issue in the "propset URL_at_base-rev" thread right
now. There are questions like, "If A tries to delete property P, and B has just
modified P, should the delete succeed or fail?" (I'm not sure this particular
question is open for debate, as it may already be determined by the existing
out-of-dateness rules, but this sort of question is raising its head.)
The tree-conflicts work is closely tied to the "out-of-dateness" policy. As
some (most?) of this policy is enforced repository-side, we need to be a bit
careful about compatibility if we now need to reconsider, extend, or duplicate
these policies on the client side, as I feel we may well need to to detect
To unsubscribe, e-mail: dev-unsubscribe_at_subversion.tigris.org
For additional commands, e-mail: dev-help_at_subversion.tigris.org
Received on 2008-02-29 16:35:20 CET