<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: vivek yadav</title>
    <description>The latest articles on DEV Community by vivek yadav (@vivek_yadav).</description>
    <link>https://dev.to/vivek_yadav</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F808439%2F050373d8-f479-40d1-b5b3-5a01dcd19bb1.jpg</url>
      <title>DEV Community: vivek yadav</title>
      <link>https://dev.to/vivek_yadav</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/vivek_yadav"/>
    <language>en</language>
    <item>
      <title>Expert:Chatting application using Huawei CloudDB, Auth service, Cloud Function, Location, Site, Map and Push Kits - Part 2</title>
      <dc:creator>vivek yadav</dc:creator>
      <pubDate>Fri, 11 Feb 2022 06:36:54 +0000</pubDate>
      <link>https://dev.to/vivek_yadav/expertchatting-application-using-huawei-clouddb-auth-service-cloud-function-location-site-map-and-push-kits-part-2-6ji</link>
      <guid>https://dev.to/vivek_yadav/expertchatting-application-using-huawei-clouddb-auth-service-cloud-function-location-site-map-and-push-kits-part-2-6ji</guid>
      <description>&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--gLNcS9C5--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/a6dq5f46cycza7iexsfs.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--gLNcS9C5--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/a6dq5f46cycza7iexsfs.png" alt="Image description" width="400" height="400"&gt;&lt;/a&gt;&lt;br&gt;
In previous article, we have developed one to one text sending application. Now in this article, we will work on sent location in chat.&lt;/p&gt;

&lt;p&gt;Previous article link: &lt;a href="https://forums.developer.huawei.com/forumPortal/en/topic/0201792529223700165?fid=0101187876626530001"&gt;https://forums.developer.huawei.com/forumPortal/en/topic/0201792529223700165?fid=0101187876626530001&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Huawei Kits Used&lt;br&gt;
Huawei Cloud DB&lt;br&gt;
Huawei Auth Service&lt;br&gt;
Huawei Cloud function.&lt;br&gt;
Huawei Push Kit&lt;br&gt;
Location kit&lt;br&gt;
Site kit&lt;br&gt;
Map kit&lt;/p&gt;

&lt;p&gt;Huawei API Used&lt;br&gt;
  1.Huawei Cloud Storage - Cloud storage is used to store users files like user profile image and images shared on the chat. Once files are uploaded successfully on storage we get the downloadable URL will act like the profile URL or the image content.&lt;/p&gt;

&lt;p&gt;2.Huawei CloudDB API - Cloud DB is used to store users data, users chat and also used to manage users chat history with other users.&lt;br&gt;
a) Upsert&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;     i) Insert data of the users from the profile.

     ii) Create and insert room id, room id is consider as a reference between two users chat. Using room id we will store all the respective chat data in                   the DB.

     iii) Insert Chat data between two users based on the room id.
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;b) Query&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;     i) Get list of Contacts for chat.

     ii) Get list of user with whom logged in user chatted before.

     ii) Get details of the chat screen with all the chat messages which include, images, text and location.
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;3.Huawei Auth Service – Using the Auth Service we are registering the user on the Ecosystem. We are using the Phone number auth service for the              same to receive the OTP and verify the user here.&lt;/p&gt;

&lt;p&gt;4.Huawei Cloud function – We are triggering the Huawei Push notification system using cloud function for the same.&lt;/p&gt;

&lt;p&gt;5.Huawei Location kit - Using location kit we will get users current location, so that they can share with other users. Using the same location co-                 ordinate, we will try to receive the nearby service shows the nearby landmark.&lt;/p&gt;

&lt;p&gt;6.Huawei Map kit –&lt;/p&gt;

&lt;p&gt;a. Map kit is used to show users shared location and nearby landmarks on the map.&lt;/p&gt;

&lt;p&gt;b. Static Map Query after the getting the location we will query the map static with the marker and create the link and upload that link to the webview to show the current location being shared.&lt;/p&gt;

&lt;p&gt;7.Huawei Site Kit –To show the landmark on the map which can be shared with different users at the given time of request for this we have used the           nearby service from the site kit.&lt;/p&gt;

&lt;p&gt;8.Huawei Push kit - Push kit is used to push notification of message to other user. So when one user send message we will notify other user via push           notification only.&lt;/p&gt;

&lt;p&gt;Used the rest end point for the cloud function to send the push notification once the message is end trigger from the device.&lt;br&gt;
On HMSMessage Received This is once parsing the data as per our need on the implementation wherein we will need to parse and image and location when shared by other success.&lt;br&gt;
Let’s start send location in chat&lt;/p&gt;

&lt;p&gt;Enable Location Kit , Site Kit and Map Kit on console as shown in below image.&lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--2tkx90Oy--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/tknqouyw19nt45f3y540.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--2tkx90Oy--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/tknqouyw19nt45f3y540.png" alt="Image description" width="880" height="506"&gt;&lt;/a&gt;&lt;br&gt;
Add dependencies&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;// HMS dependencies
implementation "com.huawei.hms:site:$rootProject.ext.sitekit"
implementation "com.huawei.hms:maps:$rootProject.ext.mapkit"
implementation "com.huawei.hms:location:$rootProject.ext.locationkit"

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Add run time location permission&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;private boolean checkLocationPermission() {
    int location_permission = ContextCompat.checkSelfPermission(this.getApplicationContext(), Manifest.permission.ACCESS_FINE_LOCATION);
    int course_permission = ContextCompat.checkSelfPermission(this.getApplicationContext(), Manifest.permission.ACCESS_COARSE_LOCATION);
    return location_permission == PackageManager.PERMISSION_GRANTED &amp;amp;&amp;amp; course_permission == PackageManager.PERMISSION_GRANTED;
}

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Let's design the page&lt;/p&gt;

&lt;p&gt;We divided page into two parts one is for map view and other half is for showing nearby places.&lt;/p&gt;

&lt;p&gt;XML&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;&amp;lt;LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:app="http://schemas.android.com/apk/res-auto"
    xmlns:tools="http://schemas.android.com/tools"
    android:layout_width="match_parent"
    android:layout_height="match_parent"
    android:orientation="vertical"
    android:weightSum="2"&amp;gt;

    &amp;lt;RelativeLayout
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_weight=".15"
        android:orientation="horizontal"&amp;gt;


        &amp;lt;ImageView
            android:id="@+id/imageLocation"
            android:layout_width="40dp"
            android:layout_height="match_parent"
            android:layout_centerVertical="true"
            android:padding="5dp"
            android:src="@drawable/ic_baseline_arrow_back" /&amp;gt;

        &amp;lt;TextView
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:layout_centerInParent="true"
            android:layout_centerVertical="true"
            android:text="@string/send_loc"
            android:textColor="@color/black"
            android:textSize="18sp"
            android:textStyle="bold" /&amp;gt;

        &amp;lt;ImageView
            android:layout_width="40dp"
            android:layout_height="match_parent"
            android:layout_alignParentEnd="true"
            android:layout_marginEnd="10dp"
            android:padding="5dp"
            android:src="@drawable/hwsearchview_ic_public_input_search"
            android:visibility="gone" /&amp;gt;


    &amp;lt;/RelativeLayout&amp;gt;

    &amp;lt;LinearLayout
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_weight=".8"
        android:orientation="vertical"&amp;gt;

        &amp;lt;FrameLayout
            android:layout_width="match_parent"
            android:layout_height="match_parent"&amp;gt;


            &amp;lt;com.huawei.hms.maps.MapView xmlns:map="http://schemas.android.com/apk/res-auto"
                android:id="@+id/mapView"
                android:layout_width="match_parent"
                android:layout_height="match_parent"
                map:cameraTargetLat="51"
                map:cameraTargetLng="10"
                map:cameraZoom="8.5"
                map:mapType="normal"
                map:uiCompass="true"
                map:uiZoomControls="true" /&amp;gt;
            &amp;lt;LinearLayout
                android:layout_width="match_parent"
                android:layout_height="wrap_content"
                android:orientation="horizontal"&amp;gt;

                &amp;lt;Button
                    android:id="@+id/btnHospital"
                    android:layout_width="0dp"
                    android:layout_height="wrap_content"
                    android:layout_marginStart="8dp"
                    android:layout_weight="1"
                    android:text="@string/btnHospital" /&amp;gt;

                &amp;lt;Button
                    android:id="@+id/btnAtm"
                    android:layout_width="0dp"
                    android:layout_height="wrap_content"
                    android:layout_toEndOf="@id/btnHospital"
                    android:layout_weight="1"
                    android:text="@string/btnAtm" /&amp;gt;

                &amp;lt;Button
                    android:id="@+id/btnPetrolBunk"
                    android:layout_width="0dp"
                    android:layout_height="wrap_content"
                    android:layout_toEndOf="@id/btnAtm"
                    android:layout_weight="1"
                    android:text="@string/btnPetrol" /&amp;gt;
            &amp;lt;/LinearLayout&amp;gt;
        &amp;lt;/FrameLayout&amp;gt;

    &amp;lt;/LinearLayout&amp;gt;

    &amp;lt;LinearLayout
        android:layout_width="match_parent"
        android:layout_height="0dp"
        android:layout_weight="1.05"
        android:orientation="vertical"&amp;gt;

        &amp;lt;TextView
            android:layout_width="match_parent"
            android:layout_height="30dp"
            android:layout_gravity="bottom"
            android:background="#D3D3D3"
            android:gravity="center_vertical"
            android:paddingStart="5dp"
            android:text="@string/nearby_places"
            android:textColor="@color/black"
            android:textSize="16sp" /&amp;gt;


        &amp;lt;RelativeLayout
            android:id="@+id/rlSendCurrentLocation"
            android:layout_width="match_parent"
            android:layout_height="60dp"
            android:layout_marginStart="20dp"
            android:paddingStart="5dp"&amp;gt;

            &amp;lt;ImageView
                android:id="@+id/currentlocation_icon_iv"
                android:layout_width="40dp"
                android:layout_height="40dp"
                android:layout_centerVertical="true"
                android:scaleType="fitXY"
                android:src="@drawable/ic_baseline_location"
                android:tint="@color/colorPrimary"
                tools:ignore="UseAppTint" /&amp;gt;

            &amp;lt;TextView
                android:id="@+id/currnet_location_title"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_marginStart="10dp"
                android:layout_marginTop="8dp"
                android:layout_toEndOf="@id/currentlocation_icon_iv"
                android:text="@string/send_location"
                android:textColor="@color/black"
                android:textSize="18sp" /&amp;gt;

            &amp;lt;TextView
                android:id="@+id/currnet_location_accurecy"
                android:layout_width="wrap_content"
                android:layout_height="wrap_content"
                android:layout_below="@id/currnet_location_title"
                android:layout_marginStart="10dp"
                android:layout_marginTop="1dp"
                android:layout_toEndOf="@id/currentlocation_icon_iv"
                android:text="@string/accuracy"
                android:textColor="@color/grey"
                android:textSize="14sp" /&amp;gt;


        &amp;lt;/RelativeLayout&amp;gt;

        &amp;lt;androidx.recyclerview.widget.RecyclerView
            android:id="@+id/rvNearByLocation"
            android:layout_width="match_parent"
            android:layout_height="match_parent" /&amp;gt;

        &amp;lt;TextView
            android:id="@+id/response_text_search"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:textIsSelectable="true" /&amp;gt;
    &amp;lt;/LinearLayout&amp;gt;
&amp;lt;/LinearLayout&amp;gt;

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--XgVudpd1--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/goe83gqxzox73q358ija.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--XgVudpd1--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/goe83gqxzox73q358ija.png" alt="Image description" width="880" height="728"&gt;&lt;/a&gt;&lt;br&gt;
It's time to start coding&lt;/p&gt;

&lt;p&gt;Get Current location&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;FusedLocationProviderClient mFusedLocationProviderClient = LocationServices.getFusedLocationProviderClient(context);
SettingsClient mSettingsClient = LocationServices.getSettingsClient(context);
LocationRequest mLocationRequest = new LocationRequest();
mLocationRequest.setInterval(5000);
mLocationRequest.setPriority(LocationRequest.PRIORITY_HIGH_ACCURACY);

mFusedLocationProviderClient.getLastLocation().addOnSuccessListener(location -&amp;gt; {
    AppLog.logD(TAG,
            "Lat long---&amp;gt;Fushed" + location.getLongitude()
                    + "," + location.getLatitude() + "," + location.getAccuracy());
    if (location != null) {
        locationMutableLiveData.postValue(location);
    }


}).addOnFailureListener(e -&amp;gt; {
    AppLog.logE(TAG, "error" + e);
    Toast.makeText(context, "Location not found", Toast.LENGTH_SHORT).show();

});

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Get Nearby location&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;public void getNearbyData(double latitude, double longitude, SearchService searchService, String locationType) {
    NearbySearchRequest request = new NearbySearchRequest();
    Coordinate location = new Coordinate(latitude, longitude);
    request.setLocation(location);
    request.setQuery(locationType);
    request.setRadius(5);
    request.setHwPoiType(HwLocationType.ADDRESS);
    request.setLanguage("en");
    request.setPageIndex(1);
    request.setPageSize(10);
    request.setStrictBounds(false);
    SearchResultListener&amp;lt;NearbySearchResponse&amp;gt; resultListener = new SearchResultListener&amp;lt;NearbySearchResponse&amp;gt;() {
        @Override
        public void onSearchResult(NearbySearchResponse results) {
            arrayListMutableLiveData.postValue(new ArrayList&amp;lt;&amp;gt;(results.getSites()));
        }

        @Override
        public void onSearchError(SearchStatus status) {
            AppLog.logE("TAG", "Error : " + status.getErrorCode() + " " + status.getErrorMessage());
        }
    };
    searchService.nearbySearch(request, resultListener);

}

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Set up Map and showing nearby places&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;@Override
public void onMapReady(HuaweiMap huaweiMap) {
    hMap = huaweiMap;
    hMap.setMyLocationEnabled(true);
    hMap.getUiSettings().setMyLocationButtonEnabled(true);
    Util.showProgressBar(LocationActivity.this);
    locationViewModel.getCurrentLocation(LocationActivity.this);
    locationViewModel.locationMutableLiveData.observe(LocationActivity.this, location -&amp;gt; {
        if (location != null) {
            this.location = location;
            updateDetails(location);
        }
    });
    locationViewModel.arrayListMutableLiveData.observe(LocationActivity.this, this::recyclerView);
}

private void updateDetails(Location location) {
    float zoom = 14.0f;
    LatLng latLng1 = new LatLng(location.getLatitude(), location.getLongitude());
    CameraUpdate cameraUpdate = CameraUpdateFactory.newLatLngZoom(latLng1, zoom);
    hMap.animateCamera(cameraUpdate);
    currentLocationAccuracy.setText(String.format("Accurate to %s meters", location.getAccuracy()));

    locationViewModel.getNearbyData(location.getLatitude(), location.getLongitude(), searchService, Constants.LOCATION_TYPE_HOSPITAL);
}

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--wu0UiSdT--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/yo9hkybdfpxz287b4hvu.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--wu0UiSdT--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/yo9hkybdfpxz287b4hvu.png" alt="Image description" width="450" height="899"&gt;&lt;/a&gt;&lt;br&gt;
Send chat massage&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;private void setMessage(String messageType) {
    ChitChatSharedPref.initializeInstance(MessageActivity.this);
    Util.showProgressBar(MessageActivity.this);
    UserChat userChat = new UserChat();
    userChat.setRoom_id(roomId);
    userChat.setMessage_timestamp(Long.parseLong(Util.getTimeStamp()));
    userChat.setChat_id(Util.getRandomNumber());
    userChat.setReceiver_name(receiverText);
    userChat.setReceiver_phone(receiverPhoneNumber);
    userChat.setSender_name(ChitChatSharedPref.getInstance().getString(Constants.USER_NAME, ""));
    userChat.setSender_phone(ChitChatSharedPref.getInstance().getString(Constants.PHONE_NUMBER, ""));

    userChat.setMessage_type(messageType);
    switch (messageType) {

        case Constants.MESSAGE_TYPE_MAP:
            userChat.setMessage_data(jsonMapModel);
            messageViewModel.saveUserChat(userChat);
            messageViewModel.userUpdatedSuccessfully.observe(MessageActivity.this, aBoolean -&amp;gt; {
                if (aBoolean) {
                    Util.stopProgressBar();
                    getChatList();
                    Toast.makeText(MessageActivity.this, getString(R.string.showMessageSuccess), Toast.LENGTH_SHORT).show();
                } else {
                    Util.stopProgressBar();
                    Toast.makeText(MessageActivity.this, getString(R.string.showMessageFailed), Toast.LENGTH_SHORT).show();
                }
            });
            break;
        case Constants.MESSAGE_TYPE_TEXT:
            userChat.setMessage_data(textSend.getText().toString());
            messageViewModel.saveUserChat(userChat);
            messageViewModel.userUpdatedSuccessfully.observe(MessageActivity.this, aBoolean -&amp;gt; {
                if (aBoolean) {
                    Util.stopProgressBar();
                    getChatList();
                } else {
                    Util.stopProgressBar();
                }
            });
            break;
    }
    messageViewModel.queryForToken(receiverPhoneNumber, MessageActivity.this);


}

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--l6YYZpuB--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/4rjvfl89f2hxiz98b26t.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--l6YYZpuB--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/4rjvfl89f2hxiz98b26t.png" alt="Image description" width="318" height="635"&gt;&lt;/a&gt;&lt;br&gt;
Send push notification&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;PushApis pushApis = new PushApis(MessageActivity.this);
if (messageType.equalsIgnoreCase(Constants.MESSAGE_TYPE_MAP)) {
    pushApis.sendPushNotification(roomId, messageType, "104739093", jsonMapModel, s);
} else if (messageType.equalsIgnoreCase(Constants.MESSAGE_TYPE_TEXT)) {
    pushApis.sendPushNotification(roomId, messageType, "104739093", MessageActivity.this.textSend.getText().toString(), s);
    textSend.setText("");
}

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;Conclusion&lt;/p&gt;

&lt;p&gt;In this article, we have learned how we can create a simple messaging application with Cloud DB, Auth Service, Push Kit , Location Kit , Site Kit and Map Kit. We can also use cloud storage to store profile picture, location, documents or audio and video files.&lt;/p&gt;

&lt;p&gt;Thanks for reading this article. Be sure to like and comment to this article, if you found it helpful. It means a lot to me.&lt;/p&gt;

&lt;p&gt;Reference&lt;/p&gt;

&lt;p&gt;&lt;a href="https://developer.huawei.com/consumer/en/agconnect/cloud-base/"&gt;https://developer.huawei.com/consumer/en/agconnect/cloud-base/&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://developer.huawei.com/consumer/en/doc/development/HMSCore-Guides/service-introduction-0000001050040060"&gt;https://developer.huawei.com/consumer/en/doc/development/HMSCore-Guides/service-introduction-0000001050040060&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://developer.huawei.com/consumer/en/hms/huawei-locationkit/"&gt;https://developer.huawei.com/consumer/en/hms/huawei-locationkit/&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://developer.huawei.com/consumer/en/hms/huawei-MapKit/"&gt;https://developer.huawei.com/consumer/en/hms/huawei-MapKit/&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://developer.huawei.com/consumer/en/hms/huawei-sitekit/"&gt;https://developer.huawei.com/consumer/en/hms/huawei-sitekit/&lt;/a&gt;    &lt;/p&gt;

</description>
    </item>
    <item>
      <title>Expert: BestPal (Chatting) application using Huawei CloudDB, Auth service, Cloud Function and Push Kit</title>
      <dc:creator>vivek yadav</dc:creator>
      <pubDate>Fri, 04 Feb 2022 09:05:45 +0000</pubDate>
      <link>https://dev.to/vivek_yadav/expert-bestpal-chatting-application-using-huawei-clouddb-auth-service-cloud-function-and-push-kit-2p56</link>
      <guid>https://dev.to/vivek_yadav/expert-bestpal-chatting-application-using-huawei-clouddb-auth-service-cloud-function-and-push-kit-2p56</guid>
      <description>&lt;p&gt;&lt;strong&gt;Introduction&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;In this article, we can learn that chat option between two people, they can share text between each other. The application needs to have instant messaging so once a user sends the message to a friend over the application, the friend will receive the push notification at the given time. The quintessence of an app like instant application is available and react to ongoing actions. Also, push notifications can be an excellent promotional tool that can be used to inform users about updates and new functionalities.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Huawei Kits Used&lt;/strong&gt;&lt;br&gt;
Huawei Cloud DB&lt;br&gt;
Huawei Auth Service&lt;br&gt;
Huawei Cloud function.&lt;br&gt;
Huawei Push Kit&lt;br&gt;
Huawei API Used&lt;/p&gt;

