Skip to content

[Feature]: Expose securityDetails() on APIResponse for HTTPS monitoring use cases #40905

@shahzad31

Description

@shahzad31

🚀 Feature Request

It would be helpful if APIResponse exposed a securityDetails() method (and ideally serverAddr()), mirroring what's already available on the browser-side Response. HTTP would resolve to null for both, matching the browser semantics.

securityDetails(): Promise<null | {
  issuer?: string;
  protocol?: string;       // e.g. "TLS 1.3"
  subjectName?: string;
  validFrom?: number;      // epoch seconds
  validTo?: number;        // epoch seconds
}>;

serverAddr(): Promise<null | {
  ipAddress: string;
  port: number;
}>;

Example

const response = await request.get('https://api.example.com/health');

const tls = await response.securityDetails();
if (tls?.validTo) {
  const daysUntilExpiry = (tls.validTo * 1000 - Date.now()) / 86_400_000;
  if (daysUntilExpiry < 30) {
    console.warn(`Cert for ${response.url()} expires in ${Math.floor(daysUntilExpiry)} days`);
  }
}

Motivation

Acknowledging the earlier decision in #32647 — closing timings() because Playwright isn't a performance testing tool — this request is intentionally different in scope:

  1. It's certificate metadata, not performance data. validTo, issuer, subjectName, protocol are what HTTPS monitoring needs (cert-expiry alerts are one of the most common production incidents), and they don't invite people to use Playwright as a load-testing tool.
  2. There's already precedent. The browser-side Response exposes exactly these fields (added in feat(response): expose connection details in API #7150 / [Feature] securityDetails on Response object #2474). TLS info isn't intrinsically browser-only; it comes from the underlying socket.
  3. The data is already being computed. lib/server/fetch.js opens the TLS connection through Node's tls module. The peer certificate is available on the socket via tlsSocket.getPeerCertificate() and the protocol via tlsSocket.getProtocol(). Surfacing the same shape as Response.securityDetails() would be a small, additive change.
  4. The userland workaround is awkward. Opening a second tls.connect() to the same host:port works, but duplicates the handshake, uses a separate socket (so cert/IP aren't guaranteed to be those of the actual request), and is brittle around proxies, SNI, and client-cert auth — all of which Playwright already handles internally.

If exposing this on the public API isn't desirable, an alternative would be surfacing it in the existing HAR/trace output (_securityDetails and serverIPAddress already exist in the HAR spec). Happy to send a PR if there's appetite. Thanks for considering!

Metadata

Metadata

Assignees

Labels

Type

No type
No fields configured for issues without a type.

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions