PrivMX DOCS
Swift

Messages

Threads allow the exchange of messages. In this section, let's take a closer look at the structure of messages and how to send them. We will also discuss some good practice when working with Threads.

About Messages

The structure of a message and a brief description of its elements is outlined in the following table:

fieldtypeencrypteddescription
databinaryyescontent of the message
infoServerInfonoadditional information assigned by the server e.g. author, creationDate, messageID and threadID
privateMetabinaryyesadditional information about the message
publicMetabinarynoadditional public information about the message, also accessible through PrivMX Bridge API

Define structure

Thread's architecture does not require you to use a specific data structure inside the messages. So before working with Threads, define what what kind of messages you want to send.

We recommend future-proofing your messages right from the start, i.e. choosing an easily modifiable format.

It is also a good idea to include its type and version in the structure of the message.

Here is an example message structure that you can use in your project.

JSON
{
    “data”:{
        “content”: "string", // string / binary data containing for example: markdown, html or json
    },
        “info”: "ServerInfo", // assigned by server,
        “publicMeta”:{
        “version”:number,
        “type”: “text”, // some kind of enum describing type of message like “event”, “html”,“markdown” etc.
    },
        “privateMeta”:{
        // meta fields
    }
}

Remember that it is only an example and you should consider your app's requirements and limitations.

Before working with messages, follow our Getting Started Guide. It will show you how to set up your project to work with PrivMX Bridge.

Sample code on this page is based on the initial assumptions.

All policies in the following examples can be build with Policy Builders, according to Policies overview.

Message data, publicMeta and privateMeta fields support any kind of data formats encoded to byte arrays. Examples in this section use JSON format serialization which is available directly in Swift.

Sending Messages

Example of sending a message in Plain Text:

Swift
let threadId = "SOME_THREAD_ID"
guard let messageData = "".data(using: .utf8) else {return}
// In this example, both publicMeta and privateMeta are empty.
let messageID = try? endpointSession?.threadApi?.sendMessage(
    in: threadId,
    withPublicMeta: Data(),
    withPrivateMeta: Data(),
    containing: messageData)

Using Message Metadata

Metadata fields inside messages make it easier to integrate Threads into new and existing projects. Threads are scheme agnostic by design, which makes them easy to integrate into any application. Metadata also allows developers to add any functionalities required by their app.

PrivateMeta

privateMeta includes additional sensitive information about the message. It's useful when we need to include the user's private data (personal information, activity details) in the message.

Like the content of the message itself, privateMeta is encrypted before sending. Since it is saved as binary data, you are free to choose any format. It can be a JSON parsed to a binary array or a more efficient binary format such as Protocol Buffers.

PublicMeta

Unlike privateMeta, publicMeta is not encrypted. It's useful when you want to include some additional info that does not require encryption.

publicMeta also does not have a specified structure and supports any binary format.

Example: Response To Another Message

Let's say that you need to implement replies to other messages inside a Thread using publicMeta.

When sending a message, include the ID of the message you want to reply to. Expanding on the example from the section on sending, it would look like that:

JSON
{
    "data":{
        "content": "string" // string / binary data containing for example: markdown, html or json
    },
    "info": "ServerInfo", // assigned by server,
    "publicMeta":{
        "version":"number",
        "type": “text”, // some kind of enum describing type of message like “event”, “html”,“markdown” etc.
        "responseTo":{messageID}
    },
}

When displaying the message in a chat, you will be able to find the message that was mentioned and display it according to the application's requirements.

Listing Messages

Your application may include multiple messages, each associated with different Threads. You can retrieve a list of all messages within a given Thread.

Define message item struct with decoded data and publicMeta. This time we use some decoding of Data fields and mapping generic message to struct used within developed App:

Swift
struct MessagePublicMeta:Codable{
    let responseTo: String
}
struct MessageData:Codable{
    let content: String
    let type: String
}
struct MessageItem:Codable{
    let messageId: String
    let publicMeta: MessagePublicMeta?
    let data: MessageData?
}

Listing the most recent messages in given Thread:

Swift
let threadId = "THREAD_ID"
let startIndex:Int64 = 0
let pageSize:Int64 = 100
    
guard let pagingList = try? endpointSession?.threadApi?
    .listMessages(
        from:threadId,
        basedOn: .init(skip: startIndex, limit: pageSize, sortOrder: .desc)) else {return}

let messages =
    pagingList.readItems.map {
        
        MessageItem(messageId: $0.id,
                publicMeta: try? JSONDecoder().decode(MessagePublicMeta.self, from: $0.publicMeta.getData() ?? Data()),
                data: try? JSONDecoder().decode(MessageData.self, from: $0.data.getData() ?? Data()))
        
    }

Modifying Messages

Depending on your project's specification, it may be necessary to modify a message. It could be e.g. changing message data, publicMeta, privateMeta. Each user with management rights is able to modify message.

Updating a message means overwriting it with the provided data. To successfully update a message, you must be the message creator or a Thread moderator.

Example of updating the message content:

Swift
var messageId = "MESSAGE_ID"
         
guard let message = try? endpointSession?.threadApi?
    .getMessage(messageId) else {return}
let newMessage = MessageData(content: "Hello World", type: "text")
guard let newMessageData = try?  JSONEncoder().encode(newMessage) else {return}
guard let privateMeta = message.privateMeta.getData() else {return}
guard let publicMeta = message.publicMeta.getData() else {return}

try? endpointSession?.threadApi?
    .updateMessage(message.id,
                    replacingData: newMessageData ,
                    replacingPublicMeta: privateMeta,
                    replacingPrivateMeta: publicMeta)

We use cookies on our website. We use them to ensure proper functioning of the site and, if you agree, for purposes such as analytics, marketing, and targeting ads.

PrivMX Endpoint Swift v2.6

This package is not up to date with the core documentation. Some of the features you've seen described in other parts of the documentation might not be mentioned here. Those changes do not influence compatibility, however

On this page

Messages | PrivMX Docs