react-native-inapp-inspector 2.2.2 → 2.2.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (159) hide show
  1. package/dist/commonjs/components/AnalyticsDetail.js +5 -1
  2. package/dist/commonjs/components/AnalyticsEventCard.js +2 -1
  3. package/dist/commonjs/components/DiffViewer.js +1 -1
  4. package/dist/commonjs/components/Inspector/BundleTab.js +22 -0
  5. package/dist/commonjs/components/Inspector/DeviceInfoTab.d.ts +3 -0
  6. package/dist/commonjs/components/Inspector/DeviceInfoTab.js +835 -0
  7. package/dist/commonjs/components/Inspector/InspectorHeader.js +12 -14
  8. package/dist/commonjs/components/Inspector/LogDetail.js +6 -3
  9. package/dist/commonjs/components/Inspector/MainScreen.js +7 -3
  10. package/dist/commonjs/components/Inspector/NetworkTab.js +92 -15
  11. package/dist/commonjs/components/Inspector/PerformanceTab.js +38 -12
  12. package/dist/commonjs/components/Inspector/SettingsPanel.js +440 -229
  13. package/dist/commonjs/components/Inspector/StorageTab.d.ts +3 -0
  14. package/dist/commonjs/components/Inspector/StorageTab.js +892 -0
  15. package/dist/commonjs/components/Inspector/TabBar.js +14 -0
  16. package/dist/commonjs/components/Inspector/TelemetryConsentModal.js +11 -2
  17. package/dist/commonjs/components/Inspector/UpdateAvailableModal.js +4 -1
  18. package/dist/commonjs/components/NetworkIcons.d.ts +6 -0
  19. package/dist/commonjs/components/NetworkIcons.js +30 -1
  20. package/dist/commonjs/constants/version.d.ts +1 -1
  21. package/dist/commonjs/constants/version.js +1 -1
  22. package/dist/commonjs/customHooks/bundleAnalyzer.js +44 -22
  23. package/dist/commonjs/customHooks/storageInspector.d.ts +67 -0
  24. package/dist/commonjs/customHooks/storageInspector.js +486 -0
  25. package/dist/commonjs/i18n/locales/en.json +8 -2
  26. package/dist/commonjs/index.d.ts +1 -0
  27. package/dist/commonjs/index.js +16 -1
  28. package/dist/commonjs/storage.d.ts +5 -0
  29. package/dist/commonjs/storage.js +18 -0
  30. package/dist/commonjs/types/enums.d.ts +5 -0
  31. package/dist/commonjs/types/enums.js +5 -0
  32. package/dist/esm/components/AnalyticsDetail.js +6 -2
  33. package/dist/esm/components/AnalyticsEventCard.js +2 -1
  34. package/dist/esm/components/DiffViewer.js +1 -1
  35. package/dist/esm/components/Inspector/BundleTab.js +22 -0
  36. package/dist/esm/components/Inspector/DeviceInfoTab.d.ts +3 -0
  37. package/dist/esm/components/Inspector/DeviceInfoTab.js +796 -0
  38. package/dist/esm/components/Inspector/InspectorHeader.js +13 -15
  39. package/dist/esm/components/Inspector/LogDetail.js +7 -4
  40. package/dist/esm/components/Inspector/MainScreen.js +7 -3
  41. package/dist/esm/components/Inspector/NetworkTab.js +93 -16
  42. package/dist/esm/components/Inspector/PerformanceTab.js +39 -13
  43. package/dist/esm/components/Inspector/SettingsPanel.js +441 -230
  44. package/dist/esm/components/Inspector/StorageTab.d.ts +3 -0
  45. package/dist/esm/components/Inspector/StorageTab.js +853 -0
  46. package/dist/esm/components/Inspector/TabBar.js +15 -1
  47. package/dist/esm/components/Inspector/TelemetryConsentModal.js +11 -2
  48. package/dist/esm/components/Inspector/UpdateAvailableModal.js +4 -1
  49. package/dist/esm/components/NetworkIcons.d.ts +6 -0
  50. package/dist/esm/components/NetworkIcons.js +23 -0
  51. package/dist/esm/constants/version.d.ts +1 -1
  52. package/dist/esm/constants/version.js +1 -1
  53. package/dist/esm/customHooks/bundleAnalyzer.js +44 -22
  54. package/dist/esm/customHooks/storageInspector.d.ts +67 -0
  55. package/dist/esm/customHooks/storageInspector.js +469 -0
  56. package/dist/esm/i18n/locales/en.json +8 -2
  57. package/dist/esm/index.d.ts +1 -0
  58. package/dist/esm/index.js +5 -0
  59. package/dist/esm/storage.d.ts +5 -0
  60. package/dist/esm/storage.js +5 -0
  61. package/dist/esm/types/enums.d.ts +5 -0
  62. package/dist/esm/types/enums.js +5 -0
  63. package/package.json +9 -1
  64. package/src/analytics.ts +35 -0
  65. package/src/bundle.ts +25 -0
  66. package/src/components/AnalyticsDetail.tsx +870 -0
  67. package/src/components/AnalyticsEventCard.tsx +442 -0
  68. package/src/components/AnalyticsGraph.tsx +583 -0
  69. package/src/components/AnimatedEntrance.tsx +64 -0
  70. package/src/components/AppHeaderLogo.tsx +109 -0
  71. package/src/components/BrandCircleIcon.tsx +144 -0
  72. package/src/components/BrandSquareIcon.tsx +144 -0
  73. package/src/components/CodeSnippet.tsx +725 -0
  74. package/src/components/ConsoleLogCard.tsx +628 -0
  75. package/src/components/CopyButton.tsx +87 -0
  76. package/src/components/DiffViewer.tsx +82 -0
  77. package/src/components/DomainHeader.tsx +237 -0
  78. package/src/components/EmptyState.tsx +73 -0
  79. package/src/components/EndOfListFooter.tsx +100 -0
  80. package/src/components/ErrorBoundary.tsx +688 -0
  81. package/src/components/HeadersSection.tsx +192 -0
  82. package/src/components/HighlightText.tsx +100 -0
  83. package/src/components/Inspector/AnalyticsFilterModal.tsx +1250 -0
  84. package/src/components/Inspector/AnalyticsTab.tsx +1336 -0
  85. package/src/components/Inspector/BundleTab.tsx +4760 -0
  86. package/src/components/Inspector/ConsoleTab.tsx +702 -0
  87. package/src/components/Inspector/CrashDetail.tsx +941 -0
  88. package/src/components/Inspector/CrashFilterModal.tsx +721 -0
  89. package/src/components/Inspector/CrashTab.tsx +871 -0
  90. package/src/components/Inspector/DeviceInfoTab.tsx +1204 -0
  91. package/src/components/Inspector/FabLauncher.tsx +80 -0
  92. package/src/components/Inspector/InspectorContext.tsx +28 -0
  93. package/src/components/Inspector/InspectorHeader.tsx +972 -0
  94. package/src/components/Inspector/LogDetail.tsx +1431 -0
  95. package/src/components/Inspector/MainScreen.tsx +262 -0
  96. package/src/components/Inspector/NavigationTracker.tsx +13 -0
  97. package/src/components/Inspector/NetworkDetail.tsx +794 -0
  98. package/src/components/Inspector/NetworkTab.tsx +1183 -0
  99. package/src/components/Inspector/NpmUpdateToast.tsx +392 -0
  100. package/src/components/Inspector/PerformanceTab.tsx +1928 -0
  101. package/src/components/Inspector/ReduxDetail.tsx +1651 -0
  102. package/src/components/Inspector/ReduxTab.tsx +954 -0
  103. package/src/components/Inspector/SettingsPanel.tsx +3447 -0
  104. package/src/components/Inspector/StorageTab.tsx +1048 -0
  105. package/src/components/Inspector/TabBar.tsx +207 -0
  106. package/src/components/Inspector/TelemetryConsentModal.tsx +416 -0
  107. package/src/components/Inspector/UpdateAvailableModal.tsx +557 -0
  108. package/src/components/JsonViewer.tsx +486 -0
  109. package/src/components/LogCard.tsx +491 -0
  110. package/src/components/LogSyntaxHighlighter.tsx +178 -0
  111. package/src/components/MetaAccordion.tsx +340 -0
  112. package/src/components/MiniBarChart.tsx +42 -0
  113. package/src/components/MiniLineChart.tsx +33 -0
  114. package/src/components/NetworkIcons.tsx +2221 -0
  115. package/src/components/SectionHeader.tsx +113 -0
  116. package/src/components/SegmentedTabs.tsx +83 -0
  117. package/src/components/Slider.tsx +300 -0
  118. package/src/components/SourcePageCard.tsx +148 -0
  119. package/src/components/Toast.tsx +131 -0
  120. package/src/components/TouchableScale.tsx +91 -0
  121. package/src/components/TreeNode.tsx +186 -0
  122. package/src/console.ts +24 -0
  123. package/src/constants/index.ts +38 -0
  124. package/src/constants/version.ts +3 -0
  125. package/src/crash.ts +32 -0
  126. package/src/customHooks/analyticsLogger.ts +336 -0
  127. package/src/customHooks/bundleAnalyzer.ts +1256 -0
  128. package/src/customHooks/consoleLogger.ts +497 -0
  129. package/src/customHooks/crashHandler.ts +944 -0
  130. package/src/customHooks/logFilters.ts +32 -0
  131. package/src/customHooks/networkLogger.ts +419 -0
  132. package/src/customHooks/performanceTracker.ts +1014 -0
  133. package/src/customHooks/reduxLogger.ts +406 -0
  134. package/src/customHooks/storageInspector.ts +509 -0
  135. package/src/customHooks/useAccordion.tsx +60 -0
  136. package/src/decorators/index.ts +184 -0
  137. package/src/helpers/gaAnalyticsRegistry.ts +204 -0
  138. package/src/helpers/index.ts +860 -0
  139. package/src/helpers/memoryManager.ts +138 -0
  140. package/src/helpers/searchQueryParser.ts +283 -0
  141. package/src/helpers/settingsStore.ts +171 -0
  142. package/src/helpers/telemetry.ts +505 -0
  143. package/src/helpers/toast.ts +17 -0
  144. package/src/i18n/index.ts +69 -0
  145. package/src/i18n/locales/en.json +1058 -0
  146. package/src/index.tsx +2356 -0
  147. package/src/native/NativeInspector.ts +397 -0
  148. package/src/native/NativeNetworkInspector.ts +24 -0
  149. package/src/network.ts +22 -0
  150. package/src/performance.ts +38 -0
  151. package/src/redux.ts +23 -0
  152. package/src/storage.ts +18 -0
  153. package/src/styles/AppColors.ts +408 -0
  154. package/src/styles/AppFonts.ts +8 -0
  155. package/src/styles/common.ts +209 -0
  156. package/src/styles/index.ts +1570 -0
  157. package/src/types/enums.ts +199 -0
  158. package/src/types/index.ts +34 -0
  159. package/src/types/interfaces.ts +515 -0
@@ -0,0 +1,469 @@
1
+ // Universal In-App Storage Inspector Adapter for AsyncStorage & MMKV
2
+ // Supports automatic module resolution, NativeModules SQLite fallback, custom instances, and full CRUD operations.
3
+ import { NativeModules } from 'react-native';
4
+ // In-memory registered storage references
5
+ let customAsyncStorage = null;
6
+ const customMMKVInstances = new Map();
7
+ // Listeners for storage mutations
8
+ const changeListeners = new Set();
9
+ const notifyChange = () => {
10
+ changeListeners.forEach(listener => {
11
+ try {
12
+ listener();
13
+ }
14
+ catch { }
15
+ });
16
+ };
17
+ /**
18
+ * Register an AsyncStorage instance with the inspector (optional override).
19
+ */
20
+ export const connectAsyncStorage = (storageInstance) => {
21
+ if (storageInstance) {
22
+ customAsyncStorage = storageInstance;
23
+ notifyChange();
24
+ }
25
+ };
26
+ /**
27
+ * Register an MMKV instance with the inspector (optional override).
28
+ */
29
+ export const connectMMKV = (mmkvInstance, id = 'default') => {
30
+ if (mmkvInstance) {
31
+ customMMKVInstances.set(id, mmkvInstance);
32
+ notifyChange();
33
+ }
34
+ };
35
+ /**
36
+ * Native Bridge Fallback for AsyncStorage:
37
+ * Directly interfaces with NativeModules.RNCAsyncStorage without needing JS package imports.
38
+ */
39
+ const getNativeAsyncStorageBridge = () => {
40
+ const nativeModule = NativeModules.RNCAsyncStorage ||
41
+ NativeModules.RNC_AsyncSQLiteDBStorage ||
42
+ NativeModules.AsyncSQLiteDBStorage;
43
+ if (nativeModule) {
44
+ return {
45
+ getAllKeys: () => {
46
+ return new Promise((resolve, reject) => {
47
+ if (typeof nativeModule.getAllKeys !== 'function') {
48
+ resolve([]);
49
+ return;
50
+ }
51
+ nativeModule.getAllKeys((err, keys) => {
52
+ if (err)
53
+ reject(err);
54
+ else
55
+ resolve(keys || []);
56
+ });
57
+ });
58
+ },
59
+ multiGet: (keys) => {
60
+ return new Promise((resolve, reject) => {
61
+ if (typeof nativeModule.multiGet !== 'function') {
62
+ resolve([]);
63
+ return;
64
+ }
65
+ nativeModule.multiGet(keys, (err, result) => {
66
+ if (err)
67
+ reject(err);
68
+ else
69
+ resolve(result || []);
70
+ });
71
+ });
72
+ },
73
+ getItem: (key) => {
74
+ return new Promise((resolve, reject) => {
75
+ if (typeof nativeModule.multiGet !== 'function') {
76
+ resolve(null);
77
+ return;
78
+ }
79
+ nativeModule.multiGet([key], (err, result) => {
80
+ if (err)
81
+ reject(err);
82
+ else
83
+ resolve(result?.[0]?.[1] ?? null);
84
+ });
85
+ });
86
+ },
87
+ setItem: (key, value) => {
88
+ return new Promise((resolve, reject) => {
89
+ if (typeof nativeModule.multiSet !== 'function') {
90
+ resolve();
91
+ return;
92
+ }
93
+ nativeModule.multiSet([[key, value]], (err) => {
94
+ if (err)
95
+ reject(err);
96
+ else
97
+ resolve();
98
+ });
99
+ });
100
+ },
101
+ removeItem: (key) => {
102
+ return new Promise((resolve, reject) => {
103
+ if (typeof nativeModule.multiRemove !== 'function') {
104
+ resolve();
105
+ return;
106
+ }
107
+ nativeModule.multiRemove([key], (err) => {
108
+ if (err)
109
+ reject(err);
110
+ else
111
+ resolve();
112
+ });
113
+ });
114
+ },
115
+ clear: () => {
116
+ return new Promise((resolve, reject) => {
117
+ if (typeof nativeModule.clear !== 'function') {
118
+ resolve();
119
+ return;
120
+ }
121
+ nativeModule.clear((err) => {
122
+ if (err)
123
+ reject(err);
124
+ else
125
+ resolve();
126
+ });
127
+ });
128
+ },
129
+ };
130
+ }
131
+ return null;
132
+ };
133
+ /**
134
+ * Auto-detect AsyncStorage:
135
+ * 1. Explicit connection
136
+ * 2. Global instance
137
+ * 3. Dynamic require '@react-native-async-storage/async-storage'
138
+ * 4. Native Bridge Direct interface
139
+ */
140
+ export const getResolvedAsyncStorage = () => {
141
+ if (customAsyncStorage)
142
+ return customAsyncStorage;
143
+ // 1. Global instances
144
+ try {
145
+ const maybeReq = globalThis?.__inAppAsyncStorage ||
146
+ globalThis?.AsyncStorage ||
147
+ global?.AsyncStorage;
148
+ if (maybeReq && typeof maybeReq.getAllKeys === 'function') {
149
+ return maybeReq;
150
+ }
151
+ }
152
+ catch { }
153
+ // 2. Dynamic runtime require
154
+ try {
155
+ const req = typeof globalThis?.require === 'function'
156
+ ? globalThis.require
157
+ : typeof require === 'function'
158
+ ? require
159
+ : null;
160
+ if (req) {
161
+ try {
162
+ const mod = req('@react-native-async-storage/async-storage');
163
+ const resolved = mod?.default || mod;
164
+ if (resolved && typeof resolved.getAllKeys === 'function') {
165
+ return resolved;
166
+ }
167
+ }
168
+ catch { }
169
+ try {
170
+ const legacyMod = req('@react-native-community/async-storage');
171
+ const resolved = legacyMod?.default || legacyMod;
172
+ if (resolved && typeof resolved.getAllKeys === 'function') {
173
+ return resolved;
174
+ }
175
+ }
176
+ catch { }
177
+ }
178
+ }
179
+ catch { }
180
+ // 3. Native Bridge Fallback (Direct SQLite)
181
+ const nativeBridge = getNativeAsyncStorageBridge();
182
+ if (nativeBridge) {
183
+ return nativeBridge;
184
+ }
185
+ return null;
186
+ };
187
+ /**
188
+ * Auto-detect MMKV:
189
+ * 1. Explicit connection
190
+ * 2. Dynamic require 'react-native-mmkv' & instantiate default instance
191
+ * 3. Global MMKV / JSI instances
192
+ */
193
+ export const getResolvedMMKV = (id = 'default') => {
194
+ if (customMMKVInstances.has(id)) {
195
+ return customMMKVInstances.get(id);
196
+ }
197
+ // 1. Dynamic require
198
+ try {
199
+ const req = typeof globalThis?.require === 'function'
200
+ ? globalThis.require
201
+ : typeof require === 'function'
202
+ ? require
203
+ : null;
204
+ if (req) {
205
+ const mmkvMod = req('react-native-mmkv');
206
+ const MMKVClass = mmkvMod?.MMKV || mmkvMod?.default?.MMKV;
207
+ if (MMKVClass && typeof MMKVClass === 'function') {
208
+ if (!customMMKVInstances.has('default')) {
209
+ try {
210
+ const defaultInst = new MMKVClass();
211
+ customMMKVInstances.set('default', defaultInst);
212
+ }
213
+ catch { }
214
+ }
215
+ }
216
+ }
217
+ }
218
+ catch { }
219
+ // 2. Global references
220
+ try {
221
+ const globalMMKV = globalThis?.mmkv ||
222
+ global?.mmkv ||
223
+ globalThis?.__MMKV__;
224
+ if (globalMMKV && typeof globalMMKV.getAllKeys === 'function') {
225
+ if (!customMMKVInstances.has('default')) {
226
+ customMMKVInstances.set('default', globalMMKV);
227
+ }
228
+ }
229
+ }
230
+ catch { }
231
+ if (customMMKVInstances.has(id)) {
232
+ return customMMKVInstances.get(id);
233
+ }
234
+ if (customMMKVInstances.size > 0) {
235
+ return customMMKVInstances.values().next().value;
236
+ }
237
+ return null;
238
+ };
239
+ export const isAsyncStorageConnected = () => {
240
+ return Boolean(getResolvedAsyncStorage());
241
+ };
242
+ export const isMMKVConnected = () => {
243
+ return Boolean(getResolvedMMKV());
244
+ };
245
+ export const getRegisteredMMKVInstanceIds = () => {
246
+ getResolvedMMKV(); // trigger auto-discovery
247
+ return Array.from(customMMKVInstances.keys());
248
+ };
249
+ /**
250
+ * Calculate approximate byte size of a UTF-8 string
251
+ */
252
+ export const calculateByteSize = (str) => {
253
+ if (!str)
254
+ return 0;
255
+ return str.length * 2;
256
+ };
257
+ /**
258
+ * Determine type and format value safely
259
+ */
260
+ export const analyzeStorageValue = (rawVal) => {
261
+ if (rawVal === null || rawVal === undefined) {
262
+ return { strVal: 'null', type: 'null', byteSize: 4 };
263
+ }
264
+ const strVal = typeof rawVal === 'string' ? rawVal : String(rawVal);
265
+ const byteSize = calculateByteSize(strVal);
266
+ if (typeof rawVal === 'number') {
267
+ return { strVal, parsedVal: rawVal, type: 'number', byteSize };
268
+ }
269
+ if (typeof rawVal === 'boolean') {
270
+ return { strVal, parsedVal: rawVal, type: 'boolean', byteSize };
271
+ }
272
+ const trimmed = strVal.trim();
273
+ if ((trimmed.startsWith('{') && trimmed.endsWith('}')) ||
274
+ (trimmed.startsWith('[') && trimmed.endsWith(']'))) {
275
+ try {
276
+ const parsed = JSON.parse(trimmed);
277
+ return { strVal, parsedVal: parsed, type: 'json', byteSize };
278
+ }
279
+ catch { }
280
+ }
281
+ if (trimmed === 'true' || trimmed === 'false') {
282
+ return { strVal, parsedVal: trimmed === 'true', type: 'boolean', byteSize };
283
+ }
284
+ if (!isNaN(Number(trimmed)) && trimmed !== '') {
285
+ return { strVal, parsedVal: Number(trimmed), type: 'number', byteSize };
286
+ }
287
+ return { strVal, type: 'string', byteSize };
288
+ };
289
+ /**
290
+ * Fetch all storage entries for given driver
291
+ */
292
+ export const fetchStorageEntries = async (driver, instanceId) => {
293
+ const entries = [];
294
+ if (driver === 'asyncStorage') {
295
+ const storage = getResolvedAsyncStorage();
296
+ if (!storage || typeof storage.getAllKeys !== 'function') {
297
+ return [];
298
+ }
299
+ try {
300
+ const keys = await storage.getAllKeys();
301
+ if (!keys || keys.length === 0)
302
+ return [];
303
+ if (typeof storage.multiGet === 'function') {
304
+ const pairs = await storage.multiGet(keys);
305
+ for (const [k, v] of pairs) {
306
+ const analysis = analyzeStorageValue(v);
307
+ entries.push({
308
+ key: k,
309
+ value: analysis.strVal,
310
+ parsedValue: analysis.parsedVal,
311
+ type: analysis.type,
312
+ byteSize: analysis.byteSize,
313
+ });
314
+ }
315
+ }
316
+ else {
317
+ for (const k of keys) {
318
+ const v = await storage.getItem(k);
319
+ const analysis = analyzeStorageValue(v);
320
+ entries.push({
321
+ key: k,
322
+ value: analysis.strVal,
323
+ parsedValue: analysis.parsedVal,
324
+ type: analysis.type,
325
+ byteSize: analysis.byteSize,
326
+ });
327
+ }
328
+ }
329
+ }
330
+ catch (err) {
331
+ console.warn('[StorageInspector] Error reading AsyncStorage keys:', err);
332
+ }
333
+ }
334
+ else if (driver === 'mmkv') {
335
+ const mmkv = getResolvedMMKV(instanceId);
336
+ if (!mmkv || typeof mmkv.getAllKeys !== 'function') {
337
+ return [];
338
+ }
339
+ try {
340
+ const keys = mmkv.getAllKeys();
341
+ for (const k of keys) {
342
+ let rawVal = null;
343
+ if (typeof mmkv.getString === 'function') {
344
+ rawVal = mmkv.getString(k);
345
+ }
346
+ if (rawVal === undefined || rawVal === null) {
347
+ if (typeof mmkv.getNumber === 'function') {
348
+ const num = mmkv.getNumber(k);
349
+ if (num !== undefined && !isNaN(num))
350
+ rawVal = num;
351
+ }
352
+ }
353
+ if (rawVal === undefined || rawVal === null) {
354
+ if (typeof mmkv.getBoolean === 'function') {
355
+ const bool = mmkv.getBoolean(k);
356
+ if (bool !== undefined)
357
+ rawVal = bool;
358
+ }
359
+ }
360
+ const analysis = analyzeStorageValue(rawVal);
361
+ entries.push({
362
+ key: k,
363
+ value: analysis.strVal,
364
+ parsedValue: analysis.parsedVal,
365
+ type: analysis.type,
366
+ byteSize: analysis.byteSize,
367
+ });
368
+ }
369
+ }
370
+ catch (err) {
371
+ console.warn('[StorageInspector] Error reading MMKV keys:', err);
372
+ }
373
+ }
374
+ // Sort alphabetically by key
375
+ entries.sort((a, b) => a.key.localeCompare(b.key));
376
+ return entries;
377
+ };
378
+ /**
379
+ * Create or Update a key-value entry (CRUD: Create / Update)
380
+ */
381
+ export const setStorageEntry = async (driver, key, value, instanceId) => {
382
+ if (!key.trim())
383
+ return false;
384
+ try {
385
+ if (driver === 'asyncStorage') {
386
+ const storage = getResolvedAsyncStorage();
387
+ if (!storage || typeof storage.setItem !== 'function')
388
+ return false;
389
+ await storage.setItem(key.trim(), value);
390
+ notifyChange();
391
+ return true;
392
+ }
393
+ else if (driver === 'mmkv') {
394
+ const mmkv = getResolvedMMKV(instanceId);
395
+ if (!mmkv || typeof mmkv.set !== 'function')
396
+ return false;
397
+ mmkv.set(key.trim(), value);
398
+ notifyChange();
399
+ return true;
400
+ }
401
+ }
402
+ catch (err) {
403
+ console.warn('[StorageInspector] Error setting storage item:', err);
404
+ }
405
+ return false;
406
+ };
407
+ /**
408
+ * Delete a single key (CRUD: Delete)
409
+ */
410
+ export const removeStorageEntry = async (driver, key, instanceId) => {
411
+ try {
412
+ if (driver === 'asyncStorage') {
413
+ const storage = getResolvedAsyncStorage();
414
+ if (!storage || typeof storage.removeItem !== 'function')
415
+ return false;
416
+ await storage.removeItem(key);
417
+ notifyChange();
418
+ return true;
419
+ }
420
+ else if (driver === 'mmkv') {
421
+ const mmkv = getResolvedMMKV(instanceId);
422
+ if (!mmkv || typeof mmkv.delete !== 'function')
423
+ return false;
424
+ mmkv.delete(key);
425
+ notifyChange();
426
+ return true;
427
+ }
428
+ }
429
+ catch (err) {
430
+ console.warn('[StorageInspector] Error removing storage item:', err);
431
+ }
432
+ return false;
433
+ };
434
+ /**
435
+ * Wipe all keys for given storage (CRUD: Clear All)
436
+ */
437
+ export const clearStorageDriver = async (driver, instanceId) => {
438
+ try {
439
+ if (driver === 'asyncStorage') {
440
+ const storage = getResolvedAsyncStorage();
441
+ if (!storage || typeof storage.clear !== 'function')
442
+ return false;
443
+ await storage.clear();
444
+ notifyChange();
445
+ return true;
446
+ }
447
+ else if (driver === 'mmkv') {
448
+ const mmkv = getResolvedMMKV(instanceId);
449
+ if (!mmkv || typeof mmkv.clearAll !== 'function')
450
+ return false;
451
+ mmkv.clearAll();
452
+ notifyChange();
453
+ return true;
454
+ }
455
+ }
456
+ catch (err) {
457
+ console.warn('[StorageInspector] Error clearing storage:', err);
458
+ }
459
+ return false;
460
+ };
461
+ /**
462
+ * Subscribe to storage mutations
463
+ */
464
+ export const subscribeToStorageChanges = (listener) => {
465
+ changeListeners.add(listener);
466
+ return () => {
467
+ changeListeners.delete(listener);
468
+ };
469
+ };
@@ -36,7 +36,12 @@
36
36
  "apis": "APIs",
37
37
  "logs": "Logs",
38
38
  "analytics": "Analytics",
39
- "redux": "Redux"
39
+ "redux": "Redux",
40
+ "bundle": "Bundle",
41
+ "performance": "Performance",
42
+ "crash": "Crash",
43
+ "device": "Device",
44
+ "storage": "Storage"
40
45
  },
41
46
  "settings": {
42
47
  "mainTitle": "Settings & Modules",
@@ -51,7 +56,8 @@
51
56
  "dormantBadge": "DORMANT",
52
57
  "protectedBadge": "PROTECTED",
53
58
  "modulesAndTools": "Modules & Tools",
54
- "uiPreferences": "UI Preferences",
59
+ "uiPreferences": "UI & Display",
60
+ "ramLimits": "RAM & Limits",
55
61
  "zeroOverheadTitle": "Zero Background Overhead",
56
62
  "zeroOverheadDesc": "Check the modules you wish to activate. Disabled modules consume 0% CPU & memory until saved.",
57
63
  "unsavedPending": "● Unsaved selections pending",
@@ -21,4 +21,5 @@ export { setMaxAnalyticsLogsLimit, getMaxAnalyticsLogsLimit, pruneAnalyticsLogs,
21
21
  export { getMaxCrashLogsLimit, pruneCrashRecords, } from './customHooks/crashHandler';
22
22
  export { setMaxPerformanceEventsLimit, getMaxPerformanceEventsLimit, prunePerformanceEvents, } from './customHooks/performanceTracker';
23
23
  export { BrandSquareIcon, BrandCircleIcon, } from './components/NetworkIcons';
24
+ export { connectAsyncStorage, connectMMKV, isAsyncStorageConnected, isMMKVConnected, getRegisteredMMKVInstanceIds, fetchStorageEntries, setStorageEntry, removeStorageEntry, clearStorageDriver, subscribeToStorageChanges, type StorageEntry, type StorageDriver, } from './customHooks/storageInspector';
24
25
  export { ActiveTab, Method, StatusFilter, SortOrder, LocalFilter, ModalAnimationType, SettingsPage, SettingsSubTab, LogFilter, ConsoleLogType, AnalyticsEventSource, GAEventCategory, StackFrameType, DiffResultType, BundleSubTab, PerformanceSubTab, CrashType, CrashExportFormat, CrashDetailSubTab, CrashFilterType, BreadcrumbType, } from './types';
package/dist/esm/index.js CHANGED
@@ -183,6 +183,8 @@ const NetworkInspector = ({ enabled = true, isEnabled = true, storage, navigatio
183
183
  bundle: false,
184
184
  performance: false,
185
185
  crash: false,
186
+ device: true,
187
+ storage: true,
186
188
  });
187
189
  const [maxNetworkLogs, setMaxNetworkLogs] = useState(100);
188
190
  const [maxAnalyticsEventsLimit, setMaxAnalyticsEventsLimit] = useState(75);
@@ -237,6 +239,8 @@ const NetworkInspector = ({ enabled = true, isEnabled = true, storage, navigatio
237
239
  bundle: false,
238
240
  performance: false,
239
241
  crash: false,
242
+ device: true,
243
+ storage: true,
240
244
  });
241
245
  setDefaultTab('apis');
242
246
  setIsAutoRamLimitEnabled(true);
@@ -1828,4 +1832,5 @@ export { setMaxAnalyticsLogsLimit, getMaxAnalyticsLogsLimit, pruneAnalyticsLogs,
1828
1832
  export { getMaxCrashLogsLimit, pruneCrashRecords, } from './customHooks/crashHandler';
1829
1833
  export { setMaxPerformanceEventsLimit, getMaxPerformanceEventsLimit, prunePerformanceEvents, } from './customHooks/performanceTracker';
1830
1834
  export { BrandSquareIcon, BrandCircleIcon, } from './components/NetworkIcons';
1835
+ export { connectAsyncStorage, connectMMKV, isAsyncStorageConnected, isMMKVConnected, getRegisteredMMKVInstanceIds, fetchStorageEntries, setStorageEntry, removeStorageEntry, clearStorageDriver, subscribeToStorageChanges, } from './customHooks/storageInspector';
1831
1836
  export { ActiveTab, Method, StatusFilter, SortOrder, LocalFilter, ModalAnimationType, SettingsPage, SettingsSubTab, LogFilter, ConsoleLogType, AnalyticsEventSource, GAEventCategory, StackFrameType, DiffResultType, BundleSubTab, PerformanceSubTab, CrashType, CrashExportFormat, CrashDetailSubTab, CrashFilterType, BreadcrumbType, } from './types';
@@ -0,0 +1,5 @@
1
+ /**
2
+ * Sub-module entry point: react-native-inapp-inspector/storage
3
+ * Universal AsyncStorage and MMKV live inspector with full CRUD operations.
4
+ */
5
+ export { connectAsyncStorage, connectMMKV, isAsyncStorageConnected, isMMKVConnected, getRegisteredMMKVInstanceIds, fetchStorageEntries, setStorageEntry, removeStorageEntry, clearStorageDriver, subscribeToStorageChanges, type StorageEntry, type StorageDriver, } from './customHooks/storageInspector';
@@ -0,0 +1,5 @@
1
+ /**
2
+ * Sub-module entry point: react-native-inapp-inspector/storage
3
+ * Universal AsyncStorage and MMKV live inspector with full CRUD operations.
4
+ */
5
+ export { connectAsyncStorage, connectMMKV, isAsyncStorageConnected, isMMKVConnected, getRegisteredMMKVInstanceIds, fetchStorageEntries, setStorageEntry, removeStorageEntry, clearStorageDriver, subscribeToStorageChanges, } from './customHooks/storageInspector';
@@ -6,6 +6,8 @@ export declare const ActiveTab: {
6
6
  readonly Bundle: "bundle";
7
7
  readonly Performance: "performance";
8
8
  readonly Crash: "crash";
9
+ readonly Device: "device";
10
+ readonly Storage: "storage";
9
11
  };
10
12
  export type ActiveTab = (typeof ActiveTab)[keyof typeof ActiveTab];
11
13
  export declare const Method: {
@@ -52,11 +54,14 @@ export declare const SettingsPage: {
52
54
  readonly Bundle: "bundle";
53
55
  readonly Performance: "performance";
54
56
  readonly Crash: "crash";
57
+ readonly Device: "device";
58
+ readonly Storage: "storage";
55
59
  };
56
60
  export type SettingsPage = (typeof SettingsPage)[keyof typeof SettingsPage] | null;
57
61
  export declare const SettingsSubTab: {
58
62
  readonly Module: "module";
59
63
  readonly Ui: "ui";
64
+ readonly Limits: "limits";
60
65
  };
61
66
  export type SettingsSubTab = (typeof SettingsSubTab)[keyof typeof SettingsSubTab];
62
67
  export declare const LogFilter: {
@@ -9,6 +9,8 @@ export const ActiveTab = {
9
9
  Bundle: 'bundle',
10
10
  Performance: 'performance',
11
11
  Crash: 'crash',
12
+ Device: 'device',
13
+ Storage: 'storage',
12
14
  };
13
15
  export const Method = {
14
16
  All: 'ALL',
@@ -49,10 +51,13 @@ export const SettingsPage = {
49
51
  Bundle: 'bundle',
50
52
  Performance: 'performance',
51
53
  Crash: 'crash',
54
+ Device: 'device',
55
+ Storage: 'storage',
52
56
  };
53
57
  export const SettingsSubTab = {
54
58
  Module: 'module',
55
59
  Ui: 'ui',
60
+ Limits: 'limits',
56
61
  };
57
62
  export const LogFilter = {
58
63
  All: 'all',
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "react-native-inapp-inspector",
3
- "version": "2.2.2",
3
+ "version": "2.2.4",
4
4
  "description": "The zero-config, all-in-one in-app debugger for React Native & Expo. Inspect Network (fetch/axios), Console logs, Stack Traces, Redux State, Firebase Analytics, and JS Bundle size directly on device.",
5
5
  "repository": {
6
6
  "type": "git",
@@ -73,10 +73,18 @@
73
73
  "require": "./dist/commonjs/bundle.js",
74
74
  "default": "./dist/commonjs/bundle.js"
75
75
  },
76
+ "./storage": {
77
+ "react-native": "./dist/commonjs/storage.js",
78
+ "types": "./dist/commonjs/storage.d.ts",
79
+ "import": "./dist/esm/storage.js",
80
+ "require": "./dist/commonjs/storage.js",
81
+ "default": "./dist/commonjs/storage.js"
82
+ },
76
83
  "./package.json": "./package.json"
77
84
  },
78
85
  "files": [
79
86
  "dist",
87
+ "src",
80
88
  "README.md",
81
89
  "android",
82
90
  "ios",
@@ -0,0 +1,35 @@
1
+ /**
2
+ * Sub-module entry point: react-native-inapp-inspector/analytics
3
+ * Clean tree-shaking & isolated Firebase/custom Analytics logger.
4
+ */
5
+ export {
6
+ setupAnalyticsLogger,
7
+ autoSetupAnalyticsLogger,
8
+ logAnalyticsEvent,
9
+ subscribeAnalyticsEvents,
10
+ clearAnalyticsEvents,
11
+ getAnalyticsEvents,
12
+ isAnalyticsConnected,
13
+ isFirebaseAnalyticsPatched,
14
+ setAnalyticsModuleEnabled,
15
+ getAnalyticsModuleEnabled,
16
+ getCurrentUserProperties,
17
+ getCurrentUserId,
18
+ getDefaultEventParameters,
19
+ getCollectionEnabled,
20
+ setMaxAnalyticsLogsLimit,
21
+ getMaxAnalyticsLogsLimit,
22
+ pruneAnalyticsLogs,
23
+ } from './customHooks/analyticsLogger';
24
+
25
+ export {
26
+ getEventCategory,
27
+ registerGAPlugin,
28
+ type GAPlugin,
29
+ } from './helpers/gaAnalyticsRegistry';
30
+
31
+ export type {
32
+ AnalyticsEvent,
33
+ AnalyticsEventSource,
34
+ GAEventCategory,
35
+ } from './types';
package/src/bundle.ts ADDED
@@ -0,0 +1,25 @@
1
+ /**
2
+ * Sub-module entry point: react-native-inapp-inspector/bundle
3
+ * Clean tree-shaking & isolated JS bundle size analyzer.
4
+ */
5
+ export {
6
+ analyzeHostAppBundle,
7
+ parseBundleSource,
8
+ getInitialBundleAnalysis,
9
+ getCachedBundleAnalysis,
10
+ clearCachedBundleAnalysis,
11
+ setBundleModuleEnabled,
12
+ getBundleModuleEnabled,
13
+ getHostScriptURL,
14
+ trackRuntimeModuleExecution,
15
+ trackRuntimeDefine,
16
+ type HostBundleAnalysisResult,
17
+ type HostBundleFileItem,
18
+ type HostBundlePackageItem,
19
+ type HostBinaryComponentItem,
20
+ type FileTypeCategory,
21
+ } from './customHooks/bundleAnalyzer';
22
+
23
+ export {
24
+ BundleSubTab,
25
+ } from './types';