&lt;p&gt;Huawei CloudDB API - Cloud DB is used to store users data, users chat and also used to manage users chat history with other users.&lt;br&gt;
a) Upsert&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;     i) Insert data of the users from the profile.

     ii) Create and insert room id, room id is consider as a reference between two users chat. Using room id will store all the respective chat data in the DB.

     iii) Insert Chat data between two users based on the room id.
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;b) Query&lt;/p&gt;
&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;     i) Get list of Contacts for chat.

     ii) Get list of users with whom logged in user chatted before.

     ii) Get details of the chat screen with all the chat messages which includes images, text and location.
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;
&lt;p&gt;Huawei Auth Service – Using the Auth Service we are registering the user on the Ecosystem. We are using the Phone number auth service for the same to receive the OTP and verify the user here.&lt;br&gt;
Huawei Cloud function – We are triggering the Huawei Push notification system using cloud function for the same.&lt;br&gt;
Huawei Push kit - Push kit is used to push notification of message to other user. So when one user send message it will notify other user through push notification only.&lt;br&gt;
Used the rest end point for the cloud function to send the push notification once the message is end, trigger from the device.&lt;br&gt;
On HMSMessage Received This is once parsing the data as per our need on the implementation, so we need to parse image and location when shared by other success.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Database structure&lt;/strong&gt;&lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--BFV4Fe24--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/j9gkqbkxiq371sikog21.PNG" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--BFV4Fe24--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/j9gkqbkxiq371sikog21.PNG" alt="Image description" width="880" height="597"&gt;&lt;/a&gt;&lt;br&gt;
Now it's time to create project on Huawei console and development&lt;br&gt;
Integration Preparations&lt;br&gt;
You must complete the following preparations:&lt;/p&gt;

&lt;p&gt;Register as a developer on Huawei console.&lt;br&gt;
Create a project and an app in AppGallery Connect.&lt;br&gt;
Generate and configure the signing certificate fingerprint.&lt;br&gt;
Enable Auth service, Push and Cloud DB.&lt;br&gt;
For details, refer to Configuring App Information in AppGallery Connect for HMS&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;First create cloud DB Zones&lt;/strong&gt;&lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--wj1KgqOY--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/j2da6fk13g56qgd9enec.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--wj1KgqOY--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/j2da6fk13g56qgd9enec.png" alt="Image description" width="880" height="315"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Create 3 object types&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;ChatRoomId: contain all chatting room id.&lt;br&gt;
User: all register user details.&lt;br&gt;
UserChat: all users chat details. &lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--S83LJ2wY--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/2sup3ze3r9eq8rctfjc8.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--S83LJ2wY--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/2sup3ze3r9eq8rctfjc8.png" alt="Image description" width="880" height="311"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Let's start development with Login Page&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;We will login with Phone number using HMS Auth service.&lt;/p&gt;

&lt;p&gt;Enable Phone number Authentication mode as shown in below image.  &lt;/p&gt;

&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--HBOVmAlj--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/xo0j1b1804y1h7g4lqgp.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--HBOVmAlj--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/xo0j1b1804y1h7g4lqgp.png" alt="Image description" width="880" height="356"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Add dependency&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;// HMS dependencies
implementation "com.huawei.agconnect:agconnect-database:$rootProject.ext.agdatabase"
implementation "com.huawei.agconnect:agconnect-auth:$rootProject.ext.agauth"
implementation "com.huawei.hms:push:$rootProject.ext.pushkit"
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--e9B40jfr--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ju0f6n7qp93ojsiib6h3.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--e9B40jfr--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ju0f6n7qp93ojsiib6h3.png" alt="Image description" width="359" height="651"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Enter the valid phone number, we will get OTP on same number using below method.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;GET OTP&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;VerifyCodeSettings settings = new VerifyCodeSettings.Builder()
        .action(VerifyCodeSettings.ACTION_REGISTER_LOGIN)
        .sendInterval(30)
        .locale(Locale.getDefault())
        .build();

Task&amp;lt;VerifyCodeResult&amp;gt; task = AGConnectAuth.getInstance().requestVerifyCode(countryCodeStr, phoneNumberStr, settings);
task.addOnSuccessListener(TaskExecutors.immediate(), verifyCodeResult -&amp;gt; {
    if (null != verifyCodeResult) {
        verifyCodeResultMutableLiveData.postValue(verifyCodeResult);
    }
});
task.addOnFailureListener(e -&amp;gt;
        AppLog.logE(TAG, "onFailure: " + e.getCause()));

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--_fVyLCz_--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/tdl42h1e2tlb7qwu68n8.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--_fVyLCz_--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/tdl42h1e2tlb7qwu68n8.png" alt="Image description" width="350" height="632"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Verify Contact details&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;PhoneUser phoneUser = new PhoneUser.Builder()
        .setCountryCode(countryCodeStr)
        .setPhoneNumber(phoneNumberStr)
        .setVerifyCode(code)
        .build();
AGConnectAuth.getInstance().createUser(phoneUser)
        .addOnSuccessListener(signInResult -&amp;gt; {
            if (signInResult != null) {
                User user = new User();
                user.setUsername(signInResult.getUser().getDisplayName());
                user.setPhoneNumber(phoneNumberStr);
                userMutableLiveData.postValue(user);
            }
        })
        .addOnFailureListener(e -&amp;gt; {
            Log.e(TAG, "verifyContactDetails: " + e.getStackTrace());
            User user = new User();
            user.setPhoneNumber(phoneNumberStr);
            userMutableLiveData.setValue(user);

        });
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;After verify, user can authenticate successfully.&lt;/p&gt;

