# Message A `Message` represents an individual message that is sent to or received from Ably. Messages are published through a channel's [`publish()`](https://ably.com/docs/pub-sub/api/javascript/rest/channel.md#publish) method and retrieved via [`history()`](https://ably.com/docs/pub-sub/api/javascript/rest/channel.md#history). #### Javascript ``` const result = await channel.history(); const message = result.items[0]; console.log(message.name, message.data); ``` ## Properties The `Message` interface has the following properties: | Property | Description | Type | | --- | --- | --- | | name | The event name, if provided. | String | | data | The message payload, if provided. | String, JSON Object, or Buffer | | extras | Metadata and/or ancillary payloads, if provided. Valid payloads include [`push`](https://ably.com/docs/push/publish.md#payload), [`headers`](https://ably.com/docs/channels.md#metadata) (a map of strings to strings for arbitrary customer-supplied metadata), [`ephemeral`](https://ably.com/docs/pub-sub/advanced.md#ephemeral), and [`privileged`](https://ably.com/docs/platform/integrations/skip-integrations.md). | JSON Object | | id | A Unique ID assigned by Ably to this message. | String | | clientId | The client ID of the publisher of this message. | String | | connectionId | The connection ID of the publisher of this message. | String | | connectionKey | A connection key, which can optionally be included for a REST publish as part of the [publishing on behalf of a realtime client functionality](https://ably.com/docs/pub-sub/advanced.md#publish-on-behalf). | String | | timestamp | Timestamp when the message was first received by the Ably, as milliseconds since the epoch. | Integer | | encoding | This will typically be empty as all messages received from Ably are automatically decoded client-side using this value. However, if the message encoding cannot be processed, this attribute will contain the remaining transformations not applied to the `data` payload. | String | | action | The action type of the message. |
| | serial | A server-assigned identifier that will be the same in all future updates of this message. It can be used to add [annotations](https://ably.com/docs/messages/annotations.md) to a message or to [update or delete](https://ably.com/docs/messages/updates-deletes.md) it. Serial will only be set if you enable annotations, updates, deletes, and appends in [rules](https://ably.com/docs/channels.md#rules). | String | | annotations | An object containing information about annotations that have been made to the object. |
| | version | An object containing version metadata for messages that have been [updated or deleted](https://ably.com/docs/messages/updates-deletes.md). |
|
| Value | Description | | --- | --- | | MESSAGE_CREATE | A new message was created. The value is `message.create`. | | MESSAGE_UPDATE | A message was updated. The value is `message.update`. | | MESSAGE_DELETE | A message was deleted. The value is `message.delete`. | | META | A meta-message from the Ably system. The value is `meta`. | | MESSAGE_SUMMARY | A summary of annotations for a message. The value is `message.summary`. | | MESSAGE_APPEND | A message was appended to an existing message. The value is `message.append`. |
| Property | Description | Type | | --- | --- | --- | | summary | An object whose keys are [annotation types](https://ably.com/docs/messages/annotations.md#annotation-types) and whose values are aggregated [annotation summaries](https://ably.com/docs/messages/annotations.md#annotation-summaries) for that annotation type. The structure of each value depends on the summarization method, for example a `total.v1` entry has a `total` field, while a `flag.v1` entry has `total` and `clientIds` fields. Always populated for a `message.summary` action and may be populated for any other action (in particular, a message retrieved from history will have its latest summary included). | `Record`>` |
| Shape | Description | Type | | --- | --- | --- | | SummaryClientIdList | The summary entry for `flag.v1`, and the per-name value for `distinct.v1` and `unique.v1`. |
| | SummaryDistinctValues | The summary entry for `distinct.v1`, an object mapping each name to a `SummaryClientIdList` value. | `Record` | | SummaryUniqueValues | The summary entry for `unique.v1`, an object mapping each name to a `SummaryClientIdList` value. | `Record` | | SummaryMultipleValues | The summary entry for `multiple.v1`, an object mapping each name to a summary client ID counts value. | `Record`>` | | SummaryTotal | The summary entry for `total.v1`. |
|
| Property | Description | Type | | --- | --- | --- | | total | The total number of clients who have published an annotation with this name (or type, depending on context). | Number | | clientIds | A list of the clientIds of all clients who have published an annotation with this name (or type, depending on context). | `String[]` | | clipped | Whether the list of clientIds has been clipped due to exceeding the maximum number of clients. | Boolean |
| Property | Description | Type | | --- | --- | --- | | total | The sum of the counts from all clients who have published an annotation with this name. | Number | | clientIds | A map from clientIds to the count each of those clients has contributed. | `Record` | | totalUnidentified | The sum of the counts from all unidentified clients who have published an annotation with this name, and so who are not included in the `clientIds` map. | Number | | clipped | Whether the `clientIds` map has been clipped due to exceeding the maximum number of clients. | Boolean | | totalClientIds | The total number of distinct identified clients (equal to the size of `clientIds` if `clipped` is false). | Number |
| Property | Description | Type | | --- | --- | --- | | total | The total number of annotations of this type that have been published for the message. | Number |
| Property | Required | Description | Type | | --- | --- | --- | --- | | serial | Optional | An Ably-generated ID that uniquely identifies this version of the message. Can be compared lexicographically to determine version ordering. For an original message with an action of `message.create`, this will be equal to the top-level `serial`. | String | | timestamp | Optional | The time this version was created (when the update or delete operation was performed). For an original message, this will be equal to the top-level `timestamp`. | Integer | | clientId | Optional | The client identifier of the user who performed the update or delete operation. Only present for `message.update` and `message.delete` actions. | String | | description | Optional | Optional description provided when the update or delete was performed. Only present for `message.update` and `message.delete` actions. | String | | metadata | Optional | Optional metadata provided when the update or delete was performed. Only present for `message.update` and `message.delete` actions. | `Record` |
## Create a message from an encoded object `Message.fromEncoded(JsonObject: any, channelOptions?: ChannelOptions): Promise` A static factory method to create a `Message` from a deserialized `Message`-like object encoded using Ably's wire protocol. The returned promise resolves with the decoded message. ### Javascript ``` const message = await Ably.Rest.Message.fromEncoded(encodedMsg); ``` ### Parameters The `Message.fromEncoded()` method takes the following parameters: | Parameter | Required | Description | Type | | --- | --- | --- | --- | | JsonObject | Required | A `Message`-like deserialized object. | Any | | channelOptions | Optional | If you have an encrypted channel, use this to allow the SDK to decrypt the data. | [ChannelOptions](https://ably.com/docs/pub-sub/api/javascript/rest/channels.md#get) |
### Returns `Promise` Returns a promise. The promise is fulfilled with the decoded message, typed `InboundMessage`: a `Message` whose `id`, `timestamp`, `action`, `version`, and `annotations` fields are guaranteed to be present. The promise is rejected with an [`ErrorInfo`](https://ably.com/docs/pub-sub/api/javascript/rest/rest-client.md#errorinfo) object if the object cannot be decoded. ## Create messages from an encoded array `Message.fromEncodedArray(JsonArray: any[], channelOptions?: ChannelOptions): Promise` A static factory method to create an array of `Message` objects from an array of deserialized `Message`-like objects encoded using Ably's wire protocol. The returned promise resolves with the decoded messages. ### Javascript ``` const messages = await Ably.Rest.Message.fromEncodedArray(encodedMsgs); ``` ### Parameters The `Message.fromEncodedArray()` method takes the following parameters: | Parameter | Required | Description | Type | | --- | --- | --- | --- | | JsonArray | Required | An array of `Message`-like deserialized objects. | `Any[]` | | channelOptions | Optional | If you have an encrypted channel, use this to allow the SDK to decrypt the data. | [ChannelOptions](https://ably.com/docs/pub-sub/api/javascript/rest/channels.md#get) |
### Returns `Promise` Returns a promise. The promise is fulfilled with an array of decoded messages, typed `InboundMessage` as for [`fromEncoded()`](#from-encoded-returns). The promise is rejected with an [`ErrorInfo`](https://ably.com/docs/pub-sub/api/javascript/rest/rest-client.md#errorinfo) object if the array cannot be decoded. ## Related Topics - [Channels](https://ably.com/docs/pub-sub/api/javascript/rest/channels.md): API reference for the Channels interface in the Ably Pub/Sub JavaScript REST SDK. - [Channel](https://ably.com/docs/pub-sub/api/javascript/rest/channel.md): API reference for the Channel interface in the Ably Pub/Sub JavaScript REST SDK. - [ChannelDetails](https://ably.com/docs/pub-sub/api/javascript/rest/channel-details.md): API reference for channel metadata (ChannelDetails) in the Ably Pub/Sub JavaScript REST SDK. - [RestAnnotations](https://ably.com/docs/pub-sub/api/javascript/rest/rest-annotations.md): API reference for message annotations (the RestAnnotations interface) in the Ably Pub/Sub JavaScript REST SDK. ## Documentation Index To discover additional Ably documentation: 1. Fetch [llms.txt](https://ably.com/llms.txt) for the canonical list of available pages. 2. Identify relevant URLs from that index. 3. Fetch target pages as needed. Avoid using assumed or outdated documentation paths.