Monday January 02, 2006 at 18:04
Subject: Subversion is a gateway drug (to darcs)
Keywords:
Subversion, Technical
Posted by: Sean Reifschneider
Subversion (svn) is a truly great replacement for CVS. I've never
really been able to get branching to work in CVS, even after reading the
documentation on it I have limited success. I know that the Python
developers were able to make it do the right thing, but I always seemed to
run into problems where CVS just wouldn't let me commit something on a
branch I made.
I've found that it's much easier to convert a CVS repository from CVS to
Subversion and do a branch in svn, than to deal with branches in CVS.
That's the big reason for me to convert from CVS to svn. I lasted a long
time without branches because CVS made it so painful. However, now that
svn makes branching so easy, I've been using them and have found that
there's another significant pain-point that's come up that makes svn
branching unusable for me.
I've been switching to darcs over the weekend...
The problem is that there's no really good way to have changes from
one branch flow to other branches. I ended up just manually building
patches that describe each branch and applying them to the other branches
where I'd do another commit. In some simple cases I could just "svn rm"
files or directories in the destination and then "svn cp" from the modified
branch to the new branch. That requires that the changes to one branch be
entirely independent (on a file level) from what is happening on the other
branch.
I have two use-cases for branches. One is where I've gone on to do
significant development on some code, but have to go back and make an
emergency patch to a release. I can't just make the fix to the head,
because I have significantly untested code in there. Another way to deal
with this is to have a "trunk" and then a "development branch". This
solves the same problem, where experimental or significant changes are done
in the "devel" branch, or a branch created for this particular work.
In subversion, this works great if I create a new branch, do the
development and complete it, with no changes made to the other branch. You
can merge back into the other branch/trunk by just doing "svn rm" and then
"svn cp" of the top-level directory of the branch. If changes are made to
both, it then becomes problematic to merge them.
I had experimented with saving off a copy of the revision created when
I did the branch, and then doing a "svn diff" from that revision to create
a patch I could apply to the other tree. However, that doesn't solve the
problem of propagating in changes from the other branch. If I change the
trunk, I probably want to pull those changes into the development tree
ASAP.
Darcs is a distributed version control system, which manages patches
between the branches itself. By distributed, I mean that if you do a check
out you have a full copy of the archive (unless you are pulling from a
"partial" repository). You can make local changes and commit them, without
needing commit privileges being granted on the source repository. This can
also be done without network connectivity.
When you have changes you want to share with another repository, you
can either "push" them to that repository (using SSH, for example), or you
can "send" them via e-mail. The latter should be great for for public
repositories, because others can pull the repository, work on changes, and
then send e-mail that the project maintainer can easily integrate.
On the down side, this does mean that if you are working with a
central repository and other developers, a commit will always be a two-step
process. First you do "darcs record" which builds a patch of the changes
you have made locally. Then you "darcs push" to send patches since the
last push. The equivalent of "svn update" is "darcs pull".
Also note that "darcs push" and "darcs pull" by default will ask you
to very every patch that you push or pull, so it can require some thinking.
However, this means that "cherry picking" of changes is the default in
darcs -- you don't have to accept all patches. If you have trusted
developers, you can probably always just accept all the patches.
One thing that bugs me about darcs is that it doesn't yell about
conflicts. Unless you're paying pretty close attention, reading all the
output that a set of "darcs pull" commands generate, it's fairly easy to
miss that there are conflicts that need resolution. I would prefer that it
yelled about it, preferably surrounded with lines of Nathan Hales around it.
I've been using darcs since Thursday or Friday, and so far it's been
working quite nicely. My largest pain-point has been fully resolved. I'll
write more about that shortly.
(Post Reply)
(Post Reply)
| Comment |
Martin v. Loewis Subject: What's wrong with "svn merge"? |
You don't mention "svn merge" when trying to integrate changes into a branch.
After creating branches/ssize_t, I do
cd ssize_t svn merge -r41942:41964 svn+ssh://pythondev@svn.python.org/python/trunkand that merges me all changes between these two revisions into the trunk. Now, where do I get the numbers from? The right number is simply the current repository revision. The left number is the number of the previous branch. You could find that number in the commit message, or you can store it in a property. Before committing the merge result, I do
svn pe py:lastmerged .and replace 41942 with 41964. Then, before the next merge, I do
svn pg py:lastmerged .to find out when the last merge was, and use that as the starting revision for the merge.
| Comment |
Author:
Sean Reifschneider Subject: That's a pretty good trick. |
I had originally tried that just by saving a file that contained the last revision I had merged from. Later I thought about storing that information in the repository so that multiple people would have access to it, that would be doable as well. Your trick looks pretty good, I think that should work. I'll have to give it a try. The darcs method I'm using now works pretty well, but is potentially of a similar number of steps as tracking the merge-points in SVN.
Sean
| Comment |
Joakim Harsman Subject: darcs can break horribly |
You should be aware that darcs can get into certain cases where it will take exponential time trying to solve conflicts, and theres no good way to solve this once it happens other than tedious manual work.
This can happen fairly easily if you have a stable branch and an unstable branch for some large feature, and a patch you're trying to pull from stable conflicts with changes you've made in unstable. See http://darcs.net/DarcsWiki/ConflictMisery
I would really love to use darcs since it's so easy to use and elegant, but it just isn't stable enough yet.
| Comment |
Dave Newton Subject: Another SVN merge trick |
Another SVN merge trick that I use for large bug fixes or code changes:
svn copy -m "foo" svn://.../trunk svn://.../branches/big-bugfix/trunk svn copy -m "bar" svn://.../branches/big-bugfix/PRE # Do lots of hairy work until you're done svn copy -m "baz" svn://.../branches/big-bugfix/POSTNow go in to your trunk directory and:
svn merge -R PRE:POST svn://.../branches/big-bugfix/trunkSo in essence you're tagging the branch before and after you've worked on it and can refer to things symbolically. That said, I like the previous poster's property trick and am going to have to look at that to see if I like it more--it looks like I might. You are still left with the problem of merging changes from trunk (or anywhere else) into your branches; since I am very liberal with my branches I will need to look in to this. DARCS is definitely catching on in many communities I hang out in, so I'll be checking it out. Dave
| Comment |
Author:
Sean Reifschneider Subject: Yeah, I've had problems also. |
My big project that required the features of Darcs for branching management has had problems. I ended up with a repository that I couldn't push or pull from. It would just hang, I let it run for up to 8 hours. I had contacted #darcs on freenode, and also looked at the wiki, but couldn't get it resolved.
I finally just gave up and went back to svn with svnmerge, and that's been working well for me. Though just last night I found a change in one branch that was missing from a branch I would have merged it from. Not sure what the story is there.
I'm playing around with git right now, but haven't had much opportunity to actually use it, particularly use it hard.
Sean