11 min read
.
on Dec 17, 2020
This tutorial will demonstrate how to build chat for live event applications using components in React.

Live events need chat to keep users engaged, but it’s often a challenge to build a chat solution that works at scale and can handle traffic load surges that occur during popular events. Modular chat kits, powered by PubNub, provide a specific solution to create chat for live events that will work at any scale, without channel or concurrency limitations. The components in our Live Event Chat Kit are optimized for the needs of most live event applications. And since the kit is modular, you can enable and disable components and customize the CSS to the needs of your application.

This tutorial will demonstrate how to build chat for live event applications using components in React. With React you can group many UI objects into one component, so you can easily build live event chat into your application with just a few components instead of dozens of UI elements. Using components for chat will enable you to create a robust chat application that can be modified easily and reused.

Live Event Chat

An example of how you can use PubNub components to build chat for live events.

Each of the live event chat components in our kit are created to be easy to reuse in another React application, customizable, and expandable for your unique needs. Modifying the components is as easy as editing the layout and CSS of the open source chat components. This tutorial and these components can be used as a seed project to make a high performance chat for live events. 

What backend API works best for live event chat?

Before we get into how to actually set up your backend and how to build with our modular live event chat components, you need to first select a robust API provider. To make the chat components work, we need a backend for transmitting messages. These components are an example of how to integrate open source React chat components, with PubNub powering the backend as the chat API. PubNub is used in the project because PubNub is capable of transmitting a high volume of messages when a live event has a large number of active participants. PubNub has been tested with live events as the primary chat API and is trusted in production for live events by PubNub customers, like LiveLike, every day. 

PubNub is a strong solution for enabling live event chat applications because it’s flexible in how you integrate with it and offers some powerful features for live events.

Key features include:

  • Billions of real-time messages are transmitted by PubNub everyday, so your live event chat room can grow without limits.

  • Storage and Playback for catching up on the conversation, so users can easily jump right back into the chat after being away from the live event. 

  • Push notifications for iOS and Android, to keep users watching with notifications in real time as new messages are sent. 

  • You can create a free account and start sending messages immediately. 

With this tutorial you don’t have to already be familiar with PubNub or PubNub SDKs. The Live Event Chat Kit is fully configured with PubNub so that you only need to replace the placeholder API keys from your PubNub dashboard. This guide will help you understand how PubNub works with each component. 

Learning more about React and Typescript

Now that you’ve reviewed how we’ll power the components, let’s get familiar with React and Typescript. React is the most frequently used framework to develop robust web apps. TypeScript is a language that’s type safe and is built on top of Javascript. With TypeScript you’ll have more flexibility over Javascript and it is the current standard in the React application world.

You don’t have to be a React or Typescript expert to follow this tutorial. Each step to use the open source react chat app components for Live Event Chat Kit is included in this tutorial. 

Getting Started Learning React tutorial from PubNub’s React documentation is a good way to familiarize yourself with the basics of React. React Overview and Walkthrough by Tania Rascia is also a great guide to React that’s more hands on. 

Typescript has a type system for type checking, additional navigation features, refactoring, and more. For a full review of all of the main benefits of Typescript and React, you should read the post Getting Started with React and TypeScript.

React development environment set up

Before you get started with React chat components, you first need to configure the necessary tools to build a live event chat application in React.

Node.js development environment set up

If you’ve already installed Node.js, skip ahead to the next section. 

If you don’t have Node.js installed, you need to download it. This guide requires you to install Node.js to install dependencies and run the chat application. To download Node.js, visit the Node.js Downloads page and select the installer for your platform.

Open your terminal and run the following commands to check the installation:

node -v
npm -v

You should see a version number after you run these commands. 

Git set up

If you’ve already installed Git, jump down to the next section. 

In order to clone the React project from GitHub, you need Git installed. 

Follow the Getting Started - Installing Git guide to install or update Git.

Open your terminal and run the following command to check the installation

git --version

You should see a version number after you run the command. 

Setting up a backend for live event chat components 

Now that you have the tools you need installed and have identified PubNub as your API provider of choice, let’s set up the backend we’ll use with our Live Event Chat Kit components. After you complete these steps, you will have API keys to use in the React Live Event Chat Kit. And remember—API keys from PubNub are always free. To get set up:

  1. Sign up for a PubNub account.

  2. Go to your PubNub Dashboard.

  3. Click Create New App.

  4. Give your app a name, and select Chat App as the app type.

  5. Click Create.

  6. Click your new app to open its settings, then click its keyset.

  7. Enable the Channel Presence feature for your keyset.

  8. Enable the Storage and Playback feature for your keyset. 

  9. Enable the Stream Controller feature for your keyset.

  10. Save the changes.

  11. Copy the Publish and Subscribe keys for the next steps.

Building and running a live event chat app With React

Once you’ve configured PubNub, you can get started with the Live Event Chat Kit components by opening your terminal and cloning the Live Event Chat Kit React app repository from GitHub. In this repo there are PubNub powered, open-source chat components and chat app UI necessary to build a live event chat solution. All of the components and their UIs are customizable.

git clone https://github.com/PubNubDevelopers/chat-component-app-live-event

