Differences
This shows you the differences between two versions of the page.
Both sides previous revisionPrevious revisionNext revision | Previous revision | ||
services:fileserver [2024/09/04 08:55] – willy | services:fileserver [Unknown date] (current) – removed - external edit (Unknown date) 127.0.0.1 | ||
---|---|---|---|
Line 1: | Line 1: | ||
- | ====== File Server ====== | ||
- | |||
- | I will not discuss how to share your files on the home network using __legacy__ tools like [[https:// | ||
- | |||
- | I will focus on how to provide access via __web browser__ and via __WebDAV__, which is a web-based sharing protocol a bit like NFS or SAMBA, but aimed ad broader __internet__ access, and not __intranet__ access. | ||
- | |||
- | The idea is to create share areas where your users will be able to store files. It is possible to extend this idea also to user-specific areas where each user can put private stuff not visible by other users, but this require a little bit extra complexity and might be addressed in the future. | ||
- | |||
- | You will be using your SSO authentication, | ||
- | |||
- | A future upgrade might prefer the use of //sFtpGo// instead of // | ||
- | |||
- | ===== Overall Architecture and Shares ===== | ||
- | |||
- | This solution leverages two tools: | ||
- | * [[services: | ||
- | * [[https:// | ||
- | |||
- | The NGINX reverse proxy will integrate both with your preferred [[selfhost: | ||
- | |||
- | I will assume, for the sake of example, that you want to share one folder called __common__. This folder is phisically located under **/ | ||
- | |||
- | I choose to assign a dedicated subdomain, **drive.mydomain.com**, | ||
- | * **https:// | ||
- | * **https:// | ||
- | * **https:// | ||
- | |||
- | You can add any more folders as separate shares as you like. | ||
- | |||
- | |||
- | === Permissions and Users === | ||
- | |||
- | Each share will be accessible by different users, so this needs to be planned a bit. For user-specific shares, not much needs to be done except run FileBrowser for the specific share as the specific user. This is left as an exercise for you. | ||
- | |||
- | For common shares instead, it'ìs important to create one common user, which i will call **fileserver** user to run the associated services, and create the **/ | ||
- | |||
- | You need to assign that folder to the **users** group and the **fileserver** user: | ||
- | <code bash> | ||
- | useradd -d / | ||
- | chown fileserver: | ||
- | </ | ||
- | |||
- | You need to set the //umask// for the fileserver user to **0002** so that any new files created by it will be writable by the users. Also, create the **.db** folder, where the FileBrowser database will need to be located, and the **.apache** folder, there specific Apache configuration need to be located: | ||
- | <code bash> | ||
- | su - fileserver | ||
- | echo "umask 0002" >> ~/.bashrc | ||
- | source ~/.bashrc | ||
- | mkdir .db | ||
- | mkdir .apache | ||
- | </ | ||
- | |||
- | |||
- | All other users which need to access the common shares must be in the **users** group. | ||
- | |||
- | |||
- | ===== Fileserver access via Browser ===== | ||
- | |||
- | I am currently using [services: | ||
- | |||
- | You will need to run **one** instance of FileBrowser for each share, thus you will to allocate one specific port for each share. I will describe how to run it for the **common** share, so // | ||
- | |||
- | So, create the specific **/ | ||
- | <file - filebrowser.common> | ||
- | BASE_URL="/ | ||
- | DATABASE="/ | ||
- | DESCRIPTION=" | ||
- | FOLDER="/ | ||
- | GROUP=" | ||
- | PORT=3002 | ||
- | USER=" | ||
- | </ | ||
- | |||
- | Create the **init.d** symlink too, and start it. Of course, choose a free port. See my [[services: | ||
- | |||
- | |||
- | ===== Fileserver access via WebDAV ===== | ||
- | |||
- | __NOTE:__ using HTTP will cause a 301 redirect to HTTPS, and WebDAV clients will fail. So use HTTPS URL in webdav clients. | ||
- | |||
- | Ok, this will __not__ be very simple, but bear with me, it will work. | ||
- | |||
- | It will be __more__ complex to add more WebDAV shares, specially if associated to different users, this is left as an exercise for you. | ||
- | |||
- | While there are a few WebDAV servers like [[https:// | ||
- | |||
- | The idea here is to run a dedicated copy of Apache as user // | ||
- | <code bash> | ||
- | emerge apache` | ||
- | </ | ||
- | WebDAV is enabled by default in Gentoo Apache ebuild, so there is no need to fix USE flags. | ||
- | |||
- | You will **not** be running Apache as system service, and this requires some effort, so, buckle up! | ||
- | |||
- | === Prepare apache folders for each share === | ||
- | |||
- | First of all, Apache needs some folders to operate as normal user, so you need to create: | ||
- | * / | ||
- | * / | ||
- | * / | ||
- | * / | ||
- | |||
- | <code bash> | ||
- | su - fileserver | ||
- | mkdir / | ||
- | mkdir / | ||
- | mkdir / | ||
- | mkdir / | ||
- | </ | ||
- | |||
- | === Create apache configuration files for each share === | ||
- | |||
- | Each share will need it's full set of Apache configuration files, because you will need to run one specific apache server for each share. | ||
- | |||
- | Put all the following files (after editing it to your needs!) under **/ | ||
- | |||
- | This is generic, and could be shared between all shares if you prefer: | ||
- | <file - apache_global.conf> | ||
- | ServerRoot "/ | ||
- | LoadModule actions_module modules/ | ||
- | LoadModule alias_module modules/ | ||
- | LoadModule auth_basic_module modules/ | ||
- | LoadModule authn_anon_module modules/ | ||
- | LoadModule authn_core_module modules/ | ||
- | LoadModule authn_dbm_module modules/ | ||
- | LoadModule authn_file_module modules/ | ||
- | LoadModule authz_core_module modules/ | ||
- | LoadModule authz_dbm_module modules/ | ||
- | LoadModule authz_groupfile_module modules/ | ||
- | LoadModule authz_host_module modules/ | ||
- | LoadModule authz_owner_module modules/ | ||
- | LoadModule authz_user_module modules/ | ||
- | LoadModule autoindex_module modules/ | ||
- | < | ||
- | LoadModule cache_module modules/ | ||
- | </ | ||
- | LoadModule dav_module modules/ | ||
- | LoadModule dav_fs_module modules/ | ||
- | LoadModule dav_lock_module modules/ | ||
- | LoadModule deflate_module modules/ | ||
- | LoadModule dir_module modules/ | ||
- | LoadModule env_module modules/ | ||
- | LoadModule expires_module modules/ | ||
- | LoadModule ext_filter_module modules/ | ||
- | < | ||
- | LoadModule file_cache_module modules/ | ||
- | </ | ||
- | LoadModule filter_module modules/ | ||
- | LoadModule headers_module modules/ | ||
- | < | ||
- | LoadModule http2_module modules/ | ||
- | </ | ||
- | LoadModule include_module modules/ | ||
- | < | ||
- | LoadModule info_module modules/ | ||
- | </ | ||
- | LoadModule log_config_module modules/ | ||
- | |||
- | # This is needed to avoid error on load due to default path being not accessible | ||
- | TransferLog / | ||
- | |||
- | LoadModule logio_module modules/ | ||
- | LoadModule mime_module modules/ | ||
- | LoadModule mime_magic_module modules/ | ||
- | LoadModule negotiation_module modules/ | ||
- | LoadModule rewrite_module modules/ | ||
- | LoadModule setenvif_module modules/ | ||
- | < | ||
- | LoadModule status_module modules/ | ||
- | </ | ||
- | LoadModule unique_id_module modules/ | ||
- | LoadModule unixd_module modules/ | ||
- | < | ||
- | LoadModule userdir_module modules/ | ||
- | </ | ||
- | LoadModule usertrack_module modules/ | ||
- | LoadModule vhost_alias_module modules/ | ||
- | Include / | ||
- | </ | ||
- | |||
- | This needs to be specific for each share: | ||
- | <file - common.conf> | ||
- | Include / | ||
- | |||
- | User fileserver | ||
- | Group users | ||
- | |||
- | DavLockDB "/ | ||
- | PidFile / | ||
- | ErrorLog / | ||
- | TransferLog / | ||
- | CustomLog / | ||
- | |||
- | DocumentRoot / | ||
- | |||
- | ServerName 127.0.0.1 | ||
- | Listen 127.0.0.1: | ||
- | |||
- | < | ||
- | DAV On | ||
- | AllowOverride All | ||
- | Options -Indexes +FollowSymlinks -ExecCGI -Includes | ||
- | Require all granted | ||
- | </ | ||
- | |||
- | SetEnv redirect-carefully | ||
- | |||
- | # vim: ts=4 filetype=apache | ||
- | </ | ||
- | |||
- | Please note the Listen directive: you want apache to be bound to // | ||
- | |||
- | === Messing with the WebDAV root folder === | ||
- | |||
- | Now, the fun part is that you want to protect this behind the NGINX reverse proxy (for HTTPS and authorization reasons) and it seems that WebDAV does **not** play well with URL redirection and similar funny things. In other words, the base url you will be using on the reverse proxy **must match** the url in the Apache. You **cannot use** rewrite directives or Alias stuff. | ||
- | |||
- | Since you will be exposing the browser-based access as **https:// | ||
- | |||
- | so, create the paths first: | ||
- | <code bash> | ||
- | su - fileserver | ||
- | cd / | ||
- | mkdir webdav | ||
- | cd webdav | ||
- | mkdir common | ||
- | </ | ||
- | |||
- | === Startup Apache for the share (and autostart) === | ||
- | |||
- | To start Apache, create the following **/ | ||
- | <file - webdav> | ||
- | ... | ||
- | </ | ||
- | this startup script | ||
- | |||
- | Link it as **/ | ||
- | <code bash> | ||
- | ln -s / | ||
- | </ | ||
- | |||
- | <file - webdav.common> | ||
- | ... | ||
- | </ | ||
- | |||
- | Now add it to the default runlevel and start it: | ||
- | <code bash> | ||
- | chmod +x / | ||
- | rc-update add webdav.common default | ||
- | / | ||
- | </ | ||
- | |||
- | |||
- | NOTE: the following needs to be rewritten, please ignore the rest of this parsagraph. | ||
- | |||
- | and mount the needed shares, you can create the **/ | ||
- | <file - apache_start.sh> | ||
- | #!/bin/bash | ||
- | # Bind/Mount the share for Apache | ||
- | if [ " | ||
- | then | ||
- | mount -o bind / | ||
- | fi | ||
- | su - filebrowser -c " | ||
- | </ | ||
- | |||
- | (ignore up to here) | ||
- | |||
- | |||
- | |||
- | |||
- | ===== Reverse Proxy and wrap-up ===== | ||
- | |||
- | Everything is protected behind the [[selfhost: | ||
- | <file - drive.conf> | ||
- | server { | ||
- | server_name drive.mydomain.com; | ||
- | listen 443 ssl; | ||
- | listen 8443 ssl; | ||
- | http2 on; | ||
- | |||
- | access_log / | ||
- | error_log / | ||
- | |||
- | # WebDAV requires basic auth, while normal auth can be used with FileBrowser | ||
- | include " | ||
- | include " | ||
- | |||
- | location / { | ||
- | include " | ||
- | include " | ||
- | root / | ||
- | } | ||
- | |||
- | location = /common { | ||
- | | ||
- | } | ||
- | |||
- | location /common/ { | ||
- | include " | ||
- | include " | ||
- | client_max_body_size 512M; | ||
- | proxy_pass http:// | ||
- | proxy_set_header Connection $http_connection; | ||
- | proxy_set_header Connection ' | ||
- | proxy_cache_bypass $http_upgrade; | ||
- | } | ||
- | |||
- | | ||
- | include " | ||
- | include " | ||
- | |||
- | # https:// | ||
- | # https:// | ||
- | set $dest $http_destination; | ||
- | if ($http_destination ~ " | ||
- | set $dest http:// | ||
- | } | ||
- | |||
- | # Warning: adding / at the end of the proxy_pass will break WebDAV! | ||
- | proxy_pass http:// | ||
- | proxy_buffering off; | ||
- | gzip off; | ||
- | proxy_pass_request_headers on; | ||
- | | ||
- | } | ||
- | client_max_body_size 100M; | ||
- | } | ||
- | </ | ||
- | |||
- | This example also shows how i have integrated [[selfhost: | ||
- | |||
- | refer to the [[selfhost: | ||
- | |||
- | ==== Main Directory Page ==== | ||
- | |||
- | As you can spot from the above NGINX configuration, | ||
- | |||
- | For this i am using my [[services: | ||
- | <file - site.json> | ||
- | { | ||
- | " | ||
- | " | ||
- | " | ||
- | " | ||
- | }, | ||
- | " | ||
- | { | ||
- | " | ||
- | " | ||
- | " | ||
- | [ { | ||
- | " | ||
- | " | ||
- | " | ||
- | " | ||
- | " | ||
- | } ] | ||
- | } | ||
- | ], | ||
- | " | ||
- | " | ||
- | " | ||
- | " | ||
- | " | ||
- | } | ||
- | } | ||
- | </ | ||
- | |||
- | |||
- | |||
- | |||
- | ===== Experimental stuff ===== | ||
- | |||
- | Just some additional experiments i did, for future references. | ||
- | |||
- | === Nephele-Serve === | ||
- | Replacing WebDAV with Nephele-Serve (which will support also CardDAV/ | ||
- | |||
- | https:// | ||
- | https:// | ||
- | |||
- | NPM needs to be enabled for the fileserver user: | ||
- | < | ||
- | NPM_PACKAGES=" | ||
- | mkdir -p " | ||
- | echo " | ||
- | </ | ||
- | |||
- | And in **~/ | ||
- | |||
- | < | ||
- | # NPM packages in homedir | ||
- | NPM_PACKAGES=" | ||
- | # Tell our environment about user-installed node tools | ||
- | PATH=" | ||
- | # Unset manpath so we can inherit from / | ||
- | unset MANPATH # delete if you already modified MANPATH elsewhere in your configuration | ||
- | MANPATH=" | ||
- | # Tell Node about these packages | ||
- | NODE_PATH=" | ||
- | </ | ||
- | |||
- | Install: | ||
- | <code bash> | ||
- | source ~/ | ||
- | npm install -g nephele-serve | ||
- | </ | ||
- | |||
- | Advantages: it's a simple server that supports pam_auth. In the future, it might **also** replace [[services: | ||
- | |||
- | Disadvantages: | ||
- | |||
- | === sFtpGO WebDAV / web browser === | ||
- | |||
- | Interesting [[https:// | ||
- | |||
- | You need to start it once then edit **sftpgo.json**: | ||
- | < | ||
- | " | ||
- | " | ||
- | " | ||
- | { | ||
- | " | ||
- | " | ||
- | " | ||
- | " | ||
- | " | ||
- | " | ||
- | " | ||
- | " | ||
- | " | ||
- | " | ||
- | " | ||
- | " | ||
- | " | ||
- | } | ||
- | ], | ||
- | </ | ||
- | Advnatages: easier than Apache to setup, support base_url | ||
- | |||
- | Disadvantages: | ||