How to Build a Vue Customer Service Chat App (ie. an Intercom.io Alternative)

Vue.js is an open source JavaScript framework with a massive developer following. Its architecture is considered cutting edge in the web development community because it composes user interfaces of reactive web components.

Chat apps are being built more frequently now than ever before. Who wants to wait on hold on the telephone in 2018? It’s way simpler for customers to contact businesses through text correspondence. This societal change has enabled companies like Intercom.io and LiveAgent to bring in substantial profits as businesses make their customer support teams chat accessible.

PubNub and ChatEngine make building an in-website support chat possible in a remarkably short amount of time. Using modern web UI frameworks like Vue.js make this next programming project or business venture a no-brainer.

Open source customer support chat with Vue and PubNub ChatEngine

This tutorial expands on my first ChatEngine example with Vue.js. The multi-user private chat interface will serve as the support agent view, so a support team can manage incoming messages from all website customers.

Respond to customer questions using website chat, built with PubNub

Let’s get started building the customer chat user interface that you see in the first picture. Lucky for us, there is a robust, open source Vue package that slashes our design and development time. On npmjs.com and GitHub, you can find Vue-Beautiful-Chat. It currently has over 200 stars and 50 forks on GitHub, so you can say it is in high demand. As a developer, I’m happy to promote it, because working with it is easy.

We will combine Vue-Beautiful-Chat with my multi-user chat and ChatEngine to provide a clean experience for all users. Support team members will be able to sign-in to the protected support page using a username and password. The authentication flow is super simple thanks to PubNub Functions. Below is a diagram of the full stack.

Architecture of a customer support chat app built with PubNub and Vue.js

ChatEngine

warning iconBefore we continue, it’s very important that you first create a ChatEngine key set. ChatEngine runs on top of PubNub. When you sign up for a free PubNub account, you must click the ChatEngine deploy button to configure your app back-end. This is all free for you – up to 1 million PubNub transactions in a month.

The ChatEngine deploy button makes PubNub Functions event handlers for ChatEngine in your PubNub account, and it deploys them to data centers around the world. If you try to use a traditional PubNub key set in your ChatEngine app, it will not work, unless you copy over the Functions and deploy them. It’s easier for you to make a new key set in the form below.


 

GitHub LogoAll of the code in this tutorial is available in my GitHub Repository.

Clone and run it with your free ChatEngine keys!

 


The Customer View

One of my favorite parts about using Vue-Beautiful-Chat is that you can add the component to an existing website, and it will automatically seat itself in the lower right-hand corner of the page, overlapping the existing content. All we need to do to make the UI appear is add a beautiful-chat HTML tag, and pass a series of event handlers and parameters as HTML attributes.

Here is the markup for the customer’s view (src/views/Customer.vue):
-AMAZONPOLLY-ONLYWORDS-START-

<template>
  <div>
    <h3>Your Website Here</h3>
    <p class="website-text">
      <b>Customers</b> can chat with a support team member using the button in the lower right corner of the page.
      <br>
      <br>
      <b>Support Team</b> members at your company can <router-link to="/support">sign in to support chat duty here</router-link>.
    </p>
    <beautiful-chat
      :participants="participants"
      :titleImageUrl="titleImageUrl"
      :messageList="messageList"
      :newMessagesCount="newMessagesCount"
      :isOpen="isChatOpen"
      :close="closeChat"
      :open="openChat"
      :showEmoji="true"
      :showFile="false"
      :showTypingIndicator="showTypingIndicator"
      :colors="colors"
      :alwaysScrollToBottom="alwaysScrollToBottom"
      :onMessageWasSent="sendMessage" />
  </div>
</template>

-AMAZONPOLLY-ONLYWORDS-END-
All of the event handlers referenced are within the script section of the file. The application’s message data is held in the Vuex Store. This global datastore enables a clean State Management Pattern to separate stateful logic from the visual component’s code.

ChatEngine events are bound to the Vuex store out-of-the-box thanks to the Vue ChatEngine plugin, which this app is also using. Name your store event handlers with CHATENGINE_ prepended for auto registration.

Vuex application data flow for Vue user interfaces

Vuex Data Flow. From vuex.vuejs.org, accessed November 2018.

The store declarations can be found in the src/store.js file.

Making the ChatEngine Instance

In the main.js file, we initialize our Vue app and also configure the ChatEngine object.
-AMAZONPOLLY-ONLYWORDS-START-

// The Vue build version to load with the `import` command
// (runtime-only or standalone) has been set in webpack.base.conf with an alias.
import Vue from 'vue';
import App from './App';
import router from './router';
import Chat from 'vue-beautiful-chat';
import store from './store';
import VueChatEngine from 'vue-chat-engine';
import ChatEngineCore from 'chat-engine';
import util from './util';
import {EventBus} from './event-bus.js';

Vue.config.productionTip = false;

// Plugin Vue Beautiful Chat for the customer UI.
Vue.use(Chat, {});

// Initialize ChatEngine with PubNub - Remember to activate ChatEngine first!
const publishKey = '_YOUR_PUBLISH_KEY_HERE_';
const subscribeKey = '_YOUR_SUBSCRIBE_KEY_HERE_';

window.$supportAPI = '_YOUR_FUNCTIONS_ENDPOINT_URL_HERE_';

if (!publishKey || !subscribeKey) {
    console.error('ChatEngine: PubNub Keys are missing.');
}

const chatEngine = ChatEngineCore.create({
    publishKey,
    subscribeKey,
});

// Plugin ChatEngine to Vue. Store methods will fire on ChatEngine events.
Vue.use(VueChatEngine, { chatEngine, store });

function created() {
    const view = window.location.href.includes('support') ? 'support' : 'customer';
    EventBus.$emit('vue-initialized-' + view, { chatEngine, store });
}

/* eslint-disable no-new */new Vue({
    el: '#app',
    store,
    components: {App},
    template: '<App/>',
    created,
    router,
});

-AMAZONPOLLY-ONLYWORDS-END-
Notice that you need to fill in some account specific keys in this file. You need to fill in the PubNub keys that you configured for a ChatEngine app. You also need to include the URL of the support authentication API. This is a secure microservice that allows your support agents to sign in with their username and password. We will need to deploy some server-side JavaScript in the PubNub admin dashboard to continue.

First, go to your PubNub Admin Dashboard and click on your ChatEngine Application. Next, click on the Functions tab on the left side.

Next, click on the existing ChatEngine Function.

You should see the ChatEngine Function endpoint, and at the bottom of the screen, there is a create button. Click create and make a new API endpoint for your new service. Make sure that it is of type On Request. The route should be support-state.

Create a new PubNub Function endpoint for your chat app sign in API

 

You should now see the endpoint alongside your ChatEngine Endpoint. Click on it so we can add the new JavaScript code.

Functions event handlers for ChatEngine and support sign in API

 

Once you see the Functions editor, you can add your API code.

Serverless Microservice

Now we add the service code. Copy and paste the code from my repository in the src/pubnub-functions/SupportChatState.js file (it’s also hosted in this GitHub Gist).

You can set your support user’s username and password in SupportChatState.js. It’s in plaintext for example purposes. It’s a better practice to move username and password to the secure PubNub Functions Vault. That way there isn’t sensitive strings in your source code. You can retrieve the keys programmatically during execution.

To globally deploy your new service, click the Restart button in the top right corner. Clicking this button will not harm the state of your existing ChatEngine app, and it will start the 2nd service.

Remember the API URL that we need to set in main.js? In your new API endpoint, click the copy URL button to get the address of the live service. Paste the URL into the code in main.js on line 22 for the variable window.$supportAPI.

Copy URL button in the PubNub Functions editor

Now your application is ready to run! Using your command line, navigate to the directory where you cloned the project with git. If you haven’t already, you will need to install Node.js and npm (do LTS). If you already have your $PATH set up to run node on the command line, go to the project parent directory and run:
-AMAZONPOLLY-ONLYWORDS-START-

npm i
npm run serve

-AMAZONPOLLY-ONLYWORDS-END-
This will boot up a local server on your computer. It will serve your Vue application at http://localhost:8080 by default. Open your web browser to view the app!

The / URL will serve the customer view. You should see the vue-beautiful-chat interface on the lower right corner of the web page. To check out the support user page, open another browser tab and navigate to /support.

The support page is protected by the username and password that you set in your PubNub Functions API code. When you enter the information and click the button, an API request will be made. If the credentials are correct, the Vue app will proceed to the support user chat UI.

Sign in to the support Vue.js chat

Thanks for reading! Check out my other Vue.js Tutorials and relevant PubNub Functions posts:

Have suggestions or questions about the content of this post? Reach out at devrel@pubnub.com.

Try PubNub Today