CVE-2026-48017 - DbGate loadReader functionName RCE

DbGate dbgate-api versions through 7.1.8 let an authenticated user call the server-side POST /runners/load-reader route with a crafted functionName value. The route built JavaScript from that value and started the generated script without applying the same shell-script permission checks used by the explicit script runner.

For a database administration tool, that is more than a package bump. A basic authenticated DbGate account may be able to reach the DbGate process authority, host files available to that process, and stored database connection material. The safe remediation upgrades the package, removes raw function-name code generation, proves load-reader calls are permissioned, and documents credential review when untrusted users had access.

GitHub later reviewed CVE-2026-47670 / GHSA-wm5r-5qp3-5vxf for the same loadReader boundary with a critical dynamic-import() bypass variant. If both alerts appear in a scanner, treat them as one remediation surface: upgrade to 7.1.9+, remove request-controlled JavaScript generation, and verify the fix closes both CVE IDs.

When to use it

Use this recipe when a repository deploys, packages, forks, wraps, or configures DbGate and may expose /runners/load-reader or shell API reader selection. It is especially useful when authenticated users, support users, demo users, contractors, tenants, automation, or agents can influence functionName, loader names, package-qualified API names, or custom plugin routes.

Use it to remediate the loadReader boundary shared with CVE-2026-47670. Do not use it to run function-name probes, process-spawn checks, or shell commands.

Inputs

  • Package manifests, lockfiles, workspaces, Dockerfiles, Compose/Helm/Kubernetes manifests, Terraform/Ansible/PaaS config, reverse-proxy routes, CI images, SBOMs, generated dependency reports, runbooks, forks, plugins, and wrappers that reference DbGate.
  • Resolved dbgate-api, dbgate, and dbgate-web versions across deployable server-side runtimes.
  • loadReader and shell API code paths: POST /runners/load-reader, loadReader, functionName, compileShellApiFunctionName, loaderScriptTemplate, route wrappers, proxy exceptions, and plugin aliases.
  • Authentication and authorization evidence showing which roles can reach loadReader execution and whether shell/script execution policy applies.
  • Runtime authority for DbGate: saved connection profiles, database passwords, SQL history, mounted files, source checkout material, cloud credentials, internal network access, and secret-rotation ownership.

Affected versions

  • Vulnerable package: dbgate-api <=7.1.8
  • Fixed package: dbgate-api 7.1.9+
  • Affected route: POST /runners/load-reader
  • Affected parameter: functionName
  • Affected source paths: DbGate runner controller and shell API function-name compilation logic

Indicator-of-exposure

  • The repository depends on, vendors, forks, builds, or deploys DbGate or dbgate-api <=7.1.8.
  • A deployable DbGate server is reachable by users who are not fully trusted administrators.
  • The repository exposes DbGate through Docker, Compose, Helm, Kubernetes, systemd, PaaS config, reverse-proxy routes, or internal admin tooling.
  • The deployed DbGate process can read database connection profiles, host files, cloud credentials, source checkout credentials, container mounts, or internal network services.
  • Product code, forks, plugins, or wrappers accept shell API function names, loader names, package-qualified API names, or route bodies from users.

Quick checks:

rg -n "dbgate|dbgate-api|load-reader|loadReader|functionName|compileShellApiFunctionName|runners/load-reader|allowShellScripting|run-shell-script" .
npm ls dbgate-api dbgate dbgate-web
pnpm why dbgate-api dbgate dbgate-web
yarn why dbgate-api dbgate dbgate-web
rg -n "dbgate|dbgate-api|DBGATE|runners/load-reader" Dockerfile* docker-compose*.yml compose*.yml charts k8s deploy .github . 2>/dev/null

Windows:

rg -n "dbgate|dbgate-api|load-reader|loadReader|functionName|compileShellApiFunctionName|runners/load-reader|allowShellScripting|run-shell-script" .
npm ls dbgate-api dbgate dbgate-web
pnpm why dbgate-api dbgate dbgate-web
yarn why dbgate-api dbgate dbgate-web
rg -n "dbgate|dbgate-api|DBGATE|runners/load-reader" Dockerfile* docker-compose*.yml compose*.yml charts k8s deploy .github .

