Notifications & consent
Your app decides what to tell customers; the customer decides how they may be reached. These calls let a signed-in customer see and change their marketing consent, and let your mobile app register the device that receives push messages.
Who calls these#
The consent calls and the device registration act on the customer signed in to the session, and on nobody else: any customer id in the body is ignored. They need a signed-in customer's token in Authorization: Bearer; see Sessions & sign-in.
How consent works#
- Master consent is one switch for all marketing. When it is off, no channel is used for marketing.
- Channel consent refines it per channel:
email,sms,pushandviber, eachgrantedorrevoked. A channel the customer never set follows the master switch. - Effective is what counts: a channel may be used when the master switch is on and the channel is granted.
- Every change is recorded with its source, so you can show when and how consent was given. Changes from these calls have the source
mobile_app.
The consent object#
What every consent call returns in data.
| Field | Description |
|---|---|
| masterboolean | The master marketing consent. |
| channelsobject | One entry per channel, email, sms, push and viber. |
| channels.<channel>.statestring | granted or revoked. granted when the customer never set it. |
| channels.<channel>.effectiveboolean | Whether the channel may be used for marketing now. |
| channels.<channel>.source, changed_atnullable | Where and when the channel was last changed. null when it never was. |
| preferredobject | The channel the customer prefers to be reached on: notification_channel_id, and source, auto or manual. |
| viber_subscribedboolean | Whether the customer follows your Viber channel. |
| given_atdatetime · ISO 8601, UTC | The most recent consent change, or when the customer registered if nothing changed since. |
Read and change consent#
Three calls behind a consent screen. Each returns the whole consent object, so you can redraw the screen from the answer.
| Call | Description |
|---|---|
| GET /customer/consents | The customer's consent. |
| PUT /customer/consent | Sets one channel. Body: channel (email, sms, push or viber) and state (granted or revoked). Setting a channel to the state it already has changes nothing. |
| PUT /customer/consents/master | Sets the master consent. Body: state, granted or revoked. |
Errors
| Status | When |
|---|---|
| 401 | The token is not a signed-in customer's. |
| 422 | API.CustomerChannelConsents.CustomerRequired: the session has no customer. API.CustomerChannelConsents.InvalidChannel or InvalidState: the value is not one of the allowed ones; fields names it. |
curl -X PUT "https://api.morffeus.com/api/v2/customer/consent" \ -H "Authorization: Bearer $SESSION_TOKEN" \ -H "Content-Type: application/json" \ -d '{ "channel": "sms", "state": "revoked" }'
{
"data": {
"master": true,
"channels": {
"email": {
"state": "granted",
"effective": true,
"source": null,
"changed_at": null
},
"sms": {
"state": "revoked",
"effective": false,
"source": "mobile_app",
"changed_at": "2026-10-01T10:02:11"
},
"push": { … },
"viber": { … }
},
"preferred": { "notification_channel_id": null, "source": "auto" },
"viber_subscribed": false,
"given_at": "2026-10-01T10:02:11"
}
}
{
"errors": {
"CustomerChannelConsents": ["API.CustomerChannelConsents.InvalidChannel"],
"fields": { … }
}
}
Register the device for push#
Tells us which push token reaches the signed-in customer on this device. Call it after sign-in and whenever the push provider gives your app a new token. The device is the one your app named when it started the session, and the customer is the session's.
Body parameters
| Parameter | Description |
|---|---|
| notification_devicerequiredobject | The device. |
| notification_device.messaging_tokenrequiredstring | The push token from Firebase Cloud Messaging. |
| notification_device.notification_channel_idrequiredinteger | The push channel: 3. |
| notification_device.device_type, device_vendor, mobile_info | Optional details about the device. |
Sending the same push token again updates the device rather than adding one, and older copies of that token for the customer are removed.
Returns
data: the device as stored.
POST /api/v2/session/firebase/token with firebase_token stores the push token on the current session token instead. It answers 204, or 422 with API.Tokens.Firebase.UnableToUpdate.
curl -X PUT "https://api.morffeus.com/api/v2/notification_device" \ -H "Authorization: Bearer $SESSION_TOKEN" \ -H "Content-Type: application/json" \ -d '{ "notification_device": { "messaging_token": "fcm-token-from-the-device", "notification_channel_id": 3 } }'
Related#
- Sessions & sign-in: the session token these calls carry.
- Account & addresses: the rest of the customer's profile.