Skip to content

Instantly share code, notes, and snippets.

@fearphage
Forked from tajchert/A_DATABASEWEAR.md
Last active August 29, 2015 14:16
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save fearphage/941917536fdba597a72a to your computer and use it in GitHub Desktop.
Save fearphage/941917536fdba597a72a to your computer and use it in GitHub Desktop.

This short code will show how to sync database file using Realm, but can be used for any file that you need to send to Wear (using Data API). It just takes any file, change it to Asset object and send it over to Wear device. Also it can be used Mobile->Wear, and Wear->Mobile.

When you need to sync database just call FileSender.syncRealm(context);, that is it!

DISCLAIMER "Proper" way would be to synchronize each transaction to DB, but it in most cases Wear is used very rarely comparing to mobile, so it would most likely cause a battery drain. My idea was to synchronize it only whene it is needed (so for example when app closes). If you want to make sure that you are using latest DB, just send trigger data using MessageAPI from Wear to Phone with ask of syncing over its database, or keep some timestapm of last edit and check it.

public class FileSender extends AsyncTask<Void, Void, Void> {
private Asset asset;
private Context context;
private GoogleApiClient mGoogleAppiClient;
private static final String TAG = "AssetsSender";
public FileSender(Asset asset, Context context) {
this.asset = asset;
this.context = context;
}
@Override
protected Void doInBackground(Void... params) {
sendData(asset);
return null;
}
@Override
protected void onPreExecute() {
mGoogleAppiClient = new GoogleApiClient.Builder(context)
.addApi(Wearable.API)
.build();
mGoogleAppiClient.connect();
}
private void sendData(Asset asset) {
if(asset == null){
return;
}
PutDataMapRequest dataMap = PutDataMapRequest.create("/ourAppDatabase");
byte[] arr = asset.getData();
dataMap.getDataMap().putByteArray("realmDatabase", arr);//for some reason .putAsset wasn't working for me in some cases
PutDataRequest request = dataMap.asPutDataRequest();
PendingResult<DataApi.DataItemResult> pendingResult = Wearable.DataApi.putDataItem(mGoogleAppiClient, request);
pendingResult.setResultCallback(new ResultCallback<DataApi.DataItemResult>() {
@Override
public void onResult(DataApi.DataItemResult dataItemResult) {
Log.d(TAG, "onResult result:" + dataItemResult.getStatus());
}
});
}
public static void syncRealm(Context context){
File writableFolder = context.getFilesDir();
File realmFile = new File(writableFolder, Realm.DEFAULT_REALM_NAME);
Asset realAsset = Tools.assetFromFile(realmFile);
new FileSender(realAsset, context).execute();
}
}
public class ListenerService extends WearableListenerService {
//Remember to decler it as well in Manifest.xml
private static final String TAG = ListenerService.class.getSimpleName();
@Override
public void onDataChanged(DataEventBuffer dataEvents) {
Log.d(TAG, "onDataChanged");
final List<DataEvent> events = FreezableUtils.freezeIterable(dataEvents);
dataEvents.close();
for (DataEvent event : events) {
Uri uri = event.getDataItem().getUri();
String path = uri.getPath();
if ("/ourAppDatabase".equals(path)) {
DataMapItem item = DataMapItem.fromDataItem(event.getDataItem());
byte[] realmAsset = item.getDataMap().getByteArray("realmDatabase");
if(realmAsset != null){
toFile(realmAsset);
//I recommend here calling a Broadcast - getBaseContext().sendBroadcast(new Intent(yourbroadcast here));
}
}
}
}
private void toFile(byte [] byteArray){
File writableFolder = ListenerService.this.getFilesDir();
File realmFile = new File(writableFolder, Realm.DEFAULT_REALM_NAME);
if (realmFile.exists()) {
realmFile.delete();
}
try {
FileOutputStream fos=new FileOutputStream(realmFile.getPath());
fos.write(byteArray);
fos.close();
}
catch (java.io.IOException e) {
Log.d(TAG, "toFile exception: " + e.getLocalizedMessage());
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment