# Authentication Building with an AI agent? Start at https://docs.payme.io/agents.md ## Related - [Environments](/payments/getting-started/environments) - [Quickstart](/payments/getting-started/quickstart) - [Callbacks](/payments/getting-started/callbacks) - [Authorization Flow](/keep/partner-authorization/authorization-flow) - [Authentication](/products-and-customers/authentication) - [Contracts](/b2b-payments/contracts) The Payments API does **not** use an `Authorization` header. You identify yourself with keys inside the JSON request body (and, on some endpoints, in custom headers). Always send `Content-Type: application/json`. ## The credentials at a glance | Credential | Who has it | What it does | Where it goes | Keep it | |------------|-----------|--------------|---------------|---------| | `seller_payme_id` (the **MPL**) | Every seller (merchant) | Identifies the seller **and, on its own, authenticates** most seller-level calls: creating sales, refunding, querying sales, updating the seller. | JSON body field `seller_payme_id` (required in the body on `generate-sale`), or header `PayMe-Merchant-Key` on the endpoints listed under *Header-based endpoints* | **Secret** — server-side only | | `payme_client_key` | **Partners** (platforms and marketplaces) only | The partner key. Needed for partner-level calls such as creating sellers and querying across sellers. | JSON body field `payme_client_key`, or header `PayMe-Partner-Key` | **Secret** — server-side only | | Public key | Every seller; one per seller per environment | Designed for browser code: tokenizing cards (Hosted Fields), Apple Pay and Google Pay flows, and reading a filtered list of the seller's transactions. | Header `PayMe-Public-Key`; first argument of `PayMe.create(apiKey, …)` | May be exposed in the browser — but note it can read transactions | Example MPL format: `MPLDEMO-MPLDEMO-MPLDEMO-1234567`. **`seller_payme_secret` is not a credential.** `create-seller` returns it, but it is a random value that PayMe never stores or checks. Ignore it. ## Merchants and partners - **A merchant** (a single seller) authenticates with `seller_payme_id`. It can call `refund-sale` with `seller_payme_id` alone — PayMe finds the partner from the seller. - **A partner** (a platform managing many sellers) also holds `payme_client_key`, sent in the body or the `PayMe-Partner-Key` header. If a partner sends both keys, the seller must belong to that partner; otherwise the request fails with error `20` ("Merchant-Seller inconsistency"). A partner can also identify the seller by the `seller_id` it set when creating the seller, together with `payme_client_key`. Partner-only endpoints documented with `payme_client_key` include `create-seller`, `update-seller`, `upload-seller-files`, `get-vas-seller`, `vas-enable`, `vas-disable`, and POS `authenticate` and `pair`. `withdraw-balance` takes either a partner's `payme_client_key` with the seller's `seller_payme_id`, or the seller's own `seller_payme_id`. The query APIs `get-sales`, `get-subscriptions`, `get-sellers` and `get-withdrawals` are not partner-only. A partner sends `payme_client_key` (or the `PayMe-Partner-Key` header). A seller without a partner key sends `seller_payme_id` in the JSON body; results are limited to that seller. `merchant_key` and `merchant_password` do not exist on a seller account: they are partner-level credentials. A seller that puts its own MPL in `payme_client_key` gets HTTP 500 with code `200` "Merchant was not found": remove the field and send `seller_payme_id` alone. Error codes you may see while setting up keys: `1` — no key sent at all; `200` — the `payme_client_key` matches no partner; `201` — the partner is inactive; `251` — the `seller_payme_id` matches no seller; `163` — the seller is inactive. ### Header-based endpoints | Header | Carries | Used on (examples) | |--------|---------|--------------------| | `PayMe-Merchant-Key` | The seller's MPL | `GET /buyers/{buyer_guid}`, `GET /documents`, 3D Secure hash resolution, `PATCH /subscriptions/{sub_payme_id}/resume` | | `PayMe-Partner-Key` | The partner's client key | `GET /sellers/{seller_payme_id}/public-keys`, `GET /banks/{country_iso_code}` | | `PayMe-Public-Key` | The seller's public key | `POST /sales/{payme_sale_id}/3ds` (called from the browser) | | `PayMe-Signature` | A static value PayMe provides on request | `/sellers/{mpl_key}/individuals`, `/sellers/{mpl_key}/mids` | `PayMe-Signature` is not computed per request: it is a static secret value that PayMe gives you on request. Keep it secret and never paste it into code samples or tickets. ### The public key Each seller has its own public key, issued separately in each environment. A partner can look it up with `GET /sellers/{seller_payme_id}/public-keys` (header `PayMe-Partner-Key`), and `create-seller` returns it as `seller_public_key`. The public key is meant for browser code, but it can read a filtered list of the seller's transactions. Use it only where you need it in the browser. In the merchant dashboard, the public key, the MPL and the Hosted Fields JSAPI credentials are on **Admin → API & Integration** (API ואינטגרציה). The Hosted Fields public key is in the section **Hosted Fields JSAPI Credentials** on that page, and it differs between the sandbox and production. `PayMe.create` takes the public key only: never put the MPL (`seller_payme_id`) in browser code. `GET /sellers/{seller_payme_id}/public-keys` is partner-only. ## Getting credentials - **Payments API — sandbox:** if you already have a PayMe account, open the test account from the dashboard: click your name at the top → **Switch to test account** → **Create test account**. A developer with no account registers at → "הרשמה" (Register), then opens the test account from the dashboard as above. The "התנסות" (Try it out) button opens a shared demo, not your own sandbox: it has no keys of your own. The sandbox is free and asks for no signatures. - **Where the keys are:** **Admin → API & Integration** shows the MPL (`seller_payme_id`, with a test/production toggle), the public key, both base URLs and the Hosted Fields JSAPI credentials. If the page is missing, install the API service from the dashboard app store (חנות אפליקציות) first; depending on your account it may carry a charge. - **Payments API — production:** the same page in production mode. Sandbox and production are separate accounts with separate credentials: a sandbox key is rejected by `live.payme.io` and vice versa. - **Partner key (`payme_client_key`):** issued to partners by PayMe Partners (). It is never given to individual sellers, even for refunds — a seller refunds with `seller_payme_id` alone. - Questions about credentials: . ## Other APIs - **B2B Payments** uses the Payments API keys: [Hosts and authentication](/b2b-payments/contracts/overview#hosts-and-authentication). - **Keep** uses OAuth 2.0 client credentials: [Authorization Flow](/keep/partner-authorization/authorization-flow). - **Products & Customers** uses a JWT: [Hosts, Authentication and Errors](/products-and-customers/authentication/hosts-authentication-and-errors#authentication). ## Keeping credentials secret - Keep `seller_payme_id`, `payme_client_key`, the client password (called `payme_merchant_secret` in older PayMe documentation; see [Callbacks](/payments/getting-started/callbacks)) and `PayMe-Signature` on your **server**. Never put them in browser or mobile code, logs, or public repositories such as GitHub. - Only the public key belongs in browser code. The 3D Secure guide makes the same split: the browser call uses the public key, the hash-resolution call "should be called from your backend". - Store tokens securely and encrypted. ### If a key leaks There is no self-service key regeneration or rotation. If you believe a key has leaked, contact PayMe support immediately.