react-native-storage-lens
v0.2.3
Published
a visual inspector for React Native local storage similar to browser DevTools.t Native local storage similar to browser DevTools.act Native local storage similar to browser DevTools.
Readme
react-native-storage-lens 🔍
A visual inspector for React Native local storage with multi-adapter support
📋 Overview
React Native Storage Lens is a developer tool that provides a visual interface to inspect, monitor, and manage local storage in React Native applications - similar to browser DevTools for web applications.
🎯 Use Cases
- 🐛 Debugging: Quickly inspect stored data during development without writing debug logs
- 🧪 QA Testing: Verify data persistence in offline-first applications
- 🔍 Development: Monitor real-time storage changes as you interact with your app
- 📱 Offline-First Apps: Essential for apps with complex local data management
- 🔐 Security Testing: Verify encrypted vs unencrypted data separation
- 👥 Multi-Storage Apps: Manage apps using multiple storage libraries (MMKV, AsyncStorage, Keychain, etc.)
✨ Features
- 📊 Visual Storage Inspector - Browse all stored data in a clean, organized UI
- 🔐 Encrypted/Unencrypted Separation - Clearly distinguish secure vs regular storage
- 🎨 Multi-Adapter Support - Works with MMKV, AsyncStorage, Expo SecureStore, Keychain, and custom adapters
- 📏 Size Analytics - See storage size for each entry (B, KB, MB)
- 🗑️ One-Tap Clear - Remove individual storage entries on the fly
- ♻️ Real-time Refresh - Update storage view without restarting the app
- 🎭 Zero Production Impact - Conditionally enabled only in development
- 🔌 Plugin Architecture - Easily add custom storage adapters
📦 Installation
npm install react-native-storage-lensPeer Dependencies
Make sure you have the storage libraries you want to use installed:
# AsyncStorage
npm install @react-native-async-storage/async-storage
# MMKV
npm install react-native-mmkv
# Expo SecureStore
npx expo install expo-secure-store
# Keychain
npm install react-native-keychain🚀 Quick Start
import { StorageLens, AsyncStorageAdapter } from 'react-native-storage-lens';
import AsyncStorage from '@react-native-async-storage/async-storage';
const App = () => {
const storageLensConfig = {
unencrypted: [
{
adapter: new AsyncStorageAdapter(AsyncStorage),
keys: ['user_preferences', 'app_settings'],
},
],
enabled: __DEV__, // Only show in development
};
return (
<View style={{ flex: 1 }}>
<YourApp />
<StorageLens config={storageLensConfig} />
</View>
);
};📖 Usage Examples
1. AsyncStorage (Unencrypted)
import { StorageLens, AsyncStorageAdapter } from 'react-native-storage-lens';
import AsyncStorage from '@react-native-async-storage/async-storage';
const App = () => {
const storageLensConfig = {
unencrypted: [
{
adapter: new AsyncStorageAdapter(AsyncStorage),
keys: ['user_preferences', 'app_settings', 'cached_data'],
},
],
enabled: __DEV__,
};
return (
<View style={{ flex: 1 }}>
<YourApp />
<StorageLens config={storageLensConfig} />
</View>
);
};2. MMKV
import { StorageLens, MMKVAdapter } from 'react-native-storage-lens';
import { MMKV } from 'react-native-mmkv';
const storage = new MMKV();
const App = () => {
const storageLensConfig = {
unencrypted: [
{
adapter: new MMKVAdapter(storage, false),
keys: ['user_data', 'cache', 'offline_queue'],
},
],
enabled: __DEV__,
};
return (
<View style={{ flex: 1 }}>
<YourApp />
<StorageLens config={storageLensConfig} />
</View>
);
};3. Expo SecureStore (Encrypted)
import { StorageLens, ExpoSecureStoreAdapter } from 'react-native-storage-lens';
import * as SecureStore from 'expo-secure-store';
const App = () => {
const storageLensConfig = {
encrypted: [
{
adapter: new ExpoSecureStoreAdapter(SecureStore),
keys: ['auth_token', 'api_key', 'user_credentials'],
},
],
enabled: __DEV__,
};
return (
<View style={{ flex: 1 }}>
<YourApp />
<StorageLens config={storageLensConfig} />
</View>
);
};4. React Native Keychain (Encrypted)
The Keychain adapter supports the common pattern of storing all data in a single keychain entry:
import { StorageLens, KeychainAdapter } from 'react-native-storage-lens';
import * as Keychain from 'react-native-keychain';
const App = () => {
const storageLensConfig = {
encrypted: [
{
adapter: new KeychainAdapter(Keychain),
keys: ['auth_token', 'api_key', 'encryption_key', 'user_credentials'],
},
],
enabled: __DEV__,
};
return (
<View style={{ flex: 1 }}>
<YourApp />
<StorageLens config={storageLensConfig} />
</View>
);
};Note: The Keychain adapter assumes you're using this storage pattern:
// Your keychain helper functions
import * as Keychain from 'react-native-keychain';
export const saveToSecureStore = async (key: string, value: any) => {
const credentials = await Keychain.getGenericPassword();
const storedData = credentials ? JSON.parse(credentials.password) : {};
storedData[key] = value;
return await Keychain.setGenericPassword('store', JSON.stringify(storedData));
};
export const getFromSecureStore = async <T>(key: string): Promise<T | null> => {
const credentials = await Keychain.getGenericPassword();
if (credentials) {
const storedData = JSON.parse(credentials.password);
return storedData[key] ?? null;
}
return null;
};5. Multiple Adapters (Complete Example)
import {
StorageLens,
AsyncStorageAdapter,
MMKVAdapter,
ExpoSecureStoreAdapter,
KeychainAdapter,
} from 'react-native-storage-lens';
import AsyncStorage from '@react-native-async-storage/async-storage';
import { MMKV } from 'react-native-mmkv';
import * as SecureStore from 'expo-secure-store';
import * as Keychain from 'react-native-keychain';
const storage = new MMKV();
const secureStorage = new MMKV({
id: 'secure-storage',
encryptionKey: 'your-encryption-key',
});
const App = () => {
const storageLensConfig = {
unencrypted: [
{
adapter: new AsyncStorageAdapter(AsyncStorage),
keys: ['user_preferences', 'app_theme', 'language'],
},
{
adapter: new MMKVAdapter(storage, false),
keys: ['cached_articles', 'offline_data', 'search_history'],
},
],
encrypted: [
{
adapter: new MMKVAdapter(secureStorage, true),
keys: ['session_token', 'device_id'],
},
{
adapter: new ExpoSecureStoreAdapter(SecureStore),
keys: ['biometric_key'],
},
{
adapter: new KeychainAdapter(Keychain),
keys: ['auth_token', 'refresh_token', 'api_key'],
},
],
enabled: __DEV__,
};
return (
<View style={{ flex: 1 }}>
<YourApp />
<StorageLens config={storageLensConfig} />
</View>
);
};🎨 Custom Adapter
Create your own adapter by extending BaseAdapter:
import { BaseAdapter } from 'react-native-storage-lens';
class CustomStorageAdapter extends BaseAdapter {
name = 'CustomStorage';
isEncrypted = false;
private customStorage: any;
constructor(customStorageInstance: any) {
super();
this.customStorage = customStorageInstance;
}
async getItem(key: string): Promise<string | null> {
return await this.customStorage.get(key);
}
async getAllKeys(): Promise<string[]> {
return await this.customStorage.keys();
}
async removeItem(key: string): Promise<void> {
await this.customStorage.remove(key);
}
async clear(): Promise<void> {
await this.customStorage.clearAll();
}
}
// Usage
const storageLensConfig = {
unencrypted: [
{
adapter: new CustomStorageAdapter(myCustomStorage),
keys: ['my_custom_key'],
},
],
enabled: __DEV__,
};⚙️ Configuration Options
| Property | Type | Required | Default | Description |
|----------|------|----------|---------|-------------|
| unencrypted | AdapterConfig[] | No | [] | Array of unencrypted storage adapters |
| encrypted | AdapterConfig[] | No | [] | Array of encrypted storage adapters |
| enabled | boolean | No | true | Enable/disable the storage lens |
AdapterConfig
| Property | Type | Required | Description |
|----------|------|----------|-------------|
| adapter | IStorageAdapter | Yes | Storage adapter instance |
| keys | string[] | Yes | Array of storage keys to monitor |
🎯 How It Works
- Add
<StorageLens>component to your app root - Configure adapters for each storage library you use
- Specify keys you want to monitor
- Tap the 🔍 floating button (bottom-right) to open the inspector
- View, refresh, or clear storage entries in real-time
🛡️ Best Practices
✅ Do's
- ✅ Set
enabled: __DEV__to only show in development - ✅ Only include storage keys your app actually uses
- ✅ Use clearly fake/mock data in example apps
- ✅ Separate encrypted and unencrypted data
- ✅ Test storage behavior in offline-first scenarios
❌ Don'ts
- ❌ Never enable in production builds
- ❌ Don't expose real API keys or secrets
- ❌ Don't monitor keys with sensitive production data
- ❌ Don't use for storing passwords in plain text
🎨 UI Preview
The Storage Lens modal displays:
- 📊 Two Sections: Unencrypted and Encrypted data
- 🔑 Key Name: The storage key
- 💾 Value: The stored data (masked if encrypted)
- 📏 Size: Calculated size in B, KB, or MB
- 🏷️ Source: Which adapter/library stored this data (color-coded)
- 🗑️ Clear Button: Remove individual entries
🤝 Contributing
Contributions are welcome! Please feel free to submit a Pull Request.
📄 License
MIT © cmcWebCode40
🔗 Links
🙏 Credits
Built with ❤️ for the React Native community
⭐ If you find this useful, please star the repo! ⭐
