Jul 2007
Subversion is a great system for centralized repository usage
and administration. One of the good (pragmatic?) things about
subversion is the simple built in access method using the
svn protocol. While the svn protocol is
good; using the webdav capability for managing
repositories is definitely a nice touch. Managing a lot of
repositories can be challenging to say the least. In this series a
quick look at setting up a single webdav based
repository; a simplistic script to add repositories, a script to
manage user and finally a full blown shell program for managing
webdav based subversion repositories.
In the example, a repository called foo is
used. The repository will reside in
/var/subversion/foo. Webdav auth files are in
/var/htpasswds/. The following pre-requisites are
needed:
First and foremost the apache installation needs to have the
appropriate module installed. Packages will be used in the
following example. On RPM based systems
yum or up2date can be used to seek out
the packages:
yum search dav | grep -i svn
or
up2date search dav | grep -i svn
And on apt systems:
apt-cache search dav | grep svn
Somewhere in the output will be something akin to
webdav+svn or just dav+svn - that is what
is needed. In the examples below httpd-dav+svn is
used:
{yum,up2date,apt-get} install httpd-dav+svn
All done - time to get on to setting up a repository.
Not unlike a standard repository, setting up a new one makes use
of the svnadmin command for the initialization:
mkdir /var/subversion svnadmin init /var/subversion/foo
At this point either an initial tree can be imported or trunk/branch/patch trees added to the repository.
In /etc/httpd/conf/httpd.conf either an include can
be added for authentication or using one of the default includes in
/etc/httpd/conf.d/ (such as the svn one) can be used,
In this example a separate include is used:
echo "Include conf/dav_svn.auth" >> /etc/httpd/conf/httpd.conf touch /etc/httpd/conf/dav_svn.auth /etc/init.d/httpd restart
On some systems the service utility can be used to
restart services:
service httpd restart
Now it is time to add an entry into the
dav_svn.auth file:
# webdav entry for foo
<Location /svn/foo>
DAV svn
SVNPath /var/subversion/foo/
AuthType Basic
AuthName Foo
AuthUserFile /var/htpasswds/foo
require valid-user
Order deny,allow
</Location>
Note that the entry also points to the htpasswd
file. Finally, create the users:
htpasswd /var/htpasswds/foo user1 htpasswd /var/htpasswds/foo user2 ...
The repository needs to be accessible by the webserver. Make sure that the user and group name reflect the apache dictated ones: example:
chown -R apache:root /var/subversion/foo
The htpasswd command allows for input of the
password or just use pwgen - in the bash
shell a pwgen password can be copied right into the
password prompt question of htpasswd. This is all
great but what happens when a new repository needs to be created or
6 new repositories? Then it is time to script.
Now two new repositories need to be added and there is no end
in sight
. Several problems have cropped up:
Before the topics are addressed, first the common pieces, as with many things at this site there is always the preferred common bits. For these two scripts (for they are to be separate) the common bits are script name, trapping and bombing out:
PROG=${0##*/}
TOPPID=$$
trap "exit 1" 1 2 3 15
...
#-----------------------------------------------------------------------------
# bomb - Simple death routine; display ERRORMESSAGE, kill TOPPID and exit.
#
# requires: ERRORMESSAGE
# returns : exit 1
#-----------------------------------------------------------------------------
bomb()
{
cat >&2 <<ERRORMESSAGE
ERROR: $@
*** ${PROG} aborted ***
ERRORMESSAGE
kill ${TOPPID} # in case we were invoked from a subshell
exit 1
}
Done, time for the svnadd.sh script. In this new
world
(also known as moving target) a generic user
with a default password for the administrators to test is added.
The steps for automatically creating a new repository are:
While the list of tasks looks scary, it most certainly is simple to implement.
repo=$1 webdav_fp=/etc/httpd/conf/webdav_svn.auth repotop=/var/subversion htaccess=/var/htpasswds
So all of the file handles needed are prepped...
The shell is amazing because of the pipe method of
connecting pieces together. To add an entry a simple
echo will suffice:
append_webdav_entry()
{
echo "Adding an entry to ${webdav_fp} for ${repo}"
echo "
# webdav entry for ${repo}
<Location /svn/${repo}>
DAV svn
SVNPath /var/subversion/${repo}/
AuthType Basic
AuthName \"${repo} SVN\"
AuthUserFile /var/htpasswds/${repo}
require valid-user
Order deny,allow
</Location>
" >> $webdav_fp || bomb "Could not add entry to ${webdav_fp}"
}
There is always room for ye olde usage() message: [1]
#-----------------------------------------------------------------------------
# usage - usage message
#-----------------------------------------------------------------------------
usage()
{
cat <<_usage_
Usage: ${PROG} repository_name
Usage: ${PROG} usage
}
The remaining steps can actually be performed from the shell
script's main routine ; first the top portion of
main():
#-----------------------------------------------------------------------------
# Main
#-----------------------------------------------------------------------------
# If no arguments were specified then... wooops...
if [ $# -eq 0 ];then
echo "No repo name specified"
usage
exit 1
fi
# If the user can't remember...
if [ "$repo" = 'usage']; then
usage
exit 0
fi
if [ -d $repotop/$repo ] ; then
bomb "Error: It looks like that repo exists!"
fi
Pretty self explanatory stuff, if the user forgot to enter a
repository name then bomb, if the user typed usage as
the argument then print the message. It is worth noting that a
repository called usage cannot be created with this
script. Last and not least - if a directory exists there
bomb() out. With the starting point of the main
routine the script is pretty much ready to go:
append_webdav_entry # Call append_webdav and build apache entry
# run the svnadmin command
echo "Creating Repository"
svnadmin create $repotop/$repo ||
bomb "Could not create a new repo at ${repotop}/${repo}"
# fixup permissions
echo "Chowning the new repo to apache"
chown -R apache:root $repotop/$repo ||
bomb "Could set proper permissions on ${repotop}/${repo}"
# add our default user with our default password
echo "Adding svn user in ${htaccess}/${repo}"
htpasswd -b -c $htaccess/$repo svn <password> ||
bomb "Could not add svn user to ${htaccess}/${repo}"
# Ummm .. restart apache - we do not use service here as it is not +DAportable
echo "Restarting Apache"
/etc/init.d/httpd restart
exit 0
Outside of the call to append_webdav_entry() the
script repeats the manual steps outlined in the first section of
the text: which is precisely what scripting for administration
is about.
Scripting is the system administrator's friend. Seeing and
identifying tasks that are often repeated is the key to success
regardless of how much tribal
[2]
knowledge goes into them; if done correctly then there is nothing
to worry about.