&lt;p&gt;Now we have to complete the user profile, as in below picture you can see we have only phone number.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Create/ Update profile&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;public void saveUser(User user, Context context) {
    CloudDBHelper.getInstance().openDb((isConnected, cloudDBZone) -&amp;gt; {
        if (isConnected &amp;amp;&amp;amp; cloudDBZone != null) {
            if (cloudDBZone == null) {
                return;
            } else {
                Task&amp;lt;Integer&amp;gt; insertTask = cloudDBZone.executeUpsert(user);
                insertTask.addOnSuccessListener(integer -&amp;gt; {
                    userMutableLiveData.setValue(true);
                    CloudDBHelper.getInstance().closeDb(context);
                }).addOnFailureListener(e -&amp;gt; {
                    userMutableLiveData.setValue(false);
                    CloudDBHelper.getInstance().closeDb(context);
                });
            }
        }
    });
}

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--JoJZvtw8--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/6cn6zfogz77xe2u8qydc.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--JoJZvtw8--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/6cn6zfogz77xe2u8qydc.png" alt="Image description" width="416" height="771"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Generate push token&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;GetToken getToken = new GetToken(app_id, UserProfileActivity.this);
getToken.setGetTokenListener(this);
getToken.execute();

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;GetToken class is a service class to generate push token&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;public class GetToken extends AsyncTask&amp;lt;Void, Void, String&amp;gt; {

    private static final String TAG = GetToken.class.getSimpleName();
    private Context context;
    private String appId;

    private GetTokenListener getTokenListener;

    public GetToken(String appId, Context context) {
        this.appId = appId;
        this.context = context;
    }

    public void setGetTokenListener(GetTokenListener getTokenListener) {
        this.getTokenListener = getTokenListener;
    }

    @Override
    protected void onPreExecute() {
        super.onPreExecute();
    }

    @Override
    protected String doInBackground(Void... voids) {
        try {
            String pushToken = HmsInstanceId.getInstance(context).getToken(appId, HmsMessaging.DEFAULT_TOKEN_SCOPE);
            AppLog.logD(TAG, pushToken);
            getTokenListener.getToken(pushToken);
            return pushToken;
        } catch (ApiException e) {
            e.printStackTrace();
        }
        return null;
    }

    @Override
    protected void onPostExecute(String s) {
        super.onPostExecute(s);

    }

}

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;It will create the user profile and update data into Cloud DB.&lt;/strong&gt;&lt;br&gt;
&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--Z1v4PYVH--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/0wu458yi8hslq7kjjv22.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--Z1v4PYVH--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/0wu458yi8hslq7kjjv22.png" alt="Image description" width="880" height="249"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Start chat for first time&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;We have to create room id for chatting between two people.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;public void callCreateRoomId(final String userMobileTo, final String userMobileFrom) {

    CloudDBHelper.getInstance().openDb(new OnDBZoneOpen() {
        @Override
        public void isDBZoneOpen(boolean isConnected, CloudDBZone cloudDBZone) {
            if (cloudDBZone != null) {
                ChatRoomId roomId = new ChatRoomId();
                mRoomDataIndex = mRoomDataIndex + 1;
                AppLog.logE(TAG, "New ROOM IS WILL BE ===&amp;gt; " + mRoomDataIndex);
                roomId.setRoom_id(String.valueOf(mRoomDataIndex));
                roomId.setUser_mobile_to(userMobileTo);
                roomId.setUser_mobile_from(userMobileFrom);
                roomId.setUpdate_shadow_flag(true);
                Task&amp;lt;Integer&amp;gt; insertTask = cloudDBZone.executeUpsert(roomId);
                insertTask.addOnSuccessListener(insertSuccessListener(roomId))
                        .addOnFailureListener(new OnFailureListener() {
                            @Override
                            public void onFailure(Exception e) {
                                AppLog.logE(TAG, "Exception in creating room id " + e.getLocalizedMessage());
                            }
                        }).addOnCanceledListener(new OnCanceledListener() {
                    @Override
                    public void onCanceled() {
                        AppLog.logE(TAG, "Inside on cancel listener");
                    }
                });
            } else {
                if (mOnApiError != null) {
                    mOnApiError.onError("Cloud database zone is null", new Throwable("CloudDBZone is null"));
                }
            }
        }
    });

}

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--vSbi-BqE--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ggsi3jndmdu0jdoatyx3.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--vSbi-BqE--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/ggsi3jndmdu0jdoatyx3.png" alt="Image description" width="880" height="183"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Get previous chats from cloudDB&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;public void getUserChatByRoomID(String roomId, Context context) {
    CloudDBZoneQuery&amp;lt;UserChat&amp;gt; query = CloudDBZoneQuery.where(UserChat.class).equalTo(DBConstants.roomId, roomId).orderByAsc(DBConstants.MESSAGE_TIMESTAMP);
    getUserChat(query, context);
}

private void getUserChat(CloudDBZoneQuery&amp;lt;UserChat&amp;gt; userQuery, Context context) {
    CloudDBHelper.getInstance().openDb((isConnected, cloudDBZone) -&amp;gt; {
        Task&amp;lt;CloudDBZoneSnapshot&amp;lt;UserChat&amp;gt;&amp;gt; queryTask = cloudDBZone.executeQuery(userQuery,
                CloudDBZoneQuery.CloudDBZoneQueryPolicy.POLICY_QUERY_FROM_CLOUD_ONLY);
        queryTask.addOnSuccessListener(userChatCloudDBZoneSnapshot -&amp;gt; {
            processSnapShot(userChatCloudDBZoneSnapshot.getSnapshotObjects(), context);
        });
    });
}


