===== This page describes some of the things I've found missing in Subversion, when coming from CVS: =====
- There is no way using Subversion to diff a local change ("working copy" in SVN speak) with a different branch.
* With CVS I can do an MFC, fix the conflicts and compare with CURRENT by using;
$ cd releng7/bin/cat
$ cvs up -j 1.3 cat.c
$ vi cat.c
$ cvs diff -r1 file
When trying this with Subversion:
$ svn diff $Fh/bin/cat .
svn: Target lists to diff may not contain both working copy paths and URLs
$ svn diff $Fh/bin/cat
svn: Not all required revisions are specified
Answer: Use the svn diff --old --new syntax:
$ cd /usr/src/bin/cat
$ svn diff --old cat.c --new ^/releng/7.0/bin/cat/cat.c
- CVS provided more abbreviations for commands.
*
$ svn info --depth immediates svn+ssh://svn.freebsd.org/base/stable/7
$ svn info --depth empty svn+ssh://svn.freebsd.org/base/head
Seems the Subversion developers are much better touch typists (and fast ones at that) than I am.
//1// and //0// should be abbreviations for //immediates// and //empty//.
- "Forced commits" are missing.
* When one makes a commit and the log message is wrong (or missing), some shops have disabled ''%%cvs admin%%'' for users, and instead have use ''%%cvs ci -f%%''. There appears to be no way to make a zero-change commit using Subversion.
- Subversion ''%%import%%'' is mostly useless.
* ''%%svn import%%'' should keep in mind what ''%%CVS%%'' knew - vendor branches are valuable thing. ''%%svn import%%'' should have been a useful tool for repeated imports of a 3rd party based source drops. ''%%svn import%%'' could have been a nice feature if had the ability to see what files on the branch were missing from the files being imported - and then issued the equivalent of ''%%svn rm%%'' on them.
- Subversion does not let you copy-n-paste revision numbers from ''%%svn log%%'':
*
$ svn log foo
------------------------------------------------------------------------
r325249 | deo | 2008-12-14 01:25:28 -0800 (Sun, 14 Dec 2008) | 1 line
..snip..
# X copy-n-paste the "r325249" as my numbers typing isn't good...
$ svn merge -c -r325249 .
svn: Non-numeric change argument (-r325249) given to -c
This is a stupid as CVS is in that you cannot give its date output from ''%%cvs log%%'' as-is as an argument to "-D".
* Sean C. Farley < scf@%%FreeBSD%%.org > tells me that ''%%svn merge -cr325249 .%%'' does work. (Sean thanks for the info!) [Though I still think the Subversion parser need a clue-by-four.] Answer: svn merge -c -r42 is equivalent to svn merge -c -42, which performs a [[http://svnbook.red-bean.com/en/1.7/svn.branchmerge.basicmerging.html#svn.branchmerge.basicmerging.undo|reverse-merge]]. The above parsing error was fixed in http://svn.apache.org/viewvc?view=revision&revision=1036032 (fix released in 1.7.0).
- Even sillier is that if I checkout a tree and make several commits from within the tree, ''%%svn log%%'' will not show them. An ''%%svn update%%'' must be done first. This is really annoying - even more so when doing a merge. Anwser: This is an FAQ: http://subversion.apache.org/faq.html#hidden-log
- Subversion does not automatically expand keywords.
* One did not have to do anything to get ''%%$Id$%%'' expanded using CVS. With Subversion one must explicitly do
*
svn add foo.c
svn propset svn:keywords "FreeBSD=%H" foo.c
At least one can tweak ''%%~/.subversion/config%%'' to add
*.c = svn:eol-style=native; svn:keywords=FreeBSD=%H; svn:mime-type=text/plain
But now ones config file is project specific.
- Some error output is useless:
*
$ cd releng7/usr.bin/logger
$ svn merge -c r175993 --record-only svn+ssh://svn.freebsd.org/base/head/usr.bin/loggger .
svn: File not found: revision 182510, path '/head/usr.bin/loggger'
That wasn't very helpful in figuring out I had a triple g's misspelling...
- There is no option at not having base files in .svn.
* Thus you will always take up twice the disk space, and spend twice as long doing a check out or update than you need to be - if you're writing to NFS and your Subversion server is just as well, if not better, connected to the client system. This is a major issue at $WORK...
Answer: A workaround that offers a partial remedy is to check out a single working copy for the entire freebsd repository at depth empty:
$ svn co --depth empty svn://svn.freebsd.org/base
$ cd base
and then update desired branches to depth infinity:
$ svn up --depth infinity head
$ svn up --depth infinity releng/9.1
With Subversion 1.7, files that don't differ between branches now share the same pristine text base file in the .svn directory.
- Subversion does not sort files in ''%%svn diff%%'' output alphabetically.
- I cannot figure out what ''%%svn log%%'' does within a directory [to understand the output].
* It does not seem to give a combined log for the entire directory (or subtree) as I hoped it would.
- The barren set of 'diff' arguments is quite annoying. The set I often use with CVS are "-u9" to see more context of a diff, and "-Bbw" to not see white space changes. Additionally, I have "diff -p" in my ~/.cvsrc. Subversion has turned this into
*
svn diff --diff-cmd diff -x -u9 -x -p -c 99 foo.c
Even in the "typical" case, Subversion requires
*
svn diff -x -p -c 99 foo.c
Unfortunately, ''%%~/.subversion/config%%'' does not seem to offer any relief from this.
(Well, you can set ''%%"diff-cmd=/usr/bin/diff"%%'' and rely on one's ''%%DIFF_OPTIONS%%'' environmental variable setting, but then diff'ing is slower than it needs to be in the "typical" case.)
Answer: This was fixed in 1.7.0. See the 'diff-extensions' option in ~/.subversion/config (to view an up-to-date config template: svn help --config-dir /tmp/conf; less /tmp/conf/config)
- Why does Subversion bother to tell me the number of lines in a commit log message?
*
r111464 | deo | 2009-01-28 14:45:42 -0800 (Wed, 28 Jan 2009) | 2 lines
Merge blah into foo.
I don't see the benefit in this output. Couldn't we get something more useful instead? Number of source lines changed in that commit for instance.
Answer: This was done to help tools that parse svn log output. See the cvsps problem where its log message parser fails if a CVS log message contains a log-message-separator line...
- Many Subversion commands bail out in processing their command-line arguments if the command operation cannot be accomplished on a particular file.
*
svn rm A B C
D A
svn: 'B' does not exist
Oh!, maybe I need to use --force (e.g. to operate like 'rm -rf').
*
svn rm --force A B C
D A
svn: 'B' does not exist
Nope, same thing. This same stupidity also happens with 'svn propdel svn:executable *'. Thus forcing one to
*
for F in * ; do svn propdel -q svn:executable $F ; done
The "-q" shuts up all the error messages that "svn: Attempting to delete nonexistent property 'svn:executable'". BUT, it also neuters the exit code. Thus one cannot know if it was able to perform the operation or not. So
*
for F in *; do
svn propdel -q svn:executable $F
if [ $? -eq 0 ]; then echo "svn propdel svn:executable $F" ; fi
done
Does not work as desired:
*
$ svn propdel svn:executable A
svn: Attempting to delete nonexistent property 'svn:executable'
$ echo $?
1
$ svn propdel -q svn:executable A
$ echo $?
0