npm package discovery and stats viewer.

Discover Tips

  • General search

    [free text search, go nuts!]

  • Package details

    pkg:[package-name]

  • User packages

    @[username]

Sponsor

Optimize Toolset

I’ve always been into building performant and accessible sites, but lately I’ve been taking it extremely seriously. So much so that I’ve been building a tool to help me optimize and monitor the sites that I build to make sure that I’m making an attempt to offer the best experience to those who visit them. If you’re into performant, accessible and SEO friendly sites, you might like it too! You can check it out at Optimize Toolset.

About

Hi, 👋, I’m Ryan Hefner  and I built this site for me, and you! The goal of this site was to provide an easy way for me to check the stats on my npm packages, both for prioritizing issues and updates, and to give me a little kick in the pants to keep up on stuff.

As I was building it, I realized that I was actually using the tool to build the tool, and figured I might as well put this out there and hopefully others will find it to be a fast and useful way to search and browse npm packages as I have.

If you’re interested in other things I’m working on, follow me on Twitter or check out the open source projects I’ve been publishing on GitHub.

I am also working on a Twitter bot for this site to tweet the most popular, newest, random packages from npm. Please follow that account now and it will start sending out packages soon–ish.

Open Software & Tools

This site wouldn’t be possible without the immense generosity and tireless efforts from the people who make contributions to the world and share their work via open source initiatives. Thank you 🙏

© 2025 – Pkg Stats / Ryan Hefner

vite-plugin-proxy-http2

v0.2.2

Published

Vite plugin for HTTP/2 proxy support with proper protocol handling

Readme

Vite HTTP/2 Proxy Plugin

CI npm version

Vite plugin that provides HTTP/2 proxy support with full feature parity to Vite's built-in proxy.

Features

  • 🚀 Native HTTP/2 Support - Uses Node's native http2 module, no intermediate proxy module.
  • 🔄 Connection Pooling - Efficient HTTP/2 connection reuse with automatic cleanup.
  • 🔌 WebSocket Support - Full WebSocket proxying with HTTP/2 upgrade handling.
  • 🍪 Cookie Management - Advanced cookie rewriting with domain and path support.
  • 🔒 Security Features - SSL validation, authentication, and X-Forwarded headers.
  • 📡 SSE Support - Server-Sent Events with buffering control.
  • 🛣️ Advanced Routing - Dynamic routing with function support.
  • 📊 Comprehensive Logging - Detailed request logging with timing information.
  • 🎯 Full Vite Compatibility - Supports Vite standard proxy configuration options.

Installation

npm install vite-plugin-proxy-http2
# or
yarn add vite-plugin-proxy-http2
# or
pnpm add vite-plugin-proxy-http2

Quick Start

Recommended: Plugin-level Configuration (HTTP/2 by default)

// vite.config.ts
import { defineConfig } from 'vite'
import http2ProxyPlugin from 'vite-plugin-proxy-http2'

export default defineConfig({
  plugins: [
    http2ProxyPlugin({
      // Global settings (optional)
      maxSessions: 50,              // Limit HTTP/2 sessions
      defaultTimeout: 30000,        // 30 second timeout for all proxies
      
      // Proxy routes
      proxy: {
        '/api': 'https://api.example.com',
        '/ws': {
          target: 'wss://websocket.example.com',
          ws: true
        }
      }
    })
  ]
})

Note: This approach ensures HTTP/2 is used by default and prevents Vite from downgrading to HTTP/1.1.

Alternative: Vite Server Configuration

// vite.config.ts
import { defineConfig } from 'vite'
import http2ProxyPlugin from 'vite-plugin-proxy-http2'

export default defineConfig({
  plugins: [http2ProxyPlugin()],
  server: {
    proxy: {
      '/api': 'https://api.example.com'
    }
  }
})

Warning: Using Vite's server.proxy may cause Vite to downgrade connections to HTTP/1.1. We recommend using the plugin-level configuration instead.

Configuration

Basic Examples

export default defineConfig({
  plugins: [
    http2ProxyPlugin({
      proxy: {
        // String shorthand
        '/api': 'https://api.example.com',
        
        // With options
        '/api': {
          target: 'https://api.example.com',
          changeOrigin: true,
          rewrite: (path) => path.replace(/^\/api/, ''),
          headers: {
            'X-Custom-Header': 'value'
          }
        },
        
        // RegExp pattern
        '^/api/.*': {
          target: 'https://api.example.com',
          changeOrigin: true
        }
      }
    })
  ]
})

Advanced Features

WebSocket Support

'/socket.io': {
  target: 'https://socket-server.com',
  ws: true,
  changeOrigin: true
}

Cookie Rewriting

'/api': {
  target: 'https://api.example.com',
  cookieDomainRewrite: 'localhost',
  cookiePathRewrite: {
    '/api': '/',
    '/api/v2': '/v2'
  }
}

Dynamic Routing

'/api': {
  target: 'https://default-api.com',
  router: (req) => {
    // Route based on headers, query params, etc.
    if (req.headers['x-api-version'] === 'v2') {
      return 'https://api-v2.example.com'
    }
    return 'https://api-v1.example.com'
  }
}

Conditional Bypass

'/api': {
  target: 'https://api.example.com',
  bypass: (req, res, options) => {
    // Skip proxy for certain conditions
    if (req.headers.accept?.includes('text/html')) {
      return '/index.html'
    }
  }
}

Protocol Support (HTTP/1.1 and HTTP/2)

// Force HTTP/1.1 for servers that don't support HTTP/2
'/legacy-api': {
  target: 'https://old-server.com',
  forceHttp1: true
}

