Alle Anleitungen

DEVOMNITOOLS / Anleitungen für Entwickler

Überprüfung des Secret-Leaks im Vitest-Entwicklungsserver (CVE-2026-112948)

Analyse von CVE-2026-112948 in Vitest 5. Erfahren Sie, warum server.fs.deny .env-Dateien nicht geschützt hat und wie Tokens mit CSPRNG rotiert werden.

DevOmniTools Research Veröffentlicht: Aktualisiert: 3 Min. Lesezeit
Vitest dev server.fs.deny bypass architecture diagram showing plain HTTP requests leaking .env and API secret files

Das Wichtigste

  • CVE-2026-112948 in Vitest 5 dev servers overrode Vite default server.fs.deny rules, exposing .env and private keys over plain HTTP.
  • Any process or local network client capable of requesting the Vite UI/API port could scrape internal secrets and API tokens.
  • All credentials residing in .env during active Vitest UI sessions should be immediately revoked and rotated using offline CSPRNG.

Executive Summary & Vulnerability Context

On October 21, 2026, the GitHub Advisory Database published CVE-2026-112948 (GHSA-p458-7748-mcp3), exposing a critical file access misconfiguration in Vitest 5 dev servers.

Under specific developer configurations—specifically when running the interactive UI (vitest --ui), Browser Mode (@vitest/browser), or when enabling the remote api flag—Vitest’s underlying HTTP server failed to apply Vite’s default server.fs.deny rules.

The outcome: sensitive project assets that Vite ordinarily guards by default—including .env, .env.local, .npmrc, private SSL certificates, .git metadata, and Vitest’s internal authentication token file (.vitest-secret-token)—could be fetched over plain HTTP by any client reachable on the network or by a malicious browser tab via cross-origin requests.

Vitest dev server.fs.deny bypass architecture diagram showing plain HTTP requests leaking .env and API secret files (CVE-2026-112948)

Technical Root Cause: Why server.fs.deny Was Overridden

In a standard Vite configuration, server.fs.deny protects sensitive paths using built-in globs:

// Vite's built-in default deny patterns:
['.env', '.env.*', '*.{crt,pem}', '**/.git/**', '**/.npmrc']

When Vitest 5 introduced its internal API server and UI token authentication (.vitest-secret-token), it programmatically appended its token file to the deny list. However, two underlying Vite runtime behaviors caused a silent bypass:

  1. Premature Array Overwrite: Vite only injects its default deny list when server.fs.deny is completely undefined. When Vitest assigned an array containing only ['.vitest-secret-token'], Vite’s default rules were discarded rather than merged.
  2. Matcher Pre-Compilation: Vite compiles the deny list into an internal regex matcher during config resolution. Dynamic runtime mutations pushed later had zero effect on the active HTTP file serving pipeline.

If you ran vitest --ui on a local network or tested apps inside a browser with multi-tab sessions, any script capable of hitting localhost:51204 could scrape your secret keys.


Remediation Workflow & Token Rotation

1. Upgrade Vitest Dependencies

Vitest maintainers released patched releases addressing matcher compilation. Upgrade your project dependencies immediately:

npm install -D vitest@latest @vitest/ui@latest @vitest/browser@latest
# or with pnpm:
pnpm update vitest @vitest/ui @vitest/browser

2. Revoke and Re-issue Leaked Credentials

Treat all secrets residing in .env as compromised if Vitest UI was active on shared networks:

  • Cloud provider access tokens (AWS, GCP, Cloudflare)
  • Database credentials (Postgres, Redis, MongoDB connection URIs)
  • OAuth 2.0 Client Secrets and JWT Signing Passphrases
  • Third-party API keys (Stripe, Resend, GitHub PATs)
Cryptographic token rotation workflow: revoking compromised .env tokens and generating 256-bit CSPRNG API keys and TOTP Base32 secrets offline

3. Generate High-Entropy Cryptographic Secrets Client-Side

When generating replacement tokens, avoid online generators that log inputs to server logs. Use the Web Crypto API (crypto.getRandomValues) for cryptographically strong pseudorandom numbers (CSPRNG):

function generateSecureToken(byteLength = 32): string {
  const bytes = new Uint8Array(byteLength);
  crypto.getRandomValues(bytes);
  return Array.from(bytes)
    .map(b => b.toString(16).padStart(2, '0'))
    .join('');
}

For immediate offline rotation without code boilerplate:


Defensive Hardening

Reinforce vitest.config.ts or vite.config.ts with explicit server.fs.strict and deny patterns:

import { defineConfig } from 'vitest/config';

export default defineConfig({
  server: {
    fs: {
      strict: true,
      deny: [
        '**/.env*',
        '**/*.pem',
        '**/*.key',
        '**/.git/**',
        '**/.npmrc',
        '**/.vitest-secret-token'
      ]
    }
  }
});

FAQ

What is the primary root cause of CVE-2026-112948 in Vitest 5?

Vitest appended its internal token file to server.fs.deny as an explicit array, which caused Vite to discard its default deny globs instead of merging them, allowing unauthenticated HTTP reads of .env and private keys.

Are command-line test runs affected by this vulnerability?

No. Headless test runs (vitest run) do not spawn an HTTP listener. The vulnerability only affects runs with --ui, @vitest/browser, or api: true.

How should leaked .env tokens be rotated securely?

Immediately revoke exposed cloud and database keys at provider dashboards, then generate new 256-bit cryptographically secure pseudorandom (CSPRNG) tokens using client-side tools without transmitting credentials over the web.