FrankandClaude Sonnet 5 bc0433e356 Fix puzzle-relay exiting immediately on Linux: force start command
Worker::runAll() parses start/stop/restart/... off the real \$argv on
Linux - which here is Symfony console's own arguments (bin/console
app:puzzle-relay), not a command it recognizes, so it printed its
usage text and exited on every boot, and Docker kept restarting it
forever. Windows skips that argv parsing entirely, which is why this
never showed up locally. Worker::\$command = 'start' is Workerman's
own mechanism for exactly this "used as a library" case - it appends
to what getArgv() returns without touching the real \$argv.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
2026-09-12 13:57:00 +02:00
2026-09-08 18:51:53 +02:00

dmtools

DM tools for the Monday-evening D&D campaign.

Symfony 8 (PHP 8.5) web app with a Bootstrap 5 + DataTables front end served through Symfony AssetMapper (no Node build step). Behind a form-login gate; there is no self-registration.

  • Not run in Docker locally (Windows dev box uses the Symfony CLI + local MariaDB).
  • Is Dockerized on the testing and live servers, behind the shared Nginx Proxy Manager at https://dmtools.fvandenberg.nl.

Repo: https://gitea.fvandenberg.nl/Frank/dmtools.git


Local development (dev box)

Prerequisites: PHP 8.5 at C:\php (on PATH so the Symfony CLI discovers it — symfony local:php:list should show 8.5), the Symfony CLI, Composer, and a local MariaDB/MySQL (WAMP is fine). .php-version pins this directory to PHP 8.5.

# 1. Point the app at your local database + dev mode
cp .env .env.local
#    then edit .env.local:
#      APP_ENV=dev
#      DATABASE_URL="mysql://root:@127.0.0.1:3307/dmtools?serverVersion=10.10.2-MariaDB&charset=utf8mb4"

# 2. Install and build
symfony composer install
symfony console doctrine:database:create
symfony console doctrine:migrations:migrate -n
symfony console importmap:install

# 3. First user, then run
symfony console app:user:create you@example.com --admin
symfony serve -d
symfony open:local

serverVersion must match your local engine (SELECT VERSION();).

Servers (testing + live)

Docker only. docker/setup.sh pins the compose project name to dmtools (containers dmtools-php, dmtools-nginx, dmtools-db).

git pull
cp .env .env.local          # first time only
#   edit .env.local: real APP_SECRET (or let setup.sh generate it),
#   DB_PASSWORD, DB_ROOT_PASSWORD, and NGINX_PORT / DB_HOST_PORT if 8085 / 3310 clash
./docker/setup.sh
docker compose -p dmtools exec php php bin/console app:user:create you@example.com --admin

Ports (bound to 127.0.0.1 on the host): nginx 8085 → :80, db 3310 → :3306.

Reverse proxy (Nginx Proxy Manager)

Add a proxy host: dmtools.fvandenberg.nl → forward to host dmtools-nginx, port 80, scheme http; request a Let's Encrypt certificate.

NPM must be able to resolve dmtools-nginx, i.e. be on the dmtools_default network. setup.sh connects it (nginx_app_1 by default; override with NPM_CONTAINER=...); to do it by hand:

docker network connect dmtools_default nginx_app_1

NPM keeps that connection across restarts; it's only needed again after a docker compose down drops the network.

Common commands

docker compose -p dmtools logs -f php
docker compose -p dmtools exec php bash
docker compose -p dmtools exec php php bin/console doctrine:migrations:migrate
./docker/restart.sh            # full down + bring-up (no rebuild)
./docker/setup.sh --down       # stop the stack

Layout notes

  • table.datatable in any Twig template is auto-initialised as a DataTable (assets/app.js). Opt out with data-datatable="false"; pass options as JSON in data-datatable-options.
  • assets/vendor/ and public/assets/ are generated (git-ignored); importmap:install on the server re-downloads vendored packages, so the servers need outbound HTTPS to jsDelivr at deploy time.
S
Description
DM tools for the monday evening campaign
Readme
27 MiB
Languages
PHP 61.3%
Twig 26.4%
JavaScript 6.5%
CSS 4.2%
Shell 1.3%
Other 0.3%