Skip to main content

Paylink Widget (@palpluss/paylink)

Embed a Palpluss payment link into any website as a modal overlay or inline iframe. The widget is pure browser-side — your backend language (Node.js, PHP, Python, Laravel, Django, etc.) does not matter.
@palpluss/paylink is a frontend-only browser package. It has no dependency on @palpluss/sdk and runs entirely in the visitor’s browser. Your server never handles raw payment credentials.

Every integration — whether you use the npm package, the CDN script, or a raw iframe — starts with a paylink ID. Here is how to generate one from the Palpluss Console. Log in to the Palpluss Console and click Create Pay Link in the left sidebar under the SERVICES section. You will see the Generate Pay Link form with the following fields: Click Advanced Options to set an expiry date or additional restrictions. Once you have filled in the values you need, click the Generate Pay Link button at the bottom of the form. A modal will appear confirming the link was created:

Step 3 — Copy only the ID

The full URL has this format:
You only need the ID portion — the UUID that comes after the last /. In the example above that is:
This is the value you pass to pay(), the <PalplussPayment> component, or the src attribute of the raw iframe:
You can click Preview in the modal to open the payment page in a new tab and confirm it looks correct before sharing it with customers.

How It Works

  1. pay() creates a modal overlay and injects an <iframe> pointing to https://link.palpluss.com/{id}?embed=1.
  2. The embedded page communicates back via window.postMessage.
  3. On success the Promise resolves with { txId, amount, phone }. On close/cancel it rejects.
The iframe origin is https://link.palpluss.com — your page never handles raw M-PESA credentials or STK callbacks.

Installation (JavaScript / TypeScript only)

If you use PHP, Python, Ruby, or any other server-side language, skip this section and jump directly to Any Backend — Raw iframe. The npm package is only needed for JavaScript/TypeScript projects.
React peer dependencies are only needed if you import @palpluss/paylink/react:

Quick Start

Get your paylink ID from the Palpluss Console → Payment Links.

API Reference

pay(paylinkId, options?)

Opens a full-screen modal containing the payment iframe. Returns a Promise<PaymentResult> that:
  • resolves when the customer completes payment
  • rejects with Error('Payment modal closed by user') when the modal is dismissed
PayOptions

openModal(paylinkId, options, resolve, reject)

Low-level function used internally by pay(). Exposed for advanced cases where you need direct control of the Promise lifecycle. Returns a cleanup() function that tears down the modal immediately.

<PalplussPayment> (React)

Import from @palpluss/paylink/react. Renders the payment iframe inline — no overlay, no modal — so you control layout and placement.
The iframe starts at minHeight: 560px and auto-resizes via RESIZE postMessage events.

Usage Examples (JavaScript / TypeScript)


Any Backend — Raw Iframe

This section is for PHP, Python, Ruby, Go, .NET, and any other server-side language. The @palpluss/paylink npm package is entirely optional — it is just a convenience wrapper around a standard <iframe>. You can embed the payment widget using plain HTML and a small <script> block in any templating engine, CMS, or static site.

How it works without the npm package

The paylink widget is an <iframe> hosted at https://link.palpluss.com/{paylink-id}?embed=1. The ?embed=1 query parameter tells the Palpluss page it is running inside an embedded context. Once loaded, the iframe sends two types of postMessage events back to your page: Your page listens for these messages and reacts accordingly. No SDK or npm package required.

Minimal HTML snippet

Replace abc-123 with your actual paylink ID from the Palpluss Console.
The allow="payment" attribute grants the iframe access to the Payment Request API in supporting browsers. It does not affect functionality in environments that don’t support it.

Framework examples

In your Blade template, output the paylink ID from your controller or config. Everything else is plain HTML:
Pass $paylinkId from your controller:

postMessage event reference

Your message event listener receives event.data with the following shapes:
Always check e.data.type before acting on a message. Other libraries on your page (analytics, chat widgets, etc.) also use postMessage and your listener will receive those events too.

Security note on postMessage

The iframe is served from https://link.palpluss.com. For production applications, validate the message origin before trusting the payload:

TypeScript Types


How the Modal Works Internally

When pay() is called:
  1. Overlay — a position: fixed; inset: 0 div with a semi-transparent backdrop is appended to document.body. z-index is set to 2147483647 (maximum) so it sits above everything.
  2. Card — a centered white card (max-width: 860px) holds the close button and the iframe.
  3. Iframe — src is https://link.palpluss.com/{id}?embed=1. The ?embed=1 query parameter tells the Palpluss page it is running inside an SDK modal.
  4. Body scroll lockdocument.body.style.overflow = 'hidden' while the modal is open, restored on cleanup.
  5. postMessage listener — listens for two event types from the iframe origin:
    • RESIZE — adjusts iframe.style.height for seamless auto-height.
    • PAYMENT_SUCCESS — extracts { txId, amount, phone }, calls onSuccess, removes the modal, resolves the Promise.
  6. Close handlers — the modal closes (and the Promise rejects) on:
    • Clicking the ✕ button
    • Clicking outside the card on the backdrop
    • Pressing Escape
  7. Cleanup — removes the overlay from the DOM, restores scroll, removes all event listeners.

Relation to @palpluss/sdk

These are completely independent. A typical full-stack integration uses @palpluss/sdk on the server to create the paylink, and then the paylink widget (or raw iframe) on the frontend to collect payment: