DEV Community

Cover image for Twilio Conversations client resilient setup
Esteban
Esteban

Posted on

1 1

Twilio Conversations client resilient setup

With Twilio Conversations SDK 2.0 release there is a new way of creating the client and setting up the event handlers. As stated in the documentation and contrary to previous versions, when the client is created in order to guarantee it has been properly initialized we must wait for the stateChanged event to fire and check the passed state to verify the initialization was completed:

import { Client } from '@twilio/conversations';

const client = new Client(token);

// Before you use the client, subscribe to the `'stateChanged'` event and wait 
// for the `'initialized'` state to be reported.
client.on('stateChanged', (state) => {
  if (state === 'initialized') {
    // Use the client
  }
}
Enter fullscreen mode Exit fullscreen mode

What if we have a momentarily unreliable connection? Simply by changing the network quality in Chrome's network tab to Slow the Twilio Client refused to initialize and that was it.

In order to make the process a bit more resilient I wrote a function that wraps the initialization event inside a promise that resolves when the client is successfully initialized and tries to recreate the client using an exponential backoff promise otherwise.

//wait is a helper function that will wait a given number of seconds.
const wait = (ms) => new Promise((res) => setTimeout(res, ms));

const createTwilioClientWithRetries = (token, depth = 0) => {
    return new Promise((resolve, reject) => {
        //Create a new Twilio Client for the token.
        const twilioClient = new Client(token);

        twilioClient.on('stateChanged', async (state) => {
            try {
                if (state === 'initialized') {
                    resolve(twilioClient);
                }
                if (state === 'failed') {
                    if (depth > 5) {
                        throw new Error("Too many retries");
                    }
                    else {
                        dispatch(setError({
                            type: TWILIO_TOKEN_FAILURE,
                            message: "Twilio Token Error"
                        }));
                        await wait(2 ** depth * 10);
                        return await createTwilioClientWithRetries(token, depth + 1);
                    }
                }
            } catch (err) {
                reject("Too many retries");
            }
        });         
    });
}
Enter fullscreen mode Exit fullscreen mode

Initially I tried to shut the client down with await twilioClient.shutdown() before calling the next iteration but it would prevent me from creating any further instances of the client afterwards for some reason.

Have fun!

Permalink: https://www.estebansastre.com/create-twilio-client-join-conversation/

Sentry blog image

How to reduce TTFB

In the past few years in the web dev world, we’ve seen a significant push towards rendering our websites on the server. Doing so is better for SEO and performs better on low-powered devices, but one thing we had to sacrifice is TTFB.

In this article, we’ll see how we can identify what makes our TTFB high so we can fix it.

Read more

Top comments (0)

Billboard image

The Next Generation Developer Platform

Coherence is the first Platform-as-a-Service you can control. Unlike "black-box" platforms that are opinionated about the infra you can deploy, Coherence is powered by CNC, the open-source IaC framework, which offers limitless customization.

Learn more

👋 Kindness is contagious

Please leave a ❤️ or a friendly comment on this post if you found it helpful!

Okay