Skip to content

feat(ja4): add stable JA4 fingerprint variant#42

Open
zeroaddresss wants to merge 1 commit into
wi1dcard:masterfrom
kairal-sec:stable-ja4
Open

feat(ja4): add stable JA4 fingerprint variant#42
zeroaddresss wants to merge 1 commit into
wi1dcard:masterfrom
kairal-sec:stable-ja4

Conversation

@zeroaddresss
Copy link
Copy Markdown

Summary

This PR adds an opt-in stable JA4 variant alongside the existing raw JA4 implementation.

The stable variant keeps the normal JA4 structure, but excludes TLS extensions that can appear or disappear depending on connection state:

  • padding (0x0015)
  • session_ticket (0x0023)
  • pre_shared_key (0x0029)

These extensions are removed from both the JA4 extension count and the extension hash input.

Why

Raw JA4 can change between fresh and resumed TLS handshakes for the same client. In practice, this can happen when connection-state-dependent extensions such as pre_shared_key, session_ticket, or padding are present in one handshake and absent in another.

That makes raw JA4 useful as a wire-level fingerprint, but less stable as a continuity signal.

This stable variant is meant for consumers that need a canonical JA4 value across expected fresh/resumed handshake differences, while preserving the existing raw JA4 behavior unchanged.

The motivation follows the stability concerns discussed by ntop here:

https://www.ntop.org/is-ja4-now-obsolete/

What changed

  • Added ja4.StableJA4Fingerprint.
  • Added fingerprint.JA4StableFingerprint.
  • Kept ja4.JA4Fingerprint behavior unchanged.
  • Kept the default proxy headers unchanged. Stable JA4 is opt-in for now, so users can wire it into custom header injectors if they need it.

Tests

Added coverage for:

  • Chrome full handshake vs PSK/resumed-style handshake.
  • Each ignored extension: padding, session_ticket, and pre_shared_key.
  • Non-ephemeral extensions still changing the stable JA4.
  • fingerprint.JA4StableFingerprint matching the ja4 package output.

Validation run locally:

go test ./...
go test -race ./...
go vet ./...
git diff --check

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant