Tuesday, 25 July 2017

Build a real-time data application using NodeJs, Socket.io

In older days real-time data updates was achieved by having a timer to refresh a page or sending an Ajax request to the server to get the new data. Sometimes it makes requests unnecessarily to server even though no data updates. This concept is called polling.
Alternatively, Real-time data update is when data is updated on server, clients get notified for a refresh or data will be pushed to clients from server. It avoids unnecessary hits to the server.

In this section, we are going to build a very simple app which will have real-time data update capability.

Requirements
Nodejs
AngularJs

Download and install NodeJs. if it is already installed, then we can go for next step.
After nodejs is installed, open command prompt and create a app directory called 'realtime-app', navigate to the directory and run the following command.

 $ npm init  

The npm init command will create an empty project with a package.json file.

We need to install Express, Socket.io and socket.io-client libraries

 $ npm install socket.io express --save  

-save will save package information in package.json and download everything to node_modeules folder.
Now, Install Jquery

 $ npm install jquery --save  

Now, we are ready to code. First code server side portion.
Create a new file called app.js in realtime-app folder.

 var express = require('express');   
 var app = express();   
 var server = require('http').createServer(app);   
 var io = require('socket.io')(server);  
 app.use(express.static(__dirname + '/node_modules'));   
 app.get('/', function(req, res,next) {   
   res.sendFile(__dirname + '/index.html');  
 });   
 server.listen(4200);   

So the server is ready to listen on port 4200.
Now we add publish and subscribe events on server. Add below code in app.js just before server.listen(4200);

 io.on('connection', function(client) {   
   console.log('Client connected...');  
   client.on('messages', function(data) {  
       client.emit('broad', data);  
   });  
 });  

io.on listening connections.
client.on listening broadcast / emit event from client. Here, server subscribes to 'message' event from client.
client.emit will broadcast an event to client. Here, when server receives 'message' event from client it broadcast 'broad' event to clients which are subscribed to 'broad' event.
so the server code is like

 var express = require('express');   
 var app = express();   
 var server = require('http').createServer(app);   
 var io = require('socket.io')(server);  
 app.use(express.static(__dirname + '/node_modules'));   
 app.get('/', function(req, res,next) {   
   res.sendFile(__dirname + '/index.html');  
 });   
 io.on('connection', function(client) {   
   console.log('Client connected...');  
   client.on('messages', function(data) {  
       client.emit('broad', data);  
   });  
 });  
 server.listen(4200);   

Now the server portion is ready.
Lets move to client portions.
First part is index.html which is the actual client to display data. Other one is a web API which will broadcast / publish the data to client when the data is updated on data source.
Create index.html file.

 <!doctype html5>   
 <html lang="en" ng-app="realtimeapp">   
   <head>  
   </head>  
   <body ng-controller="appCtrl as appc">  
     <h1>{{appc.msg}}</h1>  
     <div >{{appc.data}}</div>  
            <script src="/jquery/dist/jquery.js"></script>  
            <script src="https://ajax.googleapis.com/ajax/libs/angularjs/1.5.6/angular.min.js"></script>  
     <script src="/socket.io/socket.io.js"></script>  
 <script>    
 var app1 = angular.module('realtimeapp', []);  
 app1.controller('appCtrl', function AppController($scope,socket) {  
      self = this;  
      self.msg="Welcome Hello world";  
       socket.on('broad', function(data) {  
                 self.data = data;  
        });  
 });  
 app1.factory('socket', function ($rootScope) {  
  var socket = io.connect('http://uscgspare:4200');  
  return {  
   on: function (eventName, callback) {  
    socket.on(eventName, function () {   
     var args = arguments;  
     $rootScope.$apply(function () {  
      callback.apply(socket, args);  
     });  
    });  
   },  
   emit: function (eventName, data, callback) {  
    socket.emit(eventName, data, function () {  
     var args = arguments;  
     $rootScope.$apply(function () {  
      if (callback) {  
       callback.apply(socket, args);  
      }  
     });  
    })  
   }  
  };  
 });  
 </script>   
   </body>  
 </html>   

Inlude Angularjs, jquery and socket.io client libraries in script part. socket.io.js is client library for socket.io.

In javascript part, a factory module is created to publish (broadcast) / subscribe (recieve) the events from and to server.

socket.on('broad', function(data){..}) will listen 'broad' event from server. when 'broad' event is published from server, client will listen and get the data to display / pocess.

When data needs to be updated in client, invoke the server 'message' event will emit the 'broad' event and client index.html will receive the 'broad' event.

Assume lets have a watcher which keep on watching the data changes in data source /database. When it finds a change in data needs to be pushed to client or client needs to be notified for  new data availability. We can go either way. but i prefer the second one.

So the watcher required to have a way to invoke the Server to push the notification to client that there is data refresh required. the Second part will do invoke the server.

Before starting code, install socket.io-client

 $ npm install socket.io-client --save  

We need to modify the app.js as below

 var ioClient = require('socket.io-client');  

 var router = express.Router();  
 var socket = ioClient.connect('http://localhost:4200');  
 router.get('/', function(req, res) {  
 //logic for finding data changes  
      socket.emit('messages', 'New data available for update');  
      res.json({ message: 'hooray! welcome to our api!' });   
 });  
 app.use('/api', router);  

Here the idea is create a rest API, will be called from the watcher when it finds new data is available.
Create socket.io-client object to emit (boradcast) 'message' event to server. ioClient is connected to server and ready to listen and emit the events.

So final app.js will be like below
 var express = require('express');   
 var app = express();   
 var server = require('http').createServer(app);   
 var io = require('socket.io')(server);  
 var ioClient = require('socket.io-client');  
 app.use(express.static(__dirname + '/node_modules'));   
 app.get('/', function(req, res,next) {   
   res.sendFile(__dirname + '/index.html');  
 });   
 io.on('connection', function(client) {   
   console.log('Client connected...');  
   client.on('messages', function(data) {  
       client.emit('broad', data);  
   });  
 });  
 var router = express.Router();  
 var socket = ioClient.connect('http://localhost:4200');  
 router.get('/', function(req, res) {  
 //logic for finding data changes  
      socket.emit('messages', 'New data available for update');  
      res.json({ message: 'hooray! welcome to our api!' });   
 });  
 app.use('/api', router);  
 server.listen(4200);   

Thats it ready to run.
Step 1
 $ node app.js  

Above will up the server and available for clients on localhost and port 4200
Step 2.
Open a browser and run the index.html as 'http://localhost:4200/index.html"
It displays the default message 'Welcome Hello world'

Now open other browser window and call the api to notify new data availability to the index.html.
'http://localhost:4200/api'.

Now, the index.html will be updated with 'New data available for update'.

Calling 'http://localhost:4200/api' is emitting the 'message' event.
 socket.emit('messages', 'New data available for update');  

and server
 client.on('messages', function(data) {  
       client.emit('broad', data);  
   });  
is listening the 'message' event and again emit the 'broad' event.

Index.html is subscribed to 'broad' event,
 socket.on('broad', function(data) {  
           self.data = data;  
 });  
the above event listening 'broad' event and update the controller variable, then it reflects to view page.

So when index.html receives the flag for new data availability from data watcher, client can request the data refresh.

Thursday, 29 June 2017

MongoDB - Using Aggreagte and Text Search to compare and map records from two different datasets collections

Recently I had a scenario to compare two different data sets to find the matched records based on a text fields. The challenge is cant do it exact matching.

For Example
DataSet1 contains a record with field as
'Name : ABC Company'

DataSet2 may contains records as
Name : 'ABC Company Ltd.'

So decided to find the match based on ranking system.
Take every record in CUSTOMER1 and compare with CUSTOMER2 records and put score for the match. If the score is greater than 0.75 include CUSTOMER2 record to CUSTOMER1 record with score. Then get the highest match scored record.

Step 1.
Imported both data sets to MongoDB as two different collection, customer1 and customer2.
CUSTOMER1 data Sample
{
    "CUSTOMER1NAME": "ABC COMPANY",
    "CUSTOMER1ID": "CRM10003"
}


CUSTOMER2 data sample
{
  "CUSTOMER2NAME": "ABC COMPANY LTD.",
  "CUSTOMER2ID": "ORAXYZ100"
},
{
  "CUSTOMER2NAME": "XYZ Logistics",
  "CUSTOMER2ID": "ORAXYZ10333"
},
{
  "CUSTOMER2NAME": "ABC COMPANY (INDIA) LIMITED.",
  "CUSTOMER2ID": "ORAXYZ10022"
},
{
  "CUSTOMER2NAME": "EXCEL WORKS",
  "CUSTOMER2ID": "ORAXYZ10032"
}
 

Step 2.
Since we are going to use aggregate function with $text option, it is necessary to create TextIndex for CUSTOMER2 collection.

db.CUSTOMER2.createIndex(
                           { "CUSTOMER2NAME": "text" },
                           { name: "TextIndex" }
                         )
 
Step 3.
Below script will compare & score every record in CUSTOMER1 with CUSTOMER2 records using aggregate function.Score greater than 0.75 records are stored in CUSTOMER1 record item as match property.

  
 db.getCollection('CUSTOMER1').find({}).noCursorTimeout().forEach(function(item) {  
        var customername = item.CUSTOMER1NAME    
        var collection =    db.getCollection('CUSTOMER2').aggregate( [
        { $match: { $text: { $search: customername ,$diacriticSensitive: true  }} },
        { $project: { CUSTOMER2NAME:1, CUSTOMER2ID:1, _id: 0, score: { $meta: "textScore" } } },
        { $match: { score: { $gt: 0.75} } },
     
        ])
        if(collection._batch.length >0)
        {
            item.match = collection._batch;
        }
        db.CUSTOMERMAPPING.insert(item); 
    
})
Output of the above script will be like
  {
    "_id" : ObjectId("59540979a2109c38f5ca7112"),
    "CUSTOMER1NAME" : "ABC COMPANY",
    "CUSTOMER1ID" : "CRM10003",
    "match" : [ 
        {
            "CUSTOMER2NAME" : "ABC COMPANY (INDIA) LIMITED.",
            "CUSTOMER2ID" : "ORAXYZ10022",
            "score" : 1.25
        }, 
        {
            "CUSTOMER2NAME" : "ABC COMPANY LTD.",
            "CUSTOMER2ID" : "ORAXYZ100",
            "score" : 1.33333333333333
        }
    ]
}
 
Result will have all records from CUSTOMER2 with score property.

Step 4.
Now the step is take the maximum score from match records
 
db.getCollection('CUSTOMERMAPPING').aggregate([{
    $unwind: '$match'
}, {
    "$group": {
        "_id": "$CUSTOMER1ID",
        "CUSTOMER1NAME": {"$first": "$CUSTOMER1NAME"},
        "maxScore": {   
            "$max": "$match.score"
        },
        "matchgrp": {
            "$push": {
                "account_name": "$match.CUSTOMER2NAME",
                "acount_number": "$match.CUSTOMER2ID",
                "score": "$match.score"
            }
        }
    }
}
, {
    "$project": {
        _id: "$_id",
        CUSTOMER1NAME: "$CUSTOMER1NAME",
        topmatch: {
            "$setDifference": [{
                    "$map": {
                        "input": "$matchgrp",
                        "as": "matched",
                        "in": {
                            "$cond": [{
                                    "$eq": ["$maxScore", "$$matched.score"]
                                },
                                "$$matched",
                                false
                            ]
                        }
                    }
                },
                [false]
            ]
        }
 
    }
},{ $out : "HIGHSCOREMATCH" }],{allowDiskUse:true})  
 
$out will create result to new collection 'HIGHSCOREMATCH'
  {
    "_id" : "CRM10003",
    "CUSTOMER1NAME" : "ABC COMPANY",
    "topmatch" : [ 
        {
            "account_name" : "ABC COMPANY LTD.",
            "acount_number" : "ORAXYZ100",
            "score" : 1.33333333333333
        }
    ]
}
 
