mickael-kerjean / filestash

🦄 A modern web client for SFTP, S3, FTP, WebDAV, Git, Minio, LDAP, CalDAV, CardDAV, Mysql, Backblaze, ...
https://www.filestash.app/
GNU Affero General Public License v3.0
9.77k stars 719 forks source link

[bug] Windows WebDAV client attempts `OPTIONS` on document root and breaks #669

Open sevmonster opened 4 months ago

sevmonster commented 4 months ago

Description of the bug

Originally I was trying to use Windows' Add network location feature to sync a share link, to replace Nextcloud and its client. However, it doesn't seem to work: image

The issue appears to be that before Windows even attempts to poke or browse the WebDAV URI, it sends an OPTIONS request on the document root. I assume this is Windows attempting to test if the domain provided is indeed for a WebDAV server, or otherwise allows the WebDAV request methods. Adding the headers usually returned by the library allows it to continue past this point. I don't know if the WebDAV/HTTP spec etc. specifies that the document root should be checked, but regardless, Windows does it.

One thing that really ground my gears when testing this: The result of the above check is cached and attempting to add any other link at the same domain will fail for any later attempts. However, after getting it working, I also found out that a successful check will also be cached, and it will be assumed successful on later attempts. The only way I've seen to clear this cache is to reboot.

This can easily be worked around with a rewrite in a reverse proxy. I used the following Nginx config to kludge it:

map $request_uri#$request_method#$http_user_agent $filestash_fixdav {
    ~^/#OPTIONS#DavClnt   1; # detect Windows DavClnt probes on root
    # ...
    default '';
}
# generate the variables used by the Windows WebDAV hack
map $filestash_fixdav $filestash_fixdav_davclnt_allow {
    1       'OPTIONS, LOCK, PUT, MKCOL';
    default $upstream_http_allow;
}
map $filestash_fixdav $filestash_fixdav_davclnt_dav {
    1       '1, 2';
    default $upstream_http_dav;
}
map $filestash_fixdav $filestash_fixdav_davclnt_authorvia {
    1       'DAV';
    default $upstream_http_ms_author_via;
}

server {

    location / {
        # ...

        # HACK: fix for Microsoft DavClnt sending an OPTIONS request to
        #       document root on shared links instead of to the link itself,
        #       which does not work as DAV only works under the share URI
        if ($filestash_fixdav = 1) {
            return 200;
        }
        more_set_headers "Allow: $filestash_fixdav_davclnt_allow";
        more_set_headers "Dav: $filestash_fixdav_davclnt_dav";
        more_set_headers "Ms-Author-Via: $filestash_fixdav_davclnt_authorvia";

        # ...
    }
}

This appears to be the same bug as #241.

Step by step instructions to reproduce the bug

  1. Create a share link to any directory
  2. Try to use that directory in Windows Explorer

Can you replicate that error from the demo?

Yes. This shows that it isn't just my chosen backend (local folder), but it also happens with S3.

Observed behavior

It doesn't work

Expected behavior

It does work

sevmonster commented 1 month ago

It seems there are multiple bugs with the WebDAV implementation. I will focus this issue on the problem with Windows specifically, where it sends OPTIONS to the document root. The issue with the trailing slash appears to not be Windows-specific as I have been able to replicate it with KDE Dolphin via the webdavs:// handler.