1 /*
2  * Copyright (C) 2016 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 package com.android.contacts.util;
17 
18 import android.accounts.Account;
19 import android.content.ContentResolver;
20 import android.content.Context;
21 import android.net.ConnectivityManager;
22 import android.net.NetworkInfo;
23 import android.provider.ContactsContract;
24 
25 import com.android.contacts.model.AccountTypeManager;
26 import com.android.contacts.model.account.AccountWithDataSet;
27 import com.android.contacts.model.account.GoogleAccountType;
28 
29 import java.util.List;
30 
31 /**
32  * Utilities related to sync.
33  */
34 public final class SyncUtil {
35     private static final String TAG = "SyncUtil";
36 
37     public static final int SYNC_SETTING_SYNC_ON = 0;
38     public static final int SYNC_SETTING_GLOBAL_SYNC_OFF = 1;
39     public static final int SYNC_SETTING_ACCOUNT_SYNC_OFF = 2;
40 
SyncUtil()41     private SyncUtil() {
42     }
43 
isSyncStatusPendingOrActive(Account account)44     public static final boolean isSyncStatusPendingOrActive(Account account) {
45         if (account == null) {
46             return false;
47         }
48         return ContentResolver.isSyncPending(account, ContactsContract.AUTHORITY)
49                 || ContentResolver.isSyncActive(account, ContactsContract.AUTHORITY);
50     }
51 
52     /**
53      * Returns true {@link ContentResolver#isSyncPending(Account, String)} or
54      * {@link ContentResolver#isSyncActive(Account, String)} is true for any account in accounts
55      */
isAnySyncing(List<AccountWithDataSet> accounts)56     public static final boolean isAnySyncing(List<AccountWithDataSet> accounts) {
57         for (AccountWithDataSet accountWithDataSet : accounts) {
58             if (isSyncStatusPendingOrActive(accountWithDataSet.getAccountOrNull())) {
59                 return true;
60             }
61         }
62         return false;
63     }
64 
65     /**
66      * Returns true if the given Google account is not syncable.
67      */
isUnsyncableGoogleAccount(Account account)68     public static final boolean isUnsyncableGoogleAccount(Account account) {
69         if (account == null || !GoogleAccountType.ACCOUNT_TYPE.equals(account.type)) {
70             return false;
71         }
72         return ContentResolver.getIsSyncable(account, ContactsContract.AUTHORITY) <= 0;
73     }
74 
hasSyncableAccount(AccountTypeManager accountTypeManager)75     public static final boolean hasSyncableAccount(AccountTypeManager accountTypeManager) {
76         return !accountTypeManager.getWritableGoogleAccounts().isEmpty();
77     }
78 
isAlertVisible(Context context, Account account, int reason)79     public static boolean isAlertVisible(Context context, Account account, int reason) {
80         if (reason == SYNC_SETTING_GLOBAL_SYNC_OFF) {
81             return (SharedPreferenceUtil.getNumOfDismissesForAutoSyncOff(context) == 0);
82         } else if (reason == SYNC_SETTING_ACCOUNT_SYNC_OFF && account != null) {
83             return (SharedPreferenceUtil.getNumOfDismissesforAccountSyncOff(
84                     context, account.name) == 0);
85         }
86         return false;
87     }
88 
calculateReasonSyncOff(Context context, Account account)89     public static int calculateReasonSyncOff(Context context, Account account) {
90         // Global sync is turned off
91         if (!ContentResolver.getMasterSyncAutomatically()) {
92             if (account != null) {
93                 SharedPreferenceUtil.resetNumOfDismissesForAccountSyncOff(
94                         context, account.name);
95             }
96             return SYNC_SETTING_GLOBAL_SYNC_OFF;
97         }
98 
99         // Global sync is on, clear the number of times users has dismissed this
100         // alert so that next time global sync is off, alert gets displayed again.
101         SharedPreferenceUtil.resetNumOfDismissesForAutoSyncOff(context);
102         if (account != null) {
103             // Account level sync is off
104             if (!ContentResolver.getSyncAutomatically(account, ContactsContract.AUTHORITY)) {
105                 return SYNC_SETTING_ACCOUNT_SYNC_OFF;
106             }
107             // Account sync is on, clear the number of times users has dismissed this
108             // alert so that next time sync is off, alert gets displayed again.
109             SharedPreferenceUtil.resetNumOfDismissesForAccountSyncOff(
110                     context, account.name);
111         }
112         return SYNC_SETTING_SYNC_ON;
113     }
114 
isNetworkConnected(Context context)115     public static boolean isNetworkConnected(Context context) {
116         ConnectivityManager cm =
117                 (ConnectivityManager)context.getSystemService(Context.CONNECTIVITY_SERVICE);
118         NetworkInfo activeNetwork = cm.getActiveNetworkInfo();
119         return activeNetwork != null && activeNetwork.isConnectedOrConnecting();
120     }
121 }