Skip to content

[Bug]: Python SDK drops PaymentInstrument extensions and matches allowed instruments by ID only #299

Description

@zesttec

Version

AP2 v0.2.0 / main e1ea56d

Problem

1. Type-specific properties are silently dropped

AP2 permits a Payment Instrument type to define additional properties. [Specification]The x402 sample attempts to pass payee_address and facilitator to the generic PaymentInstrument model. [Sample]

The generated model defines only id, type, and description; its current Pydantic behavior accepts but discards the extra fields. [Model] Signed claims are created using model_dump(), so the discarded fields are absent from the signed Payment Mandate. [Signing path]

After verification, the x402 CP tries to read the missing payee_address. The resulting AttributeError causes it to replace both the destination with an environment/default address and the signed amount with the fixed value 1250. [Fallback]

Consequently, the sample can construct its EIP-3009 authorization from fallback values rather than the corresponding verified Mandate data. This should be an SDK/sample correctness and integrity issue.

2. Allowed-instrument matching is underspecified and ID-only

AP2 requires the closed payment_instrument to be present in the authorized allowed array, but it does not define the matching fields or the uniqueness namespace of id. [Constraint] [Schema]

The Python evaluator compares only id. It therefore accepts an allowed {id: "same", type: "card"} and a closed {id: "same", type: "bank"}. [Evaluator]

At minimum, this permits inconsistent signed instrument metadata. If type selects the payment profile, or IDs are scoped by type or Credential Provider, a different profile or instrument could satisfy the constraint.

Suggested fix

  • Provide a validated extension mechanism or registered per-type models, and preserve their fields through parsing and signing.
  • In the x402 sample, always use the verified payment_amount; define and validate the destination field and fail closed when it is absent.
  • Define the namespace and matching semantics of PaymentInstrument.id.
  • Require at least (type, id) matching or delegate comparison to the instrument profile.
  • Add regression tests for extension-field round trips and same-ID/different-type rejection.

Relevant log output

Code of Conduct

  • I agree to follow this project's Code of Conduct

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions