Android在SyncAdapter中提交的SharedPreference在Activity中未更新?

前端之家收集整理的这篇文章主要介绍了Android在SyncAdapter中提交的SharedPreference在Activity中未更新?前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。
在同步完成后,我正在更改SyncAdapter中的SharedPreference,但是当我访问我的活动中的首选项时,我没有看到更新的值(而是看到旧的值).我究竟做错了什么?不同的语境

我的SyncAdapter更新优先级:

class SyncAdapter extends AbstractThreadedSyncAdapter {
    private int PARTICIPANT_ID;
    private final Context mContext;
    private final ContentResolver mContentResolver;

    public SyncAdapter(Context context,boolean autoInitialize) {
        super(context,autoInitialize);
        mContext = context;
        mContentResolver = context.getContentResolver();
    }

    public SyncAdapter(Context context,boolean autoInitialize,boolean allowParallelSyncs) {
        super(context,autoInitialize,allowParallelSyncs);
        mContext = context;
        mContentResolver = context.getContentResolver();
    }

    @Override
    public void onPerformSync(Account account,Bundle extras,String authority,ContentProviderClient provider,SyncResult syncResult) {

        final SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(mContext);
        PARTICIPANT_ID = Integer.parseInt(prefs.getString("participant_id","0"));

        if (success) {
            // save and set the new participant id
            PARTICIPANT_ID = newParticipantId;
            prefs.edit().putString("participant_id",String.valueOf(newParticipantId)).commit();
        }
    }
}

该服务使用ApplicationContext初始化SyncAdapter:

public class SyncService extends Service {
    private static final Object sSyncAdapterLock = new Object();
    private static SyncAdapter sSyncAdapter = null;

    @Override
    public void onCreate() {
        synchronized (sSyncAdapterLock) {
            if (sSyncAdapter == null) {
                sSyncAdapter = new SyncAdapter(getApplicationContext(),false);
            }
        }
    }

    @Override
    public IBinder onBind(Intent intent) {
        return sSyncAdapter.getSyncAdapterBinder();
    }
}

Activity中的一个静态函数,由Activity检查SharedPreference.这不返回在SyncAdapter中提交的值,而是返回旧值. (我的设置活动和其他活动也使用旧值.):

public static boolean isUserLoggedIn(Context ctx) {
    final SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(ctx);
    int participantId = Integer.parseInt(prefs.getString("participant_id","0"));
    LOGD("dg_Utils","isUserLoggedIn.participantId: " + participantId);// TODO
    if (participantId <= 0) {
        ctx.startActivity(new Intent(ctx,LoginActivity.class).addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP));
        return false;
    }
    return true;
}

更新:当我完全关闭应用程序(从运行的应用程序中滑动)时,我获得了新的值.我还有一个SharedPreferenceChangeListener,当更改首选项时,它不会被触发.

private final SharedPreferences.OnSharedPreferenceChangeListener mParticipantIDPrefChangeListener = new SharedPreferences.OnSharedPreferenceChangeListener() {
    public void onSharedPreferenceChanged(SharedPreferences prefs,String key) {
        if (key.equals("participant_id")) {
            LOGI(TAG,"participant_id has changed,requesting to restart the loader.");
            mRestartLoader = true;
        }
    }
};

@Override
public void onActivityCreated(Bundle savedInstanceState) {
    super.onActivityCreated(savedInstanceState);

    // subscribe to the participant_id change lister
    final SharedPreferences prefs = PreferenceManager.getDefaultSharedPreferences(getActivity());
    PARTICIPANT_ID = Integer.parseInt(prefs.getString("participant_id","0"));
    prefs.registerOnSharedPreferenceChangeListener(mParticipantIDPrefChangeListener);
}

解决方法

好的,我通过@Titus的帮助,经过一些研究,拼凑了一个解决我的问题的自己.

没有更新相同上下文的DefaultSharedPreferences的原因是我已经指定了SyncService在AndroidManifest.xml中的自己的进程中运行(见下文).因此,从Android 2.3开始,其他进程被阻止访问更新的SharedPreferences文件(参见this answerContext.MODE_MULTI_PROCESS上的Android文档).

<service
        android:name=".sync.SyncService"
        android:exported="true"
        android:process=":sync"
        tools:ignore="ExportedService" >
        <intent-filter>
            <action android:name="android.content.SyncAdapter" />
        </intent-filter>
        <Meta-data
            android:name="android.content.SyncAdapter"
            android:resource="@xml/syncadapter" />
    </service>

所以在SyncAdapter和我的应用程序的UI进程中访问SharedPreferences时,我必须设置MODE_MULTI_PROCESS.因为我在整个应用程序中广泛使用了PreferenceManager.getDefaultSharedPreferences(Context),所以我编写了一个实用程序方法,并用此方法替换了PreferenceManager.getDefaultSharedPreferences(Context)的所有调用(见下文).首选项文件的默认名称是硬编码的,并从the Android source codethis answer派生.

public static SharedPreferences getDefaultSharedPreferencesMultiProcess(
        Context context) {
    return context.getSharedPreferences(
            context.getPackageName() + "_preferences",Context.MODE_PRIVATE | Context.MODE_MULTI_PROCESS);
}
原文链接:https://www.f2er.com/android/312495.html

猜你在找的Android相关文章