diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml
index 6ba265a284592e3672280c4bdf7c0aa14a25109d..23340a40daf3f2dd49bb207dbe0b5aebb97d7a0f 100644
--- a/.gitlab-ci.yml
+++ b/.gitlab-ci.yml
@@ -1,4 +1,4 @@
-image: "registry.gitlab.e.foundation:5000/e/apps/docker-android-apps-cicd:latest"
+image: "registry.gitlab.e.foundation:5000/e/apps/docker-android-apps-cicd:legacy"
stages:
- build
@@ -22,4 +22,3 @@ build:
paths:
- app/build/outputs/apk/
expire_in: 4 weeks
-
diff --git a/app/src/main/AndroidManifest.xml b/app/src/main/AndroidManifest.xml
index 0d1e0f00b9396114083b74981077a569fae1e6d0..975ed48ec892b0d6cfeb8d3ba7665739d5d12ada 100644
--- a/app/src/main/AndroidManifest.xml
+++ b/app/src/main/AndroidManifest.xml
@@ -18,15 +18,19 @@ http://www.gnu.org/licenses/gpl.html
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/app/src/main/java/foundation/e/drive/jobs/ScannerJob.java b/app/src/main/java/foundation/e/drive/jobs/ScannerJob.java
index 878f554b882119cefd4795e8131d2660ddcba33a..762c7cd758af64e7842d67184b20c0ce4e4bf7bb 100644
--- a/app/src/main/java/foundation/e/drive/jobs/ScannerJob.java
+++ b/app/src/main/java/foundation/e/drive/jobs/ScannerJob.java
@@ -13,7 +13,10 @@ import android.app.job.JobService;
import android.content.Intent;
import android.content.IntentFilter;
import android.util.Log;
+
+import foundation.e.drive.receivers.ConnectivityReceiver;
import foundation.e.drive.receivers.ScreenOffReceiver;
+import foundation.e.drive.services.InitializerService;
import foundation.e.drive.services.ObserverService;
import foundation.e.drive.utils.CommonUtils;
@@ -35,7 +38,13 @@ public class ScannerJob extends JobService {
Intent observerServiceIntent = new Intent(this, ObserverService.class);
this.startService(observerServiceIntent);
jobFinished(params, false);
+
+ if(!ConnectivityReceiver.isConnected()){
+ InitializerService.fileObserverFlag=false;
+ }
return true;
+
+
}
/**
diff --git a/app/src/main/java/foundation/e/drive/models/FileObserver.java b/app/src/main/java/foundation/e/drive/models/FileObserver.java
new file mode 100644
index 0000000000000000000000000000000000000000..9b5e76fc2cc3509c1fd0d9e5e3dc4d2df3a20d50
--- /dev/null
+++ b/app/src/main/java/foundation/e/drive/models/FileObserver.java
@@ -0,0 +1,33 @@
+package foundation.e.drive.models;
+
+import java.io.File;
+import java.io.Serializable;
+import java.util.List;
+
+public class FileObserver implements Serializable {
+
+ private List files;
+
+ //private List syncedFileStatesList;
+
+ public FileObserver(List files) {
+ this.files = files;
+
+ }
+
+ public List getFiles() {
+ return files;
+ }
+
+ public void setFiles(List files) {
+ this.files = files;
+ }
+
+// public List getSyncedFileStatesList() {
+// return syncedFileStatesList;
+// }
+//
+// public void setSyncedFileStatesList(List syncedFileStatesList) {
+// this.syncedFileStatesList = syncedFileStatesList;
+// }
+}
diff --git a/app/src/main/java/foundation/e/drive/models/SyncedFileState.java b/app/src/main/java/foundation/e/drive/models/SyncedFileState.java
index 42c76a102482a4681845082e752f1edf57211f3d..3b9255be143e3b637c1686beff0ce6d5b7d4ee8e 100644
--- a/app/src/main/java/foundation/e/drive/models/SyncedFileState.java
+++ b/app/src/main/java/foundation/e/drive/models/SyncedFileState.java
@@ -11,12 +11,14 @@ package foundation.e.drive.models;
import android.os.Parcel;
import android.os.Parcelable;
+import java.io.Serializable;
+
/**
* @author Vincent Bourgmayer
* Describe a file state which will be Synchronized (= Synced) or which has already been synced one times
*/
-public class SyncedFileState implements Parcelable {
+public class SyncedFileState implements Parcelable, Serializable {
protected SyncedFileState(){}; //@ToRemove. Test Only. It's to allow to make a mock SyncedFileState Class in test.
diff --git a/app/src/main/java/foundation/e/drive/operations/DownloadFileRemoteOperation.java b/app/src/main/java/foundation/e/drive/operations/DownloadFileRemoteOperation.java
index dce9dff620ad4ab620450b046dcd50eb94fb49e5..c8d8a211d5e5865c504f9002ed670b84cb20ec0a 100644
--- a/app/src/main/java/foundation/e/drive/operations/DownloadFileRemoteOperation.java
+++ b/app/src/main/java/foundation/e/drive/operations/DownloadFileRemoteOperation.java
@@ -24,6 +24,8 @@
*/
package foundation.e.drive.operations;
+import android.util.Log;
+
import com.owncloud.android.lib.common.OwnCloudClient;
import com.owncloud.android.lib.common.network.WebdavUtils;
import com.owncloud.android.lib.common.operations.OperationCancelledException;
@@ -40,6 +42,8 @@ import java.io.IOException;
import java.util.Date;
import java.util.concurrent.atomic.AtomicBoolean;
+import foundation.e.drive.services.InitializerService;
+
/**
* Remote operation performing the download of a remote file in the ownCloud server.
*
@@ -77,6 +81,7 @@ class DownloadFileRemoteOperation extends RemoteOperation {
tmpFile.getParentFile().mkdirs();
int status = downloadFile(client, tmpFile);
result = new RemoteOperationResult(isSuccess(status), mGet);
+
Log_OC.i(TAG, "Download of " + mRemotePath + " to " + getTmpPath() + ": " +
result.getLogMessage());
@@ -120,6 +125,9 @@ class DownloadFileRemoteOperation extends RemoteOperation {
fos.write(bytes, 0, readResult);
transferred += readResult;
}
+ // Log.e(TAG, "...DownLoad ...."+targetFile.getName());
+ InitializerService.remoteDownloadFile.add(targetFile);
+
// Check if the file is completed
// if transfer-encoding: chunked we cannot check if the file is complete
Header transferEncodingHeader = mGet.getResponseHeader("Transfer-Encoding");
diff --git a/app/src/main/java/foundation/e/drive/operations/UploadFileOperation.java b/app/src/main/java/foundation/e/drive/operations/UploadFileOperation.java
index 88276a6b9703b773b4bdaf40e115b3b11e4e59e0..44495f7782ba3add57ecf1c6eeb9fd87bb055e95 100644
--- a/app/src/main/java/foundation/e/drive/operations/UploadFileOperation.java
+++ b/app/src/main/java/foundation/e/drive/operations/UploadFileOperation.java
@@ -23,8 +23,13 @@ import com.owncloud.android.lib.resources.users.GetRemoteUserInfoOperation;
import com.owncloud.android.lib.common.operations.RemoteOperationResult.ResultCode;
import java.io.File;
import java.util.ArrayList;
+import java.util.Iterator;
+
import foundation.e.drive.database.DbHelper;
+import foundation.e.drive.models.FileObserver;
import foundation.e.drive.models.SyncedFileState;
+import foundation.e.drive.services.FileObserverService;
+import foundation.e.drive.services.InitializerService;
import foundation.e.drive.utils.CommonUtils;
/**
@@ -136,6 +141,13 @@ public class UploadFileOperation extends RemoteOperation implements ComparableOp
//if upload is a success
if( uploadResult.isSuccess() ){
+
+ try {
+ FileObserverService.files.remove(file);
+ }catch (Exception ex){
+ ex.printStackTrace();
+ }
+
Object data = uploadResult.getSingleData();
if(data != null){
mSyncedState.setLastETAG((String) data);
diff --git a/app/src/main/java/foundation/e/drive/receivers/ConnectivityReceiver.java b/app/src/main/java/foundation/e/drive/receivers/ConnectivityReceiver.java
new file mode 100644
index 0000000000000000000000000000000000000000..d6c7b25f07bfeecc9becdc97c9f78a7d46037394
--- /dev/null
+++ b/app/src/main/java/foundation/e/drive/receivers/ConnectivityReceiver.java
@@ -0,0 +1,92 @@
+package foundation.e.drive.receivers;
+
+import android.content.BroadcastReceiver;
+import android.content.Context;
+import android.content.Intent;
+import android.net.ConnectivityManager;
+import android.net.NetworkInfo;
+import android.os.Bundle;
+import android.os.Handler;
+import android.util.Log;
+
+import java.io.IOException;
+
+import foundation.e.drive.services.FileObserverService;
+import foundation.e.drive.services.InitializerService;
+import foundation.e.drive.services.MyApplication;
+
+public class ConnectivityReceiver
+ extends BroadcastReceiver {
+ private final static String TAG = ConnectivityReceiver.class.getSimpleName();
+ public static ConnectivityReceiverListener connectivityReceiverListener;
+
+ public ConnectivityReceiver() {
+ super();
+ }
+
+ public boolean isConnected;
+
+ public static boolean isConnected() {
+
+
+ try {
+ String command = "ping -c 1 ecloud.global";
+ return Runtime.getRuntime().exec(command).waitFor() == 0;
+ }catch (Exception ex){
+ ex.printStackTrace();
+ }
+ return false;
+ }
+
+
+
+ @Override
+ public void onReceive(final Context context, Intent arg1) {
+ ConnectivityManager cm = (ConnectivityManager) context
+ .getSystemService(Context.CONNECTIVITY_SERVICE);
+ final NetworkInfo activeNetwork = cm.getActiveNetworkInfo();
+
+
+ final Handler handler = new Handler();
+ handler.postDelayed(new Runnable() {
+ @Override
+ public void run() {
+ isConnected = activeNetwork != null
+ && activeNetwork.isConnectedOrConnecting();
+
+ Log.e(TAG, "connectivityReceiverListener..." + isConnected());
+ if (connectivityReceiverListener != null) {
+ connectivityReceiverListener.onNetworkConnectionChanged(isConnected);
+ }
+
+ if (isConnected()) {
+ Intent observersServiceIntent = new Intent(context, foundation.e.drive.services.ObserverService.class);
+ if (InitializerService.schedulerFlag) {
+
+ context.startService(observersServiceIntent);
+
+ } else if (InitializerService.fileObserverFlag) {
+ //
+ Bundle mBundle = new Bundle();
+ mBundle.putBoolean("isFileObserverService", true);
+ observersServiceIntent.putExtras(mBundle);
+ context.startService(observersServiceIntent);
+ }
+
+ InitializerService.schedulerFlag = false;
+ InitializerService.fileObserverFlag = false;
+ }
+ }
+ }, 20000);
+
+ //if (connectivityReceiverListener != null) {
+ Log.e(TAG, "ConnectivityReceiver onNetworkConnectionChanged...." + isConnected);
+ //connectivityReceiverListener.onNetworkConnectionChanged(isConnected);
+ //}
+
+ }
+
+ public interface ConnectivityReceiverListener {
+ void onNetworkConnectionChanged(boolean isConnected);
+ }
+}
\ No newline at end of file
diff --git a/app/src/main/java/foundation/e/drive/receivers/ScreenOffReceiver.java b/app/src/main/java/foundation/e/drive/receivers/ScreenOffReceiver.java
index 27d489598d6fb2b579ddd671612ac7a87c96541f..a294c1b50537d22d02c54e7a4840b6ad2e86861c 100644
--- a/app/src/main/java/foundation/e/drive/receivers/ScreenOffReceiver.java
+++ b/app/src/main/java/foundation/e/drive/receivers/ScreenOffReceiver.java
@@ -11,7 +11,11 @@ package foundation.e.drive.receivers;
import android.content.BroadcastReceiver;
import android.content.Context;
import android.content.Intent;
+import android.os.Bundle;
import android.util.Log;
+
+import foundation.e.drive.services.FileObserverService;
+import foundation.e.drive.services.InitializerService;
import foundation.e.drive.services.ObserverService;
import foundation.e.drive.utils.CommonUtils;
@@ -38,14 +42,6 @@ public class ScreenOffReceiver extends BroadcastReceiver {
@Override
public void onReceive(Context context, Intent intent) {
Log.i(TAG, "onReceive");
- String intentAction = intent.getAction();
- if(intentAction == null){
- Log.e(TAG, "intent Action is null");
- } else if ( intent.getAction().equals(Intent.ACTION_SCREEN_OFF)
- && CommonUtils.haveNetworkConnexion( context ) ) {
- Log.d(TAG, "onReceive: ACTION_SCREEN_OFF");
- Intent cloudIntent = new Intent(context, ObserverService.class);
- context.startService(cloudIntent);
- }
+
}
}
diff --git a/app/src/main/java/foundation/e/drive/services/FileObserverService.java b/app/src/main/java/foundation/e/drive/services/FileObserverService.java
new file mode 100644
index 0000000000000000000000000000000000000000..a54fe622becb193ad8e70fc42ed935e6076aedf2
--- /dev/null
+++ b/app/src/main/java/foundation/e/drive/services/FileObserverService.java
@@ -0,0 +1,189 @@
+package foundation.e.drive.services;
+
+import android.app.ActivityManager;
+import android.app.Service;
+import android.content.Intent;
+import android.os.AsyncTask;
+import android.os.Build;
+import android.os.Bundle;
+import android.os.Environment;
+
+import android.os.FileObserver;
+import android.os.Handler;
+import android.os.IBinder;
+import android.os.Looper;
+import android.os.Message;
+import android.support.annotation.Nullable;
+import android.util.Log;
+
+import java.io.File;
+import java.util.ArrayList;
+import java.util.List;
+import java.util.concurrent.CopyOnWriteArrayList;
+
+import foundation.e.drive.receivers.ConnectivityReceiver;
+import foundation.e.drive.utils.CommonUtils;
+import foundation.e.drive.utils.RecursiveFileObserver;
+
+
+
+public class FileObserverService extends Service {
+
+ private final static String TAG = FileObserverService.class.getSimpleName();
+ RecursiveFileObserver mFileObserver = null;
+ private int observerFlag=-1;
+ public static List files=new CopyOnWriteArrayList<>();
+ private boolean remoteFileFlag;
+
+ final Handler handler = new Handler();
+
+ @Override
+ public int onStartCommand(Intent intent, int flags, int startId) {
+ Log.d("obService", "started");
+ super.onStartCommand(intent, flags, startId);
+ startTask();
+ return START_STICKY;
+ }
+
+ @Override
+ public void onCreate() {
+ super.onCreate();
+
+ }
+
+ private void startTask() {
+
+ String path = Environment.getExternalStorageDirectory().getAbsolutePath();
+ Log.d("obService", path);
+
+
+
+ mFileObserver = new RecursiveFileObserver(getApplicationContext(), path, new RecursiveFileObserver.EventListener() {
+ @Override
+ public void onEvent(int event, File file) {
+
+ if(event==FileObserver.CLOSE_WRITE){
+
+// Log.e(TAG, "...CLOSE_WRITE ..." + event+"...file ..." + file);
+// }
+//
+//
+// //Modify =2, create =256, delete =512, movedTo =128
+// if(event== FileObserver.CREATE ||
+// event==FileObserver.MODIFY ||
+// event== FileObserver.DELETE ||
+// event ==FileObserver.MOVED_TO){
+
+ Log.i(TAG, "...Event ..." + event+"...file ..." + file);
+
+ remoteFileFlag=false;
+ if(!file.isDirectory() ){
+
+ for(File remoteFile:InitializerService.remoteDownloadFile){
+ if(remoteFile.getName().equals(file.getName())){
+ remoteFileFlag=true;
+ break;
+ }
+ }
+
+
+
+
+ if(!files.contains(file) && !remoteFileFlag){
+ files.add(file);
+ }
+ else {
+ return;
+ }
+ if(!ConnectivityReceiver.isConnected()){
+ InitializerService.fileObserverFlag=true;
+ }
+ try
+ {
+ if(observerFlag == -1){
+ new AsyncTaskRunner().execute("");
+ }
+
+
+ }
+ catch (Exception e)
+ {
+ e.printStackTrace();
+ }
+ }
+ }
+ }
+ });
+
+ mFileObserver.startWatching();
+ }
+
+ @Nullable
+ @Override
+ public IBinder onBind(Intent intent) {
+ return null;
+ }
+
+ @Override
+ public void onDestroy() {
+ Log.d("TAG", "............OnDestroy");
+
+ super.onDestroy();
+ }
+
+
+ @Override
+ public void onTaskRemoved(Intent rootIntent) {
+
+ Log.d(TAG, "............onTaskRemoved");
+ super.onTaskRemoved(rootIntent);
+ Intent intent = new Intent(this, InitializerService.class);
+ this.startActivity(intent);
+
+ }
+
+ private class AsyncTaskRunner extends AsyncTask{
+
+ @Override
+ protected String doInBackground(String... strings) {
+ observerFlag=1;
+ return null;
+ }
+
+ @Override
+ protected void onPostExecute(String s) {
+ super.onPostExecute(s);
+
+ handler.postDelayed(new Runnable() {
+ @Override
+ public void run() {
+ // Do something after 5s = 5000ms
+ try {
+ Log.d(TAG, "calling observerServiceIntent via fileObserver..");
+ Intent observersServiceIntent = new Intent(getApplicationContext(), foundation.e.drive.services.ObserverService.class);
+ Bundle mBundle = new Bundle();
+ mBundle.putBoolean("isFileObserverService", true);
+ if(files.size()!=0) {
+ mBundle.putByteArray("fileObserverObject", CommonUtils.convertToBytes(new foundation.e.drive.models.FileObserver(files)));
+ }
+
+ observersServiceIntent.putExtras(mBundle);
+ startService(observersServiceIntent);
+ }catch (Exception exception){
+ exception.printStackTrace();
+ }
+ observerFlag=-1;
+ }
+ }, 5000);
+
+
+
+
+ }
+
+ }
+
+
+
+
+}
\ No newline at end of file
diff --git a/app/src/main/java/foundation/e/drive/services/InitializerService.java b/app/src/main/java/foundation/e/drive/services/InitializerService.java
index 607edf9d813afa30631a4ad6c3cc7bad87daf2b6..ff049c246e7eec82317aeba5498bec2f176a0289 100644
--- a/app/src/main/java/foundation/e/drive/services/InitializerService.java
+++ b/app/src/main/java/foundation/e/drive/services/InitializerService.java
@@ -15,6 +15,7 @@ import android.content.Context;
import android.content.Intent;
import android.content.IntentFilter;
import android.content.SharedPreferences;
+import android.net.ConnectivityManager;
import android.os.Build;
import android.os.Environment;
import android.os.Handler;
@@ -27,12 +28,15 @@ import com.owncloud.android.lib.common.operations.OnRemoteOperationListener;
import com.owncloud.android.lib.common.operations.RemoteOperation;
import com.owncloud.android.lib.common.operations.RemoteOperationResult;
+import java.io.File;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
+import java.util.concurrent.CopyOnWriteArrayList;
import foundation.e.drive.models.SyncedFolder;
import foundation.e.drive.operations.CreateInitialFolderRemoteOperation;
+import foundation.e.drive.receivers.ConnectivityReceiver;
import foundation.e.drive.receivers.ScreenOffReceiver;
import foundation.e.drive.utils.AppConstants;
import foundation.e.drive.utils.CommonUtils;
@@ -47,7 +51,8 @@ import static foundation.e.drive.utils.AppConstants.SETTINGS_SYNCABLE_CATEGORIES
/**
* @author Vincent Bourgmayer
*/
-public class InitializerService extends Service implements OnRemoteOperationListener {
+public class InitializerService extends Service
+ implements OnRemoteOperationListener, ConnectivityReceiver.ConnectivityReceiverListener {
final private String TAG = InitializerService.class.getSimpleName();
//Complex properties
private int existingRemoteFolderCounter; //@dev-only; Temporarily used to know if all remotePath exist
@@ -56,6 +61,11 @@ public class InitializerService extends Service implements OnRemoteOperationList
private Handler mHandler;
private Account mAccount;
private int restartFolderCreationCounter =0;
+ private ConnectivityReceiver connectivityReceiver;
+
+ public static List remoteDownloadFile=new CopyOnWriteArrayList<>();
+ public static boolean schedulerFlag=false;
+ public static boolean fileObserverFlag=false;
@Override
public void onCreate() {
@@ -63,8 +73,16 @@ public class InitializerService extends Service implements OnRemoteOperationList
super.onCreate();
this.existingRemoteFolderCounter = 0;
//JobUtils.scheduleInitializerJob(getApplicationContext());
+ connectivityReceiver = new ConnectivityReceiver();
+ registerConnectivityReceiver();
+
}
+ private void registerConnectivityReceiver() {
+
+ registerReceiver(connectivityReceiver, new IntentFilter(ConnectivityManager.CONNECTIVITY_ACTION));
+
+ }
@Override
public int onStartCommand( Intent intent, int flags, int startId ) {
Log.i(TAG, "onStartCommand(...)");
@@ -284,7 +302,7 @@ public class InitializerService extends Service implements OnRemoteOperationList
.apply();
//all folder have been created
- //JobUtils.stopScheduledJob(appContext, JobUtils.InitializerJobId);
+ JobUtils.stopScheduledJob(appContext, JobUtils.InitializerJobId);
JobUtils.scheduleScannerJob(appContext);
Log.d(TAG, "RegisterReceiver: screenOffReceiver");
@@ -296,6 +314,8 @@ public class InitializerService extends Service implements OnRemoteOperationList
Intent observersServiceIntent = new Intent(getApplicationContext(), foundation.e.drive.services.ObserverService.class);
startService(observersServiceIntent);
+ //start FileObserverService
+ startService(new Intent(this, FileObserverService.class));
stopSelf();
@@ -309,6 +329,14 @@ public class InitializerService extends Service implements OnRemoteOperationList
this.mCloudClient = null;
if(this.mSyncedFolders != null) this.mSyncedFolders.clear();
this.mSyncedFolders = null;
+ unregisterConnectivityReceiver();
+ }
+ protected void unregisterConnectivityReceiver() {
+ try {
+ unregisterReceiver(connectivityReceiver);
+ } catch (IllegalArgumentException e) {
+ e.printStackTrace();
+ }
}
@Nullable
@@ -316,4 +344,12 @@ public class InitializerService extends Service implements OnRemoteOperationList
public IBinder onBind(Intent intent) {
return null;
}
+
+ @Override
+ public void onNetworkConnectionChanged(boolean isConnected) {
+
+ //just for testing code for now
+ Log.e(TAG, "onNetworkConnectionChanged...." + isConnected);
+
+ }
}
\ No newline at end of file
diff --git a/app/src/main/java/foundation/e/drive/services/MyApplication.java b/app/src/main/java/foundation/e/drive/services/MyApplication.java
new file mode 100644
index 0000000000000000000000000000000000000000..79ae6d83d3d151f591cdc38464ac92dec0636d5a
--- /dev/null
+++ b/app/src/main/java/foundation/e/drive/services/MyApplication.java
@@ -0,0 +1,25 @@
+package foundation.e.drive.services;
+
+import android.app.Application;
+
+import foundation.e.drive.receivers.ConnectivityReceiver;
+
+public class MyApplication extends Application {
+
+ private static MyApplication mInstance;
+
+ @Override
+ public void onCreate() {
+ super.onCreate();
+
+ mInstance = this;
+ }
+
+ public static synchronized MyApplication getInstance() {
+ return mInstance;
+ }
+
+ public void setConnectivityListener(ConnectivityReceiver.ConnectivityReceiverListener listener) {
+ ConnectivityReceiver.connectivityReceiverListener = listener;
+ }
+}
\ No newline at end of file
diff --git a/app/src/main/java/foundation/e/drive/services/ObserverService.java b/app/src/main/java/foundation/e/drive/services/ObserverService.java
index 0cadf83c6381f3af6a8f861c12b9b59a78716d9b..d9f19de1d444248b7dbfadcf176370a0e10f842d 100644
--- a/app/src/main/java/foundation/e/drive/services/ObserverService.java
+++ b/app/src/main/java/foundation/e/drive/services/ObserverService.java
@@ -15,18 +15,21 @@ import android.content.Context;
import android.content.Intent;
import android.content.SharedPreferences;
import android.content.pm.PackageInfo;
+import android.os.Bundle;
import android.os.Handler;
import android.os.IBinder;
import android.os.Parcelable;
import android.provider.MediaStore;
import android.support.annotation.Nullable;
import android.util.Log;
+
import com.owncloud.android.lib.common.OwnCloudClient;
import com.owncloud.android.lib.common.operations.OnRemoteOperationListener;
import com.owncloud.android.lib.common.operations.RemoteOperation;
import com.owncloud.android.lib.common.operations.RemoteOperationResult;
import com.owncloud.android.lib.resources.files.FileUtils;
import com.owncloud.android.lib.resources.files.model.RemoteFile;
+
import java.io.File;
import java.io.FileFilter;
import java.io.FileOutputStream;
@@ -40,12 +43,14 @@ import foundation.e.drive.database.DbHelper;
import foundation.e.drive.fileFilters.CrashlogsFileFilter;
import foundation.e.drive.fileFilters.FileFilterFactory;
import foundation.e.drive.fileFilters.OnlyFileFilter;
+import foundation.e.drive.models.FileObserver;
import foundation.e.drive.models.SyncedFolder;
import foundation.e.drive.models.SyncedFileState;
import foundation.e.drive.operations.DownloadFileOperation;
import foundation.e.drive.operations.ListFileRemoteOperation;
import foundation.e.drive.operations.RemoveFileOperation;
import foundation.e.drive.operations.UploadFileOperation;
+import foundation.e.drive.receivers.ConnectivityReceiver;
import foundation.e.drive.utils.AppConstants;
import foundation.e.drive.utils.CommonUtils;
import foundation.e.drive.utils.DavClientProvider;
@@ -60,7 +65,7 @@ import static foundation.e.drive.utils.AppConstants.INITIALIZATION_HAS_BEEN_DONE
* @author Vincent Bourgmayer
* This service look for remote or looale file to synchronize
*/
-public class ObserverService extends Service implements OnRemoteOperationListener{
+public class ObserverService extends Service implements OnRemoteOperationListener {
private final static String TAG = ObserverService.class.getSimpleName();
private final static int INTERSYNC_MINIMUM_DELAY = 900000; // min delay between two sync in ms.
@@ -69,18 +74,31 @@ public class ObserverService extends Service implements OnRemoteOperationListene
private int initialFolderCounter;
private Account mAccount;
private HashMap operationsForIntent;
+ private Boolean isFileObserverService = false;
+ private FileObserver fileObserverObject;
+ // private foundation.e.drive.models.FileObserver fileObserverObject;
/* Lifecycle Methods */
@Override
- public void onDestroy(){
+ public void onDestroy() {
Log.i(TAG, "onDestroy()");
super.onDestroy();
this.mSyncedFolders = null;
}
-
+
@Override
public int onStartCommand(Intent intent, int flags, int startId) {
- Log.i(TAG, "onStartCommand("+startId+")");
+ Log.i(TAG, "onStartCommand(" + startId + ")");
+
+ try {
+ Bundle bundle = intent.getExtras();
+ if (null != bundle) {
+ isFileObserverService = bundle.getBoolean("isFileObserverService");
+ fileObserverObject = (foundation.e.drive.models.FileObserver) CommonUtils.convertFromBytes(bundle.getByteArray("fileObserverObject"));
+ }
+ } catch (Exception ex) {
+ ex.printStackTrace();
+ }
CommonUtils.setServiceUnCaughtExceptionHandler(this);
@@ -91,14 +109,14 @@ public class ObserverService extends Service implements OnRemoteOperationListene
initialFolderCounter = prefs.getInt(AppConstants.INITIALFOLDERS_NUMBER, 0);
// Check if account is invalid
- if(this.mAccount == null){
+ if (this.mAccount == null) {
Log.w(TAG, "No account registered");
JobUtils.stopScheduledJob(this, JobUtils.ScannerJobId); //If no account
return super.onStartCommand(intent, flags, startId);
}
//check if user have disable eDrive's sync in account's settings
- if(!CommonUtils.isMediaSyncEnabled(mAccount) && !CommonUtils.isSettingsSyncEnabled(mAccount) ){
+ if (!CommonUtils.isMediaSyncEnabled(mAccount) && !CommonUtils.isSettingsSyncEnabled(mAccount)) {
Log.w(TAG, "eDrive syncing has been disabled in /e/ account's settings");
return super.onStartCommand(intent, flags, startId);
}
@@ -108,19 +126,26 @@ public class ObserverService extends Service implements OnRemoteOperationListene
Log.w(TAG, "Initialization hasn't been done");
Intent initializerIntent = new Intent(this, InitializerService.class);
startService(initializerIntent);
- return super.onStartCommand( intent, flags, startId );
+ return super.onStartCommand(intent, flags, startId);
}
//Check this service isn't already working
- if(isWorking){
+ if (isWorking) {
Log.w(TAG, "ObserverService is already working");
- return super.onStartCommand(intent,flags,startId);
+ getApplicationContext().stopService(new Intent(getApplicationContext(), ObserverService.class));
+ // return super.onStartCommand(intent, flags, startId);
+ startService(new Intent(this, ObserverService.class));
}
//check OperationManagerService isn't working
- if(prefs.getBoolean(AppConstants.KEY_OMS_IS_WORKING, false)){
+ if (prefs.getBoolean(AppConstants.KEY_OMS_IS_WORKING, false)) {
Log.w(TAG, "OperationManagerService is still performing some operation");
- return super.onStartCommand(intent,flags, startId);
+
+ getApplicationContext().stopService(new Intent(getApplicationContext(), OperationManagerService.class));
+ if (operationsForIntent != null && !operationsForIntent.isEmpty()) {
+ startOperationManagerService();
+ }
+
}
//Check a minimum delay has been respected between two start.
@@ -128,27 +153,28 @@ public class ObserverService extends Service implements OnRemoteOperationListene
long currentTime = System.currentTimeMillis();
//if time diff between current sync and last sync is higher or equal to delay minimum between two sync
- if( (currentTime - lastSyncTime ) < INTERSYNC_MINIMUM_DELAY ){
+ /*if( (currentTime - lastSyncTime ) < INTERSYNC_MINIMUM_DELAY ){
Log.w(TAG, "Delay between now and last call is too short");
return super.onStartCommand( intent, flags, startId );
- }
+ }*/
//check for the case where intent has been launched by initializerService
- if (!CommonUtils.haveNetworkConnexion(this)) {
+ if (!ConnectivityReceiver.isConnected()) {
Log.w(TAG, "There is no Internet connexion.");
- return super.onStartCommand( intent, flags, startId );
+ return super.onStartCommand(intent, flags, startId);
}
this.operationsForIntent = new HashMap<>();
begin();
- return super.onStartCommand( intent, flags, startId );
+ return super.onStartCommand(intent, flags, startId);
}
/* Common methods */
+
/**
* Start to bind this service to OperationManagerService or start scan if binding is already set.
* Method to factorise code that is called from different place
*/
- private void begin(){
+ private void begin() {
Log.i(TAG, "begin()");
this.isWorking = true;
clearCachedFile();
@@ -160,7 +186,7 @@ public class ObserverService extends Service implements OnRemoteOperationListene
* This method remove all the crash-logs file
* in external dir that are 10 days or more old.
*/
- private void deleteOldestCrashlogs(){
+ private void deleteOldestCrashlogs() {
Log.i(TAG, "deleteOldestCrashLogs()");
File[] fileToRemove = getExternalFilesDir(ServiceExceptionHandler.CRASH_LOG_FOLDER)
.listFiles(new CrashlogsFileFilter());
@@ -170,48 +196,51 @@ public class ObserverService extends Service implements OnRemoteOperationListene
try {
file.delete();
++counter;
- }catch (SecurityException e){
+ } catch (SecurityException e) {
e.printStackTrace();
}
}
- Log.d(TAG, counter+" old crashlogs file.s deleted");
+ Log.d(TAG, counter + " old crashlogs file.s deleted");
}
/**
* Clear cached file unused:
* remove each cached file which isn't in OperationManagerService.lockedSyncedFileState();
+ *
* @TODO rewrite this method!
*/
- private void clearCachedFile(){
+ private void clearCachedFile() {
Log.i(TAG, "clearCachedFile()");
//Load subfiles into external cache file
- File[] fileArray = this.getApplicationContext().getExternalCacheDir().listFiles(new OnlyFileFilter() );
- if(fileArray != null) {
+ File[] fileArray = this.getApplicationContext().getExternalCacheDir().listFiles(new OnlyFileFilter());
+ if (fileArray != null) {
boolean toRemove;
for (int i = -1, size = fileArray.length; ++i < size; ) {
toRemove = true;
if (toRemove) {
boolean deleteResult = fileArray[i].delete();
- Log.v(TAG+"_handleCachedFile()", "Deletion of cached file: " + deleteResult);
+ Log.v(TAG + "_handleCachedFile()", "Deletion of cached file: " + deleteResult);
}
}
- }else{
- Log.e(TAG+"_handleCachedFile()", "Array of cached file is null");
+ } else {
+ Log.e(TAG + "_handleCachedFile()", "Array of cached file is null");
}
}
/**
* Start scanning job
* Load operation from DB
+ *
* @param remote if true looks for remote change. If false, look for local change.
**/
private void startScan(boolean remote) {
- Log.i(TAG, "startScan("+remote+")");
+ Log.i(TAG, "startScan(" + remote + ")");
+
this.mSyncedFolders = loadSyncedFolders();
- if(mSyncedFolders.isEmpty() ){
+ if (mSyncedFolders.isEmpty()) {
Log.w(TAG, "List of synced folders is empty");
this.stopSelf();
return;
@@ -219,7 +248,7 @@ public class ObserverService extends Service implements OnRemoteOperationListene
//Display content of SyncedFolderList
StringBuilder logFolderList = new StringBuilder("SyncedFolder: libelle, localFolder, lastmodified, scanLocal, id :");
- for(SyncedFolder sf : mSyncedFolders){
+ for (SyncedFolder sf : mSyncedFolders) {
logFolderList.append("\n").append(sf.getLibelle()).append(", ").append(sf.getLocalFolder()).append(", ").append(sf.getLastModified()).append(", ").append(sf.isScanLocal()).append(", ").append(sf.getId());
}
Log.d(TAG, logFolderList.toString());
@@ -231,52 +260,71 @@ public class ObserverService extends Service implements OnRemoteOperationListene
Log.d(TAG, "Going to scan remote files");
ListFileRemoteOperation loadOperation = new ListFileRemoteOperation(this.mSyncedFolders, this, this.initialFolderCounter);
loadOperation.execute(client, this, new Handler());
- } catch (IllegalArgumentException e){
- Log.e(TAG, e.toString() );
+ } catch (IllegalArgumentException e) {
+ Log.e(TAG, e.toString());
}
- }else{
+ } else {
Log.w(TAG, "OwnCloudClient is null");
return;
}
} else {
- scanLocalFiles();
+
+ if (isFileObserverService && null != fileObserverObject) {
+ Log.i(TAG, "calling observer service from event event with true and files list data");
+ // List files = fileObserverObject.getFiles();
+ DbHelper.updateSyncedFolders(mSyncedFolders, this); //@ToDo: maybe do this when all contents will be synced.
+
+ List syncedFileStates = DbHelper.getSyncedFileStatesByFolders(this,
+ getIdsFromFolderToScan());
+
+ if (!syncedFileStates.isEmpty() || !fileObserverObject.getFiles().isEmpty()) {
+ handleLocalFiles(fileObserverObject.getFiles(), syncedFileStates);
+ }
+ // handleLocalFiles(fileObserverObject.getFiles(), fileObserverObject.getSyncedFileStatesList());
+
+ } else {
+ Log.i(TAG, "calling observer service with false or files list data null ");
+ if(null!=FileObserverService.files){
+ FileObserverService.files.removeAll(FileObserverService.files);
+ }
+ scanLocalFiles();
+ }
+
}
}
/**
* Get list of synced folder depending of if media and setting sync are enabled.
+ *
* @return
*/
- private List loadSyncedFolders(){
+ private List loadSyncedFolders() {
boolean mediaSyncEnabled = CommonUtils.isMediaSyncEnabled(mAccount);
boolean settingsSyncedEnabled = CommonUtils.isSettingsSyncEnabled(mAccount);
- if(mediaSyncEnabled && settingsSyncedEnabled){
+ if (mediaSyncEnabled && settingsSyncedEnabled) {
return DbHelper.getAllSyncedFolders(this);
- }else if(mediaSyncEnabled){
+ } else if (mediaSyncEnabled) {
return DbHelper.getSyncedFolderList(this, true);
- }else if(settingsSyncedEnabled){
+ } else if (settingsSyncedEnabled) {
return DbHelper.getSyncedFolderList(this, false);
- }else{
+ } else {
return new ArrayList();
}
- }
-
-
-
-
+ }
/**
* Handle end of remote Operation
+ *
* @param operation The RemoteOperation which ends and call this methods
- * @param result The result of the remote Operation
+ * @param result The result of the remote Operation
*/
@Override
- public void onRemoteOperationFinish(RemoteOperation operation, RemoteOperationResult result ) {
- Log.i( TAG, "onRemoteOperationFinish()" );
- if( operation instanceof ListFileRemoteOperation) {
+ public void onRemoteOperationFinish(RemoteOperation operation, RemoteOperationResult result) {
+ Log.i(TAG, "onRemoteOperationFinish()");
+ if (operation instanceof ListFileRemoteOperation) {
if (result.isSuccess()) {
List