// Automatically detect protocol support
'/auto': {
  target: 'https://api.example.com',
  autoDetectProtocol: true // Will use HTTP/2 if supported, fallback to HTTP/1.1
}

Security Options

'/api': {
  target: 'https://api.example.com',
  secure: true, // Verify SSL certificates
  auth: 'username:password', // Basic authentication
  xfwd: true, // Add X-Forwarded-* headers
  headers: {
    'Authorization': 'Bearer token'
  }
}

Timeout Configuration

http2ProxyPlugin({
  // Set global defaults for all proxies
  defaultTimeout: 30000,        // 30 seconds
  defaultProxyTimeout: 25000,   // 25 seconds
  
  proxy: {
    '/api': 'https://api.example.com',  // Uses global defaults
    
    '/slow-api': {
      target: 'https://slow-api.example.com',
      timeout: 60000  // Override for specific route
    }
  }
})

Server-Sent Events

'/events': {
  target: 'https://sse-server.com',
  sse: true, // Optimizes for SSE streams
  changeOrigin: true
}

Custom Response Handling

'/api': {
  target: 'https://api.example.com',
  selfHandleResponse: true,
  configure: (proxyReq, options) => {
    // Custom request/response handling
    proxyReq.on('response', (headers) => {
      console.log('Response headers:', headers)
    })
  }
}

Configuration Options

Global Plugin Options

These options are configured at the plugin level and affect all proxies:

| Option | Type | Default | Description | |--------|------|---------|-------------| | proxy | object | - | Proxy route configurations | | maxSessions | number | 100 | Maximum number of HTTP/2 sessions | | sessionMaxAge | number | 300000 | Session idle timeout in milliseconds (5 minutes) | | connectionTimeout | number | 10000 | Initial connection timeout in milliseconds | | maxQueueSize | number | 100 | Maximum queued requests across all origins | | queueTimeout | number | 30000 | Queue timeout in milliseconds | | defaultTimeout | number | 120000 | Default timeout for all proxies in milliseconds | | defaultProxyTimeout | number | - | Default proxy-specific timeout in milliseconds |

Example:

http2ProxyPlugin({
  // Global settings
  maxSessions: 50,
  sessionMaxAge: 2 * 60 * 1000, // 2 minutes
  maxQueueSize: 200,
  defaultTimeout: 30000, // 30 seconds
  
  // Proxy routes
  proxy: {
    '/api': 'https://api.example.com'
  }
})

Per-Proxy Options

These options can be configured for each individual proxy route:

| Option | Type | Default | Description | |--------|------|---------|-------------| | target | string \| object | required | Backend server URL | | changeOrigin | boolean | true | Changes the origin header to match the target | | ws | boolean | false | Enable WebSocket proxy | | rewrite | function | - | Rewrite request paths | | configure | function | - | Custom proxy configuration callback | | bypass | function | - | Conditionally bypass the proxy | | secure | boolean | true | Verify SSL certificates | | auth | string | - | Basic authentication credentials | | headers | object | - | Custom headers to add to requests | | forceHttp1 | boolean | false | Force HTTP/1.1 protocol for this proxy | | autoDetectProtocol | boolean | false | Auto-detect if origin supports HTTP/2 | | xfwd | boolean | true | Add X-Forwarded-* headers | | preserveHeaderKeyCase | boolean | false | Preserve original header key casing | | cookieDomainRewrite | string \| object | - | Rewrite cookie domains | | cookiePathRewrite | string \| object | - | Rewrite cookie paths | | router | string \| function | - | Dynamic target routing | | timeout | number | global default | Proxy timeout in milliseconds (overrides global) | | proxyTimeout | number | global default | Proxy timeout in milliseconds (overrides global) | | selfHandleResponse | boolean | false | Handle response manually | | followRedirects | boolean | false | Follow HTTP redirects | | sse | boolean | false | Optimize for Server-Sent Events |

Debugging

Enable debug logging by setting the DEBUG environment variable:

DEBUG=vite:http2-proxy npm run dev

Or set LOG_LEVEL for more detailed logging:

LOG_LEVEL=debug npm run dev

Performance

The plugin implements several performance optimizations:

  • Connection Pooling: Reuses HTTP/2 connections across requests
  • Automatic Cleanup: Removes idle connections after configurable timeout (default: 5 minutes)
  • Connection Limits: Prevents resource exhaustion with configurable session limits (default: 100)
  • Request Queueing: Handles high load with configurable queue size (default: 100 requests)
  • Stream Management: Proper HTTP/2 stream lifecycle handling
  • Timeout Handling: Configurable timeouts prevent hanging requests

Migration from http-proxy

This plugin maintains API compatibility with Vite's built-in proxy (which uses http-proxy). Simply install and add the plugin to migrate:

// vite.config.ts
import { defineConfig } from 'vite'
+import http2ProxyPlugin from 'vite-http2-proxy'

export default defineConfig({
+  plugins: [http2ProxyPlugin({
+    proxy: {
+      // Your existing proxy config works as-is,
+      // just move it into the plugin config
+      '/api': 'https://api.example.com'
+    }
  })],
  server: {
    // Remove proxy config from here
  }
})

Troubleshooting

Common Issues

  1. SSL Certificate Errors

    // Disable SSL verification for development
    '/api': {
      target: 'https://self-signed.example.com',
      secure: false
    }
  2. Cookie Issues

    // Ensure cookies work on localhost
    '/api': {
      target: 'https://api.example.com',
      cookieDomainRewrite: 'localhost',
      cookiePathRewrite: '/'
    }
  3. Timeout Errors

    // Increase timeout for slow endpoints
    '/api': {
      target: 'https://slow-api.example.com',
      timeout: 300000 // 5 minutes
    }

License

MIT