Skip to main content
Glama

proxy_list_tls_fingerprints

List unique TLS client fingerprints (JA3/JA4) from captured network traffic with occurrence counts to identify and analyze client applications.

Instructions

List unique client JA3/JA4 fingerprints across captured traffic with occurrence counts.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
limitNoMax fingerprints to return (default: 20)
hostname_filterNoFilter by hostname substring

Implementation Reference

  • Handler for the "proxy_list_tls_fingerprints" tool, which aggregates and lists client JA3/JA4 fingerprints from captured traffic.
    server.tool(
      "proxy_list_tls_fingerprints",
      "List unique client JA3/JA4 fingerprints across captured traffic with occurrence counts.",
      {
        limit: z.number().optional().default(20).describe("Max fingerprints to return (default: 20)"),
        hostname_filter: z.string().optional().describe("Filter by hostname substring"),
      },
      async ({ limit, hostname_filter }) => {
        let traffic = proxyManager.getTraffic();
    
        if (hostname_filter) {
          const h = hostname_filter.toLowerCase();
          traffic = traffic.filter((t) => t.request.hostname.toLowerCase().includes(h));
        }
    
        // Aggregate JA3 fingerprints
        const ja3Counts = new Map<string, { count: number; hostnames: Set<string> }>();
        const ja4Counts = new Map<string, { count: number; hostnames: Set<string> }>();
    
        for (const t of traffic) {
          if (t.tls?.client?.ja3Fingerprint) {
            const fp = t.tls.client.ja3Fingerprint;
            const entry = ja3Counts.get(fp) || { count: 0, hostnames: new Set() };
            entry.count++;
            entry.hostnames.add(t.request.hostname);
            ja3Counts.set(fp, entry);
          }
          if (t.tls?.client?.ja4Fingerprint) {
            const fp = t.tls.client.ja4Fingerprint;
            const entry = ja4Counts.get(fp) || { count: 0, hostnames: new Set() };
            entry.count++;
            entry.hostnames.add(t.request.hostname);
            ja4Counts.set(fp, entry);
          }
        }
    
        // Sort by count descending
        const ja3List = [...ja3Counts.entries()]
          .sort((a, b) => b[1].count - a[1].count)
          .slice(0, limit)
          .map(([fp, { count, hostnames }]) => ({
            fingerprint: fp,
            count,
            hostnames: [...hostnames].slice(0, 5),
          }));
    
        const ja4List = [...ja4Counts.entries()]
          .sort((a, b) => b[1].count - a[1].count)
          .slice(0, limit)
          .map(([fp, { count, hostnames }]) => ({
            fingerprint: fp,
            count,
            hostnames: [...hostnames].slice(0, 5),
          }));
    
        return {
          content: [{
            type: "text" as const,
            text: truncateResult({
              status: "success",
              totalExchangesWithTls: traffic.filter((t) => t.tls?.client).length,
              ja3: ja3List,
              ja4: ja4List,
            }),
          }],
        };
      },
    );

Tool Definition Quality

Score is being calculated. Check back soon.

Install Server

Other Tools

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/yfe404/proxy-mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server