==

Q-Consultation for every industry

Securely hold virtual meetings and video conferences

Learn More>

Want to learn more about our products and services?

Speak to us now

How to Build an Instant Messaging App with Ionic and QuickBlox

Hamza Mousa
18 Jun 2021
Building Instant Messaging App with Ionic and QuickBlox

Ionic is an application development framework for building hybrid mobile apps. It is a free open-source framework packed with a set of rich mobile customized libraries like gestures and UI components.

It allows developers to use Angular, Vue, and React with a set of native-like UI components.

Ionic has a large community of developers with an ecosystem of community-generated content like templates, apps, and libraries.

Since its first release in 2013, Ionic has been used for creating millions of apps for both iOS and Android devices. In earlier versions, Ionic was built on top of AngularJS and Apache Cordova.

Although the new release still uses Cordova in the background, it supports React, Angular, Vue, as well as plain JavaScript.

Ionic is used to create all sorts of apps including messaging, games, news, and customer engagement apps.

QuickBlox is a messaging infrastructure platform with enterprise-grade functionalities. It offers real-time instant messaging, video calling and conferencing, push notification, and file-sharing options.

It can be used to create custom messaging apps according to enterprise requirements and workflow. In this tutorial, we will learn how to use Ionic to build a messaging app with QuickBlox.

To combine QuickBlox robust messaging functionalities with Ionic, you have two options:

  1. JavaScript SDK
  2. QuickBlox JavaScript SDK can be used with Ionic React, Ionic Vue, or Ionic Angular. Note that Ionic is a web-first that uses cross-platform standards web-based technology. Unlike React Native which provides an abstraction layer for iOS/ Android native UI.

  3. REST-API
  4. Developers also can use QuickBlox REST-API endpoints to access all QuickBlox functionalities like messaging, WebRTC for video calling, and push notifications.

Install ionic

sudo npm install -g @ionic/cli

create a project

bash
$ ionic start quickblox-messenger

Next you will have to choose which framework you want to use: Angular, React or Vue. For this project, we will use Vue.

Now we will switch to our project directory and run the project.

$ cd quickblox-messenger
$ ionic serve

Ionic server will fire a local development server for our Ionic project here

Install required packages

In this step, we will install QuickBlox JavaScript SDK

QuickBlox SDK

$ npm install quickblox --save

Some developers may require to work with standard Vue JavaScript convention without TypeScript, here is a quick tweak to remove TypeScript.

npm uninstall --save typescript @types/jest @typescript-eslint/eslint-plugin @typescript-eslint/parser @vue/cli-plugin-typescript @vue/eslint-config-typescript

Then change all `.ts` files to `.js`, then remove Array from router/index.js.

Don’t forget to remove `lang=”ts”` from vue components script and shims-vue.d.ts file as they are not needed.

To start working with QuickBlox it is required to get our App credentials from the QuickBlox Dashboard.

Before we login, we need to initiate the QuickBlox app. It is advised to follow the best practice to keep.

QuickBlox login

Now we will create our login template. This template will go on `Home.vue` between `` and `` which is the primary container unit for Ionic.

html
<ion-content :fullscreen="true" v-if="!loggedIn">

  <ion-list lines="full" class="ion-no-margin">
    <br />
    <ion-list-header lines="full">
      <ion-label>
        Login
      </ion-label>
    </ion-list-header>
    <ion-item>
      <ion-label>Username</ion-label>
      <ion-input placeholder="" ionChange="username = $event.target.value" :value="username"></ion-input>
    </ion-item>
    <ion-item>
      <ion-label>Password</ion-label>
      <ion-input placeholder="" type="password" ionChange="password = $event.target.value" :value="password"></ion-input>
    </ion-item>
    <section class="full-width">
      <ion-button expand="full" color="primary" size="large" @click="login">Login</ion-button>
    </section>
  </ion-list>
  <!--  -->

</ion-content>
<!--  -->

Before we login, we are required to set up QuickBlox apps and get the app credentials from the QuickBlox developer’s dashboard.

To initiate the app we will set up our example here

const CREDENTIALS = {
    appId: '',
    authKey: '',
    authSecret: '',
    roomJID: '',
  }

Vue created

created() {
       QB.init(CREDENTIALS.appId, CREDENTIALS.authKey, CREDENTIALS.authSecret);
     }

To login, we will use QuickBlox login function within our Login Method. As soon as we log in we will retrieve our user details, which will include name, email, nickname and avatar.

javascript
methods: {
  login() {


    const self = this;
    const params = {
      login: self.username,
      password: self.password
    }
    QB.createSession(params, function (err, result) {
      if (err) {

        console.log('error', err)
      } else {
        self.loggedIn = true
        console.log('Session Created User login: ', params.login, {
          result

        })
        self.loggedIn = true;
        self.isLoading = true;
        self.getUserId(params.login, params.password)
      }
    });

  },
  getUserId(login, password) {
    var self = this;
    var searchParams = {
      login: login
    };
    QB.users.get(searchParams, function (error, user) {
      if (!error) {
        console.log('Getting User Id: ', user)
        // The next function call for the next step

      }
    });
  },

}

Connect to a certain dialog

QuickBlox uses dialogs as entities to classify the type of room, channel, or conversation the messages are being sent to.

There are 3 types of dialogs:

  1. Public;
  2. Private group;
  3. Direct.

You can create dialogs through the API or using the QuickBlox developer’s dashboard.

For this tutorial, we will set up the dialog using the QuickBlox dashboard.

As soon as we have our dialog or room ready, we need to connect to it to be able to send messages:

Our workflow will be as follows:

Initiate QB -> Login -> Connect to dialog -> Reiterative messages

