diff --git a/app/src/main/java/com/money/manager/ex/core/docstorage/FileStorageHelper.java b/app/src/main/java/com/money/manager/ex/core/docstorage/FileStorageHelper.java index dc29b37fd..442f62db8 100644 --- a/app/src/main/java/com/money/manager/ex/core/docstorage/FileStorageHelper.java +++ b/app/src/main/java/com/money/manager/ex/core/docstorage/FileStorageHelper.java @@ -116,9 +116,7 @@ public DatabaseMetadata createDatabase(Intent activityResultData) { */ public boolean isLocalFileChanged(DatabaseMetadata metadata) { - MmxDate localLastModifiedMmxDate = getLocalFileModifiedDate(metadata); - Date localModified = localLastModifiedMmxDate.toDate(); - + Date localModified = getLocalFileModifiedDate(metadata).toDate(); // The timestamp when the local file was downloaded. Date localSnapshot = MmxDate.fromIso8601(metadata.localSnapshotTimestamp).toDate(); @@ -128,10 +126,7 @@ public boolean isLocalFileChanged(DatabaseMetadata metadata) { } public boolean isRemoteFileChanged(DatabaseMetadata metadata) { - DocFileMetadata remote = getRemoteMetadata(metadata); - // This is current dateModified at the remote file. - Date remoteModified = remote.lastModified.toDate(); - + Date remoteModified = getRemoteFileModifiedDate(metadata).toDate(); // Check if the remote file was modified since fetched. // This is the modification timestamp of the remote file when it was last downloaded. Date remoteSnapshot = MmxDate.fromIso8601(metadata.remoteLastChangedDate).toDate(); @@ -389,13 +384,19 @@ private void showSelectLocalFileDialog() { * Reads the date/time when the local database file was last changed. * @return The date/time of the last change */ - private MmxDate getLocalFileModifiedDate(DatabaseMetadata metadata) { + public MmxDate getLocalFileModifiedDate(DatabaseMetadata metadata) { File localFile = new File(metadata.localPath); long localFileTimestamp = localFile.lastModified(); MmxDate localSnapshot = new MmxDate(localFileTimestamp); return localSnapshot; } + public MmxDate getRemoteFileModifiedDate(DatabaseMetadata metadata) { + DocFileMetadata remote = getRemoteMetadata(metadata); + // This is current dateModified at the remote file. + return remote.lastModified; + } + private void pollNewRemoteTimestamp(DatabaseMetadata metadata) { // poll every n seconds. long milliseconds = 2 * 1000; diff --git a/app/src/main/java/com/money/manager/ex/sync/SyncManager.java b/app/src/main/java/com/money/manager/ex/sync/SyncManager.java index 348ec1020..f4b1cd49f 100644 --- a/app/src/main/java/com/money/manager/ex/sync/SyncManager.java +++ b/app/src/main/java/com/money/manager/ex/sync/SyncManager.java @@ -168,7 +168,6 @@ public void invokeSyncService(String action) { } DatabaseMetadata current = mDatabases.get().getCurrent(); - String localFile = getDatabases().getCurrent().localPath; Messenger messenger = null; if (getContext() instanceof AppCompatActivity) { // Messenger handles received messages from the sync service. Can run only in a looper thread. @@ -178,11 +177,6 @@ public void invokeSyncService(String action) { Intent syncServiceIntent = IntentFactory.getSyncServiceIntent(getContext(), action, current.localPath, current.remotePath, messenger); // start service SyncService.enqueueWork(getContext(), syncServiceIntent); - - // Reset any other scheduled uploads as the current operation will modify the files. - // abortScheduledUpload(); - - // The messages from the service are received via messenger. } /** @@ -238,45 +232,6 @@ public void stopSyncServiceAlarm() { // todo use JobManager. } - /** - * Synchronization using job manager. - */ -// public void triggerSyncJob() { -// // validations -// -// if (!isActive()) return; -// -// // Make sure that the current database is also the one linked in the cloud. -// String localPath = new DatabaseManager(getContext()).getDatabasePath(); -// if (TextUtils.isEmpty(localPath)) { -// new UIHelper(getContext()).showToast(R.string.filenames_differ); -// return; -// } -// -// String remotePath = getRemotePath(); -// if (TextUtils.isEmpty(remotePath)) { -// Toast.makeText(getContext(), R.string.select_remote_file, Toast.LENGTH_SHORT).show(); -// return; -// } -// -// // easy comparison, just by the file name. -// if (!areFileNamesSame(localPath, remotePath)) { -// // The current file was probably opened through Open Database. -// Toast.makeText(getContext(), R.string.db_not_dropbox, Toast.LENGTH_LONG).show(); -// return; -// } -// -// // action -// -// new JobRequest.Builder(SyncConstants.INTENT_ACTION_SYNC) -// .setExecutionWindow(500, 1000) -// .build() -// .schedule(); -// -// // todo sync -// // todo abort scheduled job, if any. -// } - public void triggerSynchronization() { if (!canSync()) return; diff --git a/app/src/main/java/com/money/manager/ex/sync/SyncPreferenceFragment.java b/app/src/main/java/com/money/manager/ex/sync/SyncPreferenceFragment.java index 83c5274e4..f4d0f4367 100644 --- a/app/src/main/java/com/money/manager/ex/sync/SyncPreferenceFragment.java +++ b/app/src/main/java/com/money/manager/ex/sync/SyncPreferenceFragment.java @@ -19,6 +19,7 @@ import static android.content.Context.MODE_PRIVATE; +import android.app.AlertDialog; import android.os.Bundle; import android.text.TextUtils; @@ -30,13 +31,18 @@ import com.money.manager.ex.R; import com.money.manager.ex.core.Core; import com.money.manager.ex.core.UIHelper; +import com.money.manager.ex.core.docstorage.FileStorageHelper; +import com.money.manager.ex.home.DatabaseMetadata; import com.money.manager.ex.home.RecentDatabasesProvider; import com.money.manager.ex.settings.PreferenceConstants; import com.money.manager.ex.sync.events.DbFileDownloadedEvent; +import com.money.manager.ex.utils.MmxDate; import org.greenrobot.eventbus.EventBus; import org.greenrobot.eventbus.Subscribe; +import java.util.Date; + import javax.inject.Inject; import dagger.Lazy; @@ -138,14 +144,47 @@ private void initializePreferences() { // Download. viewHolder.download.setOnPreferenceClickListener(preference -> { - forceDownload(); - return true; + DatabaseMetadata currentDb = getDatabases().getCurrent(); + FileStorageHelper storage = new FileStorageHelper(getContext()); + + Date localSnapshot = MmxDate.fromIso8601(currentDb.localSnapshotTimestamp).toDate(); + Date localModified = storage.getLocalFileModifiedDate(currentDb).toDate(); + + Date remoteSnapshot = MmxDate.fromIso8601(currentDb.remoteLastChangedDate).toDate(); + Date remoteModified = storage.getRemoteFileModifiedDate(currentDb).toDate(); + + boolean isLocalModified = storage.isLocalFileChanged(currentDb); + boolean isRemoteModified = storage.isRemoteFileChanged(currentDb); + + String message = String.format( + "Local file changes indicator: %s.\n" + + "Downloading will overwrite your local version.\nDo you want to continue?" + , isLocalModified); + + showConfirmDialog("Download Warning", message, this::forceDownload); + return false; }); // Upload. viewHolder.upload.setOnPreferenceClickListener(preference -> { - forceUpload(); + DatabaseMetadata currentDb = getDatabases().getCurrent(); + FileStorageHelper storage = new FileStorageHelper(getContext()); + + Date localSnapshot = MmxDate.fromIso8601(currentDb.localSnapshotTimestamp).toDate(); + Date localModified = storage.getLocalFileModifiedDate(currentDb).toDate(); + + Date remoteSnapshot = MmxDate.fromIso8601(currentDb.remoteLastChangedDate).toDate(); + Date remoteModified = storage.getRemoteFileModifiedDate(currentDb).toDate(); + + boolean isLocalModified = storage.isLocalFileChanged(currentDb); + boolean isRemoteModified = storage.isRemoteFileChanged(currentDb); + + String message = String.format( + "Remote file changes indicator: %s.\n" + + "Uploading will overwrite your remote version.\nDo you want to continue?" + , isRemoteModified); + showConfirmDialog("Upload Warning",message,this::forceUpload); return false; }); @@ -174,4 +213,13 @@ private void forceUpload() { Timber.e(e, "uploading database"); } } + + private void showConfirmDialog(String title, String message, Runnable onConfirm) { + new AlertDialog.Builder(getActivity()) + .setTitle(title) + .setMessage(message) + .setPositiveButton("Continue", (dialog, which) -> onConfirm.run()) + .setNegativeButton("Cancel", (dialog, which) -> dialog.dismiss()) + .show(); + } } diff --git a/app/src/main/java/com/money/manager/ex/sync/SyncService.java b/app/src/main/java/com/money/manager/ex/sync/SyncService.java index 584464c10..24d9129f5 100644 --- a/app/src/main/java/com/money/manager/ex/sync/SyncService.java +++ b/app/src/main/java/com/money/manager/ex/sync/SyncService.java @@ -176,7 +176,7 @@ private void triggerSync(Messenger outMessenger, File localFile) { FileStorageHelper storage = new FileStorageHelper(getApplicationContext()); boolean isLocalModified = storage.isLocalFileChanged(currentDb); boolean isRemoteModified = storage.isRemoteFileChanged(currentDb); - Timber.d("Local file has changes: %b, Remote file has changes: %b", isLocalModified, isRemoteModified); + Timber.d("Local file has changed: %b, Remote file has changed: %b", isLocalModified, isRemoteModified); Uri uri = Uri.parse(currentDb.remotePath); // possible outcomes: