X402.Client.Policy (X402 v0.9.0)

Copy Markdown View Source

Ready-made selection policies for X402.Client.select_requirements/2.

A policy is a 2-arity function receiving a candidate requirements entry and the decoded PaymentRequired map it came from (nil when selecting from a bare list). It returns true to accept the entry, false to skip it, or {:error, reason} to abort selection with that error. Policies are passed with the :policies option and every one of them must accept an entry for it to be selected:

X402.Client.Finch.request(MyApp.Finch, url,
  signer: signer,
  policies: [
    X402.Client.Policy.max_amount("1000000"),
    X402.Client.Policy.networks(["eip155:8453", "solana:*"]),
    X402.Client.Policy.assets(["0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913"])
  ]
)

Custom policies are plain functions and compose the same way:

fn requirements, _payment_required ->
  requirements["payTo"] in MyApp.trusted_receivers()
end

Summary

Types

t()

A selection policy.

Functions

Accepts entries paying with one of the given assets (compared case-insensitively).

Accepts entries whose amount (atomic units) does not exceed limit.

Accepts entries on one of the given CAIP-2 networks.

Accepts entries using one of the given schemes.

Types

t()

@type t() :: (map(), map() | nil -> boolean() | {:error, term()})

A selection policy.

Functions

assets(assets)

(since 0.9.0)
@spec assets([String.t()]) :: t()

Accepts entries paying with one of the given assets (compared case-insensitively).

Examples

iex> policy = X402.Client.Policy.assets(["0x036CbD53842c5426634e7929541eC2318f3dCF7e"])
iex> policy.(%{"asset" => "0x036cbd53842c5426634e7929541ec2318f3dcf7e"}, nil)
true
iex> policy.(%{"asset" => "0x0000000000000000000000000000000000000000"}, nil)
false

max_amount(limit)

(since 0.9.0)
@spec max_amount(String.t() | non_neg_integer()) :: t()

Accepts entries whose amount (atomic units) does not exceed limit.

Entries with a missing or unparsable amount are skipped.

Examples

iex> policy = X402.Client.Policy.max_amount("10000")
iex> policy.(%{"amount" => "10000"}, nil)
true
iex> policy.(%{"amount" => "10001"}, nil)
false
iex> policy.(%{"amount" => "lots"}, nil)
false

iex> X402.Client.Policy.max_amount(500).(%{"amount" => "499"}, nil)
true

networks(patterns)

(since 0.9.0)
@spec networks([String.t()]) :: t()

Accepts entries on one of the given CAIP-2 networks.

A trailing * acts as a prefix wildcard (for example "eip155:*").

Examples

iex> policy = X402.Client.Policy.networks(["eip155:8453", "solana:*"])
iex> policy.(%{"network" => "eip155:8453"}, nil)
true
iex> policy.(%{"network" => "solana:5eykt4UsFv8P8NJdTREpY1vzqKqZKvdp"}, nil)
true
iex> policy.(%{"network" => "eip155:1"}, nil)
false

schemes(schemes)

(since 0.9.0)
@spec schemes([String.t()]) :: t()

Accepts entries using one of the given schemes.

Examples

iex> policy = X402.Client.Policy.schemes(["exact"])
iex> policy.(%{"scheme" => "exact"}, nil)
true
iex> policy.(%{"scheme" => "upto"}, nil)
false