Vihar
Vihar

Reputation: 3831

Cant access value of SharedPreference in different thread

In my Application ,upon login I am saving the user details like (userName, Id ,email etc.) in a sharedPreference file, so that I can access those anywhere in my application, I am doing it like this

public void put(String fileName, String key, String value)
{
    SharedPreferences sharedPref = getContext().getSharedPreferences(fileName, Context.MODE_PRIVATE);
    SharedPreferences.Editor editor = sharedPref.edit();
    editor.putString(key, value);
    editor.commit();
}

now I have spawned a different thread, which will run independently (something like Sync), I am accessing sharedPreference like this ,

mContext.getSharedPreferences(fileName, Context.MODE_PRIVATE);

but all the values in this particular preference are returned as null, am I doing anything wrong,

PS :- If I kill the app and again same thread gets spawned, I can acess the values (its quite strange, but this is happening, i.e. when user logs in for first time , these details are not accessible)

feels like sync issue with SharedPreferences , can anyone help on this?

Upvotes: 4

Views: 1183

Answers (4)

Liran Peretz
Liran Peretz

Reputation: 580

Change MODE_PRIVATE to MODE_WORLD_READABLE.

Upvotes: 1

Vihar
Vihar

Reputation: 3831

The thread which was accessing the shared preference turned out to be in a service which was running in a different process,

so changing the shared preference mode to MODE_MULTI_PROCESS instead of MODE_PRIVATE worked perfectly,

Now I can access the shared preference normally

Thanks for all who tried!

Upvotes: 1

4gus71n
4gus71n

Reputation: 4093

I'd the same issue some time ago trying to access my SharedPreference from a Service wich ran in It's own process. Here's how I solve it:

MultiProcessShared example:

public class GenericSharedPreferences {
public static final String TAG = GenericSharedPreferences.class.getSimpleName();

//region Logger
public static Logger sLogger;

static {
    sLogger = Logger.getLogger(TAG);
    if (BuildConfig.DEBUG)
        sLogger.setLevel(Level.ALL);
    else
        sLogger.setLevel(Level.OFF);
}
//endregion

public static MultiProcessShared.MultiProcessSharedPreferences getMultiProcessSharedReader(Context context) {
    return MultiProcessShared.getDefaultSharedPreferences(context);
}

public static MultiProcessShared.Editor getMultiProcessSharedWriter(Context context) {
    return MultiProcessShared.getDefaultSharedPreferences(context).edit();
}

}

My App SharedPreferences concrete implementation:

public class MyAppSharedPreferences extends GenericSharedPreferences {
...
//region Country
    private static final String SHARED_APP_COUNTRY = "shared-app-country";

    public static Country getCountry() {
        String isoCode = getMultiProcessSharedReader(MyApp.getInstance()).getString(SHARED_APP_COUNTRY);
        CountryEnum countryEnum = CountryEnum.fromIso(isoCode);
        if (countryEnum == null)
            return null;
        return countryEnum.getCountry();
    }

    public static void setCountry(String isoCode) {
        if (TextUtils.isEmpty(isoCode))
            getMultiProcessSharedReader(MyApp.getInstance()).removeString(SHARED_APP_COUNTRY);
        else
            getMultiProcessSharedWriter(MyApp.getInstance()).putString(SHARED_APP_COUNTRY, isoCode);
    }
    //endregion
...
}

MyApp is the application which I associated in the AndroidManifext.xml

Any question, feel free to ask!

Upvotes: 1

frogatto
frogatto

Reputation: 29285

I think you've chosen the right way. Actually accessing shared preferences is just an I/O operation on a XML file stored in /data/data/pkg_name/preferences. Thus it's really making sense if you would like to access it in other threads than the UI.

However, you should make sure after each operation on shared preferences, you should commit the changes in underlying layers. First off you should beware of differences between apply() and commit().

Thus, you should first commit your changes and afterwards you can access it through another threads.

Upvotes: 4

Related Questions