private void processSnapShot(CloudDBZoneObjectList&amp;lt;UserChat&amp;gt; userCloudDBZoneSnapshot, Context context) {
    if (userCloudDBZoneSnapshot != null) {
        ArrayList&amp;lt;UserChat&amp;gt; users = new ArrayList&amp;lt;&amp;gt;();
        while (userCloudDBZoneSnapshot.hasNext()) {
            UserChat user = null;
            try {
                user = userCloudDBZoneSnapshot.next();
                users.add(user);
            } catch (AGConnectCloudDBException e) {
                e.printStackTrace();
                CloudDBHelper.getInstance().closeDb(context);
            }

        }
        userChatMutableLiveData.setValue(users);
        CloudDBHelper.getInstance().closeDb(context);
    }
}

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;Start Sending chat messages&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;messageType: user can send message in text, image, location or in video Types.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;private void setMessage(String messageType) {

    Util.showProgressBar(MessageActivity.this);
    UserChat userChat = new UserChat();
    userChat.setRoom_id(roomId);
    userChat.setMessage_timestamp(Long.parseLong(Util.getTimeStamp()));
    userChat.setChat_id(Util.getRandomNumber());
    userChat.setReceiver_name(receiverText);
    userChat.setReceiver_phone(receiverPhoneNumber);
    userChat.setSender_name(ChitChatSharedPref.getInstance().getString(Constants.USER_NAME, ""));
    userChat.setSender_phone(ChitChatSharedPref.getInstance().getString(Constants.PHONE_NUMBER, ""));

    userChat.setMessage_type(messageType);
    switch (messageType) {

        case Constants.MESSAGE_TYPE_TEXT:
            userChat.setMessage_data(textSend.getText().toString());
            messageViewModel.saveUserChat(userChat);
            messageViewModel.userUpdatedSuccessfully.observe(MessageActivity.this, aBoolean -&amp;gt; {
                if (aBoolean) {
                    Util.stopProgressBar();
                    getChatList();
                } else {
                    Util.stopProgressBar();
                }
            });
            break;
    }
    messageViewModel.queryForToken(receiverPhoneNumber, MessageActivity.this);


}

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;It will save user data into cloud dB&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;public void saveUserChat(UserChat userChat) {
    CloudDBHelper.getInstance().openDb((isConnected, cloudDBZone) -&amp;gt; {
        if (cloudDBZone != null) {
            Task&amp;lt;Integer&amp;gt; insertTask = cloudDBZone.executeUpsert(userChat);
            insertTask
                    .addOnSuccessListener(integer -&amp;gt;
                            userUpdatedSuccessfully.setValue(true))
                    .addOnFailureListener(e -&amp;gt; {
                        userUpdatedSuccessfully.setValue(false);
                        AppLog.logE(TAG, e.getMessage());
                    });

        } else {
            userUpdatedSuccessfully.setValue(false);
        }
    });
}

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;strong&gt;It's time to send push notification&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;public void queryForToken(String phoneNumber, Context context) {
    CloudDBZoneQuery&amp;lt;User&amp;gt; query = CloudDBZoneQuery.where(User.class).equalTo(DBConstants.userNumber, phoneNumber);
    processNumberCheck(query, context);
}

