Skip to content

Signed Exchange Reporting #99

Open
@horo-t

Description

@horo-t

I want to extend Network Error Logging to support Signed Exchange.

Signed Exchange feature enables content publishers to sign their contents using their own private keys. User Agents (UAs) can trust the signed contents as if the contents are served from the publisher’s origins even if they are served from other distributors’ origins. Even if there is no network errors, UA may fail to load the signed content (example: the signature of the content has expired). This case is not covered by the Network Error Logging feature now. Both publishers and distributors can’t recognize the errors in the user’s environment. I want to extend Network Error Logging feature to enable both publishers and distributors to investigate the signed exchange loading errors such as certificate verification errors.

Distributor side reporting

A publisher (publisher.example) signed the article (https://publisher.example/article.html) as article.html.sxg. A distributor (distributor.example) is distributing the content at https://distributor.example/publisher.example/article.html.sxg and the certificate of publisher.example at https://distributor.example/publisher.example/cert.

If the distributor wants to investigate the signed exchange logs, the distributor sets the Report-To and NEL header in the HTTP response. This is same as the existing Network Error Logging feature.

Report-To: {"group": "sxg-errors",
            "max_age": 10886400,
            "endpoints": [{ "url": "https://report.distributor.example/" }] }
NEL: {"report_to": "sxg-errors", "max_age": 2592000}

Once UA receives the Report-To and NEL header, when UA failed to load (prefetch or navigation) the signed exchange content in the origin (https://distributor.example) because the signature has expired, UA should send the report to the end point https://report.distributor.example/.

{
  "type": "signed-exchange",
  "age": 1,
  "url": "https://distributor.example/publisher.example/article.html.sxg",
  "user_agent": "Mozilla/5.0 (X11; Linux x86_64; rv:60.0) ...",
  "body": {
    "type": "failed",
    "outer_url": "https://distributor.example/publisher.example/article.html.sxg",
    "inner_url": "https://publisher.example/article.html",
    "cert_url": "https://distributor.example/publisher.example/cert",
    "sampling_fraction": 1
  }
}

Publisher side reporting

If the publisher wants to investigate the signed exchange logs, the publisher sets the Report-To and NEL in the signed response header of the signed exchange.

Report-To: {"group": "sxg-errors",
            "max_age": 10886400,
            "endpoints": [{ "url": "https://report.publisher.example/" }] }
NEL: {"report_to": "sxg-errors", "max_age": 2592000}

Same as distributor side reporting, UA should send the report to the end point https://report.publisher.example/ when the UA failed to navigate to the signed exchange content.

{
  "type": "signed-exchange",
  "age": 1,
  "url": "https://publisher.example/article.html",
  "user_agent": "Mozilla/5.0 (X11; Linux x86_64; rv:60.0) ...",
  "body": {
    "type": "failed",
    "outer_url": "https://distributor.example/publisher.example/article.html.sxg",
    "inner_url": "https://publisher.example/article.html",
    "cert_url": "https://distributor.example/publisher.example/cert",
    "sampling_fraction": 1
  }
}

UAs must not send the report to the publisher when the UA loaded the signed exchange for prefetching, because prefetching signed exchange must be done in a privacy-preserving manner.

Error types

UA will expose the following error types.

The following detailed error types should be used only when the reporting origin (the distributor or the publisher) is same as the origin of cert-url of the signed exchange. See Hiding detailed error type section.

  • non_secure_origin
  • parse_error
  • unsupported_version
  • network_error
  • cert_fetch_error
  • cert_parse_error
  • signature_verification_error
  • cert_verification_error
  • ct_verification_error
  • ocsp_error
  • cert_requirements_not_met
  • mi_error

Hiding detailed error type

If the reporting origin (the distributor or the publisher) is different from the origin of cert url, UA must send only ok or failed. This is intended to avoid the leaking of cross-origin information in cert_url.
For example an evil attacker can do the port-scanning by checking whether the error type is cert_fetch_error or cert_parse_error if UA sends the detailed error types. Example:

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions