Эх сурвалжийг харах

Merge commit '1f290419662c8058cd4bd90a161222f4150f6f25'

drone 5 жил өмнө
parent
commit
c988459eb8
33 өөрчлөгдсөн 850 нэмэгдсэн , 389 устгасан
  1. 1 0
      build.gradle
  2. 6 1
      findbugs-filter.xml
  3. 1 1
      scripts/analysis/findbugs-results.txt
  4. 21 1
      src/androidTest/java/com/owncloud/android/UploadIT.java
  5. 10 0
      src/main/java/com/nextcloud/client/account/UserAccountManager.java
  6. 17 1
      src/main/java/com/nextcloud/client/account/UserAccountManagerImpl.java
  7. 2 0
      src/main/java/com/nextcloud/client/di/AppComponent.java
  8. 2 0
      src/main/java/com/nextcloud/client/di/ComponentsModule.java
  9. 49 0
      src/main/java/com/nextcloud/client/network/ClientFactory.java
  10. 67 0
      src/main/java/com/nextcloud/client/network/ClientFactoryImpl.java
  11. 29 0
      src/main/java/com/nextcloud/client/network/ConnectivityService.java
  12. 71 30
      src/main/java/com/nextcloud/client/network/ConnectivityServiceImpl.java
  13. 57 0
      src/main/java/com/nextcloud/client/network/NetworkModule.java
  14. 13 7
      src/main/java/com/owncloud/android/MainApp.java
  15. 9 4
      src/main/java/com/owncloud/android/datamodel/ThumbnailsCacheManager.java
  16. 3 1
      src/main/java/com/owncloud/android/files/BootupBroadcastReceiver.java
  17. 7 3
      src/main/java/com/owncloud/android/files/services/FileUploader.java
  18. 6 2
      src/main/java/com/owncloud/android/jobs/FilesSyncJob.java
  19. 7 3
      src/main/java/com/owncloud/android/jobs/NCJobCreator.java
  20. 7 6
      src/main/java/com/owncloud/android/jobs/OfflineSyncJob.java
  21. 7 5
      src/main/java/com/owncloud/android/operations/UploadFileOperation.java
  22. 6 2
      src/main/java/com/owncloud/android/ui/activity/FileActivity.java
  23. 18 6
      src/main/java/com/owncloud/android/ui/activity/FileDisplayActivity.java
  24. 1 1
      src/main/java/com/owncloud/android/ui/activity/RichDocumentsWebView.java
  25. 14 6
      src/main/java/com/owncloud/android/ui/activity/UploadListActivity.java
  26. 7 1
      src/main/java/com/owncloud/android/ui/adapter/UploadListAdapter.java
  27. 8 0
      src/main/java/com/owncloud/android/ui/fragment/FileDetailFragment.java
  28. 133 128
      src/main/java/com/owncloud/android/ui/helpers/FileOperationsHelper.java
  29. 11 1
      src/main/java/com/owncloud/android/ui/preview/PreviewImageFragment.java
  30. 11 4
      src/main/java/com/owncloud/android/utils/FilesSyncHelper.java
  31. 11 7
      src/main/java/com/owncloud/android/utils/ReceiversHelper.java
  32. 238 0
      src/test/java/com/nextcloud/client/network/ConnectivityServiceTest.kt
  33. 0 168
      src/test/java/com/owncloud/android/utils/ConnectivityUtilsTest.java

+ 1 - 0
build.gradle

