Contribute

Current Poll

 Which is your favourite IRC network?

 Undernet
 Dalnet
 Efnet
 Ircnet
 Freenode
 Other...
 None...

( 269 votes ~ 4 comments )

Recent Weblogs

More Weblogs

WebDAV on Apache2

Posted by simonw on Fri 4 Nov 2005 at 12:11

Setting up WebDAV (Web based Distributed Authoring and Versioning) was covered briefly previously in an article on SVN. But this didn't stop a plea from a member of DCGLUG for an idiots guide.

WebDAV is a way of making parts of your webserver writable to certain clients. There are obvious reasons why you might want to do this, such as making it easy to update a website, and less obvious reasons, such as sharing Calendar data, or sychronising your bookmarks in Firefox, or to supply a small amount of password protected web space for people to share documents.

Whilst it is called "Authoring and Versioning" it seems the versioning is still arriving in the Apache2 mod-dav. The "Authoring" in this context replaces FTP, and effectively adds some basic file system type behaviour, such as locking. The main reasons to use it are; firewall evasion (port 80 is nearly always open), avoiding the complexities of FTP, or because it makes sense over other solutions for some purpose. As such it is an enabling technology, WebDAV doesn't of itself do much that is new or exciting, but it will. One strong point is the easy integration with Apache 2, which means you can use other Apache directives to set up neat solutions, such as editing scripts on a website.

The example will create a WebDAV enabled directory, on the "www.example.com" website, referenced by "http://www.example.com/webdav/". The example was worked through on Debian Sid, but works "as is" under Debian Sarge.

First make sure Apache 2 is installed and the optional DAV related modules enabled;

apt-get install apache2
a2enmod dav_fs
a2enmod dav

If a2enmod or a2ensite are new to you, read Chris's introduction.

Then you need to rustle up a virtual host if you don't already have one, I created a vanilla virtual host by copying "/etc/apache2/sites-available/default" and editting it down till it reads as follows;

cat /etc/apache2/sites-available/example.com
<VirtualHost *>
        ServerAdmin webmaster@example.com
        ServerName example.com
        ServerAlias www.example.com

        DocumentRoot /home/srw/example.com
        <Directory /home/srw/example.com>
                Options Indexes MultiViews
                AllowOverride None
                Order allow,deny
                allow from all
        </Directory>
</VirtualHost>

Then remember to create the directory, and give ownership to the Apache user. Note editting sites outside of WebDAV may alter file ownership and thus break access via WebDAV.

mkdir /home/srw/example.com
chown www-data /home/srw/example.com
a2ensite example.com
apache2ctl configtest
/etc/init.d/apache2 reload

And a quick check using a browser or wget showed my empty directory index at "http://www.example.com/".

Now we need to set up an authentication scheme, because we don't want just anyone editting our website. I will use "Digest Authentication", which may muddle some old clients but ensure passwords aren't sent in plain text across the network, the alternative "Basic Authentication" is explained in detail in the Apache documentation.

Enable the module, and create a password file.

a2enmod auth_digest
htdigest -c /home/srw/digest-password webdav-example myuser

After the "htdigest" you'; be prompted to enter myuser's password.

Now we add the "WebDAV" section to the virtual host.

cat /etc/apache2/sites-available/example.com
<VirtualHost *>
        ServerAdmin webmaster@example.com
        ServerName example.com
        ServerAlias www.example.com

        DocumentRoot /home/srw/example.com
        <Directory /home/srw/example.com>
                Options Indexes MultiViews
                AllowOverride None
                Order allow,deny
                allow from all
        </Directory>

        # Note Alias goes to our DocumentRoot.
        Alias /webdav /home/srw/example.com

        # But we apply different settings
        <Location /webdav>
           DAV On
           AuthType Digest
           AuthName "webdav-example"
           AuthDigestFile  /home/srw/digest-password
           Require valid-user
       </Location>

</VirtualHost>

apache2ctl configtest

(NB: apache2ctl is quite capable of accepting very broken authentication settings, such as if you have "AuthUserFile" instead of "AuthDigestFile". It is also quite capable of ignoring errors in other extensions to the core of Apache, like mod-perl, but that is for another article).

/etc/init.d/apache2 reload