Navigate into the repository with your terminal. The Live Event Chat Kit can be tested and run from this location.

cd /chat-component-app-live-event

We’ll use Yarn to install the dependencies used by the chat components. This process takes a few minutes to download and install the dependencies.

yarn install

Next, configure the components with the API keys obtained from your PubNub dashboard. Your API keys allow you to send and receive messages on the PubNub network. 

Configure the API keys by starting the built-in message firehose included with the chat kit to simulate a live event and test the application as if there were a high volume of users present. You must start the firehose at least once, before starting the Live Event Chat application, to configure the API keys.

yarn firehose

Enter your API keys from your PubNub dashboard when prompted. You should see activity in your terminal as messages are being streamed.

Open another terminal window to the same location.

cd /chat-component-app-live-event
yarn start

The Live Event Chat Application should now open a html webpage at http://localhost:8080

You should immediately see messages in the message list stream from the message firehose started earlier. Add text in the text input area and press enter. You will see your message appear in the message list area. 

The structure of live event chat components

After reviewing how the live event chat components work together, we should review the component structure. This chat application has two major components that are required for a good chat user experience for live events or live streaming. Both of these components are designed with enough flexibility that you can customize them for your exact needs. The components are:

  • Message List: This component shows all of the messages received in the chat. This component updates as messages are received by the PubNub subscription listener.

  • Compose: This component is an area for users to draft new messages to send to the chat. New messages are published to PubNub when you press the enter key. Any other user watching the live event or live stream will see the chat messages.

The structure of live event chat components explained

Now that you know the two main components of the Live Event Chat Kit, let’s look under the hood and see how the frontend works. Once you have an understanding of how the components work, it’ll be easier to modify their behavior and customize them with your own CSS. 

Alignment of React Components

Before we go any further, let's review how the app is structured. Some of the components in the Live Event Chat Kit are primarily used to align the main UI components. Take a look:

ChatDemo: 

This component outlines the main structure of the application. If you navigate to the file src/components/ChatDemo/ChatDemo.tsx you’ll find the component structure. There are two sides: the live event panel and the message list panel. You can configure the source for the live stream here.

<ChatDemoWrapper >

    <LiveFeedPanelReactPlayerWrapper>

        <LiveFeedPanelReactPlayer
          //dailymotion
          //url="https://www.dailymotion.com/video/x61xx3z"
         
          //m3u8
          //url="https://bitdash-a.akamaihd.net/content/MI201109210084_1/m3u8s/f08e80da-bf1d-4e3d-8899-f0f6155f6efa.m3u8"
          
          //YouTube
          //url="https://youtu.be/y-E7_VHLvkE"
          
          //Vimeo
          //url="https://vimeo.com/90509568"

          //SoundCloud
          //url="https://soundcloud.com/miami-nights-1984/accelerated"

          //YouTube
          url="https://youtu.be/mJxsj51d-Pk"

          //Twitch
          //url="https://www.twitch.tv/summit1g"

        />

        <EventDetailsBottom />
        <ShareButtonsWrapper>

          <BottomShareButtonWrapper>
            <div>
              <BottomButtonImgWrapper src="https://nfodorpubnubcdn.imfast.io/images/iconShare@3x.png" />
            </div>
            <div>
              <BottomButtonTextWrapper>Share</BottomButtonTextWrapper>
            </div>
          </BottomShareButtonWrapper>


          <BottomFollowButtonWrapper>
            <div>
              <BottomButtonImgWrapper src="https://nfodorpubnubcdn.imfast.io/images/iconFollow@3x.png" />
            </div>
            <div>
              <BottomButtonTextWrapper>Follow</BottomButtonTextWrapper>
            </div>
          </BottomFollowButtonWrapper>

        </ShareButtonsWrapper>
      </LiveFeedPanelReactPlayerWrapper >

        <MessageListPanel />

    </ChatDemoWrapper>

LiveFeedReactPlayer: 

This component builds a player widget for the live event stream functionality. If you’re integrating the chat components for this application into your live stream application, you can replace this component with your own live stream player. We won’t go into the details of this component or its subcomponents; The components and subcomponents are not part of the chat components of this application. This component is included for demonstration purposes as a placeholder. 

MessageListPanel:

The MessageList component and the compose text area are aligned by this component. If you open the file src/components/MessageListPanel/MessageListPanel.tsx you’ll find the component structure. The message list area is positioned above the compose text area.

       <MessageListPanelWrapper>
          <MessageList />
          <ComposeMessageBoxWrapper>
            <UserImgWrapper src={state.eventHostAvatar} />
            <MessageInputWrapper
              autoComplete="off"
              onKeyPress={handleKeyDown}
              ref={textAreaEl}
            id="messageContent"
            />
          </ComposeMessageBoxWrapper>
        </MessageListPanelWrapper>

The MessageListPanel also shows the avatar for the current user. The avatar is set in src/AppStateContext.tsx when the initial state is defined. You can edit the avatar URL to use a different avatar service, such as Gravatar, or configure custom avatars. 

  eventHostAvatar: "https://robohash.org/ipsaquodeserunt.jpg?size=50x50&set=set1",