@@ -315,6 +315,7 @@ dependencies {
     testImplementation 'org.powermock:powermock-module-junit4:2.0.2'
     testImplementation 'org.powermock:powermock-module-junit4:2.0.2'
     testImplementation 'org.powermock:powermock-api-mockito2:2.0.2'
     testImplementation 'org.powermock:powermock-api-mockito2:2.0.2'
     testImplementation 'org.json:json:20180813'
     testImplementation 'org.json:json:20180813'
+    testImplementation "com.nhaarman.mockitokotlin2:mockito-kotlin:2.1.0"
 
 
     // dependencies for instrumented tests
     // dependencies for instrumented tests
     // JUnit4 Rules
     // JUnit4 Rules

+ 6 - 1
findbugs-filter.xml

@@ -18,8 +18,13 @@
             <Class name="~.*\.Dagger.*"/>
             <Class name="~.*\.Dagger.*"/>
             <Class name="~com.nextcloud.client.di\..*_.*"/>
             <Class name="~com.nextcloud.client.di\..*_.*"/>
         </Or>
         </Or>
-
     </Match>
     </Match>
+    <!-- Dagger generated code uses internal APIs -->
+    <Match>
+        <Class name="~.*\..*.*Factory"/>
+        <Bug pattern="IICU_INCORRECT_INTERNAL_CLASS_USE" />
+    </Match>
+
     <Bug pattern="PATH_TRAVERSAL_IN" />
     <Bug pattern="PATH_TRAVERSAL_IN" />
     <Bug pattern="ANDROID_EXTERNAL_FILE_ACCESS" />
     <Bug pattern="ANDROID_EXTERNAL_FILE_ACCESS" />
     <Bug pattern="BAS_BLOATED_ASSIGNMENT_SCOPE" />
     <Bug pattern="BAS_BLOATED_ASSIGNMENT_SCOPE" />

+ 1 - 1
scripts/analysis/findbugs-results.txt

@@ -1 +1 @@
-438
+436

+ 21 - 1
src/androidTest/java/com/owncloud/android/UploadIT.java

@@ -2,7 +2,9 @@ package com.owncloud.android;
 
 
 import android.content.ContentResolver;
 import android.content.ContentResolver;
 
 
+import com.evernote.android.job.JobRequest;
 import com.nextcloud.client.account.CurrentAccountProvider;
 import com.nextcloud.client.account.CurrentAccountProvider;
+import com.nextcloud.client.network.ConnectivityService;
 import com.owncloud.android.authentication.AccountUtils;
 import com.owncloud.android.authentication.AccountUtils;
 import com.owncloud.android.datamodel.UploadsStorageManager;
 import com.owncloud.android.datamodel.UploadsStorageManager;
 import com.owncloud.android.db.OCUpload;
 import com.owncloud.android.db.OCUpload;
@@ -27,9 +29,25 @@ import static junit.framework.TestCase.assertTrue;
 @RunWith(AndroidJUnit4.class)
 @RunWith(AndroidJUnit4.class)
 public class UploadIT extends AbstractIT {
 public class UploadIT extends AbstractIT {
 
 
-
     private UploadsStorageManager storageManager;
     private UploadsStorageManager storageManager;
 
 
+    private ConnectivityService connectivityServiceMock = new ConnectivityService() {
+        @Override
+        public boolean isInternetWalled() {
+            return false;
+        }
+
+        @Override
+        public boolean isOnlineWithWifi() {
+            return true;
+        }
+
+        @Override
+        public JobRequest.NetworkType getActiveNetworkType() {
+            return JobRequest.NetworkType.ANY;
+        }
+    };
+
     @Before
     @Before
     public void setUp() {
     public void setUp() {
         final ContentResolver contentResolver = targetContext.getContentResolver();
         final ContentResolver contentResolver = targetContext.getContentResolver();
@@ -79,6 +97,7 @@ public class UploadIT extends AbstractIT {
     public RemoteOperationResult testUpload(OCUpload ocUpload) {
     public RemoteOperationResult testUpload(OCUpload ocUpload) {
         UploadFileOperation newUpload = new UploadFileOperation(
         UploadFileOperation newUpload = new UploadFileOperation(
             storageManager,
             storageManager,
+            connectivityServiceMock,
             account,
             account,
             null,
             null,
             ocUpload,
             ocUpload,
@@ -103,6 +122,7 @@ public class UploadIT extends AbstractIT {
                 "/testUpload/2/3/4/1.txt", account.name);
                 "/testUpload/2/3/4/1.txt", account.name);
         UploadFileOperation newUpload = new UploadFileOperation(
         UploadFileOperation newUpload = new UploadFileOperation(
                 storageManager,
                 storageManager,
+                connectivityServiceMock,
                 account,
                 account,
                 null,
                 null,
                 ocUpload,
                 ocUpload,

+ 10 - 0
src/main/java/com/nextcloud/client/account/UserAccountManager.java

@@ -21,10 +21,17 @@ package com.nextcloud.client.account;
 
 
 import android.accounts.Account;
 import android.accounts.Account;
 
 
+import com.owncloud.android.lib.common.OwnCloudAccount;
+import com.owncloud.android.lib.resources.status.OwnCloudVersion;
+
 import androidx.annotation.NonNull;
 import androidx.annotation.NonNull;
 import androidx.annotation.Nullable;
 import androidx.annotation.Nullable;
 
 
 public interface UserAccountManager extends CurrentAccountProvider {
 public interface UserAccountManager extends CurrentAccountProvider {
+
+    @Nullable
+    OwnCloudAccount getCurrentOwnCloudAccount();
+
     /**
     /**
      * Get configured NextCloud's user accounts.
      * Get configured NextCloud's user accounts.
      *
      *
@@ -41,6 +48,8 @@ public interface UserAccountManager extends CurrentAccountProvider {
     @Nullable
     @Nullable
     Account getAccountByName(String name);
     Account getAccountByName(String name);
 
 
+    OwnCloudVersion getServerVersion(Account account);
+
     /**
     /**
      * Extract username from account.
      * Extract username from account.
      *
      *
@@ -56,4 +65,5 @@ public interface UserAccountManager extends CurrentAccountProvider {
             return null;
             return null;
         }
         }
     }
     }
+
 }
 }

+ 17 - 1
src/main/java/com/nextcloud/client/account/UserAccountManagerImpl.java

@@ -36,6 +36,7 @@ import com.owncloud.android.lib.common.OwnCloudClientManagerFactory;
 import com.owncloud.android.lib.common.UserInfo;
 import com.owncloud.android.lib.common.UserInfo;
 import com.owncloud.android.lib.common.operations.RemoteOperationResult;
 import com.owncloud.android.lib.common.operations.RemoteOperationResult;
 import com.owncloud.android.lib.common.utils.Log_OC;
 import com.owncloud.android.lib.common.utils.Log_OC;
+import com.owncloud.android.lib.resources.status.OwnCloudVersion;
 import com.owncloud.android.lib.resources.users.GetRemoteUserInfoOperation;
 import com.owncloud.android.lib.resources.users.GetRemoteUserInfoOperation;
 
 
 import javax.inject.Inject;
 import javax.inject.Inject;
@@ -70,6 +71,17 @@ public class UserAccountManagerImpl implements UserAccountManager {
         return AccountUtils.getCurrentOwnCloudAccount(context);
         return AccountUtils.getCurrentOwnCloudAccount(context);
     }
     }
 
 
+    @Override
+    @Nullable
+    public OwnCloudAccount getCurrentOwnCloudAccount() {
+        try {
+            Account currentPlatformAccount = getCurrentAccount();
+            return new OwnCloudAccount(currentPlatformAccount, context);
+        } catch (com.owncloud.android.lib.common.accounts.AccountUtils.AccountNotFoundException ex) {
+            return null;
+        }
+    }
+
     @Override
     @Override
     @Nullable
     @Nullable
     public Account getAccountByName(String name) {
     public Account getAccountByName(String name) {
@@ -82,9 +94,13 @@ public class UserAccountManagerImpl implements UserAccountManager {
         return null;
         return null;
     }
     }
 
 
+    @Override
+    public OwnCloudVersion getServerVersion(Account account) {
+        return AccountUtils.getServerVersion(account);
+    }
+
     public void migrateUserId() {
     public void migrateUserId() {
         AppPreferences appPreferences = AppPreferencesImpl.fromContext(context);
         AppPreferences appPreferences = AppPreferencesImpl.fromContext(context);
-
         if (appPreferences.isUserIdMigrated()) {
         if (appPreferences.isUserIdMigrated()) {
             // migration done
             // migration done
             return;
             return;

+ 2 - 0
src/main/java/com/nextcloud/client/di/AppComponent.java

@@ -23,6 +23,7 @@ package com.nextcloud.client.di;
 import android.app.Application;
 import android.app.Application;
 
 
 import com.nextcloud.client.appinfo.AppInfoModule;
 import com.nextcloud.client.appinfo.AppInfoModule;
+import com.nextcloud.client.network.NetworkModule;
 import com.nextcloud.client.whatsnew.WhatsNewModule;
 import com.nextcloud.client.whatsnew.WhatsNewModule;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.MainApp;
 
 
@@ -37,6 +38,7 @@ import dagger.android.support.AndroidSupportInjectionModule;
     AppModule.class,
     AppModule.class,
     AppInfoModule.class,
     AppInfoModule.class,
     WhatsNewModule.class,
     WhatsNewModule.class,
+    NetworkModule.class,
 })
 })
 @Singleton
 @Singleton
 public interface AppComponent {
 public interface AppComponent {

+ 2 - 0
src/main/java/com/nextcloud/client/di/ComponentsModule.java

@@ -66,6 +66,7 @@ import com.owncloud.android.ui.fragment.LocalFileListFragment;
 import com.owncloud.android.ui.fragment.OCFileListFragment;
 import com.owncloud.android.ui.fragment.OCFileListFragment;
 import com.owncloud.android.ui.fragment.contactsbackup.ContactListFragment;
 import com.owncloud.android.ui.fragment.contactsbackup.ContactListFragment;
 import com.owncloud.android.ui.preview.PreviewImageActivity;
 import com.owncloud.android.ui.preview.PreviewImageActivity;
+import com.owncloud.android.ui.preview.PreviewImageFragment;
 import com.owncloud.android.ui.preview.PreviewVideoActivity;
 import com.owncloud.android.ui.preview.PreviewVideoActivity;
 import com.owncloud.android.ui.trashbin.TrashbinActivity;
 import com.owncloud.android.ui.trashbin.TrashbinActivity;
 
 
@@ -121,6 +122,7 @@ abstract class ComponentsModule {
     @ContributesAndroidInjector abstract OCFileListFragment ocFileListFragment();
     @ContributesAndroidInjector abstract OCFileListFragment ocFileListFragment();
     @ContributesAndroidInjector abstract FileDetailActivitiesFragment fileDetailActivitiesFragment();
     @ContributesAndroidInjector abstract FileDetailActivitiesFragment fileDetailActivitiesFragment();
     @ContributesAndroidInjector abstract ChooseTemplateDialogFragment chooseTemplateDialogFragment();
     @ContributesAndroidInjector abstract ChooseTemplateDialogFragment chooseTemplateDialogFragment();
+    @ContributesAndroidInjector abstract PreviewImageFragment previewImageFragment();
 
 
     @ContributesAndroidInjector
     @ContributesAndroidInjector
     abstract ContactListFragment chooseContactListFragment();
     abstract ContactListFragment chooseContactListFragment();

+ 49 - 0
src/main/java/com/nextcloud/client/network/ClientFactory.java

@@ -0,0 +1,49 @@
+/*
+ * Nextcloud Android client application
+ *
+ * @author Chris Narkiewicz
+ * Copyright (C) 2019 Chris Narkiewicz <hello@ezaquarii.com>
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+package com.nextcloud.client.network;
+
+import android.accounts.Account;
+import android.accounts.AuthenticatorException;
+import android.accounts.OperationCanceledException;
+import android.app.Activity;
+import android.net.Uri;
+
+import com.owncloud.android.lib.common.OwnCloudClient;
+import com.owncloud.android.lib.common.accounts.AccountUtils;
+
+import java.io.IOException;
+
+public interface ClientFactory {
+
+    OwnCloudClient create(Account account)
+        throws OperationCanceledException, AuthenticatorException, IOException,
+        AccountUtils.AccountNotFoundException;
+
+    OwnCloudClient create(Account account, Activity currentActivity)
+        throws OperationCanceledException, AuthenticatorException, IOException,
+        AccountUtils.AccountNotFoundException;
+
+    OwnCloudClient create(Uri uri,
+                          boolean followRedirects,
+                          boolean useNextcloudUserAgent);
+
+    OwnCloudClient create(Uri uri, boolean followRedirects);
+}

+ 67 - 0
src/main/java/com/nextcloud/client/network/ClientFactoryImpl.java

@@ -0,0 +1,67 @@
+/*
+ * Nextcloud Android client application
+ *
+ * @author Chris Narkiewicz
+ * Copyright (C) 2019 Chris Narkiewicz <hello@ezaquarii.com>
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+package com.nextcloud.client.network;
+
+import android.accounts.Account;
+import android.accounts.AuthenticatorException;
+import android.accounts.OperationCanceledException;
+import android.app.Activity;
+import android.content.Context;
+import android.net.Uri;
+
+import com.owncloud.android.lib.common.OwnCloudClient;
+import com.owncloud.android.lib.common.OwnCloudClientFactory;
+import com.owncloud.android.lib.common.accounts.AccountUtils;
+
+import java.io.IOException;
+
+class ClientFactoryImpl implements ClientFactory {
+
+    private Context context;
+
+    ClientFactoryImpl(Context context) {
+        this.context = context;
+    }
+
+    @Override
+    public OwnCloudClient create(Account account)
+        throws OperationCanceledException, AuthenticatorException, IOException,
+        AccountUtils.AccountNotFoundException {
+        return OwnCloudClientFactory.createOwnCloudClient(account, context);
+    }
+
+    @Override
+    public OwnCloudClient create(Account account, Activity currentActivity)
+        throws OperationCanceledException, AuthenticatorException, IOException,
+        AccountUtils.AccountNotFoundException {
+        return OwnCloudClientFactory.createOwnCloudClient(account, context, currentActivity);
+    }
+
+    @Override
+    public OwnCloudClient create(Uri uri, boolean followRedirects, boolean useNextcloudUserAgent) {
+        return OwnCloudClientFactory.createOwnCloudClient(uri, context, followRedirects);
+    }
+
+    @Override
+    public OwnCloudClient create(Uri uri, boolean followRedirects) {
+        return OwnCloudClientFactory.createOwnCloudClient(uri, context, followRedirects);
+    }
+}

+ 29 - 0
src/main/java/com/nextcloud/client/network/ConnectivityService.java

@@ -0,0 +1,29 @@
+/*
+ * Nextcloud Android client application
+ *
+ * @author Chris Narkiewicz
+ * Copyright (C) 2019 Chris Narkiewicz <hello@ezaquarii.com>
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+package com.nextcloud.client.network;
+
+import com.evernote.android.job.JobRequest;
+
+public interface ConnectivityService {
+    boolean isInternetWalled();
+    boolean isOnlineWithWifi();
+    JobRequest.NetworkType getActiveNetworkType();
+}

+ 71 - 30
src/main/java/com/owncloud/android/utils/ConnectivityUtils.java → src/main/java/com/nextcloud/client/network/ConnectivityServiceImpl.java

@@ -1,41 +1,35 @@
 /*
 /*
  * Nextcloud Android client application
  * Nextcloud Android client application
  *
  *
- * @author Mario Danic
- * Copyright (C) 2017 Mario Danic
- * Copyright (C) 2017 Nextcloud GmbH.
+ * @author Chris Narkiewicz
+ * Copyright (C) 2019 Chris Narkiewicz <hello@ezaquarii.com>
  *
  *
  * This program is free software: you can redistribute it and/or modify
  * This program is free software: you can redistribute it and/or modify
  * it under the terms of the GNU Affero General Public License as published by
  * it under the terms of the GNU Affero General Public License as published by
  * the Free Software Foundation, either version 3 of the License, or
  * the Free Software Foundation, either version 3 of the License, or
- * at your option) any later version.
+ * (at your option) any later version.
  *
  *
  * This program is distributed in the hope that it will be useful,
  * This program is distributed in the hope that it will be useful,
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  * GNU Affero General Public License for more details.
  * GNU Affero General Public License for more details.
  *
  *
  * You should have received a copy of the GNU Affero General Public License
  * You should have received a copy of the GNU Affero General Public License
- * along with this program.  If not, see <http://www.gnu.org/licenses/>.
- *
- * Inspired by: https://stackoverflow.com/questions/6493517/detect-if-android-device-has-internet-connection
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
  */
  */
 
 
-package com.owncloud.android.utils;
+package com.nextcloud.client.network;
 
 
 import android.accounts.Account;
 import android.accounts.Account;
 import android.accounts.AuthenticatorException;
 import android.accounts.AuthenticatorException;
 import android.accounts.OperationCanceledException;
 import android.accounts.OperationCanceledException;
-import android.content.Context;
 import android.net.ConnectivityManager;
 import android.net.ConnectivityManager;
 import android.net.NetworkInfo;
 import android.net.NetworkInfo;
 
 
 import com.evernote.android.job.JobRequest;
 import com.evernote.android.job.JobRequest;
-import com.evernote.android.job.util.Device;
-import com.owncloud.android.authentication.AccountUtils;
+import com.nextcloud.client.account.UserAccountManager;
 import com.owncloud.android.lib.common.OwnCloudAccount;
 import com.owncloud.android.lib.common.OwnCloudAccount;
 import com.owncloud.android.lib.common.OwnCloudClient;
 import com.owncloud.android.lib.common.OwnCloudClient;
-import com.owncloud.android.lib.common.OwnCloudClientFactory;
 import com.owncloud.android.lib.common.utils.Log_OC;
 import com.owncloud.android.lib.common.utils.Log_OC;
 import com.owncloud.android.lib.resources.status.OwnCloudVersion;
 import com.owncloud.android.lib.resources.status.OwnCloudVersion;
 
 
@@ -45,21 +39,43 @@ import org.json.JSONObject;
 
 
 import java.io.IOException;
 import java.io.IOException;
 
 
-public final class ConnectivityUtils {
+import androidx.core.net.ConnectivityManagerCompat;
+import kotlin.jvm.functions.Function1;
+
+class ConnectivityServiceImpl implements ConnectivityService {
+
+    private final static String TAG = ConnectivityServiceImpl.class.getName();
 
 
-    private final static String TAG = ConnectivityUtils.class.getName();
+    private ConnectivityManager connectivityManager;
+    private UserAccountManager accountManager;
+    private ClientFactory clientFactory;
+    private GetRequestBuilder requestBuilder;
 
 
-    private ConnectivityUtils() {
-        // utility class -> private constructor
+    static class GetRequestBuilder implements Function1<String, GetMethod> {
+        @Override
+        public GetMethod invoke(String url) {
+            return new GetMethod(url);
+        }
     }
     }
 
 
-    public static boolean isInternetWalled(Context context) {
-        if (isOnlineWithWifi(context)) {
+    ConnectivityServiceImpl(ConnectivityManager connectivityManager,
+                            UserAccountManager accountManager,
+                            ClientFactory clientFactory,
+                            GetRequestBuilder requestBuilder) {
+        this.connectivityManager = connectivityManager;
+        this.accountManager = accountManager;
+        this.clientFactory = clientFactory;
+        this.requestBuilder = requestBuilder;
+    }
+
+    @Override
+    public boolean isInternetWalled() {
+        if (isOnlineWithWifi()) {
             try {
             try {
-                Account account = AccountUtils.getCurrentOwnCloudAccount(context);
+                Account account = accountManager.getCurrentAccount();
                 if (account != null) {
                 if (account != null) {
-                    OwnCloudAccount ocAccount = new OwnCloudAccount(account, context);
-                    OwnCloudVersion serverVersion = AccountUtils.getServerVersion(account);
+                    OwnCloudAccount ocAccount = accountManager.getCurrentOwnCloudAccount();
+                    OwnCloudVersion serverVersion = accountManager.getServerVersion(account);
 
 
                     String url;
                     String url;
                     if (serverVersion.compareTo(OwnCloudVersion.nextcloud_13) > 0) {
                     if (serverVersion.compareTo(OwnCloudVersion.nextcloud_13) > 0) {
@@ -68,8 +84,8 @@ public final class ConnectivityUtils {
                         url = ocAccount.getBaseUri() + "/status.php";
                         url = ocAccount.getBaseUri() + "/status.php";
                     }
                     }
 
 
-                    GetMethod get = new GetMethod(url);
-                    OwnCloudClient client = OwnCloudClientFactory.createOwnCloudClient(account, context);
+                    GetMethod get = requestBuilder.invoke(url);
+                    OwnCloudClient client = clientFactory.create(account);
 
 
                     int status = client.executeMethod(get);
                     int status = client.executeMethod(get);
 
 
@@ -100,24 +116,24 @@ public final class ConnectivityUtils {
                 Log_OC.e(TAG, e.getMessage());
                 Log_OC.e(TAG, e.getMessage());
             }
             }
         } else {
         } else {
-            return Device.getNetworkType(context).equals(JobRequest.NetworkType.ANY);
+            return getActiveNetworkType() == JobRequest.NetworkType.ANY;
         }
         }
 
 
         return true;
         return true;
     }
     }
 
 
-    public static boolean isOnlineWithWifi(Context context) {
+    @Override
+    public boolean isOnlineWithWifi() {
         try {
         try {
-            ConnectivityManager cm = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
-            NetworkInfo activeNetwork = cm.getActiveNetworkInfo();
+            NetworkInfo activeNetwork = connectivityManager.getActiveNetworkInfo();
 
 
             if (activeNetwork.isConnectedOrConnecting()) {
             if (activeNetwork.isConnectedOrConnecting()) {
                 switch (activeNetwork.getType()) {
                 switch (activeNetwork.getType()) {
                     case ConnectivityManager.TYPE_VPN:
                     case ConnectivityManager.TYPE_VPN:
                         // check if any other network is wifi
                         // check if any other network is wifi
-                        for (NetworkInfo networkInfo : cm.getAllNetworkInfo()) {
+                        for (NetworkInfo networkInfo : connectivityManager.getAllNetworkInfo()) {
                             if (networkInfo.isConnectedOrConnecting() &&
                             if (networkInfo.isConnectedOrConnecting() &&
-                                    networkInfo.getType() == ConnectivityManager.TYPE_WIFI) {
+                                networkInfo.getType() == ConnectivityManager.TYPE_WIFI) {
                                 return true;
                                 return true;
                             }
                             }
                         }
                         }
@@ -136,4 +152,29 @@ public final class ConnectivityUtils {
             return false;
             return false;
         }
         }
     }
     }
+
+    @Override
+    public JobRequest.NetworkType getActiveNetworkType() {
+        NetworkInfo networkInfo;
+        try {
+            networkInfo = connectivityManager.getActiveNetworkInfo();
+        } catch (Throwable t) {
+            return JobRequest.NetworkType.ANY;
+        }
+
+        if (networkInfo == null || !networkInfo.isConnectedOrConnecting()) {
+            return JobRequest.NetworkType.ANY;
+        }
+
+        boolean metered = ConnectivityManagerCompat.isActiveNetworkMetered(connectivityManager);
+        if (!metered) {
+            return JobRequest.NetworkType.UNMETERED;
+        }
+
+        if (networkInfo.isRoaming()) {
+            return JobRequest.NetworkType.CONNECTED;
+        } else {
+            return JobRequest.NetworkType.NOT_ROAMING;
+        }
+    }
 }
 }

+ 57 - 0
src/main/java/com/nextcloud/client/network/NetworkModule.java

@@ -0,0 +1,57 @@
+/*
+ * Nextcloud Android client application
+ *
+ * @author Chris Narkiewicz
+ * Copyright (C) 2019 Chris Narkiewicz <hello@ezaquarii.com>
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+
+package com.nextcloud.client.network;
+
+import android.content.Context;
+import android.net.ConnectivityManager;
+
+import com.nextcloud.client.account.UserAccountManager;
+
+import javax.inject.Singleton;
+
+import dagger.Module;
+import dagger.Provides;
+
+@Module
+public class NetworkModule {
+
+    @Provides
+    ConnectivityService connectivityService(ConnectivityManager connectivityManager,
+                                            UserAccountManager accountManager,
+                                            ClientFactory clientFactory) {
+        return new ConnectivityServiceImpl(connectivityManager,
+                                           accountManager,
+                                           clientFactory,
+                                           new ConnectivityServiceImpl.GetRequestBuilder());
+    }
+
+    @Provides
+    @Singleton
+    ClientFactory clientFactory(Context context) {
+        return new ClientFactoryImpl(context);
+    }
+
+    @Provides
+    @Singleton
+    ConnectivityManager connectivityManager(Context context) {
+        return (ConnectivityManager)context.getSystemService(Context.CONNECTIVITY_SERVICE);
+    }
+}

+ 13 - 7
src/main/java/com/owncloud/android/MainApp.java

@@ -48,6 +48,7 @@ import com.nextcloud.client.account.UserAccountManager;
 import com.nextcloud.client.appinfo.AppInfo;
 import com.nextcloud.client.appinfo.AppInfo;
 import com.nextcloud.client.di.ActivityInjector;
 import com.nextcloud.client.di.ActivityInjector;
 import com.nextcloud.client.di.DaggerAppComponent;
 import com.nextcloud.client.di.DaggerAppComponent;
+import com.nextcloud.client.network.ConnectivityService;
 import com.nextcloud.client.preferences.AppPreferences;
 import com.nextcloud.client.preferences.AppPreferences;
 import com.nextcloud.client.preferences.AppPreferencesImpl;
 import com.nextcloud.client.preferences.AppPreferencesImpl;
 import com.nextcloud.client.whatsnew.WhatsNewService;
 import com.nextcloud.client.whatsnew.WhatsNewService;
@@ -157,6 +158,9 @@ public class MainApp extends MultiDexApplication implements
     @Inject
     @Inject
     protected WhatsNewService whatsNew;
     protected WhatsNewService whatsNew;
 
 
+    @Inject
+    ConnectivityService connectivityService;
+
     private PassCodeManager passCodeManager;
     private PassCodeManager passCodeManager;
 
 
     @SuppressWarnings("unused")
     @SuppressWarnings("unused")
@@ -197,7 +201,8 @@ public class MainApp extends MultiDexApplication implements
                 getApplicationContext(),
                 getApplicationContext(),
                 accountManager,
                 accountManager,
                 preferences,
                 preferences,
-                uploadsStorageManager
+                uploadsStorageManager,
+                connectivityService
             )
             )
         );
         );
 
 
@@ -230,7 +235,7 @@ public class MainApp extends MultiDexApplication implements
             }
             }
         }
         }
 
 
-        initSyncOperations(uploadsStorageManager, accountManager);
+        initSyncOperations(uploadsStorageManager, accountManager, connectivityService);
         initContactsBackup(accountManager);
         initContactsBackup(accountManager);
         notificationChannels();
         notificationChannels();
 
 
@@ -356,7 +361,8 @@ public class MainApp extends MultiDexApplication implements
 
 
     public static void initSyncOperations(
     public static void initSyncOperations(
         final UploadsStorageManager uploadsStorageManager,
         final UploadsStorageManager uploadsStorageManager,
-        final UserAccountManager accountManager
+        final UserAccountManager accountManager,
+        final ConnectivityService connectivityService
     ) {
     ) {
         updateToAutoUpload();
         updateToAutoUpload();
         cleanOldEntries();
         cleanOldEntries();
@@ -375,17 +381,17 @@ public class MainApp extends MultiDexApplication implements
         initiateExistingAutoUploadEntries();
         initiateExistingAutoUploadEntries();
 
 
         FilesSyncHelper.scheduleFilesSyncIfNeeded(mContext);
         FilesSyncHelper.scheduleFilesSyncIfNeeded(mContext);
-        FilesSyncHelper.restartJobsIfNeeded(uploadsStorageManager, accountManager);
+        FilesSyncHelper.restartJobsIfNeeded(uploadsStorageManager, accountManager, connectivityService);
         FilesSyncHelper.scheduleOfflineSyncIfNeeded();
         FilesSyncHelper.scheduleOfflineSyncIfNeeded();
 
 
-        ReceiversHelper.registerNetworkChangeReceiver(uploadsStorageManager, accountManager);
+        ReceiversHelper.registerNetworkChangeReceiver(uploadsStorageManager, accountManager, connectivityService);
 
 
         if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR1) {
         if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR1) {
-            ReceiversHelper.registerPowerChangeReceiver(uploadsStorageManager, accountManager);
+            ReceiversHelper.registerPowerChangeReceiver(uploadsStorageManager, accountManager, connectivityService);
         }
         }
 
 
         if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
         if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) {
-            ReceiversHelper.registerPowerSaveReceiver(uploadsStorageManager, accountManager);
+            ReceiversHelper.registerPowerSaveReceiver(uploadsStorageManager, accountManager, connectivityService);
         }
         }
     }
     }
 
 

+ 9 - 4
src/main/java/com/owncloud/android/datamodel/ThumbnailsCacheManager.java

@@ -45,6 +45,7 @@ import android.view.MenuItem;
 import android.view.WindowManager;
 import android.view.WindowManager;
 import android.widget.ImageView;
 import android.widget.ImageView;
 
 
+import com.nextcloud.client.network.ConnectivityService;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.R;
 import com.owncloud.android.R;
 import com.owncloud.android.lib.common.OwnCloudAccount;
 import com.owncloud.android.lib.common.OwnCloudAccount;
@@ -59,7 +60,6 @@ import com.owncloud.android.ui.adapter.DiskLruImageCache;
 import com.owncloud.android.ui.fragment.FileFragment;
 import com.owncloud.android.ui.fragment.FileFragment;
 import com.owncloud.android.ui.preview.PreviewImageFragment;
 import com.owncloud.android.ui.preview.PreviewImageFragment;
 import com.owncloud.android.utils.BitmapUtils;
 import com.owncloud.android.utils.BitmapUtils;
-import com.owncloud.android.utils.ConnectivityUtils;
 import com.owncloud.android.utils.DisplayUtils.AvatarGenerationListener;
 import com.owncloud.android.utils.DisplayUtils.AvatarGenerationListener;
 import com.owncloud.android.utils.FileStorageUtils;
 import com.owncloud.android.utils.FileStorageUtils;
 import com.owncloud.android.utils.MimeTypeUtil;
 import com.owncloud.android.utils.MimeTypeUtil;
@@ -232,14 +232,19 @@ public final class ThumbnailsCacheManager {
         private Account account;
         private Account account;
         private WeakReference<ImageView> imageViewReference;
         private WeakReference<ImageView> imageViewReference;
         private OCFile file;
         private OCFile file;
+        private ConnectivityService connectivityService;
 
 
 
 
-        public ResizedImageGenerationTask(FileFragment fileFragment, ImageView imageView,
-                                          FileDataStorageManager storageManager, Account account)
+        public ResizedImageGenerationTask(FileFragment fileFragment,
+                                          ImageView imageView,
+                                          FileDataStorageManager storageManager,
+                                          ConnectivityService connectivityService,
+                                          Account account)
                 throws IllegalArgumentException {
                 throws IllegalArgumentException {
             this.fileFragment = fileFragment;
             this.fileFragment = fileFragment;
             imageViewReference = new WeakReference<>(imageView);
             imageViewReference = new WeakReference<>(imageView);
             this.storageManager = storageManager;
             this.storageManager = storageManager;
+            this.connectivityService = connectivityService;
             this.account = account;
             this.account = account;
         }
         }
 
 
@@ -361,7 +366,7 @@ public final class ThumbnailsCacheManager {
                     }
                     }
                 } else {
                 } else {
                     new Thread(() -> {
                     new Thread(() -> {
-                        if (ConnectivityUtils.isInternetWalled(MainApp.getAppContext())) {
+                        if (connectivityService.isInternetWalled()) {
                             if (fileFragment instanceof PreviewImageFragment) {
                             if (fileFragment instanceof PreviewImageFragment) {
                                 ((PreviewImageFragment) fileFragment).setNoConnectionErrorMessage();
                                 ((PreviewImageFragment) fileFragment).setNoConnectionErrorMessage();
                             }
                             }

+ 3 - 1
src/main/java/com/owncloud/android/files/BootupBroadcastReceiver.java

@@ -28,6 +28,7 @@ import android.content.Context;
 import android.content.Intent;
 import android.content.Intent;
 
 
 import com.nextcloud.client.account.UserAccountManager;
 import com.nextcloud.client.account.UserAccountManager;
+import com.nextcloud.client.network.ConnectivityService;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.datamodel.UploadsStorageManager;
 import com.owncloud.android.datamodel.UploadsStorageManager;
 import com.owncloud.android.lib.common.utils.Log_OC;
 import com.owncloud.android.lib.common.utils.Log_OC;
@@ -47,6 +48,7 @@ public class BootupBroadcastReceiver extends BroadcastReceiver {
 
 
     @Inject UserAccountManager accountManager;
     @Inject UserAccountManager accountManager;
     @Inject UploadsStorageManager uploadsStorageManager;
     @Inject UploadsStorageManager uploadsStorageManager;
+    @Inject ConnectivityService connectivityService;
 
 
     /**
     /**
      * Receives broadcast intent reporting that the system was just boot up.
      * Receives broadcast intent reporting that the system was just boot up.
@@ -59,7 +61,7 @@ public class BootupBroadcastReceiver extends BroadcastReceiver {
         AndroidInjection.inject(this, context);
         AndroidInjection.inject(this, context);
 
 
         if (Intent.ACTION_BOOT_COMPLETED.equals(intent.getAction())) {
         if (Intent.ACTION_BOOT_COMPLETED.equals(intent.getAction())) {
-            MainApp.initSyncOperations(uploadsStorageManager, accountManager);
+            MainApp.initSyncOperations(uploadsStorageManager, accountManager, connectivityService);
             MainApp.initContactsBackup(accountManager);
             MainApp.initContactsBackup(accountManager);
         } else {
         } else {
             Log_OC.d(TAG, "Getting wrong intent: " + intent.getAction());
             Log_OC.d(TAG, "Getting wrong intent: " + intent.getAction());

+ 7 - 3
src/main/java/com/owncloud/android/files/services/FileUploader.java

@@ -49,6 +49,7 @@ import android.util.Pair;
 import com.evernote.android.job.JobRequest;
 import com.evernote.android.job.JobRequest;
 import com.evernote.android.job.util.Device;
 import com.evernote.android.job.util.Device;
 import com.nextcloud.client.account.UserAccountManager;
 import com.nextcloud.client.account.UserAccountManager;
+import com.nextcloud.client.network.ConnectivityService;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.R;
 import com.owncloud.android.R;
 import com.owncloud.android.authentication.AccountUtils;
 import com.owncloud.android.authentication.AccountUtils;
@@ -72,7 +73,6 @@ import com.owncloud.android.operations.UploadFileOperation;
 import com.owncloud.android.ui.activity.FileActivity;
 import com.owncloud.android.ui.activity.FileActivity;
 import com.owncloud.android.ui.activity.UploadListActivity;
 import com.owncloud.android.ui.activity.UploadListActivity;
 import com.owncloud.android.ui.notifications.NotificationUtils;
 import com.owncloud.android.ui.notifications.NotificationUtils;
-import com.owncloud.android.utils.ConnectivityUtils;
 import com.owncloud.android.utils.ErrorMessageAdapter;
 import com.owncloud.android.utils.ErrorMessageAdapter;
 import com.owncloud.android.utils.PowerUtils;
 import com.owncloud.android.utils.PowerUtils;
 import com.owncloud.android.utils.ThemeUtils;
 import com.owncloud.android.utils.ThemeUtils;
@@ -186,6 +186,7 @@ public class FileUploader extends Service
     private FileDataStorageManager mStorageManager;
     private FileDataStorageManager mStorageManager;
     //since there can be only one instance of an Android service, there also just one db connection.
     //since there can be only one instance of an Android service, there also just one db connection.
     @Inject UploadsStorageManager mUploadsStorageManager;
     @Inject UploadsStorageManager mUploadsStorageManager;
+    @Inject ConnectivityService connectivityService;
 
 
     private IndexedForest<UploadFileOperation> mPendingUploads = new IndexedForest<>();
     private IndexedForest<UploadFileOperation> mPendingUploads = new IndexedForest<>();
 
 
@@ -401,6 +402,7 @@ public class FileUploader extends Service
             @NonNull final Context context,
             @NonNull final Context context,
             @Nullable Account account,
             @Nullable Account account,
             @NotNull final UploadsStorageManager uploadsStorageManager,
             @NotNull final UploadsStorageManager uploadsStorageManager,
+            @NotNull final ConnectivityService connectivityService,
             @Nullable final UploadResult uploadResult
             @Nullable final UploadResult uploadResult
         ) {
         ) {
             OCUpload[] failedUploads = uploadsStorageManager.getFailedUploads();
             OCUpload[] failedUploads = uploadsStorageManager.getFailedUploads();
@@ -408,8 +410,8 @@ public class FileUploader extends Service
             boolean resultMatch;
             boolean resultMatch;
             boolean accountMatch;
             boolean accountMatch;
 
 
-            boolean gotNetwork = !Device.getNetworkType(context).equals(JobRequest.NetworkType.ANY) &&
-                    !ConnectivityUtils.isInternetWalled(context);
+            boolean gotNetwork = connectivityService.getActiveNetworkType() != JobRequest.NetworkType.ANY &&
+                    !connectivityService.isInternetWalled();
             boolean gotWifi = gotNetwork && Device.getNetworkType(context).equals(JobRequest.NetworkType.UNMETERED);
             boolean gotWifi = gotNetwork && Device.getNetworkType(context).equals(JobRequest.NetworkType.UNMETERED);
             boolean charging = Device.getBatteryStatus(context).isCharging();
             boolean charging = Device.getBatteryStatus(context).isCharging();
             boolean isPowerSaving = PowerUtils.isPowerSaveMode(context);
             boolean isPowerSaving = PowerUtils.isPowerSaveMode(context);
@@ -642,6 +644,7 @@ public class FileUploader extends Service
 
 
                     newUpload = new UploadFileOperation(
                     newUpload = new UploadFileOperation(
                         mUploadsStorageManager,
                         mUploadsStorageManager,
+                            connectivityService,
                             account,
                             account,
                             file,
                             file,
                             ocUpload,
                             ocUpload,
@@ -701,6 +704,7 @@ public class FileUploader extends Service
 
 
             UploadFileOperation newUpload = new UploadFileOperation(
             UploadFileOperation newUpload = new UploadFileOperation(
                     mUploadsStorageManager,
                     mUploadsStorageManager,
+                    connectivityService,
                     account,
                     account,
                     null,
                     null,
                     upload,
                     upload,

+ 6 - 2
src/main/java/com/owncloud/android/jobs/FilesSyncJob.java

@@ -34,6 +34,7 @@ import android.text.TextUtils;
 import com.evernote.android.job.Job;
 import com.evernote.android.job.Job;
 import com.evernote.android.job.util.support.PersistableBundleCompat;
 import com.evernote.android.job.util.support.PersistableBundleCompat;
 import com.nextcloud.client.account.UserAccountManager;
 import com.nextcloud.client.account.UserAccountManager;
+import com.nextcloud.client.network.ConnectivityService;
 import com.nextcloud.client.preferences.AppPreferences;
 import com.nextcloud.client.preferences.AppPreferences;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.R;
 import com.owncloud.android.R;
@@ -81,15 +82,18 @@ public class FilesSyncJob extends Job {
     private UserAccountManager userAccountManager;
     private UserAccountManager userAccountManager;
     private AppPreferences preferences;
     private AppPreferences preferences;
     private UploadsStorageManager uploadsStorageManager;
     private UploadsStorageManager uploadsStorageManager;
+    private ConnectivityService connectivityService;
 
 
     public FilesSyncJob(
     public FilesSyncJob(
         final UserAccountManager userAccountManager,
         final UserAccountManager userAccountManager,
         final AppPreferences preferences,
         final AppPreferences preferences,
-        final UploadsStorageManager uploadsStorageManager
+        final UploadsStorageManager uploadsStorageManager,
+        final ConnectivityService connectivityService
     ) {
     ) {
         this.userAccountManager = userAccountManager;
         this.userAccountManager = userAccountManager;
         this.preferences = preferences;
         this.preferences = preferences;
         this.uploadsStorageManager = uploadsStorageManager;
         this.uploadsStorageManager = uploadsStorageManager;
+        this.connectivityService = connectivityService;
     }
     }
 
 
     @NonNull
     @NonNull
@@ -118,7 +122,7 @@ public class FilesSyncJob extends Job {
         boolean lightVersion = resources.getBoolean(R.bool.syncedFolder_light);
         boolean lightVersion = resources.getBoolean(R.bool.syncedFolder_light);
 
 
         final boolean skipCustom = bundle.getBoolean(SKIP_CUSTOM, false);
         final boolean skipCustom = bundle.getBoolean(SKIP_CUSTOM, false);
-        FilesSyncHelper.restartJobsIfNeeded(uploadsStorageManager, userAccountManager);
+        FilesSyncHelper.restartJobsIfNeeded(uploadsStorageManager, userAccountManager, connectivityService);
         FilesSyncHelper.insertAllDBEntries(preferences, skipCustom);
         FilesSyncHelper.insertAllDBEntries(preferences, skipCustom);
 
 
         // Create all the providers we'll need
         // Create all the providers we'll need

+ 7 - 3
src/main/java/com/owncloud/android/jobs/NCJobCreator.java

@@ -29,6 +29,7 @@ import android.content.Context;
 import com.evernote.android.job.Job;
 import com.evernote.android.job.Job;
 import com.evernote.android.job.JobCreator;
 import com.evernote.android.job.JobCreator;
 import com.nextcloud.client.account.UserAccountManager;
 import com.nextcloud.client.account.UserAccountManager;
+import com.nextcloud.client.network.ConnectivityService;
 import com.nextcloud.client.preferences.AppPreferences;
 import com.nextcloud.client.preferences.AppPreferences;
 import com.owncloud.android.datamodel.UploadsStorageManager;
 import com.owncloud.android.datamodel.UploadsStorageManager;
 
 
@@ -44,17 +45,20 @@ public class NCJobCreator implements JobCreator {
     private final UserAccountManager accountManager;
     private final UserAccountManager accountManager;
     private final AppPreferences preferences;
     private final AppPreferences preferences;
     private final UploadsStorageManager uploadsStorageManager;
     private final UploadsStorageManager uploadsStorageManager;
+    private final ConnectivityService connectivityService;
 
 
     public NCJobCreator(
     public NCJobCreator(
         Context context,
         Context context,
         UserAccountManager accountManager,
         UserAccountManager accountManager,
         AppPreferences preferences,
         AppPreferences preferences,
-        UploadsStorageManager uploadsStorageManager
+        UploadsStorageManager uploadsStorageManager,
+        ConnectivityService connectivityServices
     ) {
     ) {
         this.context = context;
         this.context = context;
         this.accountManager = accountManager;
         this.accountManager = accountManager;
         this.preferences = preferences;
         this.preferences = preferences;
         this.uploadsStorageManager = uploadsStorageManager;
         this.uploadsStorageManager = uploadsStorageManager;
+        this.connectivityService = connectivityServices;
     }
     }
 
 
     @Override
     @Override
@@ -67,9 +71,9 @@ public class NCJobCreator implements JobCreator {
             case AccountRemovalJob.TAG:
             case AccountRemovalJob.TAG:
                 return new AccountRemovalJob(uploadsStorageManager);
                 return new AccountRemovalJob(uploadsStorageManager);
             case FilesSyncJob.TAG:
             case FilesSyncJob.TAG:
-                return new FilesSyncJob(accountManager, preferences, uploadsStorageManager);
+                return new FilesSyncJob(accountManager, preferences, uploadsStorageManager, connectivityService);
             case OfflineSyncJob.TAG:
             case OfflineSyncJob.TAG:
-                return new OfflineSyncJob(accountManager);
+                return new OfflineSyncJob(accountManager, connectivityService);
             case NotificationJob.TAG:
             case NotificationJob.TAG:
                 return new NotificationJob(context, accountManager);
                 return new NotificationJob(context, accountManager);
             case MediaFoldersDetectionJob.TAG:
             case MediaFoldersDetectionJob.TAG:

+ 7 - 6
src/main/java/com/owncloud/android/jobs/OfflineSyncJob.java

@@ -29,8 +29,8 @@ import android.os.PowerManager;
 import com.evernote.android.job.Job;
 import com.evernote.android.job.Job;
 import com.evernote.android.job.JobManager;
 import com.evernote.android.job.JobManager;
 import com.evernote.android.job.JobRequest;
 import com.evernote.android.job.JobRequest;
-import com.evernote.android.job.util.Device;
 import com.nextcloud.client.account.UserAccountManager;
 import com.nextcloud.client.account.UserAccountManager;
+import com.nextcloud.client.network.ConnectivityService;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.datamodel.FileDataStorageManager;
 import com.owncloud.android.datamodel.FileDataStorageManager;
 import com.owncloud.android.datamodel.OCFile;
 import com.owncloud.android.datamodel.OCFile;
@@ -38,7 +38,6 @@ import com.owncloud.android.lib.common.operations.RemoteOperationResult;
 import com.owncloud.android.lib.common.utils.Log_OC;
 import com.owncloud.android.lib.common.utils.Log_OC;
 import com.owncloud.android.lib.resources.files.CheckEtagRemoteOperation;
 import com.owncloud.android.lib.resources.files.CheckEtagRemoteOperation;
 import com.owncloud.android.operations.SynchronizeFileOperation;
 import com.owncloud.android.operations.SynchronizeFileOperation;
-import com.owncloud.android.utils.ConnectivityUtils;
 import com.owncloud.android.utils.FileStorageUtils;
 import com.owncloud.android.utils.FileStorageUtils;
 import com.owncloud.android.utils.PowerUtils;
 import com.owncloud.android.utils.PowerUtils;
 
 
@@ -54,10 +53,12 @@ public class OfflineSyncJob extends Job {
     public static final String TAG = "OfflineSyncJob";
     public static final String TAG = "OfflineSyncJob";
 
 
     private static final String WAKELOCK_TAG_SEPARATION = ":";
     private static final String WAKELOCK_TAG_SEPARATION = ":";
-    private UserAccountManager userAccountManager;
+    private final UserAccountManager userAccountManager;
+    private final ConnectivityService connectivityService;
 
 
-    public OfflineSyncJob(UserAccountManager userAccountManager) {
+    public OfflineSyncJob(UserAccountManager userAccountManager, ConnectivityService connectivityService) {
         this.userAccountManager = userAccountManager;
         this.userAccountManager = userAccountManager;
+        this.connectivityService = connectivityService;
     }
     }
 
 
     @NonNull
     @NonNull
@@ -67,8 +68,8 @@ public class OfflineSyncJob extends Job {
 
 
         PowerManager.WakeLock wakeLock = null;
         PowerManager.WakeLock wakeLock = null;
         if (!PowerUtils.isPowerSaveMode(context) &&
         if (!PowerUtils.isPowerSaveMode(context) &&
-                Device.getNetworkType(context).equals(JobRequest.NetworkType.UNMETERED) &&
-                !ConnectivityUtils.isInternetWalled(context)) {
+                connectivityService.getActiveNetworkType() == JobRequest.NetworkType.UNMETERED &&
+                !connectivityService.isInternetWalled()) {
             Set<Job> jobs = JobManager.instance().getAllJobsForTag(TAG);
             Set<Job> jobs = JobManager.instance().getAllJobsForTag(TAG);
             for (Job job : jobs) {
             for (Job job : jobs) {
                 if (!job.isFinished() && !job.equals(this)) {
                 if (!job.isFinished() && !job.equals(this)) {

+ 7 - 5
src/main/java/com/owncloud/android/operations/UploadFileOperation.java

@@ -32,6 +32,7 @@ import android.util.Log;
 import com.evernote.android.job.JobRequest;
 import com.evernote.android.job.JobRequest;
 import com.evernote.android.job.util.Device;
 import com.evernote.android.job.util.Device;
 import com.google.gson.reflect.TypeToken;
 import com.google.gson.reflect.TypeToken;
+import com.nextcloud.client.network.ConnectivityService;
 import com.owncloud.android.datamodel.ArbitraryDataProvider;
 import com.owncloud.android.datamodel.ArbitraryDataProvider;
 import com.owncloud.android.datamodel.DecryptedFolderMetadata;
 import com.owncloud.android.datamodel.DecryptedFolderMetadata;
 import com.owncloud.android.datamodel.EncryptedFolderMetadata;
 import com.owncloud.android.datamodel.EncryptedFolderMetadata;
@@ -60,7 +61,6 @@ import com.owncloud.android.lib.resources.files.ReadFileRemoteOperation;
 import com.owncloud.android.lib.resources.files.UploadFileRemoteOperation;
 import com.owncloud.android.lib.resources.files.UploadFileRemoteOperation;
 import com.owncloud.android.lib.resources.files.model.RemoteFile;
 import com.owncloud.android.lib.resources.files.model.RemoteFile;
 import com.owncloud.android.operations.common.SyncOperation;
 import com.owncloud.android.operations.common.SyncOperation;
-import com.owncloud.android.utils.ConnectivityUtils;
 import com.owncloud.android.utils.EncryptionUtils;
 import com.owncloud.android.utils.EncryptionUtils;
 import com.owncloud.android.utils.FileStorageUtils;
 import com.owncloud.android.utils.FileStorageUtils;
 import com.owncloud.android.utils.MimeType;
 import com.owncloud.android.utils.MimeType;
@@ -146,6 +146,7 @@ public class UploadFileOperation extends SyncOperation {
     final private Account mAccount;
     final private Account mAccount;
     final private OCUpload mUpload;
     final private OCUpload mUpload;
     final private UploadsStorageManager uploadsStorageManager;
     final private UploadsStorageManager uploadsStorageManager;
+    final private ConnectivityService connectivityService;
 
 
     private boolean encryptedAncestor;
     private boolean encryptedAncestor;
 
 
@@ -176,6 +177,7 @@ public class UploadFileOperation extends SyncOperation {
     }
     }
 
 
     public UploadFileOperation(UploadsStorageManager uploadsStorageManager,
     public UploadFileOperation(UploadsStorageManager uploadsStorageManager,
+                               ConnectivityService connectivityService,
                                Account account,
                                Account account,
                                OCFile file,
                                OCFile file,
                                OCUpload upload,
                                OCUpload upload,
@@ -198,6 +200,7 @@ public class UploadFileOperation extends SyncOperation {
         }
         }
 
 
         this.uploadsStorageManager = uploadsStorageManager;
         this.uploadsStorageManager = uploadsStorageManager;
+        this.connectivityService = connectivityService;
         mAccount = account;
         mAccount = account;
         mUpload = upload;
         mUpload = upload;
         if (file == null) {
         if (file == null) {
@@ -579,8 +582,7 @@ public class UploadFileOperation extends SyncOperation {
 
 
             /// perform the upload
             /// perform the upload
             if (size > ChunkedFileUploadRemoteOperation.CHUNK_SIZE_MOBILE) {
             if (size > ChunkedFileUploadRemoteOperation.CHUNK_SIZE_MOBILE) {
-
-                boolean onWifiConnection = ConnectivityUtils.isOnlineWithWifi(mContext);
+                boolean onWifiConnection = connectivityService.isOnlineWithWifi();
 
 
                 mUploadOperation = new ChunkedFileUploadRemoteOperation(encryptedTempFile.getAbsolutePath(),
                 mUploadOperation = new ChunkedFileUploadRemoteOperation(encryptedTempFile.getAbsolutePath(),
                                                                         mFile.getParentRemotePath() + encryptedFileName,
                                                                         mFile.getParentRemotePath() + encryptedFileName,
@@ -722,7 +724,7 @@ public class UploadFileOperation extends SyncOperation {
 
 
         // check that internet is not behind walled garden
         // check that internet is not behind walled garden
         if (Device.getNetworkType(mContext).equals(JobRequest.NetworkType.ANY) ||
         if (Device.getNetworkType(mContext).equals(JobRequest.NetworkType.ANY) ||
-                ConnectivityUtils.isInternetWalled(mContext)) {
+                connectivityService.isInternetWalled()) {
             remoteOperationResult =  new RemoteOperationResult(ResultCode.NO_NETWORK_CONNECTION);
             remoteOperationResult =  new RemoteOperationResult(ResultCode.NO_NETWORK_CONNECTION);
         }
         }
 
 
@@ -826,7 +828,7 @@ public class UploadFileOperation extends SyncOperation {
 
 
             // perform the upload
             // perform the upload
             if (size > ChunkedFileUploadRemoteOperation.CHUNK_SIZE_MOBILE) {
             if (size > ChunkedFileUploadRemoteOperation.CHUNK_SIZE_MOBILE) {
-                boolean onWifiConnection = ConnectivityUtils.isOnlineWithWifi(mContext);
+                boolean onWifiConnection = connectivityService.isOnlineWithWifi();
 
 
                 mUploadOperation = new ChunkedFileUploadRemoteOperation(mFile.getStoragePath(),
                 mUploadOperation = new ChunkedFileUploadRemoteOperation(mFile.getStoragePath(),
                                                                         mFile.getRemotePath(), mFile.getMimeType(),
                                                                         mFile.getRemotePath(), mFile.getMimeType(),

+ 6 - 2
src/main/java/com/owncloud/android/ui/activity/FileActivity.java

@@ -40,6 +40,7 @@ import android.view.View;
 
 
 import com.google.android.material.snackbar.Snackbar;
 import com.google.android.material.snackbar.Snackbar;
 import com.nextcloud.client.account.UserAccountManager;
 import com.nextcloud.client.account.UserAccountManager;
+import com.nextcloud.client.network.ConnectivityService;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.R;
 import com.owncloud.android.R;
 import com.owncloud.android.authentication.AuthenticatorActivity;
 import com.owncloud.android.authentication.AuthenticatorActivity;
@@ -141,7 +142,10 @@ public abstract class FileActivity extends DrawerActivity
     private ServiceConnection mUploadServiceConnection;
     private ServiceConnection mUploadServiceConnection;
 
 
     @Inject
     @Inject
-    protected UserAccountManager accountManager;
+    UserAccountManager accountManager;
+
+    @Inject
+    ConnectivityService connectivityService;
 
 
     @Override
     @Override
     public void showFiles(boolean onDeviceOnly) {
     public void showFiles(boolean onDeviceOnly) {
@@ -160,7 +164,7 @@ public abstract class FileActivity extends DrawerActivity
     protected void onCreate(Bundle savedInstanceState) {
     protected void onCreate(Bundle savedInstanceState) {
         super.onCreate(savedInstanceState);
         super.onCreate(savedInstanceState);
         mHandler = new Handler();
         mHandler = new Handler();
-        mFileOperationsHelper = new FileOperationsHelper(this, getUserAccountManager());
+        mFileOperationsHelper = new FileOperationsHelper(this, getUserAccountManager(), connectivityService);
         Account account = null;
         Account account = null;
 
 
         if (savedInstanceState != null) {
         if (savedInstanceState != null) {

+ 18 - 6
src/main/java/com/owncloud/android/ui/activity/FileDisplayActivity.java

@@ -61,6 +61,7 @@ import com.google.android.material.bottomnavigation.BottomNavigationView;
 import com.google.android.material.snackbar.Snackbar;
 import com.google.android.material.snackbar.Snackbar;
 import com.nextcloud.client.appinfo.AppInfo;
 import com.nextcloud.client.appinfo.AppInfo;
 import com.nextcloud.client.di.Injectable;
 import com.nextcloud.client.di.Injectable;
+import com.nextcloud.client.network.ConnectivityService;
 import com.nextcloud.client.preferences.AppPreferences;
 import com.nextcloud.client.preferences.AppPreferences;
 import com.nextcloud.client.preferences.AppPreferencesImpl;
 import com.nextcloud.client.preferences.AppPreferencesImpl;
 import com.owncloud.android.BuildConfig;
 import com.owncloud.android.BuildConfig;
@@ -221,10 +222,13 @@ public class FileDisplayActivity extends FileActivity
     private SearchView searchView;
     private SearchView searchView;
 
 
     @Inject
     @Inject
-    protected AppPreferences preferences;
+    AppPreferences preferences;
 
 
     @Inject
     @Inject
-    protected AppInfo appInfo;
+    AppInfo appInfo;
+
+    @Inject
+    ConnectivityService connectivityService;
 
 
     @Override
     @Override
     protected void onCreate(Bundle savedInstanceState) {
     protected void onCreate(Bundle savedInstanceState) {
@@ -2394,7 +2398,9 @@ public class FileDisplayActivity extends FileActivity
         if (showPreview) {
         if (showPreview) {
             startActivity(showDetailsIntent);
             startActivity(showDetailsIntent);
         } else {
         } else {
-            FileOperationsHelper fileOperationsHelper = new FileOperationsHelper(this, getUserAccountManager());
+            FileOperationsHelper fileOperationsHelper = new FileOperationsHelper(this,
+                                                                                 getUserAccountManager(),
+                                                                                 connectivityService);
             fileOperationsHelper.startSyncForFileAndIntent(file, showDetailsIntent);
             fileOperationsHelper.startSyncForFileAndIntent(file, showDetailsIntent);
         }
         }
     }
     }
@@ -2413,7 +2419,9 @@ public class FileDisplayActivity extends FileActivity
         if (showPreview) {
         if (showPreview) {
             startActivity(showDetailsIntent);
             startActivity(showDetailsIntent);
         } else {
         } else {
-            FileOperationsHelper fileOperationsHelper = new FileOperationsHelper(this, getUserAccountManager());
+            FileOperationsHelper fileOperationsHelper = new FileOperationsHelper(this,
+                                                                                 getUserAccountManager(),
+                                                                                 connectivityService);
             fileOperationsHelper.startSyncForFileAndIntent(file, showDetailsIntent);
             fileOperationsHelper.startSyncForFileAndIntent(file, showDetailsIntent);
         }
         }
     }
     }
@@ -2440,7 +2448,9 @@ public class FileDisplayActivity extends FileActivity
             previewIntent.putExtra(EXTRA_FILE, file);
             previewIntent.putExtra(EXTRA_FILE, file);
             previewIntent.putExtra(PreviewVideoActivity.EXTRA_START_POSITION, startPlaybackPosition);
             previewIntent.putExtra(PreviewVideoActivity.EXTRA_START_POSITION, startPlaybackPosition);
             previewIntent.putExtra(PreviewVideoActivity.EXTRA_AUTOPLAY, autoplay);
             previewIntent.putExtra(PreviewVideoActivity.EXTRA_AUTOPLAY, autoplay);
-            FileOperationsHelper fileOperationsHelper = new FileOperationsHelper(this, getUserAccountManager());
+            FileOperationsHelper fileOperationsHelper = new FileOperationsHelper(this,
+                                                                                 getUserAccountManager(),
+                                                                                 connectivityService);
             fileOperationsHelper.startSyncForFileAndIntent(file, previewIntent);
             fileOperationsHelper.startSyncForFileAndIntent(file, previewIntent);
         }
         }
     }
     }
@@ -2467,7 +2477,9 @@ public class FileDisplayActivity extends FileActivity
             Intent previewIntent = new Intent();
             Intent previewIntent = new Intent();
             previewIntent.putExtra(EXTRA_FILE, file);
             previewIntent.putExtra(EXTRA_FILE, file);
             previewIntent.putExtra(TEXT_PREVIEW, true);
             previewIntent.putExtra(TEXT_PREVIEW, true);
-            FileOperationsHelper fileOperationsHelper = new FileOperationsHelper(this, getUserAccountManager());
+            FileOperationsHelper fileOperationsHelper = new FileOperationsHelper(this,
+                                                                                 getUserAccountManager(),
+                                                                                 connectivityService);
             fileOperationsHelper.startSyncForFileAndIntent(file, previewIntent);
             fileOperationsHelper.startSyncForFileAndIntent(file, previewIntent);
         }
         }
     }
     }

+ 1 - 1
src/main/java/com/owncloud/android/ui/activity/RichDocumentsWebView.java

@@ -298,7 +298,7 @@ public class RichDocumentsWebView extends ExternalSiteWebView {
         OCFile file = data.getParcelableExtra(FolderPickerActivity.EXTRA_FILES);
         OCFile file = data.getParcelableExtra(FolderPickerActivity.EXTRA_FILES);
 
 
         new Thread(() -> {
         new Thread(() -> {
-            Account account = AccountUtils.getCurrentOwnCloudAccount(this);
+            Account account = currentAccountProvider.getCurrentAccount();
             RichDocumentsCreateAssetOperation operation = new RichDocumentsCreateAssetOperation(file.getRemotePath());
             RichDocumentsCreateAssetOperation operation = new RichDocumentsCreateAssetOperation(file.getRemotePath());
             RemoteOperationResult result = operation.execute(account, this);
             RemoteOperationResult result = operation.execute(account, this);
 
 

+ 14 - 6
src/main/java/com/owncloud/android/ui/activity/UploadListActivity.java

@@ -45,6 +45,7 @@ import com.evernote.android.job.JobRequest;
 import com.evernote.android.job.util.support.PersistableBundleCompat;
 import com.evernote.android.job.util.support.PersistableBundleCompat;
 import com.google.android.material.bottomnavigation.BottomNavigationView;
 import com.google.android.material.bottomnavigation.BottomNavigationView;
 import com.nextcloud.client.account.UserAccountManager;
 import com.nextcloud.client.account.UserAccountManager;
+import com.nextcloud.client.network.ConnectivityService;
 import com.owncloud.android.R;
 import com.owncloud.android.R;
 import com.owncloud.android.datamodel.UploadsStorageManager;
 import com.owncloud.android.datamodel.UploadsStorageManager;
 import com.owncloud.android.files.services.FileUploader;
 import com.owncloud.android.files.services.FileUploader;
@@ -108,10 +109,13 @@ public class UploadListActivity extends FileActivity {
     private Unbinder unbinder;
     private Unbinder unbinder;
 
 
     @Inject
     @Inject
-    protected UserAccountManager userAccountManager;
+    UserAccountManager userAccountManager;
 
 
     @Inject
     @Inject
-    protected UploadsStorageManager uploadsStorageManager;
+    UploadsStorageManager uploadsStorageManager;
+
+    @Inject
+    ConnectivityService connectivityService;
 
 
     @Override
     @Override
     public void showFiles(boolean onDeviceOnly) {
     public void showFiles(boolean onDeviceOnly) {
@@ -172,7 +176,7 @@ public class UploadListActivity extends FileActivity {
         emptyContentHeadline.setText(noResultsHeadline);
         emptyContentHeadline.setText(noResultsHeadline);
         emptyContentMessage.setText(noResultsMessage);
         emptyContentMessage.setText(noResultsMessage);
 
 
-        uploadListAdapter = new UploadListAdapter(this, uploadsStorageManager);
+        uploadListAdapter = new UploadListAdapter(this, uploadsStorageManager, connectivityService);
 
 
         final GridLayoutManager lm = new GridLayoutManager(this, 1);
         final GridLayoutManager lm = new GridLayoutManager(this, 1);
         uploadListAdapter.setLayoutManager(lm);
         uploadListAdapter.setLayoutManager(lm);
@@ -216,7 +220,11 @@ public class UploadListActivity extends FileActivity {
 
 
         // retry failed uploads
         // retry failed uploads
         FileUploader.UploadRequester requester = new FileUploader.UploadRequester();
         FileUploader.UploadRequester requester = new FileUploader.UploadRequester();
-        new Thread(() -> requester.retryFailedUploads(this, null, uploadsStorageManager,null)).start();
+        new Thread(() -> requester.retryFailedUploads(this,
+                                                      null,
+                                                      uploadsStorageManager,
+                                                      connectivityService,
+                                                      null)).start();
 
 
         // update UI
         // update UI
         uploadListAdapter.loadUploadItemsFromDb();
         uploadListAdapter.loadUploadItemsFromDb();
@@ -288,7 +296,7 @@ public class UploadListActivity extends FileActivity {
     protected void onActivityResult(int requestCode, int resultCode, Intent data) {
     protected void onActivityResult(int requestCode, int resultCode, Intent data) {
         super.onActivityResult(requestCode, resultCode, data);
         super.onActivityResult(requestCode, resultCode, data);
         if (requestCode == FileActivity.REQUEST_CODE__UPDATE_CREDENTIALS && resultCode == RESULT_OK) {
         if (requestCode == FileActivity.REQUEST_CODE__UPDATE_CREDENTIALS && resultCode == RESULT_OK) {
-            FilesSyncHelper.restartJobsIfNeeded(uploadsStorageManager, userAccountManager);
+            FilesSyncHelper.restartJobsIfNeeded(uploadsStorageManager, userAccountManager, connectivityService);
         }
         }
     }
     }
 
 
@@ -308,7 +316,7 @@ public class UploadListActivity extends FileActivity {
 
 
             } else {
             } else {
                 // already updated -> just retry!
                 // already updated -> just retry!
-                FilesSyncHelper.restartJobsIfNeeded(uploadsStorageManager, userAccountManager);
+                FilesSyncHelper.restartJobsIfNeeded(uploadsStorageManager, userAccountManager, connectivityService);
             }
             }
 
 
         } else {
         } else {

+ 7 - 1
src/main/java/com/owncloud/android/ui/adapter/UploadListAdapter.java

@@ -40,6 +40,7 @@ import android.widget.TextView;
 
 
 import com.afollestad.sectionedrecyclerview.SectionedRecyclerViewAdapter;
 import com.afollestad.sectionedrecyclerview.SectionedRecyclerViewAdapter;
 import com.afollestad.sectionedrecyclerview.SectionedViewHolder;
 import com.afollestad.sectionedrecyclerview.SectionedViewHolder;
+import com.nextcloud.client.network.ConnectivityService;
 import com.owncloud.android.R;
 import com.owncloud.android.R;
 import com.owncloud.android.authentication.AccountUtils;
 import com.owncloud.android.authentication.AccountUtils;
 import com.owncloud.android.datamodel.OCFile;
 import com.owncloud.android.datamodel.OCFile;
@@ -72,6 +73,7 @@ public class UploadListAdapter extends SectionedRecyclerViewAdapter<SectionedVie
     private ProgressListener progressListener;
     private ProgressListener progressListener;
     private FileActivity parentActivity;
     private FileActivity parentActivity;
     private UploadsStorageManager uploadsStorageManager;
     private UploadsStorageManager uploadsStorageManager;
+    private ConnectivityService connectivityService;
     private UploadGroup[] uploadGroups;
     private UploadGroup[] uploadGroups;
 
 
     @Override
     @Override
@@ -128,6 +130,7 @@ public class UploadListAdapter extends SectionedRecyclerViewAdapter<SectionedVie
                             parentActivity,
                             parentActivity,
                             null,
                             null,
                             uploadsStorageManager,
                             uploadsStorageManager,
+                            connectivityService,
                             null))
                             null))
                         .start();
                         .start();
                     break;
                     break;
@@ -146,10 +149,13 @@ public class UploadListAdapter extends SectionedRecyclerViewAdapter<SectionedVie
         // not needed
         // not needed
     }
     }
 
 
-    public UploadListAdapter(final FileActivity fileActivity, final UploadsStorageManager uploadsStorageManager) {
+    public UploadListAdapter(final FileActivity fileActivity,
+                             final UploadsStorageManager uploadsStorageManager,
+                             final ConnectivityService connectivityService) {
         Log_OC.d(TAG, "UploadListAdapter");
         Log_OC.d(TAG, "UploadListAdapter");
         this.parentActivity = fileActivity;
         this.parentActivity = fileActivity;
         this.uploadsStorageManager = uploadsStorageManager;
         this.uploadsStorageManager = uploadsStorageManager;
+        this.connectivityService = connectivityService;
         uploadGroups = new UploadGroup[3];
         uploadGroups = new UploadGroup[3];
 
 
         shouldShowHeadersForEmptySections(false);
         shouldShowHeadersForEmptySections(false);

+ 8 - 0
src/main/java/com/owncloud/android/ui/fragment/FileDetailFragment.java

@@ -4,9 +4,12 @@
  *   @author Bartek Przybylski
  *   @author Bartek Przybylski
  *   @author David A. Velasco
  *   @author David A. Velasco
  *   @author Andy Scherzinger
  *   @author Andy Scherzinger
+ *   @author Chris Narkiewicz
+ *
  *   Copyright (C) 2011 Bartek Przybylski
  *   Copyright (C) 2011 Bartek Przybylski
  *   Copyright (C) 2016 ownCloud Inc.
  *   Copyright (C) 2016 ownCloud Inc.
  *   Copyright (C) 2018 Andy Scherzinger
  *   Copyright (C) 2018 Andy Scherzinger
+ *   Copyright (C) 2019 Chris Narkiewicz <hello@ezaquarii.com>
  *
  *
  *   This program is free software: you can redistribute it and/or modify
  *   This program is free software: you can redistribute it and/or modify
  *   it under the terms of the GNU General Public License version 2,
  *   it under the terms of the GNU General Public License version 2,
@@ -42,6 +45,7 @@ import android.widget.TextView;
 
 
 import com.google.android.material.tabs.TabLayout;
 import com.google.android.material.tabs.TabLayout;
 import com.nextcloud.client.di.Injectable;
 import com.nextcloud.client.di.Injectable;
+import com.nextcloud.client.network.ConnectivityService;
 import com.nextcloud.client.preferences.AppPreferences;
 import com.nextcloud.client.preferences.AppPreferences;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.R;
 import com.owncloud.android.R;
@@ -147,6 +151,9 @@ public class FileDetailFragment extends FileFragment implements OnClickListener,
     @Inject
     @Inject
     AppPreferences preferences;
     AppPreferences preferences;
 
 
+    @Inject
+    ConnectivityService connectivityService;
+
     /**
     /**
      * Public factory method to create new FileDetailFragment instances.
      * Public factory method to create new FileDetailFragment instances.
      *
      *
@@ -643,6 +650,7 @@ public class FileDetailFragment extends FileFragment implements OnClickListener,
                             new ThumbnailsCacheManager.ResizedImageGenerationTask(this,
                             new ThumbnailsCacheManager.ResizedImageGenerationTask(this,
                                     activity.getPreviewImageView(),
                                     activity.getPreviewImageView(),
                                     containerActivity.getStorageManager(),
                                     containerActivity.getStorageManager(),
+                                    connectivityService,
                                     containerActivity.getStorageManager().getAccount());
                                     containerActivity.getStorageManager().getAccount());
 
 
                     if (resizedImage == null) {
                     if (resizedImage == null) {

+ 133 - 128
src/main/java/com/owncloud/android/ui/helpers/FileOperationsHelper.java

@@ -45,8 +45,8 @@ import android.view.View;
 import android.webkit.MimeTypeMap;
 import android.webkit.MimeTypeMap;
 
 
 import com.evernote.android.job.JobRequest;
 import com.evernote.android.job.JobRequest;
-import com.evernote.android.job.util.Device;
 import com.nextcloud.client.account.CurrentAccountProvider;
 import com.nextcloud.client.account.CurrentAccountProvider;
+import com.nextcloud.client.network.ConnectivityService;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.R;
 import com.owncloud.android.R;
 import com.owncloud.android.datamodel.FileDataStorageManager;
 import com.owncloud.android.datamodel.FileDataStorageManager;
@@ -72,7 +72,6 @@ import com.owncloud.android.ui.dialog.SendShareDialog;
 import com.owncloud.android.ui.events.EncryptionEvent;
 import com.owncloud.android.ui.events.EncryptionEvent;
 import com.owncloud.android.ui.events.FavoriteEvent;
 import com.owncloud.android.ui.events.FavoriteEvent;
 import com.owncloud.android.ui.events.SyncEventFinished;
 import com.owncloud.android.ui.events.SyncEventFinished;
-import com.owncloud.android.utils.ConnectivityUtils;
 import com.owncloud.android.utils.DisplayUtils;
 import com.owncloud.android.utils.DisplayUtils;
 import com.owncloud.android.utils.FileStorageUtils;
 import com.owncloud.android.utils.FileStorageUtils;
 import com.owncloud.android.utils.PermissionUtil;
 import com.owncloud.android.utils.PermissionUtil;
@@ -113,15 +112,20 @@ public class FileOperationsHelper {
     private static final String FILE_EXTENSION_URL = "url";
     private static final String FILE_EXTENSION_URL = "url";
     private static final String FILE_EXTENSION_DESKTOP = "desktop";
     private static final String FILE_EXTENSION_DESKTOP = "desktop";
     private static final String FILE_EXTENSION_WEBLOC = "webloc";
     private static final String FILE_EXTENSION_WEBLOC = "webloc";
-    private FileActivity mFileActivity;
+
+    private FileActivity fileActivity;
     private CurrentAccountProvider currentAccount;
     private CurrentAccountProvider currentAccount;
+    private ConnectivityService connectivityService;
+
     /// Identifier of operation in progress which result shouldn't be lost
     /// Identifier of operation in progress which result shouldn't be lost
     private long mWaitingForOpId = Long.MAX_VALUE;
     private long mWaitingForOpId = Long.MAX_VALUE;
 
 
-    public FileOperationsHelper(FileActivity fileActivity, CurrentAccountProvider currentAccount) {
-        mFileActivity = fileActivity;
+    public FileOperationsHelper(FileActivity fileActivity,
+                                CurrentAccountProvider currentAccount,
+                                ConnectivityService connectivityService) {
+        this.fileActivity = fileActivity;
         this.currentAccount = currentAccount;
         this.currentAccount = currentAccount;
-
+        this.connectivityService = connectivityService;
     }
     }
 
 
     @Nullable
     @Nullable
@@ -188,9 +192,9 @@ public class FileOperationsHelper {
 
 
     public void startSyncForFileAndIntent(OCFile file, Intent intent) {
     public void startSyncForFileAndIntent(OCFile file, Intent intent) {
         new Thread(() -> {
         new Thread(() -> {
-            Account account = mFileActivity.getAccount();
-            FileDataStorageManager storageManager = new FileDataStorageManager(mFileActivity.getAccount(),
-                    mFileActivity.getContentResolver());
+            Account account = fileActivity.getAccount();
+            FileDataStorageManager storageManager = new FileDataStorageManager(fileActivity.getAccount(),
+                                                                               fileActivity.getContentResolver());
 
 
             // check if file is in conflict (this is known due to latest folder refresh)
             // check if file is in conflict (this is known due to latest folder refresh)
             if (file.isInConflict()) {
             if (file.isInConflict()) {
@@ -209,9 +213,9 @@ public class FileOperationsHelper {
             }
             }
 
 
             // if offline or walled garden, show old version with warning
             // if offline or walled garden, show old version with warning
-            if (Device.getNetworkType(mFileActivity).equals(JobRequest.NetworkType.ANY) ||
-                    ConnectivityUtils.isInternetWalled(mFileActivity)) {
-                DisplayUtils.showSnackMessage(mFileActivity, R.string.file_not_synced);
+            if (connectivityService.getActiveNetworkType() == JobRequest.NetworkType.ANY ||
+                    connectivityService.isInternetWalled()) {
+                DisplayUtils.showSnackMessage(fileActivity, R.string.file_not_synced);
                 EventBus.getDefault().post(new SyncEventFinished(intent));
                 EventBus.getDefault().post(new SyncEventFinished(intent));
 
 
                 return;
                 return;
@@ -220,7 +224,7 @@ public class FileOperationsHelper {
             // check for changed eTag
             // check for changed eTag
             CheckEtagRemoteOperation checkEtagOperation = new CheckEtagRemoteOperation(file.getRemotePath(),
             CheckEtagRemoteOperation checkEtagOperation = new CheckEtagRemoteOperation(file.getRemotePath(),
                 file.getEtag());
                 file.getEtag());
-            RemoteOperationResult result = checkEtagOperation.execute(account, mFileActivity);
+            RemoteOperationResult result = checkEtagOperation.execute(account, fileActivity);
 
 
             // eTag changed, sync file
             // eTag changed, sync file
             if (result.getCode() == RemoteOperationResult.ResultCode.ETAG_CHANGED) {
             if (result.getCode() == RemoteOperationResult.ResultCode.ETAG_CHANGED) {
@@ -232,25 +236,25 @@ public class FileOperationsHelper {
     }
     }
 
 
     private void syncFile(OCFile file, Account account, FileDataStorageManager storageManager) {
     private void syncFile(OCFile file, Account account, FileDataStorageManager storageManager) {
-        mFileActivity.runOnUiThread(() -> mFileActivity.showLoadingDialog(mFileActivity.getResources()
+        fileActivity.runOnUiThread(() -> fileActivity.showLoadingDialog(fileActivity.getResources()
                 .getString(R.string.sync_in_progress)));
                 .getString(R.string.sync_in_progress)));
 
 
-        SynchronizeFileOperation sfo = new SynchronizeFileOperation(file, null, account, true, mFileActivity);
-        RemoteOperationResult result = sfo.execute(storageManager, mFileActivity);
+        SynchronizeFileOperation sfo = new SynchronizeFileOperation(file, null, account, true, fileActivity);
+        RemoteOperationResult result = sfo.execute(storageManager, fileActivity);
 
 
         if (result.getCode() == RemoteOperationResult.ResultCode.SYNC_CONFLICT) {
         if (result.getCode() == RemoteOperationResult.ResultCode.SYNC_CONFLICT) {
             // ISSUE 5: if the user is not running the app (this is a service!),
             // ISSUE 5: if the user is not running the app (this is a service!),
             // this can be very intrusive; a notification should be preferred
             // this can be very intrusive; a notification should be preferred
-            Intent i = new Intent(mFileActivity, ConflictsResolveActivity.class);
+            Intent i = new Intent(fileActivity, ConflictsResolveActivity.class);
             i.setFlags(i.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK);
             i.setFlags(i.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK);
             i.putExtra(ConflictsResolveActivity.EXTRA_FILE, file);
             i.putExtra(ConflictsResolveActivity.EXTRA_FILE, file);
             i.putExtra(ConflictsResolveActivity.EXTRA_ACCOUNT, account);
             i.putExtra(ConflictsResolveActivity.EXTRA_ACCOUNT, account);
-            mFileActivity.startActivity(i);
+            fileActivity.startActivity(i);
         } else {
         } else {
             if (file.isDown()) {
             if (file.isDown()) {
                 FileStorageUtils.checkIfFileFinishedSaving(file);
                 FileStorageUtils.checkIfFileFinishedSaving(file);
                 if (!result.isSuccess()) {
                 if (!result.isSuccess()) {
-                    DisplayUtils.showSnackMessage(mFileActivity, R.string.file_not_synced);
+                    DisplayUtils.showSnackMessage(fileActivity, R.string.file_not_synced);
                     try {
                     try {
                         Thread.sleep(3000);
                         Thread.sleep(3000);
                     } catch (InterruptedException e) {
                     } catch (InterruptedException e) {
@@ -259,57 +263,57 @@ public class FileOperationsHelper {
                 }
                 }
             }
             }
         }
         }
-        mFileActivity.dismissLoadingDialog();
+        fileActivity.dismissLoadingDialog();
     }
     }
 
 
     public void openFile(OCFile file) {
     public void openFile(OCFile file) {
         if (file != null) {
         if (file != null) {
             final Intent openFileWithIntent = createOpenFileIntent(file);
             final Intent openFileWithIntent = createOpenFileIntent(file);
 
 
-            List<ResolveInfo> launchables = mFileActivity.getPackageManager().
+            List<ResolveInfo> launchables = fileActivity.getPackageManager().
                     queryIntentActivities(openFileWithIntent, PackageManager.GET_RESOLVED_FILTER);
                     queryIntentActivities(openFileWithIntent, PackageManager.GET_RESOLVED_FILTER);
 
 
             if (launchables.isEmpty()) {
             if (launchables.isEmpty()) {
-                Account account = mFileActivity.getAccount();
-                OCCapability capability = mFileActivity.getStorageManager().getCapability(account.name);
+                Account account = fileActivity.getAccount();
+                OCCapability capability = fileActivity.getStorageManager().getCapability(account.name);
                 if (capability.getRichDocumentsMimeTypeList().contains(file.getMimeType()) &&
                 if (capability.getRichDocumentsMimeTypeList().contains(file.getMimeType()) &&
                     android.os.Build.VERSION.SDK_INT >= RichDocumentsWebView.MINIMUM_API &&
                     android.os.Build.VERSION.SDK_INT >= RichDocumentsWebView.MINIMUM_API &&
                     capability.getRichDocumentsDirectEditing().isTrue()) {
                     capability.getRichDocumentsDirectEditing().isTrue()) {
-                    openFileAsRichDocument(file, mFileActivity);
+                    openFileAsRichDocument(file, fileActivity);
                     return;
                     return;
                 } else {
                 } else {
-                    DisplayUtils.showSnackMessage(mFileActivity, R.string.file_list_no_app_for_file_type);
+                    DisplayUtils.showSnackMessage(fileActivity, R.string.file_list_no_app_for_file_type);
                     return;
                     return;
                 }
                 }
             }
             }
 
 
-            mFileActivity.showLoadingDialog(mFileActivity.getResources().getString(R.string.sync_in_progress));
+            fileActivity.showLoadingDialog(fileActivity.getResources().getString(R.string.sync_in_progress));
             new Thread(new Runnable() {
             new Thread(new Runnable() {
                 @Override
                 @Override
                 public void run() {
                 public void run() {
                     Account account = currentAccount.getCurrentAccount();
                     Account account = currentAccount.getCurrentAccount();
                     FileDataStorageManager storageManager =
                     FileDataStorageManager storageManager =
-                            new FileDataStorageManager(account, mFileActivity.getContentResolver());
+                            new FileDataStorageManager(account, fileActivity.getContentResolver());
                     // a fresh object is needed; many things could have occurred to the file
                     // a fresh object is needed; many things could have occurred to the file
                     // since it was registered to observe again, assuming that local files
                     // since it was registered to observe again, assuming that local files
                     // are linked to a remote file AT MOST, SOMETHING TO BE DONE;
                     // are linked to a remote file AT MOST, SOMETHING TO BE DONE;
                     SynchronizeFileOperation sfo =
                     SynchronizeFileOperation sfo =
-                            new SynchronizeFileOperation(file, null, account, true, mFileActivity);
-                    RemoteOperationResult result = sfo.execute(storageManager, mFileActivity);
-                    mFileActivity.dismissLoadingDialog();
+                            new SynchronizeFileOperation(file, null, account, true, fileActivity);
+                    RemoteOperationResult result = sfo.execute(storageManager, fileActivity);
+                    fileActivity.dismissLoadingDialog();
                     if (result.getCode() == RemoteOperationResult.ResultCode.SYNC_CONFLICT) {
                     if (result.getCode() == RemoteOperationResult.ResultCode.SYNC_CONFLICT) {
                         // ISSUE 5: if the user is not running the app (this is a service!),
                         // ISSUE 5: if the user is not running the app (this is a service!),
                         // this can be very intrusive; a notification should be preferred
                         // this can be very intrusive; a notification should be preferred
-                        Intent i = new Intent(mFileActivity, ConflictsResolveActivity.class);
+                        Intent i = new Intent(fileActivity, ConflictsResolveActivity.class);
                         i.setFlags(i.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK);
                         i.setFlags(i.getFlags() | Intent.FLAG_ACTIVITY_NEW_TASK);
                         i.putExtra(ConflictsResolveActivity.EXTRA_FILE, file);
                         i.putExtra(ConflictsResolveActivity.EXTRA_FILE, file);
                         i.putExtra(ConflictsResolveActivity.EXTRA_ACCOUNT, account);
                         i.putExtra(ConflictsResolveActivity.EXTRA_ACCOUNT, account);
-                        mFileActivity.startActivity(i);
+                        fileActivity.startActivity(i);
                     } else {
                     } else {
                         if (!launchables.isEmpty()) {
                         if (!launchables.isEmpty()) {
                             try {
                             try {
                                 if (!result.isSuccess()) {
                                 if (!result.isSuccess()) {
-                                    DisplayUtils.showSnackMessage(mFileActivity, R.string.file_not_synced);
+                                    DisplayUtils.showSnackMessage(fileActivity, R.string.file_not_synced);
                                     try {
                                     try {
                                         Thread.sleep(3000);
                                         Thread.sleep(3000);
                                     } catch (InterruptedException e) {
                                     } catch (InterruptedException e) {
@@ -319,17 +323,17 @@ public class FileOperationsHelper {
 
 
                                 openFileWithIntent.setFlags(openFileWithIntent.getFlags() |
                                 openFileWithIntent.setFlags(openFileWithIntent.getFlags() |
                                         Intent.FLAG_ACTIVITY_NEW_TASK);
                                         Intent.FLAG_ACTIVITY_NEW_TASK);
-                                mFileActivity.startActivity(
+                                fileActivity.startActivity(
                                         Intent.createChooser(
                                         Intent.createChooser(
-                                                openFileWithIntent,
-                                                mFileActivity.getString(R.string.actionbar_open_with)
+                                            openFileWithIntent,
+                                            fileActivity.getString(R.string.actionbar_open_with)
                                         )
                                         )
                                 );
                                 );
                             } catch (ActivityNotFoundException exception) {
                             } catch (ActivityNotFoundException exception) {
-                                DisplayUtils.showSnackMessage(mFileActivity, R.string.file_list_no_app_for_file_type);
+                                DisplayUtils.showSnackMessage(fileActivity, R.string.file_list_no_app_for_file_type);
                             }
                             }
                         } else {
                         } else {
-                            DisplayUtils.showSnackMessage(mFileActivity, R.string.file_list_no_app_for_file_type);
+                            DisplayUtils.showSnackMessage(fileActivity, R.string.file_list_no_app_for_file_type);
                         }
                         }
                     }
                     }
 
 
@@ -392,21 +396,21 @@ public class FileOperationsHelper {
                 !file.getStoragePath().startsWith(MainApp.getAppContext().getFilesDir().getAbsolutePath())) {
                 !file.getStoragePath().startsWith(MainApp.getAppContext().getFilesDir().getAbsolutePath())) {
             return file.getLegacyExposedFileUri();
             return file.getLegacyExposedFileUri();
         } else {
         } else {
-            return file.getExposedFileUri(mFileActivity);
+            return file.getExposedFileUri(fileActivity);
         }
         }
     }
     }
 
 
     public void streamMediaFile(OCFile file) {
     public void streamMediaFile(OCFile file) {
-        mFileActivity.showLoadingDialog(mFileActivity.getString(R.string.wait_a_moment));
+        fileActivity.showLoadingDialog(fileActivity.getString(R.string.wait_a_moment));
         final Account account = currentAccount.getCurrentAccount();
         final Account account = currentAccount.getCurrentAccount();
         new Thread(() -> {
         new Thread(() -> {
             StreamMediaFileOperation sfo = new StreamMediaFileOperation(file.getLocalId());
             StreamMediaFileOperation sfo = new StreamMediaFileOperation(file.getLocalId());
-            RemoteOperationResult result = sfo.execute(account, mFileActivity);
+            RemoteOperationResult result = sfo.execute(account, fileActivity);
 
 
-            mFileActivity.dismissLoadingDialog();
+            fileActivity.dismissLoadingDialog();
 
 
             if (!result.isSuccess()) {
             if (!result.isSuccess()) {
-                DisplayUtils.showSnackMessage(mFileActivity, R.string.stream_not_possible_headline);
+                DisplayUtils.showSnackMessage(fileActivity, R.string.stream_not_possible_headline);
                 return;
                 return;
             }
             }
 
 
@@ -415,8 +419,8 @@ public class FileOperationsHelper {
 
 
             openFileWithIntent.setDataAndType(uri, file.getMimeType());
             openFileWithIntent.setDataAndType(uri, file.getMimeType());
 
 
-            mFileActivity.startActivity(Intent.createChooser(openFileWithIntent,
-                    mFileActivity.getString(R.string.stream)));
+            fileActivity.startActivity(Intent.createChooser(openFileWithIntent,
+                                                            fileActivity.getString(R.string.stream)));
         }).start();
         }).start();
     }
     }
 
 
@@ -428,15 +432,15 @@ public class FileOperationsHelper {
      */
      */
     public void shareFileViaLink(OCFile file, String password) {
     public void shareFileViaLink(OCFile file, String password) {
         if (file != null) {
         if (file != null) {
-            mFileActivity.showLoadingDialog(mFileActivity.getString(R.string.wait_a_moment));
-            Intent service = new Intent(mFileActivity, OperationsService.class);
+            fileActivity.showLoadingDialog(fileActivity.getString(R.string.wait_a_moment));
+            Intent service = new Intent(fileActivity, OperationsService.class);
             service.setAction(OperationsService.ACTION_CREATE_SHARE_VIA_LINK);
             service.setAction(OperationsService.ACTION_CREATE_SHARE_VIA_LINK);
-            service.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+            service.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
             if (!TextUtils.isEmpty(password)) {
             if (!TextUtils.isEmpty(password)) {
                 service.putExtra(OperationsService.EXTRA_SHARE_PASSWORD, password);
                 service.putExtra(OperationsService.EXTRA_SHARE_PASSWORD, password);
             }
             }
             service.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
             service.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
-            mWaitingForOpId = mFileActivity.getOperationsServiceBinder().queueNewOperation(service);
+            mWaitingForOpId = fileActivity.getOperationsServiceBinder().queueNewOperation(service);
 
 
         } else {
         } else {
             Log_OC.e(TAG, "Trying to share a NULL OCFile");
             Log_OC.e(TAG, "Trying to share a NULL OCFile");
@@ -446,14 +450,14 @@ public class FileOperationsHelper {
 
 
     public void getFileWithLink(OCFile file) {
     public void getFileWithLink(OCFile file) {
         if (file != null) {
         if (file != null) {
-            mFileActivity.showLoadingDialog(mFileActivity.getApplicationContext().
+            fileActivity.showLoadingDialog(fileActivity.getApplicationContext().
                     getString(R.string.wait_a_moment));
                     getString(R.string.wait_a_moment));
 
 
-            Intent service = new Intent(mFileActivity, OperationsService.class);
+            Intent service = new Intent(fileActivity, OperationsService.class);
             service.setAction(OperationsService.ACTION_CREATE_SHARE_VIA_LINK);
             service.setAction(OperationsService.ACTION_CREATE_SHARE_VIA_LINK);
-            service.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+            service.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
             service.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
             service.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
-            mWaitingForOpId = mFileActivity.getOperationsServiceBinder().queueNewOperation(service);
+            mWaitingForOpId = fileActivity.getOperationsServiceBinder().queueNewOperation(service);
 
 
         } else {
         } else {
             Log_OC.e(TAG, "Trying to share a NULL OCFile");
             Log_OC.e(TAG, "Trying to share a NULL OCFile");
@@ -471,17 +475,17 @@ public class FileOperationsHelper {
     public void shareFileWithSharee(OCFile file, String shareeName, ShareType shareType, int permissions) {
     public void shareFileWithSharee(OCFile file, String shareeName, ShareType shareType, int permissions) {
         if (file != null) {
         if (file != null) {
             // TODO check capability?
             // TODO check capability?
-            mFileActivity.showLoadingDialog(mFileActivity.getApplicationContext().
+            fileActivity.showLoadingDialog(fileActivity.getApplicationContext().
                     getString(R.string.wait_a_moment));
                     getString(R.string.wait_a_moment));
 
 
-            Intent service = new Intent(mFileActivity, OperationsService.class);
+            Intent service = new Intent(fileActivity, OperationsService.class);
             service.setAction(OperationsService.ACTION_CREATE_SHARE_WITH_SHAREE);
             service.setAction(OperationsService.ACTION_CREATE_SHARE_WITH_SHAREE);
-            service.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+            service.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
             service.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
             service.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
             service.putExtra(OperationsService.EXTRA_SHARE_WITH, shareeName);
             service.putExtra(OperationsService.EXTRA_SHARE_WITH, shareeName);
             service.putExtra(OperationsService.EXTRA_SHARE_TYPE, shareType);
             service.putExtra(OperationsService.EXTRA_SHARE_TYPE, shareType);
             service.putExtra(OperationsService.EXTRA_SHARE_PERMISSIONS, permissions);
             service.putExtra(OperationsService.EXTRA_SHARE_PERMISSIONS, permissions);
-            mWaitingForOpId = mFileActivity.getOperationsServiceBinder().queueNewOperation(service);
+            mWaitingForOpId = fileActivity.getOperationsServiceBinder().queueNewOperation(service);
 
 
         } else {
         } else {
             Log_OC.e(TAG, "Trying to share a NULL OCFile");
             Log_OC.e(TAG, "Trying to share a NULL OCFile");
@@ -495,14 +499,14 @@ public class FileOperationsHelper {
      */
      */
     public void restoreFileVersion(FileVersion fileVersion) {
     public void restoreFileVersion(FileVersion fileVersion) {
         if (fileVersion != null) {
         if (fileVersion != null) {
-            mFileActivity.showLoadingDialog(mFileActivity.getApplicationContext().
+            fileActivity.showLoadingDialog(fileActivity.getApplicationContext().
                     getString(R.string.wait_a_moment));
                     getString(R.string.wait_a_moment));
 
 
-            Intent service = new Intent(mFileActivity, OperationsService.class);
+            Intent service = new Intent(fileActivity, OperationsService.class);
             service.setAction(OperationsService.ACTION_RESTORE_VERSION);
             service.setAction(OperationsService.ACTION_RESTORE_VERSION);
-            service.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+            service.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
             service.putExtra(OperationsService.EXTRA_FILE_VERSION, fileVersion);
             service.putExtra(OperationsService.EXTRA_FILE_VERSION, fileVersion);
-            mWaitingForOpId = mFileActivity.getOperationsServiceBinder().queueNewOperation(service);
+            mWaitingForOpId = fileActivity.getOperationsServiceBinder().queueNewOperation(service);
         } else {
         } else {
             Log_OC.e(TAG, "Trying to restore a NULL FileVersion");
             Log_OC.e(TAG, "Trying to restore a NULL FileVersion");
         }
         }
@@ -517,9 +521,9 @@ public class FileOperationsHelper {
     public void unshareFileViaLink(OCFile file) {
     public void unshareFileViaLink(OCFile file) {
 
 
         // Unshare the file: Create the intent
         // Unshare the file: Create the intent
-        Intent unshareService = new Intent(mFileActivity, OperationsService.class);
+        Intent unshareService = new Intent(fileActivity, OperationsService.class);
         unshareService.setAction(OperationsService.ACTION_UNSHARE);
         unshareService.setAction(OperationsService.ACTION_UNSHARE);
-        unshareService.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+        unshareService.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
         unshareService.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
         unshareService.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
         unshareService.putExtra(OperationsService.EXTRA_SHARE_TYPE, ShareType.PUBLIC_LINK);
         unshareService.putExtra(OperationsService.EXTRA_SHARE_TYPE, ShareType.PUBLIC_LINK);
         unshareService.putExtra(OperationsService.EXTRA_SHARE_WITH, "");
         unshareService.putExtra(OperationsService.EXTRA_SHARE_WITH, "");
@@ -530,9 +534,9 @@ public class FileOperationsHelper {
     public void unshareFileWithUserOrGroup(OCFile file, ShareType shareType, String userOrGroup) {
     public void unshareFileWithUserOrGroup(OCFile file, ShareType shareType, String userOrGroup) {
 
 
         // Unshare the file: Create the intent
         // Unshare the file: Create the intent
-        Intent unshareService = new Intent(mFileActivity, OperationsService.class);
+        Intent unshareService = new Intent(fileActivity, OperationsService.class);
         unshareService.setAction(OperationsService.ACTION_UNSHARE);
         unshareService.setAction(OperationsService.ACTION_UNSHARE);
-        unshareService.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+        unshareService.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
         unshareService.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
         unshareService.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
         unshareService.putExtra(OperationsService.EXTRA_SHARE_TYPE, shareType);
         unshareService.putExtra(OperationsService.EXTRA_SHARE_TYPE, shareType);
         unshareService.putExtra(OperationsService.EXTRA_SHARE_WITH, userOrGroup);
         unshareService.putExtra(OperationsService.EXTRA_SHARE_WITH, userOrGroup);
@@ -542,9 +546,9 @@ public class FileOperationsHelper {
 
 
     private void queueShareIntent(Intent shareIntent) {
     private void queueShareIntent(Intent shareIntent) {
         // Unshare the file
         // Unshare the file
-        mWaitingForOpId = mFileActivity.getOperationsServiceBinder().queueNewOperation(shareIntent);
+        mWaitingForOpId = fileActivity.getOperationsServiceBinder().queueNewOperation(shareIntent);
 
 
-        mFileActivity.showLoadingDialog(mFileActivity.getApplicationContext().getString(R.string.wait_a_moment));
+        fileActivity.showLoadingDialog(fileActivity.getApplicationContext().getString(R.string.wait_a_moment));
     }
     }
 
 
     /**
     /**
@@ -553,10 +557,10 @@ public class FileOperationsHelper {
      * @param file File to share or unshare.
      * @param file File to share or unshare.
      */
      */
     public void showShareFile(OCFile file) {
     public void showShareFile(OCFile file) {
-        Intent intent = new Intent(mFileActivity, ShareActivity.class);
+        Intent intent = new Intent(fileActivity, ShareActivity.class);
         intent.putExtra(FileActivity.EXTRA_FILE, file);
         intent.putExtra(FileActivity.EXTRA_FILE, file);
-        intent.putExtra(FileActivity.EXTRA_ACCOUNT, mFileActivity.getAccount());
-        mFileActivity.startActivity(intent);
+        intent.putExtra(FileActivity.EXTRA_ACCOUNT, fileActivity.getAccount());
+        fileActivity.startActivity(intent);
     }
     }
 
 
 
 
@@ -570,9 +574,9 @@ public class FileOperationsHelper {
      */
      */
     public void setPasswordToShareViaLink(OCFile file, String password) {
     public void setPasswordToShareViaLink(OCFile file, String password) {
         // Set password updating share
         // Set password updating share
-        Intent updateShareIntent = new Intent(mFileActivity, OperationsService.class);
+        Intent updateShareIntent = new Intent(fileActivity, OperationsService.class);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE);
-        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
         updateShareIntent.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
         updateShareIntent.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_PASSWORD, (password == null) ? "" : password);
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_PASSWORD, (password == null) ? "" : password);
 
 
@@ -588,9 +592,9 @@ public class FileOperationsHelper {
      *                 the current password
      *                 the current password
      */
      */
     public void setPasswordToShare(OCShare share, String password) {
     public void setPasswordToShare(OCShare share, String password) {
-        Intent updateShareIntent = new Intent(mFileActivity, OperationsService.class);
+        Intent updateShareIntent = new Intent(fileActivity, OperationsService.class);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE);
-        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_ID, share.getId());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_ID, share.getId());
         updateShareIntent.putExtra(
         updateShareIntent.putExtra(
                 OperationsService.EXTRA_SHARE_PASSWORD,
                 OperationsService.EXTRA_SHARE_PASSWORD,
@@ -609,9 +613,9 @@ public class FileOperationsHelper {
      *                               date, leaving the link unrestricted. Zero makes no change.
      *                               date, leaving the link unrestricted. Zero makes no change.
      */
      */
     public void setExpirationDateToShareViaLink(OCFile file, long expirationTimeInMillis) {
     public void setExpirationDateToShareViaLink(OCFile file, long expirationTimeInMillis) {
-        Intent updateShareIntent = new Intent(mFileActivity, OperationsService.class);
+        Intent updateShareIntent = new Intent(fileActivity, OperationsService.class);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE);
-        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
         updateShareIntent.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
         updateShareIntent.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_EXPIRATION_DATE_IN_MILLIS, expirationTimeInMillis);
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_EXPIRATION_DATE_IN_MILLIS, expirationTimeInMillis);
         queueShareIntent(updateShareIntent);
         queueShareIntent(updateShareIntent);
@@ -626,9 +630,9 @@ public class FileOperationsHelper {
      *                               date, leaving the link unrestricted. Zero makes no change.
      *                               date, leaving the link unrestricted. Zero makes no change.
      */
      */
     public void setExpirationDateToShare(OCShare share, long expirationTimeInMillis) {
     public void setExpirationDateToShare(OCShare share, long expirationTimeInMillis) {
-        Intent updateShareIntent = new Intent(mFileActivity, OperationsService.class);
+        Intent updateShareIntent = new Intent(fileActivity, OperationsService.class);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE);
-        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_ID, share.getId());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_ID, share.getId());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_EXPIRATION_DATE_IN_MILLIS, expirationTimeInMillis);
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_EXPIRATION_DATE_IN_MILLIS, expirationTimeInMillis);
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_PERMISSIONS, 0);
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_PERMISSIONS, 0);
@@ -643,9 +647,9 @@ public class FileOperationsHelper {
      * @param permissions New permissions to set. A value <= 0 makes no update.
      * @param permissions New permissions to set. A value <= 0 makes no update.
      */
      */
     public void setPermissionsToShare(OCShare share, int permissions) {
     public void setPermissionsToShare(OCShare share, int permissions) {
-        Intent updateShareIntent = new Intent(mFileActivity, OperationsService.class);
+        Intent updateShareIntent = new Intent(fileActivity, OperationsService.class);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE);
-        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_ID, share.getId());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_ID, share.getId());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_PERMISSIONS, permissions);
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_PERMISSIONS, permissions);
         queueShareIntent(updateShareIntent);
         queueShareIntent(updateShareIntent);
@@ -659,9 +663,9 @@ public class FileOperationsHelper {
      * @param uploadPermission New state of the permission for editing the folder shared via link.
      * @param uploadPermission New state of the permission for editing the folder shared via link.
      */
      */
     public void setUploadPermissionsToShare(OCFile folder, boolean uploadPermission) {
     public void setUploadPermissionsToShare(OCFile folder, boolean uploadPermission) {
-        Intent updateShareIntent = new Intent(mFileActivity, OperationsService.class);
+        Intent updateShareIntent = new Intent(fileActivity, OperationsService.class);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE);
-        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
         updateShareIntent.putExtra(OperationsService.EXTRA_REMOTE_PATH, folder.getRemotePath());
         updateShareIntent.putExtra(OperationsService.EXTRA_REMOTE_PATH, folder.getRemotePath());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_PUBLIC_UPLOAD, uploadPermission);
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_PUBLIC_UPLOAD, uploadPermission);
         queueShareIntent(updateShareIntent);
         queueShareIntent(updateShareIntent);
@@ -675,9 +679,9 @@ public class FileOperationsHelper {
      * @param hideFileListing New state of the permission for editing the folder shared via link.
      * @param hideFileListing New state of the permission for editing the folder shared via link.
      */
      */
     public void setHideFileListingPermissionsToShare(OCShare share, boolean hideFileListing) {
     public void setHideFileListingPermissionsToShare(OCShare share, boolean hideFileListing) {
-        Intent updateShareIntent = new Intent(mFileActivity, OperationsService.class);
+        Intent updateShareIntent = new Intent(fileActivity, OperationsService.class);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE);
-        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_ID, share.getId());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_ID, share.getId());
 
 
         if (hideFileListing) {
         if (hideFileListing) {
@@ -691,9 +695,9 @@ public class FileOperationsHelper {
     }
     }
 
 
     public void setHideFileDownloadPermissionsToShare(OCFile file, boolean hideFileDownload) {
     public void setHideFileDownloadPermissionsToShare(OCFile file, boolean hideFileDownload) {
-        Intent updateShareIntent = new Intent(mFileActivity, OperationsService.class);
+        Intent updateShareIntent = new Intent(fileActivity, OperationsService.class);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE);
-        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
         updateShareIntent.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
         updateShareIntent.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_HIDE_FILE_DOWNLOAD, hideFileDownload);
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_HIDE_FILE_DOWNLOAD, hideFileDownload);
 
 
@@ -701,9 +705,9 @@ public class FileOperationsHelper {
     }
     }
 
 
     public void updateNoteToShare(OCShare share, String note) {
     public void updateNoteToShare(OCShare share, String note) {
-        Intent updateShareIntent = new Intent(mFileActivity, OperationsService.class);
+        Intent updateShareIntent = new Intent(fileActivity, OperationsService.class);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE_NOTE);
         updateShareIntent.setAction(OperationsService.ACTION_UPDATE_SHARE_NOTE);
-        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+        updateShareIntent.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_ID, share.getId());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_ID, share.getId());
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_NOTE, note);
         updateShareIntent.putExtra(OperationsService.EXTRA_SHARE_NOTE, note);
 
 
@@ -712,11 +716,11 @@ public class FileOperationsHelper {
 
 
     public void sendShareFile(OCFile file, boolean hideNcSharingOptions) {
     public void sendShareFile(OCFile file, boolean hideNcSharingOptions) {
         // Show dialog
         // Show dialog
-        FragmentManager fm = mFileActivity.getSupportFragmentManager();
+        FragmentManager fm = fileActivity.getSupportFragmentManager();
         FragmentTransaction ft = fm.beginTransaction();
         FragmentTransaction ft = fm.beginTransaction();
         ft.addToBackStack(null);
         ft.addToBackStack(null);
 
 
-        OCCapability capability = mFileActivity.getStorageManager().getCapability(mFileActivity.getAccount().name);
+        OCCapability capability = fileActivity.getStorageManager().getCapability(fileActivity.getAccount().name);
         SendShareDialog mSendShareDialog = SendShareDialog.newInstance(file, hideNcSharingOptions, capability);
         SendShareDialog mSendShareDialog = SendShareDialog.newInstance(file, hideNcSharingOptions, capability);
         mSendShareDialog.setFileOperationsHelper(this);
         mSendShareDialog.setFileOperationsHelper(this);
         mSendShareDialog.show(ft, "TAG_SEND_SHARE_DIALOG");
         mSendShareDialog.show(ft, "TAG_SEND_SHARE_DIALOG");
@@ -745,8 +749,8 @@ public class FileOperationsHelper {
             sendIntent.putExtra(Intent.ACTION_SEND, true);      // Send Action
             sendIntent.putExtra(Intent.ACTION_SEND, true);      // Send Action
             sendIntent.setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
             sendIntent.setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
 
 
-            mFileActivity.startActivity(Intent.createChooser(sendIntent,
-                    context.getString(R.string.actionbar_send_file)));
+            fileActivity.startActivity(Intent.createChooser(sendIntent,
+                                                            context.getString(R.string.actionbar_send_file)));
         } else {
         } else {
             Log_OC.wtf(TAG, "Trying to send a NULL OCFile");
             Log_OC.wtf(TAG, "Trying to send a NULL OCFile");
         }
         }
@@ -776,8 +780,9 @@ public class FileOperationsHelper {
                 }
                 }
 
 
                 intent.setDataAndType(uri, file.getMimeType());
                 intent.setDataAndType(uri, file.getMimeType());
-                mFileActivity.startActivityForResult(Intent.createChooser(intent,
-                        mFileActivity.getString(R.string.set_as)), 200);
+                fileActivity.startActivityForResult(Intent.createChooser(intent,
+                                                                         fileActivity.getString(R.string.set_as)),
+                                                    200);
 
 
                 intent.setDataAndType(uri, file.getMimeType());
                 intent.setDataAndType(uri, file.getMimeType());
             } catch (ActivityNotFoundException exception) {
             } catch (ActivityNotFoundException exception) {
@@ -795,21 +800,21 @@ public class FileOperationsHelper {
      */
      */
     public void syncFile(OCFile file) {
     public void syncFile(OCFile file) {
         if (!file.isFolder()) {
         if (!file.isFolder()) {
-            Intent intent = new Intent(mFileActivity, OperationsService.class);
+            Intent intent = new Intent(fileActivity, OperationsService.class);
             intent.setAction(OperationsService.ACTION_SYNC_FILE);
             intent.setAction(OperationsService.ACTION_SYNC_FILE);
-            intent.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+            intent.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
             intent.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
             intent.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
             intent.putExtra(OperationsService.EXTRA_SYNC_FILE_CONTENTS, true);
             intent.putExtra(OperationsService.EXTRA_SYNC_FILE_CONTENTS, true);
-            mWaitingForOpId = mFileActivity.getOperationsServiceBinder().queueNewOperation(intent);
-            mFileActivity.showLoadingDialog(mFileActivity.getApplicationContext().
+            mWaitingForOpId = fileActivity.getOperationsServiceBinder().queueNewOperation(intent);
+            fileActivity.showLoadingDialog(fileActivity.getApplicationContext().
                     getString(R.string.wait_a_moment));
                     getString(R.string.wait_a_moment));
 
 
         } else {
         } else {
-            Intent intent = new Intent(mFileActivity, OperationsService.class);
+            Intent intent = new Intent(fileActivity, OperationsService.class);
             intent.setAction(OperationsService.ACTION_SYNC_FOLDER);
             intent.setAction(OperationsService.ACTION_SYNC_FOLDER);
-            intent.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+            intent.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
             intent.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
             intent.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
-            mFileActivity.startService(intent);
+            fileActivity.startService(intent);
         }
         }
     }
     }
 
 
@@ -843,14 +848,14 @@ public class FileOperationsHelper {
 
 
     public void renameFile(OCFile file, String newFilename) {
     public void renameFile(OCFile file, String newFilename) {
         // RenameFile
         // RenameFile
-        Intent service = new Intent(mFileActivity, OperationsService.class);
+        Intent service = new Intent(fileActivity, OperationsService.class);
         service.setAction(OperationsService.ACTION_RENAME);
         service.setAction(OperationsService.ACTION_RENAME);
-        service.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+        service.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
         service.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
         service.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
         service.putExtra(OperationsService.EXTRA_NEWNAME, newFilename);
         service.putExtra(OperationsService.EXTRA_NEWNAME, newFilename);
-        mWaitingForOpId = mFileActivity.getOperationsServiceBinder().queueNewOperation(service);
+        mWaitingForOpId = fileActivity.getOperationsServiceBinder().queueNewOperation(service);
 
 
-        mFileActivity.showLoadingDialog(mFileActivity.getString(R.string.wait_a_moment));
+        fileActivity.showLoadingDialog(fileActivity.getString(R.string.wait_a_moment));
     }
     }
 
 
 
 
@@ -865,31 +870,31 @@ public class FileOperationsHelper {
     public void removeFiles(Collection<OCFile> files, boolean onlyLocalCopy, boolean inBackground) {
     public void removeFiles(Collection<OCFile> files, boolean onlyLocalCopy, boolean inBackground) {
         for (OCFile file : files) {
         for (OCFile file : files) {
             // RemoveFile
             // RemoveFile
-            Intent service = new Intent(mFileActivity, OperationsService.class);
+            Intent service = new Intent(fileActivity, OperationsService.class);
             service.setAction(OperationsService.ACTION_REMOVE);
             service.setAction(OperationsService.ACTION_REMOVE);
-            service.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+            service.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
             service.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
             service.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
             service.putExtra(OperationsService.EXTRA_REMOVE_ONLY_LOCAL, onlyLocalCopy);
             service.putExtra(OperationsService.EXTRA_REMOVE_ONLY_LOCAL, onlyLocalCopy);
             service.putExtra(OperationsService.EXTRA_IN_BACKGROUND, inBackground);
             service.putExtra(OperationsService.EXTRA_IN_BACKGROUND, inBackground);
-            mWaitingForOpId = mFileActivity.getOperationsServiceBinder().queueNewOperation(service);
+            mWaitingForOpId = fileActivity.getOperationsServiceBinder().queueNewOperation(service);
         }
         }
 
 
         if (!inBackground) {
         if (!inBackground) {
-            mFileActivity.showLoadingDialog(mFileActivity.getString(R.string.wait_a_moment));
+            fileActivity.showLoadingDialog(fileActivity.getString(R.string.wait_a_moment));
         }
         }
     }
     }
 
 
 
 
     public void createFolder(String remotePath, boolean createFullPath) {
     public void createFolder(String remotePath, boolean createFullPath) {
         // Create Folder
         // Create Folder
-        Intent service = new Intent(mFileActivity, OperationsService.class);
+        Intent service = new Intent(fileActivity, OperationsService.class);
         service.setAction(OperationsService.ACTION_CREATE_FOLDER);
         service.setAction(OperationsService.ACTION_CREATE_FOLDER);
-        service.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
+        service.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
         service.putExtra(OperationsService.EXTRA_REMOTE_PATH, remotePath);
         service.putExtra(OperationsService.EXTRA_REMOTE_PATH, remotePath);
         service.putExtra(OperationsService.EXTRA_CREATE_FULL_PATH, createFullPath);
         service.putExtra(OperationsService.EXTRA_CREATE_FULL_PATH, createFullPath);
-        mWaitingForOpId = mFileActivity.getOperationsServiceBinder().queueNewOperation(service);
+        mWaitingForOpId = fileActivity.getOperationsServiceBinder().queueNewOperation(service);
 
 
-        mFileActivity.showLoadingDialog(mFileActivity.getString(R.string.wait_a_moment));
+        fileActivity.showLoadingDialog(fileActivity.getString(R.string.wait_a_moment));
     }
     }
 
 
     /**
     /**
@@ -898,21 +903,21 @@ public class FileOperationsHelper {
      * @param file OCFile
      * @param file OCFile
      */
      */
     public void cancelTransference(OCFile file) {
     public void cancelTransference(OCFile file) {
-        Account account = mFileActivity.getAccount();
+        Account account = fileActivity.getAccount();
         if (file.isFolder()) {
         if (file.isFolder()) {
             OperationsService.OperationsServiceBinder opsBinder =
             OperationsService.OperationsServiceBinder opsBinder =
-                    mFileActivity.getOperationsServiceBinder();
+                    fileActivity.getOperationsServiceBinder();
             if (opsBinder != null) {
             if (opsBinder != null) {
                 opsBinder.cancel(account, file);
                 opsBinder.cancel(account, file);
             }
             }
         }
         }
 
 
         // for both files and folders
         // for both files and folders
-        FileDownloaderBinder downloaderBinder = mFileActivity.getFileDownloaderBinder();
+        FileDownloaderBinder downloaderBinder = fileActivity.getFileDownloaderBinder();
         if (downloaderBinder != null && downloaderBinder.isDownloading(account, file)) {
         if (downloaderBinder != null && downloaderBinder.isDownloading(account, file)) {
             downloaderBinder.cancel(account, file);
             downloaderBinder.cancel(account, file);
         }
         }
-        FileUploaderBinder uploaderBinder = mFileActivity.getFileUploaderBinder();
+        FileUploaderBinder uploaderBinder = fileActivity.getFileUploaderBinder();
         if (uploaderBinder != null && uploaderBinder.isUploading(account, file)) {
         if (uploaderBinder != null && uploaderBinder.isUploading(account, file)) {
             uploaderBinder.cancel(account, file);
             uploaderBinder.cancel(account, file);
         }
         }
@@ -926,14 +931,14 @@ public class FileOperationsHelper {
      */
      */
     public void moveFiles(Collection<OCFile> files, OCFile targetFolder) {
     public void moveFiles(Collection<OCFile> files, OCFile targetFolder) {
         for (OCFile file : files) {
         for (OCFile file : files) {
-            Intent service = new Intent(mFileActivity, OperationsService.class);
+            Intent service = new Intent(fileActivity, OperationsService.class);
             service.setAction(OperationsService.ACTION_MOVE_FILE);
             service.setAction(OperationsService.ACTION_MOVE_FILE);
             service.putExtra(OperationsService.EXTRA_NEW_PARENT_PATH, targetFolder.getRemotePath());
             service.putExtra(OperationsService.EXTRA_NEW_PARENT_PATH, targetFolder.getRemotePath());
             service.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
             service.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
-            service.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
-            mWaitingForOpId = mFileActivity.getOperationsServiceBinder().queueNewOperation(service);
+            service.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
+            mWaitingForOpId = fileActivity.getOperationsServiceBinder().queueNewOperation(service);
         }
         }
-        mFileActivity.showLoadingDialog(mFileActivity.getString(R.string.wait_a_moment));
+        fileActivity.showLoadingDialog(fileActivity.getString(R.string.wait_a_moment));
     }
     }
 
 
     /**
     /**
@@ -944,14 +949,14 @@ public class FileOperationsHelper {
      */
      */
     public void copyFiles(Collection<OCFile> files, OCFile targetFolder) {
     public void copyFiles(Collection<OCFile> files, OCFile targetFolder) {
         for (OCFile file : files) {
         for (OCFile file : files) {
-            Intent service = new Intent(mFileActivity, OperationsService.class);
+            Intent service = new Intent(fileActivity, OperationsService.class);
             service.setAction(OperationsService.ACTION_COPY_FILE);
             service.setAction(OperationsService.ACTION_COPY_FILE);
             service.putExtra(OperationsService.EXTRA_NEW_PARENT_PATH, targetFolder.getRemotePath());
             service.putExtra(OperationsService.EXTRA_NEW_PARENT_PATH, targetFolder.getRemotePath());
             service.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
             service.putExtra(OperationsService.EXTRA_REMOTE_PATH, file.getRemotePath());
-            service.putExtra(OperationsService.EXTRA_ACCOUNT, mFileActivity.getAccount());
-            mWaitingForOpId = mFileActivity.getOperationsServiceBinder().queueNewOperation(service);
+            service.putExtra(OperationsService.EXTRA_ACCOUNT, fileActivity.getAccount());
+            mWaitingForOpId = fileActivity.getOperationsServiceBinder().queueNewOperation(service);
         }
         }
-        mFileActivity.showLoadingDialog(mFileActivity.getString(R.string.wait_a_moment));
+        fileActivity.showLoadingDialog(fileActivity.getString(R.string.wait_a_moment));
     }
     }
 
 
     public long getOpIdWaitingFor() {
     public long getOpIdWaitingFor() {
@@ -969,12 +974,12 @@ public class FileOperationsHelper {
      * @param account OC account which credentials will be checked.
      * @param account OC account which credentials will be checked.
      */
      */
     public void checkCurrentCredentials(Account account) {
     public void checkCurrentCredentials(Account account) {
-        Intent service = new Intent(mFileActivity, OperationsService.class);
+        Intent service = new Intent(fileActivity, OperationsService.class);
         service.setAction(OperationsService.ACTION_CHECK_CURRENT_CREDENTIALS);
         service.setAction(OperationsService.ACTION_CHECK_CURRENT_CREDENTIALS);
         service.putExtra(OperationsService.EXTRA_ACCOUNT, account);
         service.putExtra(OperationsService.EXTRA_ACCOUNT, account);
-        mWaitingForOpId = mFileActivity.getOperationsServiceBinder().queueNewOperation(service);
+        mWaitingForOpId = fileActivity.getOperationsServiceBinder().queueNewOperation(service);
 
 
-        mFileActivity.showLoadingDialog(mFileActivity.getString(R.string.wait_checking_credentials));
+        fileActivity.showLoadingDialog(fileActivity.getString(R.string.wait_checking_credentials));
     }
     }
 
 
     public void uploadFromCamera(Activity activity, int requestCode) {
     public void uploadFromCamera(Activity activity, int requestCode) {

+ 11 - 1
src/main/java/com/owncloud/android/ui/preview/PreviewImageFragment.java

@@ -2,7 +2,10 @@
  * ownCloud Android client application
  * ownCloud Android client application
  *
  *
  * @author David A. Velasco
  * @author David A. Velasco
+ * @author Chris Narkiewicz
+ *
  * Copyright (C) 2015 ownCloud Inc.
  * Copyright (C) 2015 ownCloud Inc.
+ * Copyright (C) 2019 Chris Narkiewicz <hello@ezaquarii.com>
  *
  *
  * This program is free software: you can redistribute it and/or modify
  * This program is free software: you can redistribute it and/or modify
  * it under the terms of the GNU General Public License version 2,
  * it under the terms of the GNU General Public License version 2,
@@ -50,6 +53,8 @@ import com.caverock.androidsvg.SVG;
 import com.caverock.androidsvg.SVGParseException;
 import com.caverock.androidsvg.SVGParseException;
 import com.github.chrisbanes.photoview.PhotoView;
 import com.github.chrisbanes.photoview.PhotoView;
 import com.google.android.material.snackbar.Snackbar;
 import com.google.android.material.snackbar.Snackbar;
+import com.nextcloud.client.di.Injectable;
+import com.nextcloud.client.network.ConnectivityService;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.R;
 import com.owncloud.android.R;
 import com.owncloud.android.datamodel.OCFile;
 import com.owncloud.android.datamodel.OCFile;
@@ -69,6 +74,8 @@ import java.io.FileNotFoundException;
 import java.io.IOException;
 import java.io.IOException;
 import java.lang.ref.WeakReference;
 import java.lang.ref.WeakReference;
 
 
+import javax.inject.Inject;
+
 import androidx.annotation.DrawableRes;
 import androidx.annotation.DrawableRes;
 import androidx.annotation.NonNull;
 import androidx.annotation.NonNull;
 import androidx.annotation.StringRes;
 import androidx.annotation.StringRes;
@@ -86,7 +93,7 @@ import pl.droidsonroids.gif.GifDrawable;
  * If the {@link OCFile} passed is not downloaded, an {@link IllegalStateException} is generated on
  * If the {@link OCFile} passed is not downloaded, an {@link IllegalStateException} is generated on
  * instantiation too.
  * instantiation too.
  */
  */
-public class PreviewImageFragment extends FileFragment {
+public class PreviewImageFragment extends FileFragment implements Injectable {
 
 
     private static final String EXTRA_FILE = "FILE";
     private static final String EXTRA_FILE = "FILE";
 
 
@@ -116,6 +123,8 @@ public class PreviewImageFragment extends FileFragment {
 
 
     private LoadBitmapTask mLoadBitmapTask;
     private LoadBitmapTask mLoadBitmapTask;
 
 
+    @Inject ConnectivityService connectivityService;
+
     /**
     /**
      * Public factory method to create a new fragment that previews an image.
      * Public factory method to create a new fragment that previews an image.
      *
      *
@@ -256,6 +265,7 @@ public class PreviewImageFragment extends FileFragment {
                                 new ThumbnailsCacheManager.ResizedImageGenerationTask(this,
                                 new ThumbnailsCacheManager.ResizedImageGenerationTask(this,
                                         mImageView,
                                         mImageView,
                                         containerActivity.getStorageManager(),
                                         containerActivity.getStorageManager(),
+                                        connectivityService,
                                         containerActivity.getStorageManager().getAccount());
                                         containerActivity.getStorageManager().getAccount());
                         if (resizedImage == null) {
                         if (resizedImage == null) {
                             resizedImage = thumbnail;
                             resizedImage = thumbnail;

+ 11 - 4
src/main/java/com/owncloud/android/utils/FilesSyncHelper.java

@@ -40,6 +40,7 @@ import com.evernote.android.job.JobManager;
 import com.evernote.android.job.JobRequest;
 import com.evernote.android.job.JobRequest;
 import com.evernote.android.job.util.Device;
 import com.evernote.android.job.util.Device;
 import com.nextcloud.client.account.UserAccountManager;
 import com.nextcloud.client.account.UserAccountManager;
+import com.nextcloud.client.network.ConnectivityService;
 import com.nextcloud.client.preferences.AppPreferences;
 import com.nextcloud.client.preferences.AppPreferences;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.datamodel.ArbitraryDataProvider;
 import com.owncloud.android.datamodel.ArbitraryDataProvider;
@@ -216,7 +217,9 @@ public final class FilesSyncHelper {
         }
         }
     }
     }
 
 
-    public static void restartJobsIfNeeded(UploadsStorageManager uploadsStorageManager, UserAccountManager accountManager) {
+    public static void restartJobsIfNeeded(final UploadsStorageManager uploadsStorageManager,
+                                           final UserAccountManager accountManager,
+                                           final ConnectivityService connectivityService) {
         final Context context = MainApp.getAppContext();
         final Context context = MainApp.getAppContext();
 
 
         FileUploader.UploadRequester uploadRequester = new FileUploader.UploadRequester();
         FileUploader.UploadRequester uploadRequester = new FileUploader.UploadRequester();
@@ -242,9 +245,13 @@ public final class FilesSyncHelper {
         }
         }
 
 
         new Thread(() -> {
         new Thread(() -> {
-            if (!Device.getNetworkType(context).equals(JobRequest.NetworkType.ANY) &&
-                    !ConnectivityUtils.isInternetWalled(context)) {
-                uploadRequester.retryFailedUploads(context, null, uploadsStorageManager, null);
+            if (connectivityService.getActiveNetworkType() != JobRequest.NetworkType.ANY &&
+                    !connectivityService.isInternetWalled()) {
+                uploadRequester.retryFailedUploads(context,
+                                                   null,
+                                                   uploadsStorageManager,
+                                                   connectivityService,
+                                                   null);
             }
             }
         }).start();
         }).start();
     }
     }

+ 11 - 7
src/main/java/com/owncloud/android/utils/ReceiversHelper.java

@@ -30,6 +30,7 @@ import android.content.IntentFilter;
 import com.evernote.android.job.JobRequest;
 import com.evernote.android.job.JobRequest;
 import com.evernote.android.job.util.Device;
 import com.evernote.android.job.util.Device;
 import com.nextcloud.client.account.UserAccountManager;
 import com.nextcloud.client.account.UserAccountManager;
+import com.nextcloud.client.network.ConnectivityService;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.MainApp;
 import com.owncloud.android.datamodel.UploadsStorageManager;
 import com.owncloud.android.datamodel.UploadsStorageManager;
 
 
@@ -44,8 +45,9 @@ public final class ReceiversHelper {
 
 
     public static void registerNetworkChangeReceiver(
     public static void registerNetworkChangeReceiver(
         final UploadsStorageManager uploadsStorageManager,
         final UploadsStorageManager uploadsStorageManager,
-        final UserAccountManager accountManager
-    ) {
+        final UserAccountManager accountManager,
+        final ConnectivityService connectivityService
+        ) {
         Context context = MainApp.getAppContext();
         Context context = MainApp.getAppContext();
 
 
         IntentFilter intentFilter = new IntentFilter();
         IntentFilter intentFilter = new IntentFilter();
@@ -56,7 +58,7 @@ public final class ReceiversHelper {
             @Override
             @Override
             public void onReceive(Context context, Intent intent) {
             public void onReceive(Context context, Intent intent) {
                 if (!Device.getNetworkType(context).equals(JobRequest.NetworkType.ANY)) {
                 if (!Device.getNetworkType(context).equals(JobRequest.NetworkType.ANY)) {
-                    FilesSyncHelper.restartJobsIfNeeded(uploadsStorageManager, accountManager);
+                    FilesSyncHelper.restartJobsIfNeeded(uploadsStorageManager, accountManager, connectivityService);
                 }
                 }
             }
             }
         };
         };
@@ -66,7 +68,8 @@ public final class ReceiversHelper {
 
 
     public static void registerPowerChangeReceiver(
     public static void registerPowerChangeReceiver(
         final UploadsStorageManager uploadsStorageManager,
         final UploadsStorageManager uploadsStorageManager,
-        final UserAccountManager accountManager
+        final UserAccountManager accountManager,
+        final ConnectivityService connectivityService
     ) {
     ) {
         Context context = MainApp.getAppContext();
         Context context = MainApp.getAppContext();
 
 
@@ -78,7 +81,7 @@ public final class ReceiversHelper {
             @Override
             @Override
             public void onReceive(Context context, Intent intent) {
             public void onReceive(Context context, Intent intent) {
                 if (Intent.ACTION_POWER_CONNECTED.equals(intent.getAction())) {
                 if (Intent.ACTION_POWER_CONNECTED.equals(intent.getAction())) {
-                    FilesSyncHelper.restartJobsIfNeeded(uploadsStorageManager, accountManager);
+                    FilesSyncHelper.restartJobsIfNeeded(uploadsStorageManager, accountManager, connectivityService);
                 }
                 }
             }
             }
         };
         };
@@ -88,7 +91,8 @@ public final class ReceiversHelper {
 
 
     public static void registerPowerSaveReceiver(
     public static void registerPowerSaveReceiver(
         final UploadsStorageManager uploadsStorageManager,
         final UploadsStorageManager uploadsStorageManager,
-        final UserAccountManager accountManager
+        final UserAccountManager accountManager,
+        final ConnectivityService connectivityService
     ) {
     ) {
         Context context = MainApp.getAppContext();
         Context context = MainApp.getAppContext();
 
 
@@ -99,7 +103,7 @@ public final class ReceiversHelper {
             @Override
             @Override
             public void onReceive(Context context, Intent intent) {
             public void onReceive(Context context, Intent intent) {
                 if (!PowerUtils.isPowerSaveMode(context)) {
                 if (!PowerUtils.isPowerSaveMode(context)) {
-                    FilesSyncHelper.restartJobsIfNeeded(uploadsStorageManager, accountManager);
+                    FilesSyncHelper.restartJobsIfNeeded(uploadsStorageManager, accountManager, connectivityService);
                 }
                 }
             }
             }
         };
         };

+ 238 - 0
src/test/java/com/nextcloud/client/network/ConnectivityServiceTest.kt

@@ -0,0 +1,238 @@
+/*
+ * Nextcloud Android client application
+ *
+ * @author Chris Narkiewicz
+ * Copyright (C) 2019 Chris Narkiewicz <hello@ezaquarii.com>
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU Affero General Public License as published by
+ * the Free Software Foundation, either version 3 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU Affero General Public License for more details.
+ *
+ * You should have received a copy of the GNU Affero General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+package com.nextcloud.client.network
+
+import android.accounts.Account
+import android.net.ConnectivityManager
+import android.net.NetworkInfo
+import android.net.Uri
+import com.nextcloud.client.account.UserAccountManager
+import com.nhaarman.mockitokotlin2.any
+import com.nhaarman.mockitokotlin2.mock
+import com.nhaarman.mockitokotlin2.verify
+import com.nhaarman.mockitokotlin2.whenever
+import com.owncloud.android.lib.common.OwnCloudAccount
+import com.owncloud.android.lib.common.OwnCloudClient
+import com.owncloud.android.lib.resources.status.OwnCloudVersion
+import org.apache.commons.httpclient.HttpStatus
+import org.apache.commons.httpclient.methods.GetMethod
+import org.junit.Assert.*
+import org.junit.Before
+import org.junit.Test
+import org.junit.runner.RunWith
+import org.junit.runners.Suite
+import org.mockito.ArgumentCaptor
+import org.mockito.Mock
+import org.mockito.MockitoAnnotations
+
+@RunWith(Suite::class)
+@Suite.SuiteClasses(
+    ConnectivityServiceTest.IsConnected::class,
+    ConnectivityServiceTest.WifiConnectionWalledStatusOnLegacyServer::class,
+    ConnectivityServiceTest.WifiConnectionWalledStatus::class
+)
+class ConnectivityServiceTest {
+
+    internal abstract class Base {
+        companion object {
+            fun mockNetworkInfo(connected: Boolean, connecting: Boolean, type: Int): NetworkInfo {
+                val networkInfo = mock<NetworkInfo>()
+                whenever(networkInfo.isConnectedOrConnecting).thenReturn(connected or connecting)
+                whenever(networkInfo.isConnected).thenReturn(connected)
+                whenever(networkInfo.type).thenReturn(type)
+                return networkInfo
+            }
+
+            const val SERVER_BASE_URL = "https://test.server.com"
+        }
+
+        @Mock
+        lateinit var platformConnectivityManager: ConnectivityManager
+
+        @Mock
+        lateinit var networkInfo: NetworkInfo
+
+        @Mock
+        lateinit var accountManager: UserAccountManager
+
+        @Mock
+        lateinit var clientFactory: ClientFactory
+
+        @Mock
+        lateinit var client: OwnCloudClient
+
+        @Mock
+        lateinit var getRequest: GetMethod
+
+        @Mock
+        lateinit var requestBuilder: ConnectivityServiceImpl.GetRequestBuilder
+
+        @Mock
+        lateinit var platformAccount: Account
+
+        @Mock
+        lateinit var ownCloudAccount: OwnCloudAccount
+
+        @Mock
+        lateinit var baseServerUri: Uri
+
+        lateinit var connectivityService: ConnectivityServiceImpl
+
+        @Before
+        fun setUpMocks() {
+            MockitoAnnotations.initMocks(this)
+            connectivityService = ConnectivityServiceImpl(
+                platformConnectivityManager,
+                accountManager,
+                clientFactory,
+                requestBuilder
+            )
+            whenever(platformConnectivityManager.activeNetworkInfo).thenReturn(networkInfo)
+            whenever(requestBuilder.invoke(any())).thenReturn(getRequest)
+            whenever(clientFactory.create(any())).thenReturn(client)
+            whenever(accountManager.currentOwnCloudAccount).thenReturn(ownCloudAccount)
+            whenever(accountManager.currentAccount).thenReturn(platformAccount)
+            whenever(baseServerUri.toString()).thenReturn(SERVER_BASE_URL)
+            whenever(ownCloudAccount.baseUri).thenReturn(baseServerUri)
+        }
+    }
+
+    internal class IsConnected : Base() {
+
+        @Test
+        fun `connected to wifi`() {
+            whenever(networkInfo.isConnectedOrConnecting).thenReturn(true)
+            whenever(networkInfo.type).thenReturn(ConnectivityManager.TYPE_WIFI)
+            assertTrue(connectivityService.isOnlineWithWifi)
+        }
+
+        @Test
+        fun `connected to wifi and vpn`() {
+            whenever(networkInfo.isConnectedOrConnecting).thenReturn(true)
+            whenever(networkInfo.type).thenReturn(ConnectivityManager.TYPE_VPN)
+            val wifiNetworkInfoList = arrayOf(
+                mockNetworkInfo(
+                    connected = true,
+                    connecting = true,
+                    type = ConnectivityManager.TYPE_VPN
+                ),
+                mockNetworkInfo(
+                    connected = true,
+                    connecting = true,
+                    type = ConnectivityManager.TYPE_WIFI
+                )
+            )
+            whenever(platformConnectivityManager.allNetworkInfo).thenReturn(wifiNetworkInfoList)
+            assertTrue(connectivityService.isOnlineWithWifi)
+        }
+
+        @Test
+        fun `connected to mobile network`() {
+            whenever(networkInfo.isConnectedOrConnecting).thenReturn(true)
+            whenever(networkInfo.type).thenReturn(ConnectivityManager.TYPE_MOBILE)
+            assertFalse(connectivityService.isOnlineWithWifi)
+        }
+    }
+
+    internal class WifiConnectionWalledStatusOnLegacyServer : Base() {
+
+        @Before
+        fun setUp() {
+            whenever(networkInfo.isConnectedOrConnecting).thenReturn(true)
+            whenever(networkInfo.type).thenReturn(ConnectivityManager.TYPE_WIFI)
+            whenever(accountManager.getServerVersion(any())).thenReturn(OwnCloudVersion.nextcloud_13)
+            assertTrue("Precondition failed", connectivityService.isOnlineWithWifi)
+        }
+
+        fun mockResponse(maintenance: Boolean = true, httpStatus: Int = HttpStatus.SC_OK) {
+            whenever(client.executeMethod(getRequest)).thenReturn(httpStatus)
+            val body = """{"maintenance":$maintenance}"""
+            whenever(getRequest.responseContentLength).thenReturn(body.length.toLong())
+            whenever(getRequest.responseBodyAsString).thenReturn(body)
+        }
+
+        @Test
+        fun `false maintenance status flag is used`() {
+            mockResponse(maintenance = false, httpStatus = HttpStatus.SC_OK)
+            assertFalse(connectivityService.isInternetWalled)
+        }
+
+        @Test
+        fun `true maintenance status flag is used`() {
+            mockResponse(maintenance = true, httpStatus = HttpStatus.SC_OK)
+            assertTrue(connectivityService.isInternetWalled)
+        }
+
+        @Test
+        fun `maintenance flag is ignored when non-200 HTTP code is returned`() {
+            mockResponse(maintenance = false, httpStatus = HttpStatus.SC_NO_CONTENT)
+            assertTrue(connectivityService.isInternetWalled)
+        }
+
+        @Test
+        fun `status endpoint is used to determine internet state`() {
+            mockResponse()
+            connectivityService.isInternetWalled
+            val urlCaptor = ArgumentCaptor.forClass(String::class.java)
+            verify(requestBuilder).invoke(urlCaptor.capture())
+            assertTrue("Invalid URL used to check status", urlCaptor.value.endsWith("/status.php"))
+        }
+
+    }
+
+    internal class WifiConnectionWalledStatus : Base() {
+
+        @Before
+        fun setUp() {
+            whenever(networkInfo.isConnectedOrConnecting).thenReturn(true)
+            whenever(networkInfo.type).thenReturn(ConnectivityManager.TYPE_WIFI)
+            whenever(accountManager.getServerVersion(any())).thenReturn(OwnCloudVersion.nextcloud_14)
+            assertTrue("Precondition failed", connectivityService.isOnlineWithWifi)
+        }
+
+        fun mockResponse(contentLength: Long = 0, status: Int = HttpStatus.SC_OK) {
+            whenever(client.executeMethod(any())).thenReturn(status)
+            whenever(getRequest.statusCode).thenReturn(status)
+            whenever(getRequest.responseContentLength).thenReturn(contentLength)
+        }
+
+        @Test
+        fun `status 204 means internet is not walled`() {
+            mockResponse(contentLength = 0, status = HttpStatus.SC_NO_CONTENT)
+            assertFalse(connectivityService.isInternetWalled)
+        }
+
+        @Test
+        fun `other status than 204 means internet is walled`() {
+            mockResponse(contentLength = 0, status = HttpStatus.SC_GONE)
+            assertTrue(connectivityService.isInternetWalled)
+        }
+
+        @Test
+        fun `index endpoint is used to determine internet state`() {
+            mockResponse()
+            connectivityService.isInternetWalled
+            val urlCaptor = ArgumentCaptor.forClass(String::class.java)
+            verify(requestBuilder).invoke(urlCaptor.capture())
+            assertTrue("Invalid URL used to check status", urlCaptor.value.endsWith("/index.php/204"))
+        }
+    }
+
+}

+ 0 - 168
src/test/java/com/owncloud/android/utils/ConnectivityUtilsTest.java

@@ -1,168 +0,0 @@
-/*
- * Nextcloud Android client application
- *
- * @author Edvard Holst
- * Copyright (C) 2019 Edvard Holst
- * Copyright (C) 2019 Nextcloud GmbH
- *
- * This program is free software: you can redistribute it and/or modify
- * it under the terms of the GNU General Public License as published by
- * the Free Software Foundation, either version 3 of the License, or
- * (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- * GNU General Public License for more details.
- *
- * You should have received a copy of the GNU General Public License
- * along with this program. If not, see <https://www.gnu.org/licenses/>.
- */
-package com.owncloud.android.utils;
-
-import android.accounts.Account;
-import android.content.Context;
-import android.net.ConnectivityManager;
-import android.net.NetworkInfo;
-
-import com.owncloud.android.authentication.AccountUtils;
-import com.owncloud.android.lib.common.OwnCloudAccount;
-import com.owncloud.android.lib.common.OwnCloudClient;
-import com.owncloud.android.lib.common.OwnCloudClientFactory;
-import com.owncloud.android.lib.resources.status.OwnCloudVersion;
-
-import org.apache.commons.httpclient.HttpStatus;
-import org.apache.commons.httpclient.methods.GetMethod;
-import org.json.JSONObject;
-import org.junit.Before;
-import org.junit.Test;
-import org.junit.runner.RunWith;
-import org.mockito.Mock;
-import org.mockito.MockitoAnnotations;
-import org.powermock.api.mockito.PowerMockito;
-import org.powermock.core.classloader.annotations.PowerMockIgnore;
-import org.powermock.core.classloader.annotations.PrepareForTest;
-import org.powermock.modules.junit4.PowerMockRunner;
-
-import static org.junit.Assert.*;
-import static org.mockito.ArgumentMatchers.eq;
-import static org.mockito.Mockito.mock;
-import static org.mockito.Mockito.when;
-import static org.powermock.api.mockito.PowerMockito.mockStatic;
-
-@RunWith(PowerMockRunner.class)
-@PowerMockIgnore({"org.slf4j.*"})
-@PrepareForTest({AccountUtils.class, OwnCloudClientFactory.class, ConnectivityUtils.class})
-public class ConnectivityUtilsTest {
-
-    @Mock
-    private Context context;
-
-    @Mock
-    private ConnectivityManager connectivityManager;
-
-    @Mock
-    private NetworkInfo networkInfo;
-
-    @Mock
-    private Account account;
-
-    @Mock
-    private OwnCloudAccount ocAccount;
-
-    @Mock
-    private OwnCloudClient client;
-
-    @Mock
-    private GetMethod getMethod;
-
-    @Before
-    public void setUp() {
-        MockitoAnnotations.initMocks(this);
-
-        when(context.getSystemService(Context.CONNECTIVITY_SERVICE)).thenReturn(connectivityManager);
-        when(connectivityManager.getActiveNetworkInfo()).thenReturn(networkInfo);
-
-        mockStatic(AccountUtils.class);
-        mockStatic(OwnCloudClientFactory.class);
-    }
-
-    @Test
-    public void isOnlineWithWifi_assertTrueWhenOnWifi() {
-        when(networkInfo.isConnectedOrConnecting()).thenReturn(true);
-        when(networkInfo.getType()).thenReturn(ConnectivityManager.TYPE_WIFI);
-
-        assertTrue("Falsely indicated connection not on WiFi", ConnectivityUtils.isOnlineWithWifi(context));
-    }
-
-    @Test
-    public void isOnlineWithWifi_assertTrueWhenOnVPNWithAdditionalWiFiConnection() {
-        when(networkInfo.isConnectedOrConnecting()).thenReturn(true);
-        when(networkInfo.getType()).thenReturn(ConnectivityManager.TYPE_VPN);
-        NetworkInfo[] networkInfoList = new NetworkInfo[1];
-        NetworkInfo wifiNetworkInfo = mock(NetworkInfo.class);
-        when(wifiNetworkInfo.isConnectedOrConnecting()).thenReturn(true);
-        when(wifiNetworkInfo.getType()).thenReturn(ConnectivityManager.TYPE_WIFI);
-        networkInfoList[0] = wifiNetworkInfo;
-        when(connectivityManager.getAllNetworkInfo()).thenReturn(networkInfoList);
-
-        assertTrue("Falsely indicated connection not on WiFi", ConnectivityUtils.isOnlineWithWifi(context));
-    }
-
-    @Test
-    public void isOnlineWithWifi_assertFalseWhenNotOnWifi() {
-        when(networkInfo.isConnectedOrConnecting()).thenReturn(true);
-        when(networkInfo.getType()).thenReturn(ConnectivityManager.TYPE_MOBILE);
-
-        assertFalse("Falsely indicated connection on WiFi", ConnectivityUtils.isOnlineWithWifi(context));
-    }
-
-    @Test
-    public void isInternetWalled_assertFalseWhenOnOlderNC() throws Exception {
-        // Ensure we are on WiFi
-        when(networkInfo.isConnectedOrConnecting()).thenReturn(true);
-        when(networkInfo.getType()).thenReturn(ConnectivityManager.TYPE_WIFI);
-
-        PowerMockito.when(AccountUtils.getCurrentOwnCloudAccount(eq(context))).thenReturn(account);
-        PowerMockito.whenNew(OwnCloudAccount.class).withAnyArguments().thenReturn(ocAccount);
-        PowerMockito.when(AccountUtils.getServerVersion(eq(account))).thenReturn(OwnCloudVersion.nextcloud_13);
-        PowerMockito.when(OwnCloudClientFactory.createOwnCloudClient(eq(account), eq(context))).thenReturn(client);
-        PowerMockito.whenNew(GetMethod.class).withAnyArguments().thenReturn(getMethod);
-
-        // Return SC_OK
-        when(client.executeMethod(getMethod)).thenReturn(HttpStatus.SC_OK);
-
-        // Content length should be > 0.
-        when(getMethod.getResponseContentLength()).thenReturn(1024L);
-
-        JSONObject jsonObj = new JSONObject();
-        jsonObj.put("maintenance", false);
-
-        when(getMethod.getResponseBodyAsString()).thenReturn(jsonObj.toString());
-
-        assertFalse("internet was falsely claimed to be walled",
-                    ConnectivityUtils.isInternetWalled(context));
-    }
-
-    @Test
-    public void isInternetWalled_assertFalseWhenOnNewerNC() throws Exception {
-        // Ensure we are on WiFi
-        when(networkInfo.isConnectedOrConnecting()).thenReturn(true);
-        when(networkInfo.getType()).thenReturn(ConnectivityManager.TYPE_WIFI);
-
-        PowerMockito.when(AccountUtils.getCurrentOwnCloudAccount(eq(context))).thenReturn(account);
-        PowerMockito.whenNew(OwnCloudAccount.class).withAnyArguments().thenReturn(ocAccount);
-        PowerMockito.when(AccountUtils.getServerVersion(eq(account))).thenReturn(OwnCloudVersion.nextcloud_14);
-        PowerMockito.when(OwnCloudClientFactory.createOwnCloudClient(eq(account), eq(context))).thenReturn(client);
-        PowerMockito.whenNew(GetMethod.class).withAnyArguments().thenReturn(getMethod);
-
-        // Return SC_NO_CONTENT
-        when(client.executeMethod(getMethod)).thenReturn(HttpStatus.SC_NO_CONTENT);
-
-        // Content length should be 0.
-        when(getMethod.getResponseContentLength()).thenReturn(0L);
-
-        assertFalse("internet was falsely claimed to be walled",
-                    ConnectivityUtils.isInternetWalled(context));
-    }
-}