Now in principal we can edit "example.com" using WebDAV, but do we have a client? Debian has "cadaver" which is a simple(?) command line WebDAV client, which is very handy for testing things.

apt-get install cadaver
cadaver http://www.example.com/webdav/

Once in you can use a selection of fairly normal shell commands, and even "tab completion" of file names, whilst "edit filename" will invoke your editor of choice.

We could have made a simpler configuration, by using a "<Directory>" instead of a "<Location>" directive, without the Alias, and created a simple filestore for one or more users.

I'm still uncovering the mysteries of cadaver and WebDAV, and have yet to deploy it in anger, although I use it to sync my bookmarks, and we are experimenting at work.

Other patterns of configuration can be applied, as you can use "<Limit>" to only allow certain WebDAV operations against a directory, this means you don't always need two ways to refer to the same directory. Although this is needed if in one view the files are handled differently, such as scripts which are usually executed, then you have to override that handler in the WebDAV view.

I also found that the Indexes (such as index.html) may have a default lock against them. Try something like this if it happens to you;

cadaver http://www.example.com/webdav/
Authentication required for webdav-example on server `www.example.com':
Username: myuser
Password:
dav:/webdav/> edit index.html
Locking `index.html': failed:
423 Locked
dav:/webdav/> discover index.html
Discovering locks on `index.html':
Lock token <opaquelocktoken:28cfc4e4-9c04-0410-bed0-c546ac2f7a25>:
  Depth 0 on `http://www.example.com/webdav/index.html'
  Scope: exclusive  Type: write  Timeout: infinite
  Owner: (none)
