Send web push

Add a Web Push action to an automation or broadcast, write your notification, and choose which of a person's browsers receive it.

Web push is turned on per account

Web push is available to accounts that Customer.io has turned it on for. If you don’t see a Web tab under Settings > Push, contact your account manager.

Before you send, set up web push on your website, so that the people you want to reach have web devices on their profiles.

Create a web push

  1. In your automation or broadcast workflow, drag a Web Push action into your workflow.
  2. Click the action to change its settings, like Sending behavior, Subscription preference, and action conditions. The Platform setting shows Web, because this action only sends to browsers.
  3. Click Add content to open the composer. Use the Rich Push editor. Customer.io doesn’t send Custom Payload messages to browsers.
  4. Fill in the notification fields.
  5. Choose which browsers receive the message in Device. See last used device or all devices.
  6. Click Send test… to test your message, then save it.

The preview shows a generic notification. Each browser draws notifications differently, so see what each browser shows before you rely on images or buttons.

Notification fields

FieldRequiredDescription
TitleRecommendedThe first line of the notification. Every browser shows it. Keep it short; most platforms show one or two lines. If you leave it blank, the notification’s title is “Customer.io”.
MessageYesThe body of the notification. Every browser shows it, but most platforms cut off long text.
ImageNoA large image. Only Chrome and Edge on Windows and Chrome on Android show it.
LinkNoThe https:// page that opens when someone clicks the notification. If you leave it blank, the notification opens your site’s home page.
Notification iconNoA small https:// image, like your logo, that appears beside your text. Safari doesn’t show it.
BadgeNoA small, single-color https:// image. Only Chrome on Android shows it, in the status bar. Use a shape on a transparent background; Android shows it as a silhouette.
Action buttonsNoUp to two buttons, each with a label of up to 32 characters and an optional https:// URL. A button without a URL opens your Link. Safari doesn’t show buttons.
Custom DataNoExtra key-value pairs with string values. Customer.io sends them with the notification as custom_data. The Customer.io service worker doesn’t display them; if you import our worker into your own, your code can read them.

Notification Sound doesn’t affect web push. App does: browsers aren’t tied to one of your apps, so keep your default app selected. Selecting another app excludes browsers. There is no website selector.

Browsers limit how much content a notification can carry. Below the action buttons, the composer shows how many bytes your web fields use, out of a budget of 3,179 bytes. The count is before Liquid renders, so leave room for personalized values. If a rendered notification is too large, Customer.io doesn’t send it to that browser.

Advanced options

Open Advanced options to change how browsers present your notification. Browser and operating system support varies: unsupported options can be ignored. Test on the browsers your audience uses; these settings don’t override notification permissions or Focus settings.

ControlHow to use it
Keep on screen until dismissedRequests that the notification stay visible until someone dismisses it. Browsers can ignore this request.
Silent (no sound or vibration)Requests a silent notification. Clear Vibration pattern (Android) before turning this on.
Replace earlier notification with the same tagGive related notifications the same tag to replace an earlier notification. Use 1–64 characters: A–Z, a–z, 0–9, _, ., :, or -. Liquid is allowed.
Alert again when replacingRequests another alert when replacing a notification. Set a tag first. Sound and vibration still depend on Silent and the browser’s settings.
Vibration pattern (Android)Enter milliseconds alternating vibration and pauses, like 200, 100, 200 (up to 10 values). Turn off Silent first. Other platforms can ignore vibration.
LanguageSet a language tag, like en or pt-BR. This describes the notification’s language; it doesn’t translate your text.
Text directionChoose Auto, Left to right, or Right to left. Browsers can ignore direction.
Show time (event time instead of arrival)Set the displayed time using Liquid that renders to epoch milliseconds or an ISO-8601 date. This doesn’t schedule delivery.
App badge count (Safari / Home Screen apps)Set a whole number from 0 to 99999, or Liquid that renders to one. 0 clears the badge. Requires browser support for app badges; this is separate from the Badge image above.

For an event-triggered order automation using the latest Liquid version, set the tag to order-{{ event.order_id | default: "general" }}. The fallback groups updates without an order ID under order-general; choose a fallback that fits your replacement behavior. Turn on Alert again when replacing if each update should request an alert. A rendered tag with unsupported characters, like spaces or #, is dropped along with Alert again when replacing; the notification still sends without replacement.