Most matched record from CUSTOMER2 will be mapped to CUSTOMER1 record.
Even the match will not be 100% accurate, it reduces our time for mapping manually.
Exported the final output in a excel and business user reviewed fixed the wrong matches. It reduces the time for us, instead of doing millions of records manually search and mapping.

Thanks
 

Friday, 22 February 2013

SQL server - Sync two SQL tables with same schema

Sync data in two tables with same schema in generic way explained here.

Recently I had a requirement in one of our project that need to sync two different database with few common master data tables. Since I don't have control  in source database, I could not use replication or trigger concept. So I got this logic doing Google, and customized it for insert and update records.

Here I have used MERGE statement for SQL 2008 and as well as insert and update statements for SQL 2005.

Here I am taking two tables cities, cities1 with same schema as

CREATE TABLE [dbo].[Cities](
      [CityId] [int] IDENTITY(1,1) NOT NULL,
      [CityName] [varchar](50) NULL,
)

CREATE TABLE [dbo].[Cities1](
      [CityId] [int] IDENTITY(1,1) NOT NULL,
      [CityName] [varchar](50) NULL,
)


INSERT INTO [dbo].[Cities] ([CityName]) VALUES ('Chennai')
INSERT INTO [dbo].[Cities] ([CityName]) VALUES ('Mumbai')
INSERT INTO [dbo].[Cities] ([CityName]) VALUES ('Bangalore') 

INSERT INTO [dbo].[Cities1] ([CityName]) VALUES ('Chennai')
INSERT INTO [dbo].[Cities1] ([CityName]) VALUES ('Bangalore')
So I am going to insert and update whatever in [dbo].[Cities] table to [dbo].[Cities1] table by giving table names and primary key fields of each table.
Logic behind this is generate SQL statement and execute it.
DECLARE @currentTableName sysname
DECLARE @newTableName sysname
DECLARE @currentSchemaName sysname
DECLARE @newSchemaName sysname

DECLARE @CurrentKey sysname
DECLARE @NewSchemaKey sysname

DECLARE @sqlcmd varchar(max)
DECLARE @colname sysname
DECLARE @collist varchar(max)
DECLARE @Valcollist varchar(max)

DECLARE @UpdateCollist varchar(max)

SET @currentTableName = 'Cities'
SET @newTableName = 'Cities1'
SET @currentSchemaName = 'dbo'
SET @newSchemaName = 'dbo'

SET @CurrentKey = 'CityId'
SET @NewSchemaKey = 'CityId'

SET @collist = ''
SET @Valcollist = ''
SET @UpdateCollist =''

DECLARE colCursor CURSOR FOR
select c.name from sys.all_columns c
inner join sys.all_objects o
on c.object_id = o.object_id
where o.type = 'U'
and o.name = @currentTableName
and o.schema_id = schema_id(@currentSchemaName)
ORDER BY column_id
OPEN colCursor  
FETCH NEXT FROM colCursor INTO @colname  
WHILE @@FETCH_STATUS = 0  
BEGIN  
       SET @collist = @collist + '[' + @colname + ']'
       SET @Valcollist = @Valcollist + 'S.[' + @colname + ']'
       SET @UpdateCollist = @UpdateCollist + 'D.[' + @colname + '] = S.['+@colname+']'
      
       FETCH NEXT FROM colCursor INTO @colname  
       IF @@FETCH_STATUS = 0
       BEGIN
               SET @collist = @collist + ','
               SET @UpdateCollist = @UpdateCollist + ','
               SET @Valcollist = @Valcollist + ','
         END
END  
CLOSE colCursor  
DEALLOCATE colCursor
SET @sqlcmd = 'SET IDENTITY_INSERT [' + @newSchemaName + '].[' +
@newTableName + '] ON;'

----- SQL 2008
--SET @sqlcmd = @sqlcmd + 'MERGE INTO ['+@newTableName+']  As D
--USING ['+@currentTableName+'] As S
--ON D.['+ @NewSchemaKey+']CityId = S.['+@CurrentKey+']
--WHEN MATCHED Then Update
--                Set '+@UpdateCollist+'
--WHEN NOT MATCHED then
--          Insert ('+@collist+')
--          Values ('+@Valcollist+');'


-- SQL 2005
-- UPDATE

SET @sqlcmd = @sqlcmd +
' UPDATE ['+@newTableName+'] SET ' +@UpdateCollist+'
FROM ['+@currentTableName+'] WHERE
['+@currentTableName+'].['+@CurrentKey+'] = ['+@newTableName+'].['+@NewSchemaKey+'];'


---- Insert
SET @sqlcmd = @sqlcmd +
'INSERT INTO [' + @newSchemaName + '].[' + @newTableName + '] ('
+ @collist +
') SELECT ' + @collist +
' FROM [' + @currentSchemaName + '].[' + @currentTableName + ']
WHERE [' + @currentTableName + '].[' + @CurrentKey + '] NOT IN
(SELECT [' + @newTableName + '].[' + @NewSchemaKey + '] FROM [' + @newTableName + ']);'


SET @sqlcmd = @sqlcmd + 'SET IDENTITY_INSERT [' + @newSchemaName +
'].[' + @newTableName + '] OFF;'
--EXEC (@sqlcmd)
PRINT @sqlcmd
Thank you. Enjoy coding.

Monday, 31 December 2012

Build an Android app using JQuery and HTML

In this post, I am going to explain how to create a simple android application using Html and javascript as grphical interface. Basic concept is loading html file in Webview object using Web Client in Android.

Assuming Eclipse environment for developing Android applications is ready.

What we are going to do sample?
Create a html file which contains few hard coded contacts list items and two buttons (Exit & About) on the top in Main page. On About click, About us page will be shown. Back button in About Us page returns to Main page.

Create new Android project by clicking File>New>Android Application Project and name it as 'MyContacts'.

First we design a simple HTML file to host it on mobile.
Contact.html
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
    <meta name="viewport" content="width=device-width, initial-scale=1" />
    <title></title>
    <script src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.1/jquery.min.js"></script>
    <style type="text/css">
        body
        {
            background: Black;
            color: White;
            font-size: small;
        }
        .Header
        {
            border: 1px solid #AAA;
            width: 100%;
        }
        
        .Button
        {
            text-align: center;
            border: 1px solid #333;
            background: #AAA;
            width: 50px;
            font-weight: bold;
            padding: 5px;
            float: left;
            color: #000;
            margin: 1px;
            cursor:pointer;
        }
        .Left
        {
            float: left;
        }
        .Right
        {
            float: Right;
        }
        .Content
        {
         Float:Left;
            width: 100%;
            background: #AAA;
            border: 1px solid #AAA;
            height: auto;
            margin: 1px;
        }
        
        .AboutUs
        {
         Float:Left;
            width: 100%;
            background: #AAA;
            border: 1px solid #AAA;
            height: auto;
            margin: 1px;
            padding:10px;
        }
        
        .ContentHeader
        {
            border: 1px solid #333;
            padding: 2px;
            font-weight: bold;
            color: #000;
        }
        .ContentItem
        {
            border: 1px solid #333;
            padding: 2px;
            margin: 1px;
            color: #333;
        }
    </style>
   <script type="text/javascript">
   $(document).ready(function(){
    $("#About").click(function(){
     $(".Content").hide(); 
     $(".AboutUs").show(); 
     });
    $("#Back").click(function(){
     $(".Content").show(); 
     $(".AboutUs").hide(); 
     });
   });
    </script>
</head>
<body>
    <div class="Header">
        <div class="Button Left">
            Exit</div>
        <div id="About" class="Button Right">
            About</div>
    </div>
    <div class="Content">
        <div class="ContentHeader">
            Contacts</div>
        <div class="ContentItem">
            Andrew</div>
        <div class="ContentItem">
            Chris</div>
        <div class="ContentItem">
            David</div>
        <div class="ContentItem">
            Mickel</div>
        <div class="ContentItem">
            Mahesh</div>
    </div>
    <div class="AboutUs" style="display:none;">
    Developed By : tekpot.blogspot.com<br/>
    Thank You! <br/>
    Happy Coding!
    <div id="Back" class="Button Right">
            Back</div>
    </div>
    
</body>
</html>

Preview will be as