dav:/webdav/> unlock index.html
Unlocking `index.html':Enter locktoken: opaquelocktoken:28cfc4e4-9c04-0410-bed0-c546ac2f7a25
 succeeded.
dav:/webdav/> edit html

The desirable client, at least for those who find FTP challenging, is a filesystem client. But as you'll see from my question earlier, getting some of these clients to work nicely can be more challenging than perhaps is immediately desirable. Although there are fairly simple workarounds for most of these issues. More on the Debian WebDAV clients when I get more time to play.


Posted by legooolas (144.173.xx.xx) on Fri 4 Nov 2005 at 14:57
Don't suppose anyone has any insight on if you can get apache to do WebDAV things as the user themselves? Just that it would be nice to be able to allow users access to their homedir, for example, which is all owned by them and not by Apache at all... We haven't been able to find a workaround for this as of yet.

[ Parent | Reply to this comment ]

Posted by Anonymous (62.252.xx.xx) on Fri 4 Nov 2005 at 16:18
Suexec is probably the only way to go.

[ Parent | Reply to this comment ]

Posted by legooolas (144.173.xx.xx) on Fri 4 Nov 2005 at 16:32
I was meaning more if anyone has actually managed to do this, as we tried and failed horribly :)

The mod_dav FAQ at http://www.webdav.org/mod_dav/faq/#03-01 suggests using something like a CGI with suexec, but unfortunately doesn't give any pointers to anything which can do such a thing or any more info on such. :)

[ Parent | Reply to this comment ]

Posted by simonw [Weblogs] (84.45.xx.xx) on Fri 4 Nov 2005 at 17:57
Not done it, I suspect the limiting factor is client usability, and you may be better off with a VPN and Samba (or NFS).

The Plone site has some interesting comments on clients, but I suspect, scratch that - I know, Plone itself is overkill for what you are trying to do.

http://plone.org/documentation/how-to/webdav

Isn't Plone overkill for everything ;-)

A friend commented that the Novell WebDAV client for Windows, mentioned on the Plone site, has moved, but that he has the original download file. Somehow I doubt he has rights to redistribute it though, I mean it isn't Debian.

[ Parent | Reply to this comment ]

Posted by mverwijs (131.211.xx.xx) on Mon 12 Dec 2005 at 13:30
> A friend commented that the Novell WebDAV client for Windows, mentioned on the 
> Plone site, has moved, but that he has the original download file.
Haven't tested it, but on the plone page you mentioned, there's an alternative link to the Novell WebDAV client: --> http://d321.k12.id.us/Support/Docs/NOVELL/NetDrive4.1/ndint.exe

[ Parent | Reply to this comment ]

Posted by Anonymous (72.140.xx.xx) on Tue 15 Nov 2005 at 13:15
There is no way to do this ... and I doubt that it will come in apache 2.1.

Apache SuExec is only for CGI. Everything else runs as a single user.

It's a *nix problem really. Any solution requires that you run Apache as root. Apparently there was a version of apache which would fork children running as different users (so main server has to run as root) but it was abandoned.

I have thought of a workaround. It is quite straightforward to write an AuthN/AuthZ pair (you can find examples in perl on the net). The AuthN module
can call a hook that you write. In that script make a system call using 'sudo'
to chown your webdav-accessible files to the apache user. You need to add a logout script somewhere (a CGI with a button on a web page) which runs another
'sudo' call to chown everything back to you. Set up 'sudoers' to allow these
scripts to be run by the webuser without a password.

Ugly but ...

[ Parent | Reply to this comment ]

Posted by cheaven (72.38.xx.xx) on Sat 5 Nov 2005 at 14:26
SMB Web Client may be of interest to you.

C.

[ Parent | Reply to this comment ]

Posted by jeld (24.39.xx.xx) on Fri 4 Nov 2005 at 16:49
Here is a simple trick I used to make a location read only for everyone and read and write for myself (my workstation).
        DAV On
        Order Deny,Allow
        Deny from all
        Allow from 127.0.0.1
        Allow from 10.1.1.0/24
        
                Allow from 10.1.1.42
        
I am restricting by IP, but in a similar way, you can restrict things by user name or something else.

You are off the edge of the map, mate. Here there be monsters!

[ Parent | Reply to this comment ]

Posted by jeld (24.39.xx.xx) on Fri 4 Nov 2005 at 16:53
Crap! My code snippet was eaten by a Grue! How do you post stuff with less-than-greater-than brackets?

You are off the edge of the map, mate. Here there be monsters!

[ Parent | Reply to this comment ]

Posted by simonw [Weblogs] (84.45.xx.xx) on Fri 4 Nov 2005 at 17:43
HTML markup for less then or greater than signs is; ampersand lt semicolon (or gt), that is 4 characters in total, no spaces.

Although note that it is a pig when posting articles to get this right inside "pre" tags as preview seems to handle it different to post, as it got muddled, Steve is working on that. Kupu anyone?!

[ Parent | Reply to this comment ]

Posted by jeld (24.39.xx.xx) on Fri 4 Nov 2005 at 18:28
Thats what I did, I replaced tag brackets with entities, but it still ate them :(
That damned Grue. It is very dark here.

You are off the edge of the map, mate. Here there be monsters!

[ Parent | Reply to this comment ]

Posted by Steve [Scratchpad ~ Weblogs] (82.41.xx.xx) on Fri 4 Nov 2005 at 19:01

Sadly the code is ... intricate ... so currently you have to escape them to preview, then re-escape them to confirm.

I will have it fixed shortly I hope. The problem here is coming from the way that the HTML::Scrubber module normalises input text on each step - and I use that to sanitize potentially hostile code as input by users.

Steve
--

[ Parent | Reply to this comment ]

Posted by Steve [Scratchpad ~ Weblogs] (82.41.xx.xx) on Fri 4 Nov 2005 at 19:39

The most common cases of using markup in plain-text comments should now be working correctly - although this is just a quick hack.

Times like this I think I should just use plain text always, or maybe bbcode!

Steve
--

[ Parent | Reply to this comment ]

Posted by syscomet (82.161.xx.xx) on Fri 11 Nov 2005 at 15:02
Since the ACL extensions aren't supported in Apache, it's a little tricky to sort out decent permissions. I'm interested in seeing if it becomes possible to use Subversion under Apache as a file-system provider, once the ACLs and locking are sorted.

In the meantime, I have something which definitely does not scale well, as you need to edit apache.conf for every user; if you use Apache's "Include" directive, with something like "Include conf/davusers/*.dvu" then you can make it a little more scalable. The layout I use lets me have a WebDAV area where all users with WebDAV accounts can read anything, but writing is limited to the owner of each sub-area.

Instead of using Apache directives to limit writing outside the sub-areas, I limit the ability of an Apache security bug to let someone move things around; the top-level webdav area is owned by root:web-runtime-group mode 0750 and each sub-area is owned web-runtime-user:web-runtime-group mode 0750. I should probably put in some restrictions at the top level too, so that clients have their attempts to write be rejected, instead of failing.

<ifmodule mod_dav.c>
<directory /path/to/webdav/>
allow from 127.0.0.1 ::1
allow from 192.0.2.1
# other allowed clients
Dav on
AuthType Basic
AuthName "MySystemName WebDAV Storage"
AuthUserFile /path/to/web/etc/passwd.dav
Require valid-user
# These are the HTTP methods used in DAV, beyond the usual GET/HEAD/OPTIONS
# <limit put post delete propfind proppatch mkcol copy move lock unlock>
# </limit>
</directory>

<directory /path/to/webdav/fred/>
<limitexcept get options propfind>
Require user fred
</limitexcept>
</directory>

<directory /path/to/webdav/barney/>
<limitexcept get options propfind>
Require user barney
</limitexcept>
</directory>

<directory /path/to/webdav/wilma/>
<limitexcept get options propfind>
Require user wilma
</limitexcept>
</directory>

</ifmodule>

Note that there are even more methods once you get into fancier stuff; my comments in my subversion area say something about REPORT, for instance.

Hope this provides some useful ideas to people.

[ Parent | Reply to this comment ]

Posted by syscomet (82.161.xx.xx) on Sun 13 Nov 2005 at 19:41
I don't know what broke, when, but I've just found that this is actually broken.

The "Require valid-user" isn't being inherited by the sub-directories. :-(

Suggestions for a fix welcome.

[ Parent | Reply to this comment ]

Posted by Anonymous (216.234.xx.xx) on Thu 15 Dec 2005 at 20:44
I followed these instructions to set up a DAV directory and it all works fine if I unlock a file first, but by default every single file is locked, even when they are not created yet. Is there a way to disable default locking of everything?

[ Parent | Reply to this comment ]

Posted by Anonymous (84.154.xx.xx) on Tue 7 Mar 2006 at 15:14

As I was following these instructions I found them very user-friendly and I think I know now much more about WebDAV then some hours ago, but unlikely I got an error I can't fix. So here's my listing:

root@aither:/etc/apache2/sites-available# cadaver http://www.example.com/webdav/
Could not access /webdav/ (not WebDAV-enabled?):
405 Method Not Allowed
Connection to `www.example.com' closed.
dav:!>

