Script: Shlink
Reported by: @Corgei
Guidelines
- Read and understood guidelines: yes
- Verbose mode used: yes
Issue occurs during: Script Update
Environment
- Linux distribution: Debian
- Proxmox version: 9.1
- Default settings: No
- Advanced settings: Yes
- Exact command:
bash -c "$(curl -fsSL https://raw.githubusercontent.com/community-scripts/ProxmoxVE/main/ct/shlink.sh)"
Description
After running the built-in update command inside a Shlink LXC (installed via this repo's ct/shlink.sh / install/shlink-install.sh), the Shlink Web Client loses its configured server and shows the "Welcome! Add a server" screen, even though the Shlink API backend continues to work fine.
Root cause (confirmed by reading install/shlink-install.sh and ct/shlink.sh):
- On initial install,
install/shlink-install.sh creates /opt/shlink-web-client/servers.json with the initial API key so the Web Client works out of the box.
- On update,
update_script() in ct/shlink.sh does:
- For /opt/shlink (API): backs up
.env and data/, does CLEAN_INSTALL=1 fetch_and_deploy_gh_release ..., then restores the backup. This correctly preserves configuration.
- For /opt/shlink-web-client (Web Client): does
CLEAN_INSTALL=1 fetch_and_deploy_gh_release ... with NO backup/restore step for servers.json.
- Because
CLEAN_INSTALL=1 wipes the target directory before redeploying, servers.json (and any other user customization under /opt/shlink-web-client, e.g. a custom nginx config placed there) is permanently deleted on every update. The Web Client then has no server configured and shows the onboarding screen, which looks like a "connection lost" / outage to the end user, even though nothing about the API, database, or network changed.
This is inconsistent with how /opt/shlink itself is handled (backup + restore around the clean install) and is easy to reproduce on every update.
Steps to reproduce
- Install Shlink via this repo's script, opting in to "Install Shlink Web Client?" during setup.
- Confirm the Web Client works and has a server configured (/opt/shlink-web-client/servers.json exists and is populated).
- Run
update from the container console (or re-run the ct script with the update path).
- After the update finishes, open the Web Client in a browser.
Error output
No error/exception is thrown by the update script itself; it reports success. The symptom is only visible in the browser: the Web Client shows the onboarding screen ("Welcome! This application will help you manage your Shlink servers." / "+ Add a server") instead of the previously configured server, because /opt/shlink-web-client/servers.json no longer exists.
Verification performed on an affected container:
$ ls -la /opt/shlink-web-client/servers.json
ls: cannot access '/opt/shlink-web-client/servers.json': No such file or directory
$ curl -s http://127.0.0.1:3000/servers.json
(404 / empty — served via try_files /servers.json /conf.d/servers.json;, neither path exists after the update)
Meanwhile the API itself remains healthy:
$ curl -s -o /dev/null -w '%{http_code}\n' http://127.0.0.1:8080/rest/health
200
Additional context
Suggested fix, mirroring what is already done for /opt/shlink:
In ct/shlink.sh update_script(), before the CLEAN_INSTALL for shlink-web-client, back up /opt/shlink-web-client/servers.json (if it exists) to a temp location, and restore it after fetch_and_deploy_gh_release completes — the same backup/restore pattern already used for /opt/shlink/.env and /opt/shlink/data. For example:
if [[ -f /opt/shlink-web-client/servers.json ]]; then
cp /opt/shlink-web-client/servers.json /opt/shlink-web-client-servers.json.bak
fi
CLEAN_INSTALL=1 fetch_and_deploy_gh_release "shlink-web-client"
"shlinkio/shlink-web-client" "prebuild" "latest" "/opt/shlink-web-client"
"shlink-web-client_*_dist.zip"
if [[ -f /opt/shlink-web-client-servers.json.bak ]]; then
mv /opt/shlink-web-client-servers.json.bak /opt/shlink-web-client/servers.json
fi
As a workaround, I'm currently keeping a persistent copy of servers.json outside /opt/shlink-web-client and using a systemd path unit to restore it automatically whenever the directory changes, but this should ideally be fixed in the upstream update script so every user doesn't need to do this themselves.
Script: Shlink
Reported by: @Corgei
Guidelines
Issue occurs during: Script Update
Environment
bash -c "$(curl -fsSL https://raw.githubusercontent.com/community-scripts/ProxmoxVE/main/ct/shlink.sh)"Description
After running the built-in
updatecommand inside a Shlink LXC (installed via this repo'sct/shlink.sh/install/shlink-install.sh), the Shlink Web Client loses its configured server and shows the "Welcome! Add a server" screen, even though the Shlink API backend continues to work fine.Root cause (confirmed by reading install/shlink-install.sh and ct/shlink.sh):
install/shlink-install.shcreates/opt/shlink-web-client/servers.jsonwith the initial API key so the Web Client works out of the box.update_script()inct/shlink.shdoes:.envanddata/, doesCLEAN_INSTALL=1 fetch_and_deploy_gh_release ..., then restores the backup. This correctly preserves configuration.CLEAN_INSTALL=1 fetch_and_deploy_gh_release ...with NO backup/restore step forservers.json.CLEAN_INSTALL=1wipes the target directory before redeploying,servers.json(and any other user customization under /opt/shlink-web-client, e.g. a custom nginx config placed there) is permanently deleted on every update. The Web Client then has no server configured and shows the onboarding screen, which looks like a "connection lost" / outage to the end user, even though nothing about the API, database, or network changed.This is inconsistent with how /opt/shlink itself is handled (backup + restore around the clean install) and is easy to reproduce on every update.
Steps to reproduce
updatefrom the container console (or re-run the ct script with the update path).Error output
No error/exception is thrown by the update script itself; it reports success. The symptom is only visible in the browser: the Web Client shows the onboarding screen ("Welcome! This application will help you manage your Shlink servers." / "+ Add a server") instead of the previously configured server, because /opt/shlink-web-client/servers.json no longer exists.
Verification performed on an affected container:
$ ls -la /opt/shlink-web-client/servers.json
ls: cannot access '/opt/shlink-web-client/servers.json': No such file or directory
$ curl -s http://127.0.0.1:3000/servers.json
(404 / empty — served via
try_files /servers.json /conf.d/servers.json;, neither path exists after the update)Meanwhile the API itself remains healthy:
$ curl -s -o /dev/null -w '%{http_code}\n' http://127.0.0.1:8080/rest/health
200
Additional context
Suggested fix, mirroring what is already done for /opt/shlink:
In ct/shlink.sh
update_script(), before the CLEAN_INSTALL for shlink-web-client, back up /opt/shlink-web-client/servers.json (if it exists) to a temp location, and restore it afterfetch_and_deploy_gh_releasecompletes — the same backup/restore pattern already used for /opt/shlink/.env and /opt/shlink/data. For example:if [[ -f /opt/shlink-web-client/servers.json ]]; then
cp /opt/shlink-web-client/servers.json /opt/shlink-web-client-servers.json.bak
fi
CLEAN_INSTALL=1 fetch_and_deploy_gh_release "shlink-web-client"
"shlinkio/shlink-web-client" "prebuild" "latest" "/opt/shlink-web-client"
"shlink-web-client_*_dist.zip"
if [[ -f /opt/shlink-web-client-servers.json.bak ]]; then
mv /opt/shlink-web-client-servers.json.bak /opt/shlink-web-client/servers.json
fi
As a workaround, I'm currently keeping a persistent copy of servers.json outside /opt/shlink-web-client and using a systemd path unit to restore it automatically whenever the directory changes, but this should ideally be fixed in the upstream update script so every user doesn't need to do this themselves.