Hello all, I’am pulling data from server to couchbase lite (My device) although the problem occurs here pulled data is not updating immediately even after replication status is IDLE or STOPPED, I tried by placing a thread.wait for 5 second to allow data to be settle in device which works fine. But how to confirm whether the data in mobile has been updated successfully same as on server without using sleep(5000) thread wait.
In my current work all working fine after put a wait for 5 second after replication is stopped or idle. But wait is not reliable and proper way I’ve to make sure as data has been updated in device.
I’ve used changed listener but same problem happening there it seems I’ve to put a wait for 5 sec to all data to be settle on device.
You definitely should not need to wait. Checking via the callback is more reliable, but you’re saying that’s not working either. How are you checking your data is synced?
ok Let me show my code here:
Here the pulling sync:
syncUrl = new URL("http://000.000.000.000:4984/db");
Replication pullReplication = database.createPullReplication(syncUrl);
pullReplication.setContinuous(true);
pullReplication.start();
//This is change listener means if Replication status is changed either IDLE or Stopped anything inside change listener will execute
pullReplication.addChangeListener(new Replication.ChangeListener() {
@Override
public void changed(Replication.ChangeEvent changeEvent) {
if (changeEvent.getStatus().toString().equals("REPLICATION_IDLE")) {
//Here is my code/function I want to execute along updated database
}
}
}); //listener
I would like to know if something is missing from here that’s causing data to be replicated immediately.
Is there a guest user enabled on the sync gateway ? because I couldn’t see any authenticator passed to your pull replicator. Please check wether any errors on replication there could be something like 401, if guest user is disabled and you are not passing the credentials with replicator.
Here’s the configuration file:
{
"interface":":4984",
"adminInterface":"0.0.0.0:4985",
"log":["*"],
"replications":[
{
"replication_id":"My Replication",
"source": "db",
"target": "http://000.000.000.000:4985/etp",
"continuous":true
}
],
"databases":{
"etp":{
"users": { "GUEST": { "disabled": false, "admin_channels": ["*"] } },
"server":"http://000.000.000.000:8091",
"username":"myuser",
"password":"************",
"sync":`function(doc) {channel(doc.channels);}`
}
}
}
But currently replication pulling is working the only issue I’ve that I’ve to wait for few seconds after pulling data when replication status is change either IDLE or STOPPED. If I wait for 5 second then I checked in my mobile data is showing as 2.8mb means data has been pulled on my device. While I don’t want to wait by using sleep(5000) as I said its not proper way. I should make sure data is pulled successfully or my device data is same as server…
I usually look at replication state transitions. See if this blog post helps: https://blog.couchbase.com/determining-status-replication-couchbase-lite/
I think I’m validating wrong to check either the document has been replicated or not. How to check either a document is exist in couch db by using its id? I want to check by finding a single document using its Id after replicating to see either the database is updated or not.
You can use the getDocument API to check if document exists in db or not.
Also, have you tried registering for database change listener and handling change notifications in the callback?
I am sorry all of you but I am newbie here what I am trying to do its just an signup activity for which I want to make sure on signup button click pulled all updated/latest data via replication on device and validate either the user is already registered or not. Please have look on this complete code so may you can point a mistake.
**// Database Configuration**
try {
manager = new Manager(new AndroidContext(getApplicationContext()), Manager.DEFAULT_OPTIONS);
} catch (IOException e) {
e.printStackTrace();
}
Database database = null;
try {
database = manager.getDatabase("db");
} catch (CouchbaseLiteException e) {
e.printStackTrace();
}
//End of Database Configuration
//Replication Starts Here:
URL syncUrl;
String ret;
syncUrl = new URL("http://000.000.000.000:4984/db");
Replication pullReplication = database.createPullReplication(syncUrl);
pullReplication.setContinuous(true);
pullReplication.start();
//Replication End here
//Replication ChangeListener Start Here
res.addChangeListener(new Replication.ChangeListener() {
@Override
public void changed(Replication.ChangeEvent changeEvent) {
boolean validate1=false; // This will check either user exist in pulled data or not
ReplicationState dest = changeEvent.getTransition().getDestination();
if(dest.name().equals("IDLE") || dest.name().equals("STOPPED")) { // if replication is IDLE or STOPPED
//Set query
Query query = database.createAllDocumentsQuery();
QueryEnumerator result = null;
try {
result = query.run();
} catch (CouchbaseLiteException e) {
e.printStackTrace();
}
//Validating email in pulled data
Document doc = database.getDocument("aleem");
`Preformatted text`//This document is already exist in server so after replication it should also be in device data
String retemail = (String) doc.getProperty("email");
if(retemail == null){
Log.d("Rep Status:", "Account not exist");
validate1=true;
}
else {
validate1=false;
Log.d("Rep Status:", "Account exist"); // I should get this result
}
}});
Output is here:
07-08 13:59:52.477 17930-18619/elambak.elambak_portal D/Dest:: IDLE
//Means replication is in IDLE
07-08 13:59:52.487 17930-18619/elambak.elambak_portal D/Rep Status:: Account not exist
//So if replication is idle and data is replicated then It should say account is exist
//because account is already exist on server but it says "Account not exist
Again in this current work if I put thread to sleep for 5000 second then all working fine it seems like replication require little time to settle data in device even if its status is IDLE or STOPPED.
I hope anybody can catch the issue or mistake I am doing.
Thank You All
As suggested above, have you tried registering for database change listener and handling change notifications in the callback?
Hello here again; I really need your help. Though i am doing little mistake somewhere that you may point:
URL syncUrl;
String ret;
syncUrl = new URL("http://172.104.145.208:4984/etp"); // I am testing with the Android emulator
Replication pullReplication = database.createPullReplication(syncUrl);
pullReplication.setContinuous(true);
//pullReplication.addChangeListener((Replication.ChangeListener) this);
pullReplication.start();
Here’s simple pull replication code that’s calling when you click on signup button from android activity. ok, This data need to be pulled so that user can proceed signup with validity about either the account is exist or not.
What’s going wrong here once application is installed and run there’s no data which is fine.
Once user clicks on signup button I found application has some data it showing in android application setting. It’s means data has been pulled which is fine.
But on server I’ve deleted all documents but when proceeding signup it says email already exist.
When I tried to create account from another id its working fine means push working but on pull it is not getting data from server because I had deleted documents from server so where it is getting from the data?
Please reply me or ask anything about this work.
Can you turn on appropriate logging to see what documents are being fetched on pull. Also, in your change listener, please log the changes that you see. Also please specify the logic that you are using to check if user exists.
How did you delete the documents on the server? Did you delete it via the sync gateway API ?