Hey, there fellow developers ...
In this example, I'll demonstrate how to create a simple messaging app to engage users on your website, this is important for support websites, eCommerce stores, social media websites, and many more scenarios.
We'll be using the real-time APIs to publish messages. On the backend, store the message in a database for future reference then publish the message to the user's channel. Example:
// Theoratical users
const john = {
name: 'John',
id: 'random-text-1'
}
const ahmad = {
name: 'Ahmad',
id: 'random-text-2'
}
Now to communicate with each other, ideally, when John visits my profile, you need to check MY settings if I accept non-friends messages and that John isn't blocked by me. (not included in the example, let me know if you're interested to know how).
Then, once John clicks "Message Ahmad", a chat window will be opened based on my ID, and you'll need to subscribe John to my messages' channel as well as his.
Prepare the environment
import wixRealtime from 'wix-realtime';
const messages = []; // Storing the conversation messages locally.
1. Add a messages listener.
In this step, we'll handle the messages sent by me "Ahmad" to John.
// Subscribe to my channel
const ahmadChannel = { name: 'user-messages', resourceId: `msg-${ahmad.id}` }
wixRealtime.subscribe(ahmadChannel, (notification, channel) => {
/* All received messages from "Ahmad" are meant for John, we can
control that later on */
const message = {
_id: notification.payload.id, // a unique message identifier
origin: 'forign', // Determain who own the message.
date: new Date(), // The date that the message was received on.
message: notification.payload.message // The actual mesage
}
// Add the message to the messages array
messages.push(message);
// Update the repeater displayed messages:
$w('#repeaterMsgs').data = messages;
})
2. Allow John to receive his messages on other devices.
Most of the time, you'll have more than one device opened, say for example on your computer and your phone, this will ensure that whatever John sends me from his computer will also appear on the conversation on his phone.
/* Subscribe to John messages. This is important because we want other tabs/pages
that the website is opened on to listen to the messages and display them as well,
so when John sends a message to me from his laptop, the message will also appear
on his phone or computer. */
const myChannel = { name: 'user-messages', resourceId: `msg-${john.id}` }
wixRealtime.subscribe(myChannel, (notification, channel) => {
/* All received messages from the user himself, but we need to check whether
the message is sent from this device/tab/window or not */
if (messages.map(items => items._id).indexOf(notification.payload.id) === -1) {
// Store the message and display it
const message = {
_id: notification.payload.id, // a unique message identifier
origin: 'me', // Determain who own the message.
date: new Date(), // The date that the message was received on.
message: notification.payload.message // The actual mesage
}
// Add the message to the messages array
messages.push(message);
// Update the repeater displayed messages:
$w('#repeaterMsgs').data = messages;
} else {
// Ignore the message because it's already here.
}
})
3. Allow John to send messages (Backend & Frontend).
To allow John to send me a message, we need a backend module and a frontend app.
A) Prepare the backend function that will publish the messages:
import wixRealtimeBackend from 'wix-realtime-backend';
export function sendMessage(message, toId) {
// Specify the user channel
const channel = { name : 'user-messages', resourceId: `msg-${toId}`};
// Prepare the payload
const payload = {
id: String(Math.floor(Math.random() * 10000)),
message: message
}
// Prepare the payload options
const payloadOptions = {
users: [toId],
includePublisher: true
}
*/ users: List of users to receive the message, in our case only one person
should receive it, which is the specified person */
// Publish the message to the specified recipants
return wixRealtimeBackend.publish(channel, payload, payloadOptions) .then(() => {
// You can store the message in a database here
return Promise.resolve();
});
}
In this step, you can store the messages in a database to view them on tabs opened later, see when it's delivered, seen, and more. (Not included in the example).
B) Now prepare the frontend app to send the message, we'll create a function that will be triggered when the user clicks on "Send" or hit "Enter".
// Import our backend function, make sure to replace the module below with your module name
import chat from 'backend/myModule.jsw';
function send(message) {
// Check if there's something to send or not.
if (typeof message === 'string' && message.length > 0) {
// Add the message to the messages array
messages.push(message);
// Update the repeater displayed messages:
$w('#repeaterMsgs').data = messages;
// Send the message
return chat.sendMessage(message).then(() => {
// Handle the case where the message is successfully sent
}).catch(err => {
console.error(err);
// Mark the failed message as "not sent" with red marker or something.
})
}
}
$w('messageInputBox').onInput(event => {
// Enable the "Send" button if there's a message and disable it if otherwise
if (event.target.value) {
if (!$w('sendBtn').enabled) { $w('sendBtn').enable() }
} else {
if ($w('sendBtn').enabled) { $w('sendBtn').disable() }
}
})
// Trigger the the function to send the message.
$w('sendBtn').onClick(() => send($w('messageInputBox').value));
$w('messageInputBox').onKeyPress((event) => {
if (event.key === 'Enter') {
// Check if the user wants to send the message or create a new line
if (event.shiftKey) {
// Create a new line
$w('messageInputBox').value = `${$w('messageInputBox').value}\n`;
} else {
// Disable the text input
$w('messageInputBox').disable().then(() => send($w('messageInputBox').value));
}
}
})
Here you have it, folks, if you have any questions feel free to ask in the comments below, if you want to request a tutorial about this topic you can do that too.
Take a look at my previous tutorials videos.
Hope this was helpful~!
@Ahmad Can you give a live website link where you implemented this? Please?
Can this be used dynamically?
Hi,
I can not load the full page.
Interesting stuff --> like always! Thumbs up!
👍🙏🔥