In the above html file I have included JQuery plugin google reference. Instead download JQuery and include local reference to html file.
Copy paste Contact.html and Jquery.min.js files in Project folders as mentioned path bellow.
MyContacts/assets/www/contact.html
Create a Webview object and load our Contact.html page in MyContacts activity class.
import android.webkit.WebView;
import android.webkit.WebViewClient;

public class ContactActivity extends Activity {
    /** Called when the activity is first created. */
 WebView mWebView;  

    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.main);
        mWebView = (WebView) findViewById(R.id.webview); 
        mWebView.getSettings().setJavaScriptEnabled(true);  
        mWebView.getSettings().setDomStorageEnabled(true);  
        mWebView.loadUrl("file:///android_asset/www/Contact.html");
    }
}
In the above code WebView mWebView; webview object is declared.

        mWebView.getSettings().setJavaScriptEnabled(true);  
        mWebView.getSettings().setDomStorageEnabled(true);  

above statements enable Javascript and DOM object in Android Webview.

        mWebView.loadUrl("file:///android_asset/www/Contact.html");

LoadUrl loads html file mentioned in the path. Http url can be given in LoadUrl method.
Example

        mWebView.loadUrl("Http://google.com");

Compile and run the application in simulator.
Main Page


About Us page


Thats it we have developed a simple Android application using Javascript and html with out using much Java code.

Wait for next post to load data from server and display on html and javascript.

Happy Coding! :-)

Tuesday, 11 September 2012

Javascript Pivot Library

Arikai - Javascript Pivot Library - Niral Aakkam

A new version of Arikai - a simple javascript pivot library is released. Easy, simple, client side pivot table report generator using Jquery. Arikai supports SUM, AVG, MIN, MAX and COUNT aggregate functions. 

Arikai online demo - Niral Aakkam
Arikai online demo - Niral Aakkam

Edit Layout button offers user to change the report dynamically. New fields can be added  in to / swapped Column Area / Row Area by drag n drop. Few steps of javascript code generates the Pivot Table.

Check Arikai online demo here.

Javascript file and stylesheet file are available for downloaded at Niral Aakkam. or GitHub

Sample website in C# is available at Niral Aakkam dowload page. or GitHub
 

For more information visit Niral Aakkam web site.

Friday, 7 September 2012

Location using GPS in Android programming

GPS Location in Android

Find current latitude and longitude location by using GPS

No need GPRS or Internet connection

We need to add permission for accessing GPS. So put following tag in Android manifest file
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"></uses-permission>  
Import the necessary libraries
 import android.location.Location;  
 import android.location.LocationListener;  
 import android.location.LocationManager;  
Create a Listener class for loaction
 /* Class My Location Listener */  
 public class MyLocationListener implements LocationListener {  
   @Override  
   public void onLocationChanged(Location loc) {  
     loc.getLatitude();  
     loc.getLongitude();  
     String Text = "My current location is: " + "Latitude = "  
         + loc.getLatitude() + "Longitude = " + loc.getLongitude();  
     Toast.makeText(getApplicationContext(), Text, Toast.LENGTH_SHORT)  
         .show();  
     Log.d("TAG", "Starting..");  
   }  
   @Override  
   public void onProviderDisabled(String provider) {  
     Toast.makeText(getApplicationContext(), "Gps Disabled",  
         Toast.LENGTH_SHORT).show();  
   }  
   @Override  
   public void onProviderEnabled(String provider) {  
     Toast.makeText(getApplicationContext(), "Gps Enabled",  
         Toast.LENGTH_SHORT).show();  
   }  
   @Override  
   public void onStatusChanged(String provider, int status, Bundle extras) {  
   }  
 }/* End of Class MyLocationListener */  
Declare LocationManager object in Activity
  LocationManager locationManager; 
  private String provider;
