Fix imported file ownership in the generated PikaPods migration script

The generated migrate-from-pikapods.sh (services/mattermost.sh's existing
"Migrating from an existing Mattermost instance?" prompt on fresh installs)
already correctly parameterizes PROJECT_DIR/MM_CONTAINER/DB_CONTAINER per
instance — no bug there. What it missed: after rsync/cp-ing files in from
the export, it never touched ownership, so the imported ./data landed
owned by whoever ran the script instead of the fixed UID 2000
mattermost/mattermost-team-edition runs as. Every file write then failed
with permission denied — confirmed live as the actual cause of a
client-side "stream closed" error on image/file uploads after a real
migration.

Adds chown -R 2000:2000 ./data right after the copy step, and a root
check up front since chowning to an arbitrary UID needs it (docker/psql
access already implied running as root in practice, just never enforced
explicitly). Usage lines updated to say `sudo` to match.

Verified by reconstructing the exact generated script from the real
source heredocs (head + variable substitution + body, the same three
pieces the actual cat/cat>> sequence produces) and syntax-checking the
result — root check and chown both land in the right place, and
PROJECT_DIR/MM_CONTAINER/DB_CONTAINER still resolve correctly per instance.
This commit is contained in:
Claude
2026-08-15 02:58:59 +00:00
parent 767479d113
commit a7d3dc5b5d
+15 -2
View File
@@ -788,7 +788,7 @@ MD
# before running.
#
# Usage:
# ./migrate-from-pikapods.sh <path-to-sql-dump> <path-to-files-dir>
# sudo ./migrate-from-pikapods.sh <path-to-sql-dump> <path-to-files-dir>
################################################################################
MIGRATE_HEAD
@@ -803,13 +803,18 @@ MIGRATE_VARS
cat >> "$DIR/migrate-from-pikapods.sh" << 'MIGRATE_BODY'
set -uo pipefail
# Needed for the chown to UID 2000 near the end (an ordinary user generally
# can't chown files to an arbitrary UID that isn't their own).
[ "${EUID:-$(id -u)}" -eq 0 ] || { echo "Run as root: sudo $0 ..."; exit 1; }
cd "$PROJECT_DIR" || exit 1
SQL_DUMP="${1:-}"
FILES_DIR="${2:-}"
if [ -z "$SQL_DUMP" ] || [ -z "$FILES_DIR" ]; then
echo "Usage: $0 <path-to-sql-dump> <path-to-files-dir>"
echo "Usage: sudo $0 <path-to-sql-dump> <path-to-files-dir>"
exit 1
fi
[ -f "$SQL_DUMP" ] || { echo "SQL dump not found: $SQL_DUMP"; exit 1; }
@@ -856,6 +861,14 @@ echo "Copying files into ./data..."
mkdir -p ./data
rsync -a "$FILES_DIR"/ ./data/ 2>/dev/null || cp -a "$FILES_DIR"/. ./data/
# mattermost/mattermost-team-edition runs as fixed UID/GID 2000 — an SFTP'd
# copy from elsewhere lands owned by whoever ran this script instead, and
# every file write then fails with "permission denied" until this is
# fixed. Confirmed live: this is what broke image/file uploads with a
# client-side "stream closed" error after a migration.
echo "Fixing ownership on imported files (mattermost image expects UID/GID 2000)..."
chown -R 2000:2000 ./data
echo "Starting Mattermost..."
docker compose up -d