SharedPreferences
Cache Library
SharedPreferences
Overview
SharedPreferences is an interface for storing small collections of key-value pairs in Android applications, automatically cached for efficient data access.
Details
SharedPreferences is used for storing relatively small collections of key-values in Android. A SharedPreferences object points to a file containing key-value pairs and provides simple methods to read and write them. Each SharedPreferences file is managed by the framework and can be private or shared. An important feature is that SharedPreferences are cached automatically. The first access to a particular SharedPreferences loads the XML file, and subsequent reads work from the cache, making it very efficient. It's suitable for storing application settings, user preferences, and simple state information.
Pros and Cons
Pros
- Automatic Caching: Framework automatically manages cache
- Fast Access: High-speed reading from memory cache after initial load
- Simple API: Intuitive and easy-to-use methods
- Type Safe: Type-specific getter methods for safe operations
- Persistent: Data persists after app restart
- Atomic Operations: Safe writing with commit and apply
Cons
- Small Data Only: Not suitable for large data
- XML Format: Cannot store complex data structures
- Main Thread: Synchronous operations block main thread
- Type Limited: Only supports primitive types and String
- Deprecated: DataStore is the recommended modern alternative
Key Links
- SharedPreferences | Android Developers
- Data Storage Guide | Android Developers
- DataStore Migration Guide
- GeeksforGeeks SharedPreferences
Usage Examples
Basic Usage
// Get SharedPreferences instance
SharedPreferences sharedPref = getSharedPreferences("MyAppPrefs", Context.MODE_PRIVATE);
// Save data
SharedPreferences.Editor editor = sharedPref.edit();
editor.putString("username", "john_doe");
editor.putInt("user_age", 25);
editor.putBoolean("is_logged_in", true);
editor.apply(); // Save asynchronously
// Read data
String username = sharedPref.getString("username", "");
int age = sharedPref.getInt("user_age", 0);
boolean isLoggedIn = sharedPref.getBoolean("is_logged_in", false);
Default SharedPreferences in Activity
public class MainActivity extends AppCompatActivity {
private SharedPreferences prefs;
@Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main);
// Use default SharedPreferences
prefs = PreferenceManager.getDefaultSharedPreferences(this);
// Check first launch
if (isFirstLaunch()) {
showWelcomeScreen();
setFirstLaunchCompleted();
}
}
private boolean isFirstLaunch() {
return prefs.getBoolean("first_launch", true);
}
private void setFirstLaunchCompleted() {
prefs.edit()
.putBoolean("first_launch", false)
.apply();
}
}
User Settings Storage and Retrieval
public class SettingsManager {
private static final String PREFS_NAME = "AppSettings";
private static final String KEY_THEME = "theme";
private static final String KEY_NOTIFICATIONS = "notifications_enabled";
private static final String KEY_LANGUAGE = "language";
private Context context;
private SharedPreferences prefs;
public SettingsManager(Context context) {
this.context = context;
this.prefs = context.getSharedPreferences(PREFS_NAME, Context.MODE_PRIVATE);
}
// Theme settings
public void setTheme(String theme) {
prefs.edit()
.putString(KEY_THEME, theme)
.apply();
}
public String getTheme() {
return prefs.getString(KEY_THEME, "light");
}
// Notification settings
public void setNotificationsEnabled(boolean enabled) {
prefs.edit()
.putBoolean(KEY_NOTIFICATIONS, enabled)
.apply();
}
public boolean isNotificationsEnabled() {
return prefs.getBoolean(KEY_NOTIFICATIONS, true);
}
// Language settings
public void setLanguage(String language) {
prefs.edit()
.putString(KEY_LANGUAGE, language)
.apply();
}
public String getLanguage() {
return prefs.getString(KEY_LANGUAGE, "en");
}
}
Session Management
public class SessionManager {
private static final String PREF_NAME = "UserSession";
private static final String KEY_IS_LOGGED_IN = "isLoggedIn";
private static final String KEY_USER_TOKEN = "userToken";
private static final String KEY_USER_ID = "userId";
private static final String KEY_LOGIN_TIME = "loginTime";
private SharedPreferences pref;
private SharedPreferences.Editor editor;
private Context context;
public SessionManager(Context context) {
this.context = context;
pref = context.getSharedPreferences(PREF_NAME, Context.MODE_PRIVATE);
editor = pref.edit();
}
public void createLoginSession(String token, String userId) {
editor.putBoolean(KEY_IS_LOGGED_IN, true);
editor.putString(KEY_USER_TOKEN, token);
editor.putString(KEY_USER_ID, userId);
editor.putLong(KEY_LOGIN_TIME, System.currentTimeMillis());
editor.commit(); // Save immediately
}
public boolean isLoggedIn() {
return pref.getBoolean(KEY_IS_LOGGED_IN, false);
}
public String getUserToken() {
return pref.getString(KEY_USER_TOKEN, null);
}
public String getUserId() {
return pref.getString(KEY_USER_ID, null);
}
public void logoutUser() {
editor.clear();
editor.apply();
// Redirect to login screen
Intent intent = new Intent(context, LoginActivity.class);
intent.addFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP);
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
context.startActivity(intent);
}
public boolean isSessionExpired() {
long loginTime = pref.getLong(KEY_LOGIN_TIME, 0);
long currentTime = System.currentTimeMillis();
long sessionDuration = 24 * 60 * 60 * 1000; // 24 hours
return (currentTime - loginTime) > sessionDuration;
}
}
Kotlin Usage Example
class PreferenceHelper(context: Context) {
companion object {
private const val PREF_NAME = "MyAppPrefs"
private const val KEY_USER_NAME = "user_name"
private const val KEY_USER_EMAIL = "user_email"
private const val KEY_IS_FIRST_RUN = "is_first_run"
}
private val prefs: SharedPreferences = context.getSharedPreferences(PREF_NAME, Context.MODE_PRIVATE)
var userName: String
get() = prefs.getString(KEY_USER_NAME, "") ?: ""
set(value) = prefs.edit().putString(KEY_USER_NAME, value).apply()
var userEmail: String
get() = prefs.getString(KEY_USER_EMAIL, "") ?: ""
set(value) = prefs.edit().putString(KEY_USER_EMAIL, value).apply()
var isFirstRun: Boolean
get() = prefs.getBoolean(KEY_IS_FIRST_RUN, true)
set(value) = prefs.edit().putBoolean(KEY_IS_FIRST_RUN, value).apply()
fun clearAllData() {
prefs.edit().clear().apply()
}
}
// Usage example
class MainActivity : AppCompatActivity() {
private lateinit var prefHelper: PreferenceHelper
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_main)
prefHelper = PreferenceHelper(this)
// Read and write data
prefHelper.userName = "John Doe"
val name = prefHelper.userName
if (prefHelper.isFirstRun) {
// First launch processing
setupFirstRun()
prefHelper.isFirstRun = false
}
}
}
Change Monitoring with Listener
public class PreferenceWatcher implements SharedPreferences.OnSharedPreferenceChangeListener {
private SharedPreferences prefs;
public void startWatching(Context context) {
prefs = PreferenceManager.getDefaultSharedPreferences(context);
prefs.registerOnSharedPreferenceChangeListener(this);
}
public void stopWatching() {
if (prefs != null) {
prefs.unregisterOnSharedPreferenceChangeListener(this);
}
}
@Override
public void onSharedPreferenceChanged(SharedPreferences sharedPreferences, String key) {
switch (key) {
case "theme_setting":
String newTheme = sharedPreferences.getString(key, "light");
applyTheme(newTheme);
break;
case "notification_enabled":
boolean notificationsEnabled = sharedPreferences.getBoolean(key, true);
updateNotificationSettings(notificationsEnabled);
break;
case "language_setting":
String language = sharedPreferences.getString(key, "en");
updateLanguage(language);
break;
}
}
private void applyTheme(String theme) {
// Theme change processing
}
private void updateNotificationSettings(boolean enabled) {
// Notification settings change processing
}
private void updateLanguage(String language) {
// Language change processing
}
}
Encrypted SharedPreferences
// Using EncryptedSharedPreferences (API 23+)
public class SecurePreferenceManager {
private static final String FILE_NAME = "encrypted_prefs";
private SharedPreferences encryptedPrefs;
public SecurePreferenceManager(Context context) {
try {
MasterKey masterKey = new MasterKey.Builder(context)
.setKeyScheme(MasterKey.KeyScheme.AES256_GCM)
.build();
encryptedPrefs = EncryptedSharedPreferences.create(
context,
FILE_NAME,
masterKey,
EncryptedSharedPreferences.PrefKeyEncryptionScheme.AES256_SIV,
EncryptedSharedPreferences.PrefValueEncryptionScheme.AES256_GCM
);
} catch (Exception e) {
e.printStackTrace();
// Fallback: regular SharedPreferences
encryptedPrefs = context.getSharedPreferences(FILE_NAME, Context.MODE_PRIVATE);
}
}
public void saveSecureData(String key, String value) {
encryptedPrefs.edit()
.putString(key, value)
.apply();
}
public String getSecureData(String key, String defaultValue) {
return encryptedPrefs.getString(key, defaultValue);
}
}