Subversion - gher-uliege/Documentation GitHub Wiki
Subversion is an open source version control system (VCS).
The tool was the main VCS at GHER from 2008 to 2016. Since then, git
has been increasingly used and several projects have been moved from SVN to git.
- The official webpage: http://subversion.tigris.org/
- A book (337 pages!): http://svnbook.red-bean.com/
- Tutorial on subversion: http://artis.imag.fr/~Xavier.Decoret/resources/svn/index.html
- https://subversion.apache.org/
- https://help.ubuntu.com/community/Subversion
- http://www.onlamp.com/pub/a/onlamp/2002/10/31/subversion.html
sudo aptitude install subversion
sudo addgroup subversion
sudo adduser abarth subversion
sudo mkdir /home/svn
cd /home/svn
sudo mkdir repos
sudo chown -R www-data repos
sudo chgrp -R subversion repos
sudo chmod -R g+rws repos
sudo svnadmin create /home/svn/repos
sudo chmod -R g+rws /home/svn
sudo chgrp -R subversion /home/svn
Create a user account on modb which belongs to the group "subversion".
From the command line:
sudo adduser aalvera
sudo adduser aalvera subversion
or using the GUI
sudo users-admin
It is advisable to use SSH keys and ssh-agent to cache your passphrase. Otherwise, Subversion will prompt you to enter your password/passphrase several times when communicating with the server. For more information: https://help.ubuntu.com/community/SSHHowto and instructions can be found here: http://fedoranews.org/dowen/sshkeys
For example, your repository might look like:
calc/
trunk/
tags/
branches/
calendar/
trunk/
tags/
branches/
spreadsheet/
trunk/
tags/
branches/
trunk : common development version
tags : contains the released versions of software. They are usually not changed afterwards
branches : parallel development branches contains usually new feature which are not yet well tested. Once the branch has stabilized it is merged into trunk.
Create a project with the following directory structure
mkdir tmpdir
cd tmpdir
mkdir -p projectA/{trunk,branches,tags}
Import this into the repository:
svn import . svn+ssh://modb.oce.ulg.ac.be/home/svn/repos --message 'Initial repository layout'
Clean-up:
cd ..
rm -rf tmpdir
svn co svn+ssh://modb.oce.ulg.ac.be/home/svn/repos/projectA/trunk projectA
Checked out revision 0.
cd projectA
cp /somewhere/hello.f90 .
svn add hello.f90
A hello.f90
svn commit -m 'add some file'
Adding hello.f90
Transmitting file data .
Committed revision 1.
Make some changes. Examine differences with
$ svn diff
Index: hello.f90
===================================================================
--- hello.f90 (revision 1)
+++ hello.f90 (working copy)
@@ -1,5 +1,6 @@
program hello
implicit none
+ integer :: i
\
write(6,*) 'hello world'
Upload changes
svn commit -m 'add integer'
... to make backups! It's possible to dump the contents of the repository (including all revisions) into a dumpfile. This format is portable, and you can use it to reconstruct a repository if necessary.
`svnadmin dump /home/svn/repos | gzip -9 > svndump-$(date +%Y%m%d-%H%M).gz
This way, the repository can be restored via
gunzip -c `<file>`.gz | svnadmin load /home/svn/repos
gunzip -c
.gz | svnadmin load /home/svn/repos
The following configuration allows you to access the subversion server on modb without entering your password all the time. All commands shown hereafter are to be exectuted on your local machine (normally you do not need to work directly in your modb account)
Include the following in your file ~/.ssh/config file (create it if it does not exist):
Host modb gher04 modb.oce.ulg.ac.be
HostName modb.oce.ulg.ac.be
ForwardAgent yes
User `<your username on modb>
It is also convenient to define the following:
Host *
ForwardX11 yes
ForwardAgent yes
Create a SSH key:
ssh-keygen -t rsa -b 4096 -C "some comment"
Copy your SSH key to modb:
ssh-copy-id -i ~/.ssh/id_rsa.pub modb
Execute the commands on your computer at the directory where your copy of the project is found.
List existing projects
svn list svn+ssh://[email protected]/home/svn/repos
Download a project, for example Gher3D:
svn checkout svn+ssh://[email protected]/home/svn/repos/Gher3D/trunk local-directory
If you downloaded the files before, update your local version with the command:
svn update
Edit the files in your local directory. To see changes between local and repository:
svn diff
To add or delete files on the repository, use
svn add filename
svn delete filename
```bash
To actually commit these changes on the server, use
```bash
svn commit -m "some comments"
For a good tracking of the changes, try to add comments when you do the commit.
To find out which projects are in the modb.oce.ulg.ac.be subversion repository:
svn list svn+ssh://modb.oce.ulg.ac.be/home/svn/repos
```bash
If the user-name on the local machine is not the same as on the server
you can use something like
```bash
svn [command] svn+ssh://[email protected]/home/svn/repos
If you are interested in a particular revision of a project (let's say, the number 3008), you can use the command checkout with additionnal arguments:
svn checkout svn+ssh://modb.oce.ulg.ac.be/home/svn/repos/Project_Name@3008
These operations simply consists in copying the trunk to a another directory.
The trunk is copied to a directory under tags:
svn copy svn+ssh://modb.oce.ulg.ac.be/home/svn/repos/projectA/trunk svn+ssh://modb.oce.ulg.ac.be/home/svn/repos/projectA/tags/r1.1 -m 'release 1.1'
Subversion stores only differences between files. The command svn copy
does thus not physically copy the whole repository. To checkout a
particular release, we need only to specify its location:
svn co svn+ssh://modb.oce.ulg.ac.be/home/svn/repos/projectA/tags/r1.1 projectA
Now the trunk is copied to the directory branch:
svn copy svn+ssh://modb.oce.ulg.ac.be/home/svn/repos/projectA/trunk \
svn+ssh://modb.oce.ulg.ac.be/home/svn/repos/projectA/branches/parallel -m 'MPI version'
To checkout a branch, we need only to specify its location:
svn co svn+ssh://modb.oce.ulg.ac.be/home/svn/repos/projectA/branches/parallel projectA
When working with multiple branches, it might be useful to checkout everything:
svn co svn+ssh://modb.oce.ulg.ac.be/home/svn/repos/projectA`\
A projectA/trunk
A projectA/trunk/hello.f90
A projectA/trunk/Makefile
A projectA/branches
A projectA/branches/parallel
A projectA/branches/parallel/hello.f90
A projectA/branches/parallel/Makefile
A projectA/tags
A projectA/tags/r1.0
A projectA/tags/r1.0/hello.f90
A projectA/tags/r1.0/Makefile
To avoid that trunk and branche diverge, it is good to reintegrate the changes done in the trunk to the branch on a regular basis. All changes of the branch have to be commited, then
cd /path/to/branch
svn status # no changes
svn merge ^/OAK/trunk
Before merging a branch back to the trunk, it is safer to merge first all changes from trunk to the branch and test the code.
See "Keeping a Branch in Sync" http://svnbook.red-bean.com/en/1.7/svn.branchmerge.basicmerging.html.
After running the steps in "Keeping a branch in sync", one can reintegrate the branch into trunk:
cd /path/to/trunk
svn up
svn status
svn commit -m 'last changes'
svn up
svn merge --reintegrate ^/divaonweb/branches/divaonweb-nginx
As SVN stores the differences between versions of a same file, tracking changes is very easy.
Use the command svn log
with the name of the file as argument. The log
indicates:
- who modified the file and when it was modified
- the revision number corresponding to the revision
- a message explaining the change (the ''-m 'message for commit' '' option of svn commit)
$ svn log hello.f90`\
------------------------------------------------------------------------
r10 | abarth | 2008-02-24 18:02:35 +0100 (Sun, 24 Feb 2008) | 1 line
\
add a real
------------------------------------------------------------------------
r2 | abarth | 2008-02-22 21:57:57 +0100 (Fri, 22 Feb 2008) | 1 line
\
add some file
------------------------------------------------------------------------
Check the diff command in the SVN bool: http://svnbook.red-bean.com/en/1.7/svn.ref.svn.c.diff.html
What is the difference between version 10 and 2:
$ svn diff -r 10:2 hello.f90
Index: hello.f90
===================================================================
--- hello.f90 (revision 10)
+++ hello.f90 (revision 2)
@@ -1,7 +1,6 @@
program hello
implicit none
integer :: i
- real :: r
\
write(6,*) 'hello world'
If you type only
svn diff hello.f90
the output will be the differences between the last committed version and the version you are working on.
If the tabulations and/or spaces in the file have changed, then the
svn diff
command will yield a long list of differences that you probably don't care about. In this case, you would prefer to use
diff -E -b -w
where
- -E : Ignore changes due to tab expansion.
- -b : Ignore changes in the amount of white space/
- -w : Ignore all white space.
To force svn to use these optional arguments, the syntax is as follows:
svn diff --diff-cmd diff -x "-E -w -b" -r10:2 hello.f90
or
svn diff --diff-cmd /usr/bin/diff -x "-E -w -b" -r10:2 hello.f90
Hence it is the --diff-cmd option that allows the user to select the diff command, while the argument placed after the -x are the actual options of the diff command.
For situations when you want to go back to an older version of a file, the command to use is svn merge, as explained at http://svnbook.red-bean.com/en/1.2/svn.branchmerge.commonuses.html#svn.branchmerge.commonuses.undo
The typical steps to follow are:
1. Roll back the changed made:
svn merge -r 3010:3008 svn+ssh://modb.oce.ulg.ac.be/home/svn/repos/projectA/trunk/file_to_modify
2. Check the status
svn status
M file_to_modify
3. Check if the unwanted changes are removed:
svn diff
4. Commit
svn commit -m "Undoing change committed in r3010."
Before solving conflicts, the best thing is to try to avoid them. If you know you are going to work on a same projects with other colleagues at the same time, try to work on different files.
If for some reasons you have to face conflicts, the first thing is to consult the SVN book: http://svnbook.red-bean.com/en/1.7/svn.tour.cycle.html#svn.tour.cycle.resolve
The conflicts will appear when you use the command
svn update
If you try to commit when a conflict was detected, then the commit will be aborted.
Different possibilities can occur for a given file. If before the name of the file you have
- U: it means that the file was updated.
- G: the file was merged, meaning that your modifications and those from the other users were done without any overlap.
- Conflict discovered in file_name: a conflict has to be solved.
In that case, several options are offered:
- (p) postpone: the conflict will be resolved later
- (df) diff-full: show all changes made to merged file
- (e) edit: change merged file in an editor
- (mc) mine-conflict: accept my version for all conflicts (same)
- (tc) theirs-conflict: accept their version for all conflicts (same)
- (s) show all options.
For ever conflicted file, three extra unversioned files are created in your working copy:
- filename.mine
- filename.rOLDREV
- filename.rNEWREV
Once you have solved the conflict, use the command
svn resolved file_name
and commit the file. The three intermediate files will be removed automatically.
An SVN checkout within an SVN checkout from a different repository is possible, using the svn:externals property:
`svn propget svn:externals . > /tmp/svn_external
add a line to the file /tmp/svn_external (maybe empty) with the local directory name and the URL:
ncArray https://svn.code.sf.net/p/octave/code/trunk/octave-forge/extra/ncArray/inst
Update the properties and checkout
svn propset svn:externals -F /tmp/svn_external .
svn up
-
When working over SSH, it is advisable to use keys and ssh-agent to cache your passphrase. Otherwise, Subversion will prompt you to enter your password/passphrase several times when communicating with the server.
-
Avoid using two files with the same name in the same directory using different lower case and upper case letters. This can cause trouble when using SVN on some systems (Windows-Dos).
For example to set a file permission to executable), do not use
chmod +x filename
svn commit -m 'changed permission'
since no change on the file will be captured by svn. The solution is to use
svn propset `[`svn:executable`](svn:executable)` '*' filename
svn commit -m 'changed permission'
Source: http://lexfridman.com/blogs/research/2011/02/21/executable-files-in-svn/
The message looks like
Transmitting file data .......svn: Commit failed (details follow):
svn: While preparing 'filename' for commit
svn: File 'filename' is out of date
Possible solution: use the update command
svn delete filename
svn commit -m 'message'
svn update
svn add filename
svn commit -m 'another message'
svn add *
will work but gives warning messages. Another solution is
svn status | grep -v "^.[ \t]*\..*" | grep "^?" | awk '{print $2}' | xargs svn add
which looks for files of which the status is ?
Source: http://snipplr.com/view/15471/