I'm sure I got everything to work until this point like this idiots guide said. Perhaps someone has any comments/suggestions/solves to my problem?

Thanks.
Martl

[ Parent | Reply to this comment ]

Posted by simonw [Weblogs] (212.24.xx.xx) on Tue 7 Mar 2006 at 16:18
Missing "Dav On"?
Failure to restart Apache?
Probably best asked of your local {G}LUG.

[ Parent | Reply to this comment ]

Posted by Anonymous (62.179.xx.xx) on Sun 12 Mar 2006 at 21:18
If you using www.example.com you must configure nameserver

[ Parent | Reply to this comment ]

Posted by Anonymous (66.226.xx.xx) on Tue 21 Mar 2006 at 19:22
I followed these instructions exactly and I am getting the same error

/var/lock/apache2# cadaver http://192.168.0.2/calendar/
Could not access /calendar/ (not WebDAV-enabled?):
405 Method Not Allowed
Connection to `192.168.0.2' closed.
dav:!>

Here is my virtual host:


ServerAdmin webmaster@servebeer.com
ServerName dnsName/calendar
ServerAlias 192.168.0.2/calendar

DocumentRoot /var/www/calendar

Options Indexes MultiViews
AllowOverride All
Order allow,deny
allow from all

# Note Alias goes to our DocumentRoot.
Alias /calendar /var/www/calendar

# But we apply different settings

DAV On
AuthType Digest
AuthName "webdav-example"
AuthDigestFile /var/www/digest-password
Require valid-user


[ Parent | Reply to this comment ]

Posted by vishal (196.1.xx.xx) on Mon 13 Mar 2006 at 14:39
this is good . IN the " add the "WebDAV" section to the virtual host"
# But we apply different settings

DAV On
AuthType Digest
AuthName "webdav-example"
AuthDigestFile /home/srw/digest-password
Require valid-user





we can not user capital "DAV On" we have to use small "dav on".

Thanking you .

[ Parent | Reply to this comment ]

User Login

Username:

Password:

Register Account

Quick Site Search