Override onCreate method of Activity
@Override  
   public void onCreate(Bundle savedInstanceState) {  
     super.onCreate(savedInstanceState);  
     setContentView(R.layout.main);   
     LocationListener mlocListener = new MyLocationListener();  
     locationManager.requestLocationUpdates(LocationManager.GPS_PROVIDER, 0, 0, mlocListener);     
      Criteria criteria = new Criteria();  
       criteria.setAccuracy(Criteria.ACCURACY_COARSE);  
       criteria.setAccuracy(Criteria.ACCURACY_FINE);  
       provider = locationManager.getBestProvider(criteria, true);  
       locationManager.requestLocationUpdates(provider, 61000, 250,  
         mlocListener);  
   }
Happy coding...

Saturday, 11 August 2012

Android AutoCompleteTextView data binding based on another AutoCompleteTextView selection

Android - Bind data to an AutoCompleteTextView based on another AutoCompleteTextView selection

Hi friends, here I am going to explain how to load an AutoCompleteTextView based on the selection of another AutoCompleteTextView in Android.

Create screen layout xml file

Add following in layout xml file as station_input.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
        android:id="@+id/ station_input"
        android:layout_width="wrap_content"
        android:layout_height="wrap_content"
        android:orientation="vertical"
        android:padding="10dp" >

        <AutoCompleteTextView
            android:id="@+id/fromStation"
            android:layout_width="wrap_content"
            android:layout_height="wrap_content"
            android:ems="10"
            android:imeOptions="actionNext"
            android:inputType="text"
            android:singleLine="true"
            android:text="@string/From" >
            <requestFocus />
        </AutoCompleteTextView>

         <AutoCompleteTextView
             android:id="@+id/toStation"
             android:layout_width="wrap_content"
             android:layout_height="wrap_content"
             android:ems="10"
             android:imeOptions="actionDone"
            android:inputType="text"
            android:singleLine="true"
             android:text="@string/To" >
            <requestFocus />
        </AutoCompleteTextView>
    </LinearLayout>

Add list_station.xml to the project layout folder

<?xml version="1.0" encoding="utf-8"?>
<TextView xmlns:android="http://schemas.android.com/apk/res/android"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    android:padding="10dp"
    android:textSize="14sp"
    android:textColor="#000">
</TextView>

Bind data to first AutoCompleteTextView

 // Inflate the popup_layout.xml
LinearLayout viewGroup = (LinearLayout) context.findViewById(R.id. station_input);
LayoutInflater layoutInflater = (LayoutInflater) context.getSystemService(Context.LAYOUT_INFLATER_SERVICE);
  View layout = layoutInflater.inflate(R.layout. station_input, viewGroup);

    
    // bind all stations to station auto complete
  AutoCompleteTextView fromStation = (AutoCompleteTextView) layout.findViewById(R.id.fromStation) ;
                   // Helper class for getting Stations list from Databse. 
  DatabaseHelper helper = new  DatabaseHelper();
  List<String> stationsList =helper.GetStations(context); 
  ArrayAdapter<String> adapter = new ArrayAdapter<String>(context, R.layout.list_station, stationsList);
  fromStation.setAdapter(adapter);
  fromStation.setText("");

  
  
  
  toStation = (AutoCompleteTextView) layout.findViewById(R.id.toStation) ;
  toStation.setText("");

setOnItemClickListener for first AutoCompleteTextView

//  add item click listener for fromStation AutocompleteTextView 
  fromStation.setOnItemClickListener(new OnItemClickListener() {
  public void onItemClick(AdapterView<?> arg0, View arg1, int arg2,long arg3){
                                // get the clicked item in fromStation
String fromStationSelected = arg0.getItemAtPosition(arg2).toString().split("-")[1];

                                 // Helper class for getting Stations list from Databse.
DatabaseHelper  helper = new  DatabaseHelper();
  List<String> stationsList = helper.GetToStation(context,  fromStationSelected ); 
  ArrayAdapter<String> adapter = new ArrayAdapter<String>(context, R.layout.list_station, stationsList);
  toStation.setAdapter(adapter);
  toStation.setText("");
 
}
});
    
  toStation.setOnItemClickListener(new OnItemClickListener() {
  public void onItemClick(AdapterView<?> arg0, View arg1, int arg2,long arg3){
  
  // to do what ever you want in item click of second AutoCompleteTextView (toStation)
          
}
});



If any better way, please feel free to comment.

Enjoy Coding.