== Subversion Setup and Configuration (SVN) == This article explains how to perform version control using Subversion (Linux or Windows server) and SVN (Linux client) or TortoiseSVN (Windows client). ==Subversion under Linux== ===Installation=== Install package while installing Linux, or from the menu Start > System > Add/Remove Software. ===Configuration=== ====Setup Server Permissions==== Create a directory where future repositories will be stored. Note: this is not the repository, but a container to the repositories. $ mkdir /data/repos Create a specific user to run Subversion. Create system account for ''svnuser'' (use repository directory as home directory): $ /usr/sbin/groupadd -r svnuser $ /usr/sbin/useradd -g svnuser -c "Subversion User" -d /data/repos -s /bin/bash -r -l -n svnuser Run Subversion server (svnserve). Restrict Subversion to allow exporting trees only under a specific directory (-d for daemon, -T for threaded, -r for root directory). Execute one of these commands (assuming the repository is in ''/data/repos''): $ svnserve -d -T -r /data/repos $ sudo -u svnuser svnserve -d -T -r /data/repos $ su -l svnuser -c "svnserve -d -T -r /data/repos" Add exception rule to firewall to allow traffice through port 3690 on the subversion server. In Ubuntu: $ ufw status $ # Only to 192.168.0.31: ufw allow from 192.168.0.0/24 to 192.168.0.31 port 3690 $ ufw allow from 192.168.0.0/24 to any port 3690 > ** Note for SELinux / Fedora Core 3+ / Red Hat Enterprise users ** ((Subversion FAQ, http://subversion.tigris.org/faq.html)) : > In addition to regular Unix permissions, under SELinux every file, directory, process, etc. has a 'security context'. When a process attempts to access a file, besides checking the Unix permissions the system also checks to see if the security context of the process is compatible with the security context of the file. > Fedora Core 3, among other systems, comes with SELinux installed by default, configured so that Apache runs in a fairly restricted security context. To run Subversion under Apache, you have to set the security context of the repository to allow Apache access (or turn off the restrictions on Apache, if you think all this is overkill). The chcon command is used to set the security context of files (similarly to how the chmod sets the traditional Unix permissions). For example, one user had to issue this command > $ chcon -R -h -t httpd_sys_content_t PATH_TO_REPOSITORY > to set the security context to be able to successfully access the repository. ====Script for Start/Stop Subversion Service==== Create a script to launch ''svnserve'' at server boot time. The file should be called ''/etc/init.d/svnserve'': #!/bin/bash # # Startup script for the Subversion's SVNSERVE # # chkconfig: - 85 15 # description: Subversion is an excellent VCS. # processname: svnserve # pidfile: /var/run/subversion.pid # config: /etc/subversion.conf or /etc/subversion/config ? # # Author: Dejan Lekic, dejan@nu6.org, http://dejan.lekic.org # Version: 1.0 # Modification: # 2005.01.11 by Wan-rong Jih # 2006.08.17 by Siegwart Mayr # # Source function library. . /etc/rc.d/init.d/functions # This will prevent initlog from swallowing up a pass-phrase prompt. INITLOG_ARGS="" # Path to the svnserve binary. svnserve_prog=/usr/bin/svnserve svnserve_exec=svnserve svnserve_pidf=/var/run/subversion.pid svnserve_user=svnuser svnserve_repo=/data/repos RETVAL=0 start() { echo -n $"Starting $svnserve_exec: " #echo -n $"Executing $svnserve_prog -d -T -r $svnserve_repo" echo -n $"Repository => $svnserve_repo" su -l $svnserve_user -c $"$svnserve_prog -d -T -r $svnserve_repo" RETVAL=$? #echo [ $RETVAL = 0 ] && touch /var/lock/subsys/subversion [ $RETVAL -eq 0 ] && echo_success [ $RETVAL -ne 0 ] && echo_failure echo `/sbin/pidof svnserve` > $svnserve_pidf echo return $RETVAL } stop() { echo -n $"Stopping $prog: " killproc $svnserve_exec RETVAL=$? echo [ $RETVAL = 0 ] && rm -f /var/lock/subsys/subversion $svnserve_pidf } # See how we were called. case "$1" in start) start ;; stop) stop ;; status) status $svnserve_exec ;; restart) stop start ;; reload) echo -n $"Reloading $svnserve_exec: " killproc $svnserve_exec -HUP RETVAL=$? echo ;; condrestart) if [ -f $svnserve_pidf ] ; then stop start fi ;; *) echo $"Usage: $prog {start|stop|restart|reload|condrestart|status}" exit 1 esac exit $RETVAL ===Creating a Project Repository=== Create a project repository (''proj1'') in directory ''/data/repos'': $ svnadmin create /data/repos/proj1 Add a repository user to have access to the project. Edit file ''proj1/conf/passwd'' to include: [users] jdoe = mypassword123 Edit file ''proj1/conf/svnserve.conf'' to include: [general] password-db = passwd realm = My Realm Set correct file permissions for project repository: $ chmod -R 750 proj1 $ chown -R svnuser:svnuser proj1 Create layout of project: $ mkdir tmpdir $ cd tmpdir $ mkdir proj1 $ mkdir proj1/trunk $ mkdir proj1/branches $ mkdir proj1/tags Import a project (''/tmpdir/proj1'') into the empty repository (''proj1''): $ svn import /tmpdir/proj1 svn://server1.example.com/proj1 --message "Initial import" ===Checkout a Project (get a Working Copy)=== Checkout a copy of the project ''/data/repos/proj1'' to create a working copy: $ mkdir /projects/proj1 $ cd /projects/proj1 $ svn checkout svn://server1.example.com/proj1 ===Submitting Changes to Repository=== Update your current copy with the latest repository changes: $ svn update Commit your changes to the repository (and log changes): $ svn commit --message "Added a few more things" ===Configure Server for Log Editing=== Create or edit the file ''proj1/hooks/pre-revprop-change'' to have the following: # The hook program typically does not inherit the environment of # its parent process. For example, a common problem is for the # PATH environment variable to not be set to its usual value, so # that subprograms fail to launch unless invoked via absolute path. # If you're having unexpected problems with a hook program, the # culprit may be unusual (or missing) environment variables. # # Here is an example hook script, for a Unix /bin/sh interpreter.# For more examples and pre-written hooks, see those in # the Subversion repository at # http://svn.collab.net/repos/svn/trunk/tools/hook-scripts/ and # http://svn.collab.net/repos/svn/trunk/contrib/hook-scripts/ REPOS="$1" REV="$2" USER="$3" PROPNAME="$4" ACTION="$5" if [ "$ACTION" = "M" -a "$PROPNAME" = "svn:log" ]; then exit 0; fi echo "Changing revision properties other than svn:log is prohibited" >&2 exit 1 Make sure the file is owned by ''svnuser:svnuser'' and permissions are set to user read-execute (''-r-x------''). ==Subversion under Windows== ===Installation=== * Download server from Subversion: http://subversion.tigris.org * Download client from TortoiseSVN: http://tortoisesvn.tigris.org * Run installation for each. ===Configuration=== * Server: Default values are just fine. * Client: In Windows Explorer, right-click on a folder, and select "Tortoise SVN" > "Settings". Default values are just fine. ===Repository Setup (directory under Version Control)=== * Create a directory for all repositories (this is not a repository, but the container of all repositories): Eg: ''D:\repos'' * Create a directory for a project repository: Eg: ''D:\repos\ezfit4'' * Create Repository: In Windows Explorer, right-click on folder to be repository. Select "TortoiseSVN" > "Create Repository here". Eg: ''D:\repos\ezfit4\'' * Import project to Repository: In Windows Explorer, right-click on project folder to be imported into the repository. Select "TortoiseSVN" > "Import". Eg: ''C:\proj\ezfit4\'' * NOTE: Project should have a directory structure that supports a trunk, branches, and tags. Eg: C:\proj\ezfit4\trunk C:\proj\ezfit4\branches C:\proj\ezfit4\tags * Enable port 3690 on firewall (or alternatively, add firewall access to svnserve.exe). ===Server Setup=== ====Run Service==== Create a Windows service to run server (svnserve.exe). This allows the system to run the server without needing a user to be logged in. * Download SVNservice from http://dark.clansoft.dk/~mbn/svnservice/ * Unpack svnservice.zip and copy svnservice.exe to same folder as svnserve.exe (i.e. ''C:\Program Files\Subversion\bin''). * Install service: C:\> cd C:\Program Files\Subversion\bin\ C:\> SVNService -install -d -r D:\repos * Syntax: *: ''SVNService -install '''''' to install the service. *: ''SVNService -setup '''''' to change command line parameters for svnserve. *: ''SVNService -remove'' to remove the service. * Run service SVNservice from Control Panel > Administration Tools > Services > SVNservice. Set it up to run automatically at startup. ====Repository Authentication (Quickstart)==== Under repository, create/edit a file ''conf/svnserve.conf'' with the following (For example: ''D:\repos\ezfit4\conf\svnserve.conf''): [general] anon-access = none auth-access = write password-db = passwd realm = MyProject Under repository, create/edit a file ''conf/passwd'' with the following (For example: ''D:\repos\ezfit4\conf\passwd''): [users] smayr = mypasswordhere joel = anotherpasswordhere ====Repository Authentication (Detailed)==== The default svnserve setup provides anonymous read-only access, so whilst you can use the repo-browser in TortoiseSVN to view a repository using an ''svn://''//URL//, you won't be able to perform any normal Subversion operations such as checkout, update or commit. To enable write access to a repository, you need to edit the ''conf/svnserve.conf'' file in your repository directory. This file controls the configuration of the svnserve daemon, and also contains useful documentation. You can enable anonymous write access by simply setting: [general] anon-access = write However, you will not know who has made changes to a repository, as the ''svn:author'' property will be empty. You will also be unable to control who makes changes to a repository. This is a somewhat risky setup! One way to overcome this is to create a password database: [general] anon-access = none auth-access = write password-db = password.conf Where password.conf is a file which exists in the same location as ''svnserve.conf'', it can also exist on a path relative to the ''conf'' directory and has a structure of: [users] username = password ... This example would deny all access for unauthenticated (anonymous) users, and give read-write access to all users in the ''password.conf'' file. If you have multiple repositories, then setting up an authentication realm should make administration easier. For example, if you have two repositories, creatively named TestRepo and TestRepo2, and they both live as sub-directories under ''c:\repos'', to setup an authentication realm between them: ''c:\repos\TestRepo\conf\svnserve.conf'' [general] anon-access = read auth-access = write password-db = password.conf ''c:\repos\TestRepo2\conf\svnserve.conf'' [general] realm = /TestRepo TestRepo2 now shares the same password database as TestRepo, which gives read-only unauthenticated (anonymous) access and read-write access for authenticated users. ====Test Server==== Point browser or SVN client (TortoiseSVN or RapidSVN) to repository. For example: ''svn://localhost/ezfit4'' ===Checkout a Project (get a Working Copy)=== * Create a destination project directory: Eg: C:\proj\ezfit4.workcopy * Checkout: In Windows Explorer, right-click on folder to be used as destination. Select "Checkout". * Use Project: In Windows Explorer, go to the folder and launch the project or edit the required files. ===Submitting Changes to Repository=== * Update: Get and incorporate the new changes on the repository to your own project. This is important, so when you finally upload your changes, it will contain what the repository had. * Commit: After Update, you can now submit your project changes to the repository. ===Configure Server for Log Editing=== Open hooks directory in repository: ''D:\repos\ezfit4\hooks'' Create file ''pre-revprop-change.bat'' file in that folder with these contents (For example: ''D:\repos\ezfit4\hooks\pre-revprop-change.bat''): rem # PRE-REVPROP-CHANGE HOOK rem # Only allow log messages to be changed. if "%4" == "svn:log" exit 0 echo Property '%4' cannot be changed >&2 exit 1 Perform previous steps for each repository that needs log editing. === Setup Branches and Tags === * Branches are parallel development copies, to add new features without tampering with the main project trunk. * Tags are static snapshots of a specific release, to have as an archive. **Create a Branch/Tag** To create a branch (or tag), simply use one of the following: * In svn use ''copy'' command: % svn copy SRC DST * In TortoiseSVN use Branch/Tag command: * Right-click on project * TortoiseSVN > Branch/Tag * Select a target folder such as ''svn://server/projname/branches/projname-1.0'' === Synchronizing Branch To Trunk === * Periodically you merge trunk changes into the branch, so that the branch contains all the trunk changes plus the new feature. The synchronisation process uses Merge a range of revisions. When the feature is complete then you can merge it back to trunk using either Reintegrate a branch or Merge two different trees. * [[http://svnbook.red-bean.com/en/1.5/svn.branchmerge.basicmerging.html|Basic Merging]]