# Updating Globus-ILIAS-Rest in production This document describes how to deploy a new version of **Globus-ILIAS-Rest** to the production installation (`https://www.lernen-mit-globus-baumarkt.de`). > Production host in this setup is `hati` (the ILIAS host of > `www.lernen-mit-globus-baumarkt.de`). > Test/dev deployments use the same steps with a different `NODE_ENV` > (`test` → `globusfm-dev2`, `dev`/`dev2` → local). ## Overview of what has to be updated Production consists of **three parts** that may change independently: | Part | Location | Updated with | |----------------------|----------------------------------------------|--------------------------------| | Node.js REST service | the project dir on the server, run via `pm2` | code + `npm install` + restart | | Frontend (Vue SPA) | `vue/dist` (built, **not** in git) | `npm run build` | | PHP component | `$ILIASBASEDIR/globus-ilias-rest` | `copyPhpHati` | A full update therefore touches all three; a code-only change may only need the first two. ## Prerequisites - Node.js **v22.x** installed on the server (`node -v`). - `pm2` installed and the service already registered as `globus-ilias-rest`. - `NODE_ENV=prod` is set for the service (e.g. in `~/.bashrc` or in the pm2 environment). **It must be set before starting the app.** - `settings.prod.json` exists and is correct (DB credentials, ports, tokens). - The PHP component is already installed under the ILIAS base dir. ## Before you start 1. **Announce a short maintenance window** — restarting the service briefly interrupts the POPCORN sync and the `/popcorn` SPA. 2. **Back up the current state** (so you can roll back): - note the current git revision (`git rev-parse HEAD`) or tag - the settings are in git, but keep a copy of the server's `settings.prod.json` if it was modified on the server ## Update steps Run the following on the production host, inside the project directory. ### 1. Get the new code Always update via git: git fetch --all git checkout # e.g. v0.4.0 or master git pull > Always deploy via git. Only files tracked in git are deployed; untracked or > locally modified files must not reach production. Make sure the working copy > is clean (`git status`) and on the intended revision before proceeding. ### 2. Install dependencies npm install (Use `npm ci` if you want a clean, lockfile-exact install.) ### 3. Build the frontend The production build must use the production env values (`vue/.env.production`). `vite.config.js` selects that file when `VITE_ENV=production` is set: VITE_ENV=production npm run build This writes the SPA to `vue/dist/`, which `app.js` serves under `/popcorn/ui`. > Do **not** rely on `cp vue/.env.$NODE_ENV vue/.env` for production: with > `NODE_ENV=prod` there is no `vue/.env.prod` file. Use `VITE_ENV=production`. ### 4. Update the PHP component (only if `php/` changed) ./copyPhpHati `copyPhpHati` copies `php/globus-ilias-rest/*` and its `.htaccess` into `$ILIASBASEDIR/globus-ilias-rest` (`/var/local/ilias/globusfach/ilias/...` on `hati`). > **Check the target path first.** Open `copyPhpHati` and verify that `P` > (`/var/local/ilias/globusfach/ilias/globus-ilias-rest`) still matches the > actual ILIAS base dir on the server. The path can change between ILIAS > installations/upgrades — if it does, fix it in the script before running it. > The `token` file protects the PHP endpoint and is covered by `.htaccess` > (`Require all denied`). After copying, make sure the file is still present > and the owner/permissions are correct (`chown -R www-data:www-data`). > Note: the repo currently has **no** `copyPhp` script, although `package.json` > defines `"php": "bash copyPhp"`. On `hati` use `copyPhpHati` directly. The > final line of `copyPhpHati` > (`sudo cp $P/api.php $P/login.php`) refers to the old `api.php` name and will > fail / is a no-op now that the file is called `login.php`; the preceding > `cp` already installs `login.php`. ### 5. Restart the service pm2 restart globus-ilias-rest pm2 save Check that it is online: pm2 ls ### 6. Run the self test NODE_ENV=prod npm run test-connect All tests must succeed. (The tests for "the rest service" require the service to be running — see step 5.) ## Verify the deployment Quick manual checks against production: # service version curl https://www.lernen-mit-globus-baumarkt.de/popcorn/api/version > The `/api/version` endpoint must return the version from `package.json` > (e.g. `{"version":"0.4.0"}`). If it differs, the deployed code is not the > revision you expected — check the update/restart steps above before > continuing. # authenticated API curl "https://www.lernen-mit-globus-baumarkt.de/popcorn/api/user?token=$TOKEN" # PHP component curl "https://www.lernen-mit-globus-baumarkt.de/globus-ilias-rest/login.php?token=$ILIASTOKEN&command=ping" # frontend (SPA) curl -I https://www.lernen-mit-globus-baumarkt.de/popcorn/ui/ Then load the SPA in the browser and verify the user search / course pages work. ## Rollback If something is wrong: 1. Restore the previous revision: - `git checkout ` 2. `npm install` 3. `VITE_ENV=production npm run build` 4. `./copyPhpHati` (if the PHP component changed) 5. `pm2 restart globus-ilias-rest` 6. Re-run `NODE_ENV=prod npm run test-connect` ## Notes / gotchas - **Node version:** production requires Node v22.x. Do not install Node from an OS package manager (usually too old). - **`NODE_ENV`** must be `prod` for the service, otherwise the wrong `settings.*.json` is loaded. - **Tokens:** two different tokens are used — the REST `authtoken` (`settings.prod.json`) and the PHP `iliastoken` (also stored in `php/globus-ilias-rest/token`). If one changes, update both. - **HTTPS only:** the service must be reached via https, otherwise the auth token can be read. - **Frontend is not in git** (`vue/dist` and `node_modules` are ignored) — it must be built on the server (or explicitly synced). - **`npm run php`** is currently broken (no `copyPhp` script); use `copyPhpHati` for production. ## Logs - Application log: `$INSTALLDIR/log.log` — should be included in a logrotation job. - Log level is configured via `settings.prod.json` → `log.level` (default `info`); the `LOG_LEVEL` env var overrides it (`debug`, `info`, `warn`, `error`, `silent`/`off`). - pm2 logs: pm2 logs globus-ilias-rest pm2 flush # clear pm2 logs pm2 logging can be turned off with `--disable-logs` (not advised).