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 🙏

© 2026 – Pkg Stats / Ryan Hefner

http2-antifingerprint

v1.17.1

Published

Prevents identifying http2 requests

Readme

HTTP/2 Antifingerprint

Allows to create ClientHttp2Session with passive fingerprint evasion by changing JA3, HTTP/2 options, header order and pseudo-header order.

Example

const http2antifingerprint = require("http2-antifingerprint"); // default import
const { http2antifingerprint } = require("http2-antifingerprint"); // particular import

(async () => {
  const options = {
    proxy: {
      scheme: "http",
      user: "user", // Is not mandatory
      password: "password", // Is not mandatory
      host: "example.com",
      port: 80,
    },
    onSwitchingProtocols: (response) => console.log(response.statusCode), // Callback is fired on connection upgrade
  };

  const listener = () => {};

  const client = await http2antifingerprint.connect(
    "https://example.com",
    listener,
    options
  ); // Returns a Promise
  client.on("error", (err) => console.error(err)); // Methods of node:http2 session are left intact

  const request = client.request(
    {
      ":method": "POST",
      ":authority": "example.com",
      ":scheme": "https",
      ":path": "/",
      "user-agent": "node",
      "accept-encoding": "gzip, deflate, br",
      "accept-language": "en-US",
    },
    {}, // Client session request options from node:http2
    {
      reorderPseudoHeaders: true, // Headers starting with colon will be reordered
      reorderHeaders: false, // All other headers that do not start with colon will not be reordered
      preferChromeHeaderOrder: true, // The headers provided will maintain chrome header order that depend on the http method
    }
  );

  // Further API is left intact

  request.on("response", (headers) => {
    for (const name in headers) {
      console.log(`${name}: ${headers[name]}`);
    }
  });

  request.setEncoding("utf8");
  let data = "";
  request.on("data", (chunk) => {
    data += chunk;
  });
  request.on("end", () => {
    console.log(`\n${data}`);
    client.close();
  });
  request.end();
})();

API

Creating a HTTP/2 session

await http2antifingerprint.connect([authority], [listener], [options])

Returns a Promise<ClientHttp2Session>.

  • [authority] - the remote HTTP/2 server to connect to. This must be in the form of a minimal, valid URL with the http:// or https:// prefix, host name, and IP port (if a non-default port is used). Userinfo (user ID and password), path, querystring, and fragment details in the URL will be ignored.
  • [listener] - will be registered as a one-time listener of the 'connect' event. Not mandatory.
  • [options] - not a mandatory argument.

[options] can have proxy object consisting of scheme, host and port and may contain user or password properties.

[options] can have onSwitchingProtocols callback that is getting called with the http.IncomingMessage argument. Since 1.1.4 supports any http2 option, such as createConnection. Can have tlsConnectOverrides that override the existing default TLS values. Might be useful for encryption setting override or for custom ALPN protocols:

const options = {
  tlsConnectOverrides: {
    ALPNProtocols: ["h2", "http/1.1", "spdy/3.1"],
  },
};
const client = await http2antifingerprint.connect(
  "https://example.com",
  listener,
  options
);

banOriginalHeaderOrder - allows to never send the original order given in request options

banOriginalPseudoHeaderOrder - allows to never send the original pseudo-header order given in request options

ca - specify .pem certificate

seed - allows to set up http2 window values depending on numeric value. History acquired using _http2antifingerprint.seedHistory

isRequestDependsOnSeed - should _http2antifingerprint.seedHistory generate entry and update http2 window settings on every new request from the same session. Defaults to false

Creating a request

const request = client.request([headers], [client session options], [header options]);

  • [headers] - an object that contains key-value pairs of pseudo-headers and headers.
  • [client session options] - the same semantics as in node:http2 built-in package. Can be an empty object.
  • [header options] - not a mandatory argument that can have reorderPseudoHeaders and reorderHeaders boolean properties. Both are true by default.

Fallbacks to parent's client session options if [header options] are not specified.

Can have preferChromeHeaderOrder property that cannot be used with reorderPseudoHeaders or with reorderHeaders properties. In such case, header ordering will be chrome, because many sites reject non-chrome header orders or detect bots with it. Defaults to false

  • reorderPseudoHeaders defaults to true
  • reorderHeaders defaults to true

Can have strictMode boolean property. If specified, the client.request method call without second and third arguments will reject with error. false by default.

negotiationSpoof allows to spoof tls's secureProtocol and sigals list during client hello stage, if set to true. Defaults to false.

curveSpoof allows to spoof the elliptic curves. Defaults to tls.DEFAULT_ECDH_CURVE.

spoofSecureOptions allows to imitate various OpenSSL implementations to execute during hello stage. Defaults to false.

Notice: if preferChromeHeaderOrder is true, it is not required to set reorderPseudoHeaders and reorderHeaders properties to false as they will default to false.

legacyTlsSpoof allows to imitate under TLSv.1.2 versions. Servers often reject such versions including the node.js http2 server

forceTlsV1 - use only TLSv1 if true. Requires legacyTlsSpoof to be true

forceTlsV1dot1 - use only TLSv1.1 if true. Requires legacyTlsSpoof to be true

forceTlsV1dot2 - use only TLSv1.2 if true. Requires legacyTlsSpoof to be true

tls - prefer any TLS version if above options won't work. Overrides forceTls... options

Test

npm test