messageViewModel.tokenMutableLiveData.observe(MessageActivity.this, s -&amp;gt; {
    PushApis pushApis = new PushApis(MessageActivity.this);
if (messageType.equalsIgnoreCase(Constants.MESSAGE_TYPE_TEXT)) {
        pushApis.sendPushNotification(roomId, messageType, "104739093", MessageActivity.this.textSend.getText().toString(), s);
        textSend.setText("");
    }
});

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--ZefiuAwV--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/qb86lmsyyizh1itwcr6m.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--ZefiuAwV--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/qb86lmsyyizh1itwcr6m.png" alt="Image description" width="722" height="1310"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Setting up push messaging API's&lt;/strong&gt;&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight plaintext"&gt;&lt;code&gt;public class PushApis {

    private Context context;

    public PushApis(Context context) {
        this.context = context;
    }

    public void sendPushNotification(String chatId, String message, String appId, String messageData, String userPushTokens) {
        try {
            StrictMode.ThreadPolicy policy = new StrictMode.ThreadPolicy.Builder().permitAll().build();
            StrictMode.setThreadPolicy(policy);
            String response = "";
            URL url = new URL(Constants.TOKEN_URL);
            HttpURLConnection connection = (HttpURLConnection) url.openConnection();
            connection.setDoOutput(true);
            connection.setInstanceFollowRedirects(false);
            connection.setRequestMethod("POST");
            connection.setRequestProperty("Content-Type", "application/x-www-form-urlencoded");
            connection.setRequestProperty("POST", "/oauth2/v3/token   HTTP/1.1");
            connection.setRequestProperty("Host", "oauth-login.cloud.huawei.com");
            HashMap&amp;lt;String, String&amp;gt; params = new HashMap&amp;lt;&amp;gt;();
            params.put("grant_type", "client_credentials");
            params.put("client_secret", Constants.CLIENT_SECRET);
            params.put("client_id", Constants.CLIENT_ID);
            String postDataLength = getDataString(params);
            OutputStream os = connection.getOutputStream();
            BufferedWriter writer = new BufferedWriter(
                    new OutputStreamWriter(os, "UTF-8"));
            writer.write(postDataLength);

            writer.flush();
            writer.close();
            os.close();
            int responseCode = connection.getResponseCode();


            if (responseCode == HttpsURLConnection.HTTP_OK) {
                String line;

                BufferedReader br = new BufferedReader(new InputStreamReader(connection.getInputStream()));
                while ((line = br.readLine()) != null) {
                    response += line;
                }
            } else {
                response = "";

            }
            AppLog.logE("Response", response);
            Gson gson = new Gson();
            BearerRequest bearerRequest = gson.fromJson(response, BearerRequest.class);
            triggerPush(bearerRequest.getAccess_token(), appId, chatId, message, messageData, userPushTokens);
        } catch (Exception e) {
            e.printStackTrace();
        }
    }

    private String getDataString(HashMap&amp;lt;String, String&amp;gt; params) throws UnsupportedEncodingException {
        StringBuilder result = new StringBuilder();
        boolean first = true;
        for (Map.Entry&amp;lt;String, String&amp;gt; entry : params.entrySet()) {
            if (first)
                first = false;
            else
                result.append("&amp;amp;");
            result.append(URLEncoder.encode(entry.getKey(), "UTF-8"));
            result.append("=");
            result.append(URLEncoder.encode(entry.getValue(), "UTF-8"));
        }
        return result.toString();
    }

    private void triggerPush(String bearer, String appId, String chatId, String messageType, String messageData, String userPushTokens) {
        try {
            StrictMode.ThreadPolicy policy = new StrictMode.ThreadPolicy.Builder().permitAll().build();
            StrictMode.setThreadPolicy(policy);
            String response = null;
            URL url = new URL("https://push-api.cloud.huawei.com/v1/" + appId + "/messages:send");
            HttpURLConnection connection = (HttpURLConnection) url.openConnection();
            connection.setDoOutput(true);
            connection.setInstanceFollowRedirects(false);
            connection.setRequestMethod("POST");
            connection.setDoOutput(true);
            connection.setRequestProperty("Content-Type", "application/x-www-form-urlencoded");
            connection.setRequestProperty("Authorization", "Bearer " + bearer);
            connection.setRequestProperty("Host", "oauth-login.cloud.huawei.com");
            connection.setRequestProperty("POST", "/oauth2/v2/token   HTTP/1.1");
            OutputStream os = connection.getOutputStream();
            Data data = new Data();
            data.message = messageType;
            data.roomId = chatId;
            data.messageData = messageData;
            data.sender_name = senderName;
            data.sender_phone = senderPhone;
            data.title = context.getResources().getString(R.string.app_name);

            ArrayList&amp;lt;String&amp;gt; token = new ArrayList&amp;lt;&amp;gt;();
            token.add(userPushTokens);

            Message message = new Message();
            message.tokens = token;
            message.data = data.toString();

            PushMessageRequest pushMessageRequest = new PushMessageRequest();

            pushMessageRequest.message = message;
            pushMessageRequest.validate_only = false;

            BufferedWriter writer = new BufferedWriter(
                    new OutputStreamWriter(os, "UTF-8"));

            Gson gson = new Gson();
            JSONObject jsonObject = new JSONObject(gson.toJson(pushMessageRequest, PushMessageRequest.class));
            writer.write(jsonObject.toString());
            writer.flush();
            writer.close();
            os.close();
            int responseCode = connection.getResponseCode();
            String line = null;
            BufferedReader br = new BufferedReader(new InputStreamReader(connection.getInputStream()));
            while ((line = br.readLine()) != null) {
                response += line;
            }
            AppLog.logE("Response", response);
        } catch (Exception e) {
            e.getStackTrace();
        }
    }
}

&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;&lt;a href="https://res.cloudinary.com/practicaldev/image/fetch/s--3vgHwvLd--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/qcpyg0j00gn97ekr8j33.png" class="article-body-image-wrapper"&gt;&lt;img src="https://res.cloudinary.com/practicaldev/image/fetch/s--3vgHwvLd--/c_limit%2Cf_auto%2Cfl_progressive%2Cq_auto%2Cw_880/https://dev-to-uploads.s3.amazonaws.com/uploads/articles/qcpyg0j00gn97ekr8j33.png" alt="Image description" width="395" height="790"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Conclusion&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;In this article, we have learned how we can create a simple messaging application with cloud dB, auth service and push kit. We can also use cloud storage for store profile picture, location, documents or audio and video files.&lt;/p&gt;

&lt;p&gt;Thanks for reading this article. Be sure to like and comment to this article, if you found it helpful. It means a lot to me.&lt;/p&gt;

&lt;p&gt;&lt;strong&gt;Reference&lt;/strong&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://developer.huawei.com/consumer/en/agconnect/cloud-base/"&gt;https://developer.huawei.com/consumer/en/agconnect/cloud-base/&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://developer.huawei.com/consumer/en/doc/development/HMSCore-Guides/service-introduction-0000001050040060"&gt;https://developer.huawei.com/consumer/en/doc/development/HMSCore-Guides/service-introduction-0000001050040060&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;&lt;a href="https://developer.huawei.com/consumer/en/agconnect/auth-service/"&gt;https://developer.huawei.com/consumer/en/agconnect/auth-service/&lt;/a&gt;       &lt;/p&gt;

</description>
      <category>huawei</category>
      <category>cloud</category>
      <category>push</category>
      <category>java</category>
    </item>
  </channel>
</rss>
