A2U (App-to-User) API
Updated: Jul 31, 2026
Copy for LLM
The A2U (App-to-User) API lets you send notifications to your players directly from your backend server using the Facebook Graph API.
A2U notifications are one of the most effective re-engagement tools available because they reach players where they already are: on Facebook. A well-timed, relevant notification can bring a lapsed player back into your game at exactly the right moment.
This API identifies the recipient by their player ID (
FBInstant.player.getID()) and is called on your app node with an app access token. Because it does not depend on an App Scoped User ID, it works for all of your players -- including users who onboarded entirely in a Zero Permissions environment. It replaces the older endpoint that identified players by App Scoped User ID; new integrations should use the player-ID API described here.This guide covers what A2U notifications are, how they differ from other notification channels, the API endpoint and parameters, scheduling, deep linking, bot messages, use cases, rate limits, and policies.
What Are A2U Notifications?
A2U notifications are server-initiated messages from your game to specific players. Unlike Custom Updates (which are sent from within the game client during a play session) or Game Updates via Messenger (which are delivered through Messenger only), A2U notifications are:
- Sent from your backend server using the Facebook Graph API
- Triggered by server-side logic (not by in-game player actions)
- Targeted to a specific player by their player ID
- Delivered across multiple channels -- the Facebook notifications jewel, the on-platform game notifications, and Messenger bot messages
A single call attempts delivery across the available channels; the actual channels used are subject to further filtering by Meta to protect the player experience.
How A2U Differs from Other Channels
| Aspect | A2U API | Custom Updates | Game Updates (Messenger) |
|---|---|---|---|
Origin | Your backend server | Game client (SDK) | Your backend server (Messenger API) |
Delivery | Facebook notifications + Messenger | In-game conversation/context | Messenger inbox |
Trigger | Server-side event or schedule | Player action in-game | Server-side event or schedule |
Recipient | Player ID | Current session | Player ID |
Content | Title, body, optional image or bot template | Rich image, text, CTA, data | Rich templates, images, buttons |
Setup | Graph API + app access token | SDK call | Messenger bot + webhook |
Sending Notifications
Send a notification by making a
POST request to your app’s notifications edge with an app access token.API Endpoint
POST https://graph.fb.gg/{app-id}/notifications
Authenticate the request with your app access token.
Request Parameters
| Parameter | Required | Description |
|---|---|---|
player_id | Yes | The recipient’s player ID, obtained in the client with FBInstant.player.getID(). |
message | Yes | The notification content, as a JSON object (see Message Object below). |
label | No | A label used to group similar notification types together. Useful for organizing and filtering notifications. |
payload | No | Custom data (JSON) attached to your game’s URL. It is available when the player opens your game from the notification. See Deep Linking with payload. |
schedule_interval | No | Delay, in seconds, before the notification is sent. Must be between 300 (5 minutes) and 2592000 (30 days). Omit it (or send 0) to deliver immediately. See Scheduling Notifications. |
bot_message_payload_elements | No | Advanced configuration for the Messenger bot message. See Bot Messages. |
Message Object
The
message parameter is a JSON object with the following fields:| Field | Required | Description |
|---|---|---|
title | Yes | The notification title. |
body | Yes | The notification body text. |
media_url | No | A URL to an image shown with the notification. Recommended for Messenger bot messages when you are not supplying bot_message_payload_elements; the jewel and on-platform notifications render from title and body. |
Basic Example
curl -X POST "https://graph.fb.gg/{app-id}/notifications" \
-H "Content-Type: application/json" \
-d '{
"access_token": "{app-access-token}",
"player_id": "{player-id}",
"message": {
"title": "Your energy is full!",
"body": "Come back and play -- your lives have recharged.",
"media_url": "https://www.example.com/img/energy_full.png"
},
"label": "energy_full",
"payload": "{\"screen\":\"gameplay\",\"ref\":\"energy_full\"}"
}'
// Node.js example async function sendNotification(appId, appAccessToken, playerId, message, options = {}) { const response = await fetch(`https://graph.fb.gg/${appId}/notifications`, { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ access_token: appAccessToken, player_id: playerId, message, // { title, body, media_url? } label: options.label, payload: options.payload, // JSON string of custom launch data schedule_interval: options.scheduleInterval, // seconds, optional }), }); return await response.json(); }
Response
On success, the endpoint returns the created notification’s ID:
{ "success": true, "notification_id": "1234567890" }
Scheduling Notifications
To schedule a notification for the future instead of sending it immediately, set
schedule_interval to the number of seconds from now that the notification should be delivered.- Range:
300(5 minutes) to2592000(30 days). - Pending limit: A maximum of 5 pending scheduled notifications per recipient. Additional scheduled sends for that player are rejected until some are delivered.
- Omitting
schedule_interval(or setting it to0) sends the notification immediately.
// Remind the player to return in 4 hours await sendNotification(APP_ID, APP_ACCESS_TOKEN, playerId, { title: 'Your daily reward is waiting!', body: 'Log in to claim it before it expires.', }, { label: 'daily_reward', scheduleInterval: 4 * 60 * 60, // 14400 seconds });
Note: Canceling a scheduled notification is not currently available on this endpoint.
Deep Linking with payload
Use the
payload parameter to deep-link the player to a specific screen or action in your game. Provide a JSON string; when the player opens your game from the notification, read it in the client with FBInstant.getEntryPointData().async function handleNotificationEntry() { await FBInstant.initializeAsync(); const entryPointData = FBInstant.getEntryPointData(); if (entryPointData) { const data = typeof entryPointData === 'string' ? JSON.parse(entryPointData) : entryPointData; switch (data.ref) { case 'energy_full': showGameplayScreen(); break; case 'daily_reward': showDailyRewardScreen(); break; case 'tournament_start': showTournamentLobby(); break; default: showMainMenu(); } } else { showMainMenu(); } await FBInstant.startGameAsync(); }
Bot Messages
When a notification is delivered as a Messenger bot message, you can control its appearance in two ways:
Advanced bot templates
Set
bot_message_payload_elements to send a richer Messenger XMA instead of the standard message built from title and body. This field takes the elements array from the Messenger generic template format.Personalized content with user information
In a Zero Permissions environment you cannot access player profile data (name, photo) directly. Instead, use the SDK to create reusable notification content that renders an image overlay with user data resolved server-side, then reference it when sending.
Use
FBInstant.player.createNEZPNotificationContentAsync() to generate the content and receive a notification_content_id:const notificationContentId = await FBInstant.player.createNEZPNotificationContentAsync({ imageOverlayPath: 'ig_views/profile_view.xml', pathToCSS: 'ig_views/styles.css', initialData: { wordSubmitted: 'APPLE' }, notificationTitle: ' just took their turn!', notificationSubtitle: 'It is your turn now!', recipients: ['6719542978151885'], });
Then send the notification by including
notification_content_id (as message’s stored-content reference) with the player_id. The player_id must be one of the recipients specified in the SDK call.For the full API reference, see FBInstant.player.
Use Cases
A2U notifications are most effective when they are relevant to the specific player receiving them. Common use cases include:
- Re-engage lapsed players: “Your energy is full,” “Your daily reward is waiting,” or a comeback bonus after several days of inactivity.
- Social and friend activity: “A friend just beat your high score,” “A friend joined the Weekend Challenge,” or “A friend started playing.”
- Time-sensitive events: A tournament starting, a limited-time event, or expiring in-game resources.
- Scheduled reminders: Streak reminders or daily-login nudges, delivered with
schedule_interval. - Turn-based prompts: “It is your turn” messages, personalized with user information through bot messages.
Segment your player base and send targeted notifications rather than the same generic message to everyone -- irrelevant notifications lead to higher opt-out rates.
Rate Limits and Policies
Rate Limits
Facebook enforces rate limits on A2U notifications to protect the player experience:
- Per-player limits: You can send a limited number of notifications to each individual player within a given time window. Exceeding this limit results in the notification being rejected.
- Per-app limits: Your app has an overall daily notification budget across all players. This budget scales with your app’s active user count.
- Throttling: If you send a large volume of notifications in a short period, the API may throttle your requests. Implement backoff logic and spread sends over time.
Content Policies
- Relevance: Notifications must be relevant to the player’s game activity. Do not send marketing messages, promotional content for other apps, or unrelated information.
- Accuracy: Notification content must be truthful and accurately represent what the player will find when they open the game.
- No deception: Do not use misleading language to trick players into opening the game.
- Compliance: All notifications must comply with Facebook’s Platform Policies and Advertising Policies.
Violating notification policies can result in throttling, your app being flagged for review, or, in severe cases, suspension from the platform.
Error Handling
async function sendNotificationWithErrorHandling(appId, appAccessToken, playerId, message) { try { const response = await fetch(`https://graph.fb.gg/${appId}/notifications`, { method: 'POST', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ access_token: appAccessToken, player_id: playerId, message, }), }); const data = await response.json(); if (data.error) { switch (data.error.code) { case 4: console.warn('Rate limited. Retry later with backoff.'); break; case 100: console.error('Invalid parameter:', data.error.message); break; default: console.error('Notification error:', data.error); } } return data; } catch (error) { console.error('Network error:', error); return null; } }
Next Steps
- Notification Best Practices -- Consolidated best practices across all notification channels.
- Notification Guidelines -- Content formatting and quality criteria for notification messages.
- Notification Service -- Set up notifications with no code through the App Dashboard.
- Game Updates via Messenger -- Send rich, interactive messages through Messenger.
- Notifications Overview -- Compare all notification channels.
- Custom Updates -- Send in-game updates and messages from the game client.