Authenticated Remote Code Execution via loadReader functionName code injection in DbGate
Date: 2026-06
Affected: npm/dbgate-api
Attack vector: command-injection
Category: vulnerability-disclosure
Severity: Critical
CVE: CVE-2026-47668
CVE-2026-47670
CWE: CWE-1188
CWE-20
CWE-77
CWE-78
CWE-94
CVSS:  (CVSS:3.1/AV:N/AC:L/PR:N/UI:N/S:C/C:H/I:H/A:H)

### Summary DbGate is vulnerable to authenticated Remote Code Execution (RCE). Any user with valid DbGate credentials can execute arbitrary OS commands as root by exploiting an unsanitized `functionName` parameter in the `/runners/load-reader` endpoint. The `require = null` mitigation is trivially bypassed via dynamic `import()`. <br/> ### Details **Code injection via `functionName` in loadReader** The `/runners/load-reader` endpoint interpolates the `functionName` parameter directly into a dynamically generated JavaScript script template without any sanitization: ```javascript // packages/api/src/controllers/runners.js (loadReader / loaderScriptTemplate) const reader = await dbgateApi.${functionName}({...}); ``` By injecting a newline character into `functionName`, an attacker breaks out of the template expression and injects arbitrary JavaScript code. The injected code uses `await import('child_process')` to bypass the `require = null` mitigation (since `import()` is a language keyword, not a function that can be nullified), achieving arbitrary command execution as the process user (root in Docker). The June 2025 security fix ([commit cf3f95c](https://github.com/dbgate/dbgate/commit/cf3f95c952)) added `require = null` to the generated script, but this is trivially bypassed: ```javascript // Mitigation in generated script: require = null; // Bypass via dynamic import (language keyword, cannot be nullified): const { execSync } = await import('child_process'); execS


Mitigations:

Architectural layers (MAESTRO):