`src/Schuly.API/Plugins/PluginHost.cs:278-284` (`PluginConnectionString`) builds each plugin's DB connection string by swapping only `Database=` on the same underlying Postgres credentials — there's one superuser role behind every plugin database (see also `compose.dev.yml`, a single `POSTGRES_PASSWORD`).
Exploit: a plugin opens its own `NpgsqlConnection` with `Database=schuly-dev` (or another plugin's DB name) using its already-injected credentials and reads/writes the entire host DB or any other plugin's tables.
Fix: create a dedicated least-privilege Postgres role per plugin, granted only on its own database.
Found during the Aug 2026 security sweep.
`src/Schuly.API/Plugins/PluginHost.cs:278-284` (`PluginConnectionString`) builds each plugin's DB connection string by swapping only `Database=` on the same underlying Postgres credentials — there's one superuser role behind every plugin database (see also `compose.dev.yml`, a single `POSTGRES_PASSWORD`).
Exploit: a plugin opens its own `NpgsqlConnection` with `Database=schuly-dev` (or another plugin's DB name) using its already-injected credentials and reads/writes the entire host DB or any other plugin's tables.
Fix: create a dedicated least-privilege Postgres role per plugin, granted only on its own database.
Found during the Aug 2026 security sweep.