mirror of
https://github.com/projectsend/projectsend.git
synced 2026-09-11 22:38:54 +00:00
d6fd5a917d
Uploads live outside the web root, so PHP authorizes every download and then hands the file to the web server with a header naming it. Four routes decided that for themselves and all four hard-coded nginx's spelling. On Apache or LiteSpeed nothing acts on the header, so the empty body PHP sent goes to the visitor: files upload fine, thumbnails are broken images, and downloads arrive as 0 bytes, with every other page working. Reported as #1765 from an Apache 2.4 install, and before that as #1266, #1215, #870 and #1271. It is also a regression from v1, which had a download_method setting -- php, apache_xsendfile, litespeed, nginx_xaccel -- defaulting to php. v1 therefore worked on any server out of the box and v2 did not, and a v1 Apache user migrating lost every download with nothing to tell them why. So the four sites now go through one FileDelivery, and it picks: auto (default) nginx when SERVER_SOFTWARE says nginx, else php nginx X-Accel-Redirect, a URL path via the internal location xsendfile X-Sendfile, an absolute path (Apache mod_xsendfile, LiteSpeed) php BinaryFileResponse Defaulting to auto rather than nginx is the point of the change: a default that assumes nginx leaves an Apache install exactly as broken as it is today until somebody reads INSTALL.md. Slow beats empty. Auto never picks xsendfile, even where the module is loaded. mod_xsendfile also needs XSendFilePath to allow the storage directory, which cannot be seen from here, and choosing it on the strength of the module being present would trade a silent failure an administrator can diagnose from the dashboard for one nobody can. BinaryFileResponse rather than a readfile loop because it answers Range requests. nginx does that itself on the fast path, so hand-rolling it would have broken seeking through a video on exactly the installations this fallback exists for. Verified end to end: 206 with the right Content-Range through the live stack. Two guards. Every method checks the path cannot climb out of the storage area -- nginx resolves `..` in the URL it is handed as happily as PHP would -- and the two methods that hand over a filesystem path resolve it and prove it lands inside the root. Callers pass paths from rows they just authorized, so this is a backstop; it is here because the cost of being wrong once is handing over any file the web server can read. The dashboard's System panel names the method, with a warning icon and a dialog when PHP is doing the sending: what is happening, what it costs (one worker held for the whole of each download, so a few large simultaneous ones can occupy every worker while the processor sits idle), why it is set that way, and the three ways out. Written to be accurate rather than reassuring -- nothing is broken, it does not scale -- and the notice stays even when php was chosen deliberately, because the trade-off is the same either way. /system/settings/downloads repeats it, which is where somebody coming from v1 goes looking for the dropdown. An environment variable rather than a stored setting: it describes the server this installation runs on, not a preference, and a value in the database travels to a different server in a restore and is wrong there. Read only in config/projectsend.php, so config:cache cannot blank it. The suite pins itself to nginx. Left at auto it would detect no server at all, fall back to php, and quietly retire the coverage of the mechanism most installations actually use.
109 lines
3.1 KiB
Bash
109 lines
3.1 KiB
Bash
APP_NAME=ProjectSend
|
|
PROJECTSEND_EDITION=community
|
|
|
|
# Emergency off switch for the CAPTCHA on public forms, for an operator who
|
|
# has a shell but no working login. Everything else about the feature is
|
|
# configured at /system/settings/captcha.
|
|
# PROJECTSEND_CAPTCHA_DISABLED=true
|
|
|
|
# How downloads leave the server. Left unset (or "auto"), ProjectSend hands
|
|
# files to nginx when it is running behind nginx, and streams them through
|
|
# PHP on anything else -- which works everywhere but holds a PHP worker for
|
|
# the whole of each download. Set "xsendfile" for Apache with mod_xsendfile
|
|
# (or LiteSpeed) once XSendFilePath allows storage/app/files, "nginx" when
|
|
# an nginx proxy in front is the one serving /protected-files/, or "php" to
|
|
# stream deliberately. The dashboard's System panel shows which is in use.
|
|
# PROJECTSEND_FILE_DELIVERY=auto
|
|
|
|
# Optional: uid/gid the app/web containers' internal user runs as, so the
|
|
# bind-mounted repo needs no permission fixes. Defaults to 1000; override
|
|
# if your host user's `id -u`/`id -g` differ.
|
|
# WWWUSER=1000
|
|
# WWWGROUP=1000
|
|
|
|
# Optional: create the first administrator unattended on container start.
|
|
# Leave unset to use the first-run setup screen instead.
|
|
# ADMIN_NAME="Administrator"
|
|
# ADMIN_EMAIL=admin@example.com
|
|
# ADMIN_PASSWORD=
|
|
APP_ENV=local
|
|
APP_KEY=
|
|
APP_DEBUG=true
|
|
APP_TIMEZONE=UTC
|
|
APP_URL=http://localhost
|
|
|
|
# Required whenever a proxy/load balancer sits in front of this app (an
|
|
# ALB, Cloudflare, a hosted ingress) — otherwise every request looks like
|
|
# it comes from the proxy, collapsing per-IP rate limits and the download
|
|
# IP log. Comma-separated addresses/CIDRs, or "*" to trust any proxy
|
|
# (only safe when nothing but the proxy can reach the app).
|
|
# TRUSTED_PROXIES=
|
|
|
|
APP_LOCALE=en
|
|
APP_FALLBACK_LOCALE=en
|
|
APP_FAKER_LOCALE=en_US
|
|
|
|
APP_MAINTENANCE_DRIVER=file
|
|
# APP_MAINTENANCE_STORE=database
|
|
|
|
PHP_CLI_SERVER_WORKERS=4
|
|
|
|
BCRYPT_ROUNDS=12
|
|
|
|
LOG_CHANNEL=stack
|
|
LOG_STACK=single
|
|
LOG_DEPRECATIONS_CHANNEL=null
|
|
LOG_LEVEL=debug
|
|
|
|
DB_CONNECTION=mysql
|
|
DB_HOST=db
|
|
DB_PORT=3306
|
|
DB_DATABASE=projectsend
|
|
DB_USERNAME=projectsend
|
|
DB_PASSWORD=secret
|
|
|
|
SESSION_DRIVER=redis
|
|
SESSION_LIFETIME=120
|
|
SESSION_ENCRYPT=false
|
|
SESSION_PATH=/
|
|
SESSION_DOMAIN=null
|
|
|
|
BROADCAST_CONNECTION=log
|
|
FILESYSTEM_DISK=local
|
|
|
|
# Set this only if your web server and PHP-FPM run as different system
|
|
# users — common on cPanel/Plesk shared hosting. Uploaded files are
|
|
# written 0600 in 0700 directories, which nginx cannot read, and since
|
|
# nginx is what actually streams a download (PHP authorizes, then hands
|
|
# it the path) every download fails while the rest of the site works.
|
|
# Relaxes those to 0644/0755, which every account on the machine can
|
|
# read — leave it off if your web server and PHP are the same user.
|
|
# FILES_WEB_SERVER_READABLE=true
|
|
QUEUE_CONNECTION=redis
|
|
|
|
CACHE_STORE=redis
|
|
CACHE_PREFIX=
|
|
|
|
MEMCACHED_HOST=127.0.0.1
|
|
|
|
REDIS_CLIENT=phpredis
|
|
REDIS_HOST=redis
|
|
REDIS_PASSWORD=null
|
|
REDIS_PORT=6379
|
|
|
|
MAIL_MAILER=smtp
|
|
MAIL_HOST=mailpit
|
|
MAIL_PORT=1025
|
|
MAIL_USERNAME=null
|
|
MAIL_PASSWORD=null
|
|
MAIL_ENCRYPTION=null
|
|
MAIL_FROM_ADDRESS="hello@example.com"
|
|
MAIL_FROM_NAME="${APP_NAME}"
|
|
|
|
AWS_ACCESS_KEY_ID=
|
|
AWS_SECRET_ACCESS_KEY=
|
|
AWS_DEFAULT_REGION=us-east-1
|
|
AWS_BUCKET=
|
|
AWS_USE_PATH_STYLE_ENDPOINT=false
|
|
|