Do not run crafted functionName values, process-spawn probes, or shell commands through DbGate during triage.

Remediation strategy

  • Upgrade every controlled dbgate-api, DbGate package, image, lockfile, SBOM, and deployment artifact to 7.1.9+.
  • If this repository owns a DbGate fork, wrapper, or plugin boundary, replace raw function-name interpolation with a finite registry of approved reader functions. Reject malformed package-qualified names before script generation.
  • Require the same kind of permission and platform checks for load-reader execution that apply to explicit shell/script execution.
  • Add route, authorization, and policy tests that verify untrusted users cannot select arbitrary shell API functions or reach generated-code execution.
  • Reduce DbGate runtime authority: least-privilege OS user, narrow mounts, restricted egress, secret-manager-backed database credentials, and no cloud metadata access unless required.
  • Rotate database credentials, DbGate tokens, and any host or integration secrets reachable by the DbGate process if broad authenticated users could access the vulnerable route.

The prompt

You are remediating CVE-2026-48017 / GHSA-hv83-ggc4-v385, a DbGate
`/runners/load-reader` server-side JavaScript code-injection issue caused by
unvalidated `functionName` input. Produce exactly one output:

- A reviewer-ready PR/change request that upgrades DbGate, removes unsafe
  function-name code generation or gates it behind strict validation and
  permissions, adds safe regression coverage, refreshes generated artifacts,
  and documents operator cleanup, or
- TRIAGE.md if this repository does not control an affected DbGate runtime,
  package, fork, plugin, image, or deployment.

## Rules

- Scope only CVE-2026-48017 / GHSA-hv83-ggc4-v385 and directly related DbGate
  load-reader hardening.
- Treat DbGate sessions, bearer tokens, database connection strings, saved
  connection profiles, query history, SQL results, environment variables, cloud
  credentials, mounted files, and host logs as sensitive.
- Do not send exploit payloads, crafted code snippets, process-spawn probes, or
  shell commands through `/runners/load-reader` or any DbGate runner endpoint.
- Do not print secrets, database rows, query history, decoded tokens, or
  connection profile material into logs, reports, snapshots, or commits.
- Do not rely on string deny-lists, UI-only validation, or `require=null` style
  sandboxing as the sole security control.
- Do not auto-merge.

## Steps

1. Inventory every DbGate reference controlled by this repository:
   `package.json`, lockfiles, workspaces, Dockerfiles, Compose files, Helm
   charts, Kubernetes manifests, Terraform, Ansible, reverse-proxy routes,
   PaaS config, CI images, SBOMs, generated dependency reports, runbooks,
   forks, plugins, and local wrappers.
2. Determine every resolved `dbgate-api`, `dbgate`, and `dbgate-web` version.
   A target is vulnerable if the server-side `dbgate-api` runtime resolves to
   `7.1.8` or earlier.
3. Search for load-reader and shell API function-name handling:
   `POST /runners/load-reader`, `loadReader`, `functionName`,
   `compileShellApiFunctionName`, `loaderScriptTemplate`, shell API plugin
   extraction, route wrappers, proxy bypasses, and custom DbGate plugins.
4. Classify who can authenticate to the affected DbGate runtime: fully trusted
   administrators, internal developers, tenant users, contractors, automation
   accounts, shared demo users, or internet-facing users.
5. If this repository only contains an unrelated client or documentation, stop
   with `TRIAGE.md` listing checked files, runtime owner, and required fixed
   version `dbgate-api 7.1.9+`.
6. Upgrade all controlled DbGate runtime packages and images to `7.1.9+`.
   Regenerate lockfiles, package-manager metadata, image digests, SBOMs,
   deployment render output, dependency reports, and docs that pin versions.
7. Where this repository owns product code, forks, wrappers, or plugins,
   replace raw `functionName` handling with fail-closed validation:
   - accept only known reader function identifiers from an approved registry;
   - parse package-qualified names into structured fields before use;
   - reject empty names, separators, punctuation, comments, whitespace,
     operators, parentheses, quotes, brackets, template markers, and control
     characters;
   - map approved names to functions without concatenating user input into
     generated JavaScript;
   - return non-secret validation errors.