In Show time (event time instead of arrival), use the time of the event that triggered your automation:

LIQUID
{{ event_timestamp | times: 1000 }}

Customer.io event timestamps use seconds; multiplying by 1000 converts them to milliseconds. If you turn on Silent, leave the vibration pattern empty. Check receipt and replacement behavior on a real browser before sending to your audience.

Personalize with Liquid

You can use Liquid in every field, including the URLs. When Customer.io sends a notification, it renders each field and checks that the icon, badge, and button URLs start with https://. If one of them doesn’t, Customer.io removes that field and sends the rest.

A Liquid error stops the notification

If a field uses a variable that doesn’t exist for the person or the event, like {{event.request_id}}, Customer.io doesn’t send the notification, while your website and data integration report no errors. What happens depends on the field:

  • Notification icon, Badge, Action buttons, Replace earlier notification with the same tag, Show time (event time instead of arrival), and App badge count (Safari / Home Screen apps) only go to browsers. If one of them doesn’t render, Customer.io doesn’t send the notification to browsers and retries the delivery with WEBPUSH_RENDER_FAILED, in case the data arrives in the meantime. If it still doesn’t render, the delivery fails.
  • Title, Message, Image, Link, and Custom Data are the same fields that app push uses (app push calls Link Deep Link or Web URL). If one of them doesn’t render, Customer.io doesn’t send the notification, and the delivery fails with a Liquid error, like any other push message.

Make sure your event or person always has every variable your message uses, or give optional variables a fallback. On the latest Liquid version, use the default filter. With legacy Liquid, use if/else fallbacks. For example, on the latest version:

LIQUID
https://example.com/bookings/{{ event.request_id | default: "" }}

Last used device or all devices

The Device setting decides which eligible browsers on a profile receive the message, subject to the selected App.

  • Last used device (default) sends to one browser: the person’s most recently used web device. Customer.io only picks among the person’s browsers, so their iOS and Android devices don’t count. Registering or updating a browser’s device updates its last_used time. The plugin re-registers when the subscription, signed-in person, or device metadata changes, including a new browser major version. Upgrading to SDK 0.7.0 also re-registers existing subscribers once on their next identified visit to record the site origin. An unchanged site visit doesn’t otherwise need to re-register or update last_used.
  • All profile devices sends to every eligible browser on the profile, subject to the selected App. Use it when people should get the notification in every browser they’ve turned on alerts in, like a laptop and a work computer.

For more about these options, see choose which devices receive your message.

Only web push actions send to browsers

A Push Notification action with Platform set to iOS & Android sends to a person’s iOS and Android devices, not their browsers. To reach browsers, add a web push action. Last used device picks within the action’s platform, so a person’s newest browser never takes the place of their phone for a mobile push, and their phone never takes the place of their browser for a web push.

Test your message

Click Send test… in the composer and paste your browser’s subscription JSON. To get it, sign in to your site in the browser you want to test, open your browser’s JavaScript console, and run:

JAVASCRIPT
JSON.stringify(await cioanalytics.webPush.subscription())

Use the test to check that the notification appears and clicking it opens your link. Settings and composer test sends check the push relay without creating a real automation delivery. They don’t create an automation Sent tab entry or automation delivery metrics. To verify those, trigger a real test automation as described in test your setup.

The test uses your Sample data to render Liquid. If a field doesn’t render, the dialog tells you which variable is missing. Fix it before you send to your audience, because a field that doesn’t render stops the notification for real recipients too.

Transactional push doesn’t reach browsers

Transactional push messages go to a person’s iOS and Android devices only. To send push to browsers, use a web push action in an automation or broadcast.

Metrics

Web push uses the same push metrics as app push:

  • Sent: Customer.io handed the notification to the browser’s push service.
  • Delivered: The Customer.io service worker showed the notification. A browser that couldn’t receive the notification right away reports delivered when it shows the notification, if the push service still holds it.
  • Opened: Someone clicked the notification or one of its buttons.
Updated October 22, 2026