{"version":3,"sources":["../src/constants.ts","../src/encode-url.ts","../src/request.ts","../src/response.ts","../src/fetchers.ts","../src/parse-url.ts"],"names":["transactionFromBase64","address","reference"],"mappings":"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","file":"index.node.cjs","sourcesContent":["/** @internal */\nexport const SOLANA_PAY_PROTOCOL = \"solana:\";\n","import type { Address } from \"gill\";\nimport { SOLANA_PAY_PROTOCOL } from \"./constants.js\";\n\n/**\n * Fields of a Solana Pay transaction request URL.\n */\nexport interface SolanaPayTransactionRequestURLFields {\n  /** `link` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#link) */\n  link: URL;\n  /** `label` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#label-1) */\n  label?: string;\n  /** `message` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#message-1).  */\n  message?: string;\n}\n\n/**\n * Fields of a Solana Pay transfer request URL.\n */\nexport interface SolanaPayTransferRequestURLFields {\n  /** `recipient` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#recipient) */\n  recipient: Address;\n  /** `amount` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#amount) */\n  amount?: number | string;\n  /** `spl-token` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#spl-token) */\n  splToken?: Address;\n  /** `reference` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#reference) */\n  reference?: Address | Address[];\n  /** `label` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#label) */\n  label?: string;\n  /** `message` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#message).  */\n  message?: string;\n  /** `memo` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#memo) */\n  memo?: string;\n}\n\n/**\n * Encode a Solana Pay URL\n *\n * @param fields Fields to encode in the URL\n */\nexport function encodeSolanaPayURL(\n  fields: SolanaPayTransactionRequestURLFields | SolanaPayTransferRequestURLFields,\n): URL {\n  return \"link\" in fields ? encodeTransactionRequestURL(fields) : encodeTransferRequestURL(fields);\n}\n\nfunction encodeTransactionRequestURL({ link, label, message }: SolanaPayTransactionRequestURLFields): URL {\n  if (link.protocol !== \"https:\") {\n    throw new Error(\"Link must use HTTPS protocol\");\n  }\n\n  // Remove trailing slashes\n  const pathname = link.search\n    ? encodeURIComponent(String(link).replace(/\\/\\?/, \"?\"))\n    : String(link).replace(/\\/$/, \"\");\n  const url = new URL(SOLANA_PAY_PROTOCOL + pathname);\n\n  if (label) {\n    url.searchParams.append(\"label\", label);\n  }\n\n  if (message) {\n    url.searchParams.append(\"message\", message);\n  }\n\n  return url;\n}\n\nfunction encodeTransferRequestURL({\n  recipient,\n  amount,\n  splToken,\n  reference,\n  label,\n  message,\n  memo,\n}: SolanaPayTransferRequestURLFields): URL {\n  const url = new URL(SOLANA_PAY_PROTOCOL + recipient);\n\n  if (amount) {\n    url.searchParams.append(\"amount\", amount.toString());\n  }\n\n  if (splToken) {\n    url.searchParams.append(\"spl-token\", splToken);\n  }\n\n  if (reference) {\n    if (!Array.isArray(reference)) {\n      reference = [reference];\n    }\n\n    for (const pubkey of reference) {\n      url.searchParams.append(\"reference\", pubkey);\n    }\n  }\n\n  if (label) {\n    url.searchParams.append(\"label\", label);\n  }\n\n  if (message) {\n    url.searchParams.append(\"message\", message);\n  }\n\n  if (memo) {\n    url.searchParams.append(\"memo\", memo);\n  }\n\n  return url;\n}\n","import { Address } from \"gill\";\n\nexport interface SolanaPayTransactionRequestGetRequest {\n  // get request takes not data\n}\n\nexport interface SolanaPayTransactionRequestPostRequest {\n  account: Address;\n}\n\nexport function validateSolanaPayRequestUrl(url: URL): void {\n  if (url.protocol !== \"https:\") {\n    throw new Error(\"URL must use HTTPS protocol\");\n  }\n}\n","import { transactionFromBase64, type Transaction } from \"gill\";\n\nexport class SolanaPayResponseError extends Error {\n  name = \"SolanaPayResponseError\";\n}\n\nexport interface SolanaPayTransactionRequestGetResponse {\n  label: string;\n  icon: string;\n}\n\nexport interface SolanaPayTransactionRequestPostResponse {\n  transaction: Transaction;\n  message?: string;\n}\n\n/**\n * Parse provided input to be a valid Solana Pay Transaction Request's\n * [GET response](https://github.com/solana-foundation/solana-pay/blob/master/SPEC.md#get-response)\n * per the spec\n */\nexport function parseSolanaPayGetResponse(data: any): SolanaPayTransactionRequestGetResponse {\n  if (!data.label || typeof data.label !== \"string\") {\n    throw new SolanaPayResponseError(\"Invalid response: missing or invalid label\");\n  }\n\n  if (!data.icon || typeof data.icon !== \"string\") {\n    throw new SolanaPayResponseError(\"Invalid response: missing or invalid icon\");\n  }\n\n  let iconUrl: URL;\n  try {\n    iconUrl = new URL(data.icon);\n  } catch {\n    throw new SolanaPayResponseError(\"Invalid icon URL format\");\n  }\n\n  if (iconUrl.protocol !== \"http:\" && iconUrl.protocol !== \"https:\") {\n    throw new SolanaPayResponseError(\"Icon URL must use HTTP or HTTPS protocol\");\n  }\n\n  // jpg is not in the v1.1 spec, but they should be :)\n  const allowedExtensions = [\".svg\", \".png\", \".webp\", \".jpg\", \".jpeg\"];\n  const hasValidExtension = allowedExtensions.some((ext) => iconUrl.pathname.toLowerCase().endsWith(ext));\n\n  if (!hasValidExtension) {\n    throw new SolanaPayResponseError(\"Icon must be SVG, PNG, WebP, or JPEG format\");\n  }\n\n  return {\n    label: data.label,\n    icon: data.icon,\n  };\n}\n\n/**\n * Parse provided input to be a valid Solana Pay Transaction Request's\n * [POST response](https://github.com/solana-foundation/solana-pay/blob/master/SPEC.md#post-response)\n * per the spec\n */\nexport function parseSolanaPayPostResponse(data: any): SolanaPayTransactionRequestPostResponse {\n  if (!data.transaction || typeof data.transaction !== \"string\") {\n    throw new SolanaPayResponseError(\"Invalid response: missing or invalid transaction\");\n  }\n\n  if (data.message && typeof data.message !== \"string\") {\n    throw new SolanaPayResponseError(\"Invalid response: message must be string\");\n  }\n\n  let transaction: Transaction | null = null;\n\n  try {\n    transaction = transactionFromBase64(data.transaction);\n  } catch {\n    throw new SolanaPayResponseError(\"Invalid transaction data as base64\");\n  }\n\n  return {\n    transaction,\n    message: data.message,\n  };\n}\n","import { SolanaPayTransactionRequestPostRequest, validateSolanaPayRequestUrl } from \"./request.js\";\nimport {\n  parseSolanaPayGetResponse,\n  parseSolanaPayPostResponse,\n  SolanaPayTransactionRequestGetResponse,\n  SolanaPayTransactionRequestPostResponse,\n} from \"./response.js\";\n\n/**\n * Generic HTTP fetcher for Solana Pay transaction request endpoints.\n *\n * Validates URL, makes request, and optionally parses the JSON response.\n *\n * @template TResponse - Expected response type (defaults to unknown)\n * @param url - Solana Pay transaction request URL (must be https://)\n * @param config - Request configuration\n * @param config.method - HTTP method (GET or POST)\n * @param config.body - Request body (JSON stringified)\n * @param config.parser - Optional response parser/validator\n * @param config.requestInit - Optional fetch options\n * @returns Parsed response or raw JSON if no parser provided\n * @throws {Error} Invalid URL, HTTP error, JSON parse error, or schema validation error\n */\nexport async function fetchSolanaPayRequest<TResponse = unknown>(\n  url: URL,\n  config: {\n    method: \"GET\" | \"POST\";\n    body?: unknown;\n    parser?: (data: unknown) => TResponse;\n    requestInit?: RequestInit;\n  },\n): Promise<TResponse> {\n  validateSolanaPayRequestUrl(url);\n\n  const baseHeaders: HeadersInit = {\n    Accept: \"application/json\",\n    \"Accept-Encoding\": \"gzip, deflate, br\",\n  };\n\n  if (config.method === \"POST\" || config.body !== undefined) {\n    baseHeaders[\"Content-Type\"] = \"application/json\";\n  }\n\n  // Destructure to exclude headers from requestInit since we handle them separately\n  const { headers: _headers, ...restRequestInit } = config.requestInit || {};\n\n  const response = await fetch(url, {\n    method: config.method,\n    headers: {\n      ...baseHeaders,\n      ...config.requestInit?.headers,\n    },\n    body: config.body !== undefined ? JSON.stringify(config.body) : undefined,\n    ...restRequestInit,\n  });\n\n  if (!response.ok) {\n    throw new Error(`HTTP ${response.status}: ${response.statusText}`);\n  }\n\n  let data: unknown;\n  try {\n    data = await response.json();\n  } catch (error) {\n    throw new Error(`Failed to parse response as JSON: ${error instanceof Error ? error.message : String(error)}`);\n  }\n\n  if (config.parser) {\n    try {\n      return config.parser(data);\n    } catch (error) {\n      throw new Error(`Failed to validate response schema: ${error instanceof Error ? error.message : String(error)}`);\n    }\n  }\n\n  return data as TResponse;\n}\n\n/**\n * Fetches merchant information for a Solana Pay transaction request.\n *\n * Makes a GET request to retrieve the merchant's label and icon, which are displayed\n * to the user before presenting the transaction for signing.\n *\n * @param url - Solana Pay transaction request URL (must be https://)\n * @param options - Optional fetch configuration\n * @returns Merchant label and icon\n * @throws {Error} Invalid URL, HTTP error, or invalid response schema\n *\n * @example\n * ```typescript\n * const { label, icon } = await fetchSolanaPayGetRequest(\n *   new URL('https://merchant.example.com/api')\n * );\n * console.log(label); // \"Example Merchant\"\n * console.log(icon);  // \"https://merchant.example.com/icon.svg\"\n * ```\n */\nexport async function fetchSolanaPayGetRequest(\n  url: URL,\n  options?: RequestInit,\n): Promise<SolanaPayTransactionRequestGetResponse> {\n  return fetchSolanaPayRequest(url, {\n    method: \"GET\",\n    parser: parseSolanaPayGetResponse,\n    requestInit: options,\n  });\n}\n\n/**\n * Requests a transaction from a Solana Pay merchant endpoint.\n *\n * Makes a POST request with the user's account address. The merchant returns a\n * serialized transaction (unsigned or partially signed) for the wallet to sign.\n *\n * @param url - Solana Pay transaction request URL (must be https://)\n * @param body - Request body containing the user's account address\n * @param options - Optional fetch configuration\n * @returns transaction and optional message\n * @throws {Error} Invalid URL, HTTP error, or invalid response schema\n *\n * @example\n * ```typescript\n * const { transaction, message } = await fetchSolanaPayPostRequest(\n *   new URL('https://merchant.example.com/api'),\n *   { account: address(\"user123...\") }\n * );\n * // transaction is automatically decoded and deserialized\n * // message is an optional string to display to the user\n * ```\n */\nexport async function fetchSolanaPayPostRequest(\n  url: URL,\n  body: SolanaPayTransactionRequestPostRequest,\n  options?: RequestInit,\n): Promise<SolanaPayTransactionRequestPostResponse> {\n  return fetchSolanaPayRequest(url, {\n    method: \"POST\",\n    body,\n    parser: parseSolanaPayPostResponse,\n    requestInit: options,\n  });\n}\n\n/**\n * Solana Pay transaction request methods.\n *\n * @property {Function} get - Fetch merchant information (label and icon)\n * @property {Function} post - Request a transaction from the merchant\n *\n * @example\n * ```typescript\n * const { label, icon } = await solanaPayTransactionRequest.get(url);\n * const { transaction } = await solanaPayTransactionRequest.post(url, { account });\n * ```\n */\nexport const solanaPayTransactionRequest = {\n  get: fetchSolanaPayGetRequest,\n  post: fetchSolanaPayPostRequest,\n};\n","import { address, type Address } from \"gill\";\n// import BigNumber from \"bignumber.js\";\nimport { SOLANA_PAY_PROTOCOL } from \"./constants.js\";\n\n/**\n * A Solana Pay transaction request URL\n */\nexport interface SolanaPayTransactionRequestURL {\n  /** `link` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#link) */\n  link: URL;\n  /** `label` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#label-1) */\n  label?: string;\n  /** `message` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#message-1) */\n  message?: string;\n}\n\n/**\n * A Solana Pay transfer request URL\n */\nexport interface SolanaPayTransferRequestURL {\n  /** `recipient` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#recipient) */\n  recipient: Address;\n  /** `amount` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#amount) */\n  amount?: number;\n  /** `spl-token` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#spl-token) */\n  splToken: Address | undefined;\n  /** `reference` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#reference) */\n  reference?: Address[];\n  /** `label` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#label) */\n  label?: string;\n  /** `message` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#message) */\n  message?: string;\n  /** `memo` in the [Solana Pay spec](https://github.com/solana-labs/solana-pay/blob/master/SPEC.md#memo) */\n  memo?: string;\n}\n\n/**\n * Thrown when a URL can't be parsed as a Solana Pay URL\n */\nexport class SolanaPayParseURLError extends Error {\n  name = \"SolanaPayParseURLError\";\n}\n\n/**\n * Parse a Solana Pay URL as a Transfer Request or Transaction Request\n *\n * @param url - URL to parse\n *\n * @throws {SolanaPayParseURLError}\n */\nexport function parseSolanaPayURL(url: string | URL): SolanaPayTransactionRequestURL | SolanaPayTransferRequestURL {\n  if (typeof url === \"string\") {\n    if (url.length > 2048) throw new SolanaPayParseURLError(\"length invalid\");\n    url = new URL(url);\n  }\n\n  if (url.protocol !== SOLANA_PAY_PROTOCOL) throw new SolanaPayParseURLError(\"protocol invalid\");\n  if (!url.pathname) throw new SolanaPayParseURLError(\"missing pathname\");\n\n  return /[:%]/.test(url.pathname) ? parseTransactionRequestURL(url) : parseTransferRequestURL(url);\n}\n\nfunction parseTransactionRequestURL({ pathname, searchParams }: URL): SolanaPayTransactionRequestURL {\n  const link = new URL(decodeURIComponent(pathname));\n  if (link.protocol !== \"https:\") throw new SolanaPayParseURLError(\"link invalid\");\n\n  const label = searchParams.get(\"label\") || undefined;\n  const message = searchParams.get(\"message\") || undefined;\n\n  return {\n    link,\n    label,\n    message,\n  };\n}\n\nfunction parseTransferRequestURL({ pathname, searchParams }: URL): SolanaPayTransferRequestURL {\n  let recipient: Address;\n  try {\n    recipient = address(pathname);\n  } catch (error: any) {\n    throw new SolanaPayParseURLError(\"recipient invalid\");\n  }\n\n  let amount: number | undefined;\n  const amountParam = searchParams.get(\"amount\");\n  if (amountParam != null) {\n    if (!/^\\d+(\\.\\d+)?$/.test(amountParam)) throw new SolanaPayParseURLError(\"amount invalid\");\n\n    try {\n      amount = parseFloat(amountParam);\n    } catch (err) {\n      throw new SolanaPayParseURLError(\"amount invalid\");\n    }\n    if (!amount) throw new SolanaPayParseURLError(\"amount invalid\");\n    if (Number.isNaN(amount)) throw new SolanaPayParseURLError(\"amount NaN\");\n    if (amount < 0) throw new SolanaPayParseURLError(\"amount negative\");\n    // 0 is a valid `amount`\n  }\n\n  let splToken: Address | undefined;\n  const splTokenParam = searchParams.get(\"spl-token\");\n  if (splTokenParam != null) {\n    try {\n      splToken = address(splTokenParam);\n    } catch (error) {\n      throw new SolanaPayParseURLError(\"spl-token invalid\");\n    }\n  }\n\n  let reference: Address[] | undefined;\n  const referenceParams = searchParams.getAll(\"reference\");\n  if (referenceParams.length) {\n    try {\n      reference = referenceParams.map((reference) => address(reference));\n    } catch (error) {\n      throw new SolanaPayParseURLError(\"reference invalid\");\n    }\n  }\n\n  const label = searchParams.get(\"label\") || undefined;\n  const message = searchParams.get(\"message\") || undefined;\n  const memo = searchParams.get(\"memo\") || undefined;\n\n  return {\n    recipient,\n    amount,\n    splToken,\n    reference,\n    label,\n    message,\n    memo,\n  };\n}\n"]}