8. Add permission and platform checks before load-reader execution:
   - require an explicit server-side permission for reader/script execution;
   - reject the route when shell scripting or generated runner execution is
     disabled by platform policy;
   - ensure non-admin or basic users cannot invoke arbitrary reader loaders;
   - fail closed when role, package identity, or function identity is unknown.
9. Add regression tests that do not execute attacker code:
   - vulnerable package versions are rejected by dependency policy;
   - malformed `functionName` values are rejected before script generation;
   - non-admin users cannot call or configure load-reader execution;
   - generated runner code is not built from raw request parameters;
   - validation and audit logs omit tokens, connection profiles, query text,
     environment variables, and database results.
10. Harden deployment where this repository controls runtime:
    - run DbGate as a least-privilege user;
    - mount only required paths and make them read-only where possible;
    - deny cloud metadata and unnecessary internal egress;
    - keep database credentials in a secret manager or deployment secret;
    - isolate DbGate from source checkout and deployment credentials.
11. Add a PR body section named `CVE-2026-48017 operator actions` that states:
    - DbGate and `dbgate-api` versions before and after;
    - whether `/runners/load-reader` was reachable and by which roles;
    - whether custom forks, plugins, or wrappers handled `functionName`;
    - which database credentials, DbGate tokens, host files, and integration
      secrets may have been reachable before the patch;
    - whether credential rotation, session invalidation, log review, or image
      rebuilds are required;
    - which validation commands passed and which unrelated failures remain.
12. Run available validation: package install, lockfile integrity, unit/API
    tests, authz tests, route tests, lint/typecheck, container build,
    deployment rendering, SBOM refresh, and dependency/security scans.
13. Use PR title:
    `fix(sec): remediate CVE-2026-48017 in DbGate`.

## Stop conditions

- No affected DbGate runtime, package, image, fork, plugin, or deployment is
  controlled by this repository.
- The DbGate runtime is supplied by another team or vendor; name the owner and
  required version in `TRIAGE.md`.
- A fixed DbGate version cannot be consumed without a broader migration.
- Product requirements intentionally allow non-admin users to trigger arbitrary
  DbGate runner functions; document the required product/security decision.
- Verification would require executing exploit payloads, process-spawn probes,
  live database queries, or secret-bearing runtime inspection.
- Validation fails for unrelated pre-existing reasons; document those failures
  instead of broadening scope.

Verification - what the reviewer looks for

  • No controlled lockfile, image, SBOM, package manifest, or deployment target resolves server-side dbgate-api to 7.1.8 or earlier.
  • loadReader and /runners/load-reader cannot build generated code from raw request-controlled functionName values.
  • Any remaining reader selection path uses a finite approved registry and server-side permission checks.
  • Non-admin or basic users cannot reach arbitrary runner execution.
  • Tests prove rejection without running shell commands or exploit-like payloads.
  • Operator notes cover database credential rotation, DbGate session invalidation, log review, and runtime hardening when untrusted authenticated users had access.

Watch for

  • Updating an npm manifest while Docker images, global installs, Helm charts, or SBOMs still resolve an old DbGate runtime.
  • Treating “authenticated” as trusted in shared admin portals, demos, internal tools, or customer-support environments.
  • Blocking the UI while leaving API, proxy, import, or plugin routes able to pass functionName through.
  • Validation that checks only one name format while package-qualified names or plugin aliases take a different path.
  • Logs that capture bearer tokens, database credentials, SQL text, query results, or generated runner scripts.

Output contract

Return one of:

  • A reviewer-ready PR/change request that upgrades DbGate runtime packages to 7.1.9+, replaces raw functionName handling with a finite approved registry, applies server-side permission checks to loadReader execution, refreshes generated artifacts, hardens runtime deployment, and documents operator cleanup.
  • TRIAGE.md when no controlled affected DbGate runtime, package, image, fork, plugin, wrapper, or deployment exists.

The output must list versions before/after, loadReader reachability by role, custom forks/plugins/wrappers in scope, whether CVE-2026-47670 is closed by the same patch, validation commands, artifacts refreshed, and required session, credential, log-review, or image-rebuild actions. It must not include crafted payloads, generated runner code, tokens, database rows, query history, connection profiles, or environment values.

References