In this section as well, we will know how we will get messages.

javascript

// Connect soon as get user's data
getUserId(login, password) {
  var self = this;
  var searchParams = {
    login: login
  };
  QB.users.get(searchParams, function (error, user) {
    if (!error) {
      console.log('Getting User Id: ', user)
      // The next function call for the next step
      self.connect({
             userId: user.id,
             password: password
      })
    }
  });
},
connect(userCredentials) {
  let self = this;
  console.log('connect', userCredentials)
  QB.chat.connect(userCredentials, function (error, contactList) {
    if (!error) {
      console.log('Connected')
      console.log('Contact list: ', contactList)
      var roomId = CREDENTIALS.roomJID;
      // Join Specific Room
      console.log('Joining Dialog*')
      QB.chat.muc.join(roomId, function (error, result) {
        if (error) {
          console.error('Could not join the dialog', roomId)
          return
        }
        console.log({
          result
        })
        var dialogId = result.dialogId
        // Getting Messages List
        self.getMessages(dialogId)
      });
    } else {
      console.error('QB Connection Error')
    }
  });
},
// Get the dialog messages
getMessages(dialogId) {
  let self = this;
  console.log('Getting the Dialog Messages...')
  var params = {
    chat_dialog_id: dialogId,
    sort_desc: 'date_sent',
    limit: 10,
    skip: 0
  };
  QB.chat.message.list(params, function (error, messages) {
    if (!error) {
      console.log(messages)
      // self.toast('success', 'Retrieving messages: ' + messages.limit)
      self.isLoading = false;
      if (messages.limit > 0) {
        self.messages = _.reverse(messages.items);
        var userIDs = _.map(messages.items, (msg) => {
          return msg.sender_id
        })
        self.userIDs = userIDs;
        self.getUsers(userIDs)
      }
    } else {
      console.log({
        error
      })
    }
  });
}

To be able to display the messages with information about users, we will have to fetch the user’s data per every message as in the following method.

javascript

getUsers(userIds) {
  let self = this;
  var searchParams = {
    filter: {
      field: 'id',
      param: 'in',
      value: userIds
    }
  };
  // Get user
  QB.users.listUsers(searchParams, function (error, result) {
    if (!error) {
      console.log(result.items)
      self.user's = result.items
    } else {
      console.error('Could not get the user details [QB.users.listUsers]')
    }
  });
},
getUserName(id) {
  var users = JSON.parse(JSON.stringify(this.users))
  var user = _.find(users, (o) => {
    return o.user.id == id
  })
  console.log(id, users, user)
  if (user) {
    return user.user.full_name;
  }

}

Here we will display the room messages, by this piece of code under our login template.

html
<!--  -->
<ion-content :fullscreen="true" v-if="loggedIn">
  <ion-list>
    <ion-item v-if="!messages">
      <p>loading....</p>
    </ion-item>


    <ion-item v-for="(i,index) in messages" v-bind:key="index">
      <ion-avatar slot="start">
        <img src="https://i.pravatar.cc/150?img=3">
      </ion-avatar>
      <ion-label>
        <h2>{{getUserName(i.sender_id)}}
        </h2>
        <!-- <h3>I'm a big deal</h3> -->
        <small>{{ i.updated_at }}</small>

        <p>{{i.message}} {{i.body}}</p>
      </ion-label>
    </ion-item>

  </ion-list>
</ion-content>

Sending messages

To send a message, we will connect our input form and send the message content as the user clicks the “send” button.

html
<!--directly after messages list -->
<!-- send message -->
<ion-footer class="ion-no-borderx" v-if="loggedIn && messages">
  <ion-toolbar>
    <ion-input placeholder="" @ionChange="newMessage = $event.target.value" :value="newMessage"></ion-input>
    <ion-button color="primary" slot="and" @click="createNewMessage">
      <ion-icon :icon="add"></ion-icon>
    </ion-button>
  </ion-toolbar>
</ion-footer>
javascript
createNewMessage() {
  let self = this;
  console.log('Sending a new message')
  var message = {
    type: "groupchat",
    body: self.newMessage,
    extension: {
      save_to_history: 1,
      dialog_id: CREDENTIALS.roomJID
    },
    markable: 1
  };
  var msgID = QB.chat.send(CREDENTIALS.roomJID, message);
  this.newMessage = ""

}

Subscribe to new messages

We need to get new messages from QuickBlox, so here we will create a message listener function just under the QuickBlox Initiate function. This function will push new messages directly to our messages list.

javascript
created() {
  QB.init(CREDENTIALS.appId, CREDENTIALS.authKey, CREDENTIALS.authSecret);
  // Subscribe to new messages
  QB.chat.onMessageListener = onMessage;
  var self = this;
  function onMessage(userId, message) {
    message.sender_id = userId;
    self.messages.push(message)
    self.newMessage = ""
    console.log('New Message: ', {
      userId,
      message
    })
  }

}

Conclusion

As our tutorial came to an end, we explored the basic logic to how to build QuickBlox Ionic apps. Although we used Vue for this tutorial, the same concept can be done for Angular, React, and plain JavaScript.

Ionic is a fast efficient way to create a hybrid app without a hustle. It offers different framework choices easily maintained and can be packed for iOS, Android, and Desktop for multiple systems (Linux, Windows, and macOS). The Ionic QuickBlox app can serve as a template for developing custom-flow communication apps.

Have Questions? Need Support?

Join the QuickBlox Developer Discord Community, where you can share ideas, learn about our software, & get support.

Join QuickBlox Discord

Leave a Comment

Your email address will not be published. Required fields are marked *

Read More

Ready to get started?

QUICKBLOX
QuickBlox post-box