Ben Collins-Sussman <sussman@collab.net> writes:
>
> > So I suspect that this Hudson Scenario has always failed over DAV,
> > ever since M2 last April. We just never noticed it, because we didn't
> > get the python tests working over DAV until last month. :-(
So here's the latest. M5 is done, and M4 is waiting on two bugs. The
bugs are both python-regression-test failures that work over ra_local,
but fail over ra_dav.
(These are two of the infamous "Greg Hudson" scenarios. If developers
are interested, look at doc/user/manual/dirversioning.texi for more
details.)
Here's are the ra_dav bugs and their proposed solutions. Greg Stein,
please feel free to comment on the solutions. Karl and I have figured
out ways to tweak the network layer to avoid these bugs, and we also
feel that the tweaks are theoretically correct, not just "hacks".
More importantly, it means we don't have to go rewrite the whole
commit system right now -- that can remain a Beta issue.
1. to replace a file, the user must {delete, add, commit}. If the
user instead attempts to {delete, commit, add, commit}, the second
commit will fail.
ANALYSIS
After the first commit, the working copy is in an interesting
state. The parent dir is at revision 1, and the deleted item is
at revision 2 but marked as 'deleted'. (This state will go away
if the user ever updates.) Meanwhile, the user schedules a new
item (of the same name) for addition, and tries to commit.
As cmpilato pointed out, the commit-driver does a replace_dir(1)
for the parent, and then tries to delete the item before adding
it. The commit-driver is assuming that some kind of "mirror" of
the working copy is being built on the server; it assumes that
it's editing a transaction based on revision 1, hence the delete
before the add. And in fact, this *is* how ra_local currently
works.
Of course, ra_local is building a transaction based on the HEAD
revision, and thus is merging-on-the-fly. When the commit-driver
tries to delete the item, mod_dav_svn justly complains that no
such item exists.
SOLUTION
mod_dav_svn should be trapping and ignoring the "item already
missing" error that it's getting from the filesystem. Why?
Because mod_dav_svn is *merging* on the fly, and in the world of
merging, deletion is an idempotent operation. (svn_fs_merge() has
the same rule: if you need to delete something, and it's already
gone, it just moves on.) This is a pretty easy fix, and I'm
almost done with it.
2. ra_dav is unable to prevent users from committing propchanges on
out-of-date dirs. Thus users could end up with working copies
containing dirs whose revision numbers are incorrect.
ANALYSIS
Well, duh. When ra_dav sends PROPPATCH on a directory,
mod_dav_svn is always applying it to the "latest" version of the
directory. There's a good chance that the change will apply
cleanly, and then ra_dav goes and bumps the directory revision --
but the whole thing should have failed an out-of-dateness check to
begin with.
SOLUTION
ra_dav can't know if the directory is out-of-date or not; only
someone looking at the filesystem can see that. So the change
needs to happen in mod_dav_svn.
Specifically, the "working" revision of the directory needs to be
sent in the PROPPATCH request body. mod_dav_svn can then look at
the node-rev-id of the latest version of the directory, see what
revision it was *created* in (it's part of the skel), and compare
it to the "working" revision from the client. It's an easy
out-of-dateness check that requires no undeltifying, and is a
foreshadowing of the commit-system of the future. :-)
---------------------------------------------------------------------
To unsubscribe, e-mail: dev-unsubscribe@subversion.tigris.org
For additional commands, e-mail: dev-help@subversion.tigris.org
Received on Sat Oct 21 14:36:45 2006