Compose Component

Now that you’ve reviewed the structure of the Live Event Chat Kit, let’s investigate how the Compose Component works. You can find the Compose Component in the src/components/ComposeMessageBox directory. Open the file ComposeMessageBox.tsx. The component returns a text input area:

<SendMessageField></SendMessageField>

There is also a function for key press events that dispatches the SEND_MESSAGE function found in the src/AppStateContext.tsx file. This is how new messages are published.

const handleKeyDown: React.KeyboardEventHandler  = event => {
    if (event.key === 'Enter') {
      if (textAreaEl?.current !== null) {
        dispatch({
          type: "SEND_MESSAGE",
          payload: { messageContent: textAreaEl.current!.value! }
        } as {
          type: "SEND_MESSAGE",
          payload: {
            messageContent: string
          }
        });
        textAreaEl.current!.value = "";
      }
    }
  };

The channel that the messages will be published to is defined in src/AppStateContext.tsx when the initial state is defined:

channel:"liveeventdemo.row1",

The contents of the input field are published to the live stream channel by the SEND_MESSAGE function. The SEND_MESSAGE function also appends additional JSON formatted data to the message, such as the sender name and an avatar. 

case "SEND_MESSAGE": {
      const msgId: string = generateUUID();
      state.pubnub.publish({
        channel: state.channel,
        sendByPost: true,
        message: {
          "internalKey": msgId,
          "key": msgId,
          "senderId": "bc296603-b349-43de-8574-0a3a9392e30a",
          "message": action.payload.messageContent,
          "UserAvatar": "https://robohash.org/ipsaquodeserunt.jpg?size=50x50&set=set1",
          "timetoken": "1592439990",
          "senderName": "Mr. Robot",
          "dateFormat": null,
          "reactions": null,
          "addMessageReaction": null,
          "addActions": null
      },
      });
      return { ...state }
    }

Message List Component

Now that you’re sending messages, let’s look at how receiving them works. The message list component is found in the src/components/MessageList directory. Open the file MessageList.tsx. The MessageList component returns a list of messages from the messages in the state.messages array and scrolls to the bottom.

  const { state } = useAppState();
  const [stopOnScroll, setStopOnScroll] = useState(false);
  const messagesEndRef = useRef<null | HTMLDivElement>(null)
  const scrollToBottom = () => {
   messagesEndRef?.current?.scrollIntoView({ block: "end", inline: "nearest", behavior: "smooth" });
    }

  useScrollPosition(({ prevPos, currPos }) => {
    const isShow = currPos.y > prevPos.y
    console.log(`${isShow}`);
    if (isShow !== stopOnScroll) setStopOnScroll(isShow)
  }, [])

  useEffect(scrollToBottom, [state.messages]);

  const Messages = Array.from(state.messages).map((onemessage: UserMessage) => {
    return (
      <>
        <div ref={messagesEndRef} />
        <Message message={onemessage} key={onemessage.key} />
      </>
    );
  }
  );

  return (
    <MessageListWrapper>
      {Messages}
    </MessageListWrapper>
  );

You’ll find the message subcomponent in the src/components/Message directory. Each message is formatted with the user’s avatar, the sender name, and the message text.

return (
  <MessageWrapper>
    <AvatarWrapper src={props.message.UserAvatar}/>
    <SenderNameWrapper>{props.message.senderName}</SenderNameWrapper>
    <MessageMessageWrapper>{props.message.message}</MessageMessageWrapper>
  </MessageWrapper>
);

The array for displaying messages, state.messages, is managed by the src/AppStateContext.tsx file. You’re sending and receiving messages to state.channel (configured to "liveeventdemo.row1”). At the start of the application the subscription for messages begins for the channel.

    // Subscribe on the default channel.
      state.pubnub.subscribe(
        {
          channels: [state.channel], //Only one channel.
          withPresence: state.presence, 
        }
      );

New messages from the subscription are received by a PubNub API listener callback.

state.pubnub.addListener({
        message: (messageEvent) => {
          dispatch({
            type: "ADD_MESSAGE",
            payload: messageEvent.message
          });
        }
});

The message list array is updated with the new messages using the ADD_MESSAGE function. The ADD_MESSAGE function adds the new message to the end of the array. The ADD_MESSAGE function also discards old messages. 

   case "ADD_MESSAGE": {
      //If the messagelist is over our cap we discard the oldest message in the list.
      if (state.messages.length > state.maxMessagesInList ){
        state.messages.shift();
      }

      const merged: AppState = {
        ...state,
        messages: [
          ...state.messages as Array<UserMessage>,
          {
            ...action.payload as UserMessage
          }
        ]
      };
      return merged;
    }

More live event chat features

Now you know exactly how to build a truly engaging and real-time chat experience for your live event or live stream with PubNub. From here, you can customize the CSS and expand the chat application with more features to meet your needs. Since the Live Event Chat Kit is component-based, you can use the components in this tutorial as a template; You can use the open-source react chat components in your React chat application. Some common ways you can expand your live event chat with PubNub to include more functionality are:

Need more help building messaging for live events? Get in touch with our sales team to quickly get your in-app chat up and running.

More From PubNub