@mostly-good-metrics/react-native 0.1.0
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.
- package/README.md +228 -0
- package/lib/commonjs/index.js +267 -0
- package/lib/commonjs/index.js.map +1 -0
- package/lib/commonjs/storage.js +161 -0
- package/lib/commonjs/storage.js.map +1 -0
- package/lib/module/index.js +261 -0
- package/lib/module/index.js.map +1 -0
- package/lib/module/storage.js +152 -0
- package/lib/module/storage.js.map +1 -0
- package/lib/typescript/src/index.d.ts +51 -0
- package/lib/typescript/src/index.d.ts.map +1 -0
- package/lib/typescript/src/storage.d.ts +32 -0
- package/lib/typescript/src/storage.d.ts.map +1 -0
- package/package.json +86 -0
- package/src/index.ts +308 -0
- package/src/storage.ts +171 -0
|
@@ -0,0 +1,261 @@
|
|
|
1
|
+
import { AppState, Platform } from 'react-native';
|
|
2
|
+
import { MostlyGoodMetrics as MGMClient, SystemEvents, SystemProperties } from '@mostly-good-metrics/javascript';
|
|
3
|
+
import { AsyncStorageEventStorage, persistence, getStorageType } from './storage';
|
|
4
|
+
// Use global to persist state across hot reloads
|
|
5
|
+
const g = globalThis;
|
|
6
|
+
|
|
7
|
+
// Initialize or restore state
|
|
8
|
+
if (!g.__MGM_RN_STATE__) {
|
|
9
|
+
g.__MGM_RN_STATE__ = {
|
|
10
|
+
appStateSubscription: null,
|
|
11
|
+
isConfigured: false,
|
|
12
|
+
currentAppState: AppState.currentState,
|
|
13
|
+
debugLogging: false,
|
|
14
|
+
lastLifecycleEvent: null
|
|
15
|
+
};
|
|
16
|
+
}
|
|
17
|
+
const state = g.__MGM_RN_STATE__;
|
|
18
|
+
const DEDUPE_INTERVAL_MS = 1000; // Ignore duplicate events within 1 second
|
|
19
|
+
|
|
20
|
+
function log(...args) {
|
|
21
|
+
if (state.debugLogging) {
|
|
22
|
+
console.log('[MostlyGoodMetrics]', ...args);
|
|
23
|
+
}
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
/**
|
|
27
|
+
* Track a lifecycle event with deduplication.
|
|
28
|
+
*/
|
|
29
|
+
function trackLifecycleEvent(eventName, properties) {
|
|
30
|
+
const now = Date.now();
|
|
31
|
+
|
|
32
|
+
// Deduplicate events that fire multiple times in quick succession
|
|
33
|
+
if (state.lastLifecycleEvent && state.lastLifecycleEvent.name === eventName && now - state.lastLifecycleEvent.time < DEDUPE_INTERVAL_MS) {
|
|
34
|
+
log(`Skipping duplicate ${eventName} (${now - state.lastLifecycleEvent.time}ms ago)`);
|
|
35
|
+
return;
|
|
36
|
+
}
|
|
37
|
+
state.lastLifecycleEvent = {
|
|
38
|
+
name: eventName,
|
|
39
|
+
time: now
|
|
40
|
+
};
|
|
41
|
+
log(`Tracking lifecycle event: ${eventName}`);
|
|
42
|
+
MGMClient.track(eventName, properties);
|
|
43
|
+
}
|
|
44
|
+
|
|
45
|
+
/**
|
|
46
|
+
* Handle app state changes for lifecycle tracking.
|
|
47
|
+
*/
|
|
48
|
+
function handleAppStateChange(nextAppState) {
|
|
49
|
+
if (!MGMClient.shared) return;
|
|
50
|
+
log(`AppState change: ${state.currentAppState} -> ${nextAppState}`);
|
|
51
|
+
|
|
52
|
+
// App came to foreground
|
|
53
|
+
if (state.currentAppState.match(/inactive|background/) && nextAppState === 'active') {
|
|
54
|
+
trackLifecycleEvent(SystemEvents.APP_OPENED);
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
// App went to background
|
|
58
|
+
if (state.currentAppState === 'active' && nextAppState.match(/inactive|background/)) {
|
|
59
|
+
trackLifecycleEvent(SystemEvents.APP_BACKGROUNDED);
|
|
60
|
+
// Flush events when going to background
|
|
61
|
+
MGMClient.flush().catch(e => log('Flush error:', e));
|
|
62
|
+
}
|
|
63
|
+
state.currentAppState = nextAppState;
|
|
64
|
+
}
|
|
65
|
+
|
|
66
|
+
/**
|
|
67
|
+
* Track app install or update events.
|
|
68
|
+
*/
|
|
69
|
+
async function trackInstallOrUpdate(appVersion) {
|
|
70
|
+
if (!appVersion) return;
|
|
71
|
+
const previousVersion = await persistence.getAppVersion();
|
|
72
|
+
const isFirst = await persistence.isFirstLaunch();
|
|
73
|
+
if (isFirst) {
|
|
74
|
+
trackLifecycleEvent(SystemEvents.APP_INSTALLED, {
|
|
75
|
+
[SystemProperties.VERSION]: appVersion
|
|
76
|
+
});
|
|
77
|
+
await persistence.setAppVersion(appVersion);
|
|
78
|
+
} else if (previousVersion && previousVersion !== appVersion) {
|
|
79
|
+
trackLifecycleEvent(SystemEvents.APP_UPDATED, {
|
|
80
|
+
[SystemProperties.VERSION]: appVersion,
|
|
81
|
+
[SystemProperties.PREVIOUS_VERSION]: previousVersion
|
|
82
|
+
});
|
|
83
|
+
await persistence.setAppVersion(appVersion);
|
|
84
|
+
} else if (!previousVersion) {
|
|
85
|
+
await persistence.setAppVersion(appVersion);
|
|
86
|
+
}
|
|
87
|
+
}
|
|
88
|
+
|
|
89
|
+
/**
|
|
90
|
+
* MostlyGoodMetrics React Native SDK
|
|
91
|
+
*/
|
|
92
|
+
const MostlyGoodMetrics = {
|
|
93
|
+
/**
|
|
94
|
+
* Configure the SDK with an API key and optional settings.
|
|
95
|
+
*/
|
|
96
|
+
configure(apiKey, config = {}) {
|
|
97
|
+
// Check both our state and the underlying JS SDK
|
|
98
|
+
if (state.isConfigured || MGMClient.isConfigured) {
|
|
99
|
+
log('Already configured, skipping');
|
|
100
|
+
return;
|
|
101
|
+
}
|
|
102
|
+
state.debugLogging = config.enableDebugLogging ?? false;
|
|
103
|
+
log('Configuring with options:', config);
|
|
104
|
+
|
|
105
|
+
// Create AsyncStorage-based storage
|
|
106
|
+
const storage = new AsyncStorageEventStorage(config.maxStoredEvents);
|
|
107
|
+
|
|
108
|
+
// Restore user ID from storage
|
|
109
|
+
persistence.getUserId().then(userId => {
|
|
110
|
+
if (userId) {
|
|
111
|
+
log('Restored user ID:', userId);
|
|
112
|
+
}
|
|
113
|
+
});
|
|
114
|
+
|
|
115
|
+
// Configure the JS SDK
|
|
116
|
+
// Disable its built-in lifecycle tracking since we handle it ourselves
|
|
117
|
+
MGMClient.configure({
|
|
118
|
+
apiKey,
|
|
119
|
+
...config,
|
|
120
|
+
storage,
|
|
121
|
+
osVersion: getOSVersion(),
|
|
122
|
+
trackAppLifecycleEvents: false // We handle this with AppState
|
|
123
|
+
});
|
|
124
|
+
state.isConfigured = true;
|
|
125
|
+
|
|
126
|
+
// Set up React Native lifecycle tracking
|
|
127
|
+
if (config.trackAppLifecycleEvents !== false) {
|
|
128
|
+
log('Setting up lifecycle tracking, currentAppState:', state.currentAppState);
|
|
129
|
+
|
|
130
|
+
// Remove any existing listener (in case of hot reload)
|
|
131
|
+
if (state.appStateSubscription) {
|
|
132
|
+
state.appStateSubscription.remove();
|
|
133
|
+
state.appStateSubscription = null;
|
|
134
|
+
}
|
|
135
|
+
|
|
136
|
+
// Track initial app open
|
|
137
|
+
trackLifecycleEvent(SystemEvents.APP_OPENED);
|
|
138
|
+
|
|
139
|
+
// Track install/update
|
|
140
|
+
trackInstallOrUpdate(config.appVersion).catch(e => log('Install/update tracking error:', e));
|
|
141
|
+
|
|
142
|
+
// Subscribe to app state changes
|
|
143
|
+
state.appStateSubscription = AppState.addEventListener('change', handleAppStateChange);
|
|
144
|
+
}
|
|
145
|
+
},
|
|
146
|
+
/**
|
|
147
|
+
* Track an event with optional properties.
|
|
148
|
+
*/
|
|
149
|
+
track(name, properties) {
|
|
150
|
+
if (!state.isConfigured) {
|
|
151
|
+
console.warn('[MostlyGoodMetrics] SDK not configured. Call configure() first.');
|
|
152
|
+
return;
|
|
153
|
+
}
|
|
154
|
+
|
|
155
|
+
// Add React Native specific properties
|
|
156
|
+
const enrichedProperties = {
|
|
157
|
+
[SystemProperties.DEVICE_TYPE]: getDeviceType(),
|
|
158
|
+
$storage_type: getStorageType(),
|
|
159
|
+
...properties
|
|
160
|
+
};
|
|
161
|
+
MGMClient.track(name, enrichedProperties);
|
|
162
|
+
},
|
|
163
|
+
/**
|
|
164
|
+
* Identify a user.
|
|
165
|
+
*/
|
|
166
|
+
identify(userId) {
|
|
167
|
+
if (!state.isConfigured) {
|
|
168
|
+
console.warn('[MostlyGoodMetrics] SDK not configured. Call configure() first.');
|
|
169
|
+
return;
|
|
170
|
+
}
|
|
171
|
+
log('Identifying user:', userId);
|
|
172
|
+
MGMClient.identify(userId);
|
|
173
|
+
// Also persist to AsyncStorage for restoration
|
|
174
|
+
persistence.setUserId(userId).catch(e => log('Failed to persist user ID:', e));
|
|
175
|
+
},
|
|
176
|
+
/**
|
|
177
|
+
* Clear the current user identity.
|
|
178
|
+
*/
|
|
179
|
+
resetIdentity() {
|
|
180
|
+
if (!state.isConfigured) return;
|
|
181
|
+
log('Resetting identity');
|
|
182
|
+
MGMClient.resetIdentity();
|
|
183
|
+
persistence.setUserId(null).catch(e => log('Failed to clear user ID:', e));
|
|
184
|
+
},
|
|
185
|
+
/**
|
|
186
|
+
* Manually flush pending events to the server.
|
|
187
|
+
*/
|
|
188
|
+
flush() {
|
|
189
|
+
if (!state.isConfigured) return;
|
|
190
|
+
log('Flushing events');
|
|
191
|
+
MGMClient.flush().catch(e => log('Flush error:', e));
|
|
192
|
+
},
|
|
193
|
+
/**
|
|
194
|
+
* Start a new session with a fresh session ID.
|
|
195
|
+
*/
|
|
196
|
+
startNewSession() {
|
|
197
|
+
if (!state.isConfigured) return;
|
|
198
|
+
log('Starting new session');
|
|
199
|
+
MGMClient.startNewSession();
|
|
200
|
+
},
|
|
201
|
+
/**
|
|
202
|
+
* Clear all pending events without sending them.
|
|
203
|
+
*/
|
|
204
|
+
clearPendingEvents() {
|
|
205
|
+
if (!state.isConfigured) return;
|
|
206
|
+
log('Clearing pending events');
|
|
207
|
+
MGMClient.clearPendingEvents().catch(e => log('Clear error:', e));
|
|
208
|
+
},
|
|
209
|
+
/**
|
|
210
|
+
* Get the number of pending events.
|
|
211
|
+
*/
|
|
212
|
+
async getPendingEventCount() {
|
|
213
|
+
if (!state.isConfigured) return 0;
|
|
214
|
+
return MGMClient.getPendingEventCount();
|
|
215
|
+
},
|
|
216
|
+
/**
|
|
217
|
+
* Clean up resources. Call when unmounting the app.
|
|
218
|
+
*/
|
|
219
|
+
destroy() {
|
|
220
|
+
if (state.appStateSubscription) {
|
|
221
|
+
state.appStateSubscription.remove();
|
|
222
|
+
state.appStateSubscription = null;
|
|
223
|
+
}
|
|
224
|
+
MGMClient.reset();
|
|
225
|
+
state.isConfigured = false;
|
|
226
|
+
state.lastLifecycleEvent = null;
|
|
227
|
+
log('Destroyed');
|
|
228
|
+
}
|
|
229
|
+
};
|
|
230
|
+
|
|
231
|
+
/**
|
|
232
|
+
* Get device type based on platform.
|
|
233
|
+
*/
|
|
234
|
+
function getDeviceType() {
|
|
235
|
+
if (Platform.OS === 'ios') {
|
|
236
|
+
// Could use react-native-device-info for more accuracy
|
|
237
|
+
return Platform.isPad ? 'tablet' : 'phone';
|
|
238
|
+
}
|
|
239
|
+
if (Platform.OS === 'android') {
|
|
240
|
+
return 'phone'; // Could detect tablet with dimensions
|
|
241
|
+
}
|
|
242
|
+
return 'unknown';
|
|
243
|
+
}
|
|
244
|
+
|
|
245
|
+
/**
|
|
246
|
+
* Get OS version based on platform.
|
|
247
|
+
*/
|
|
248
|
+
function getOSVersion() {
|
|
249
|
+
const version = Platform.Version;
|
|
250
|
+
if (Platform.OS === 'ios') {
|
|
251
|
+
// iOS returns a string like "15.0"
|
|
252
|
+
return String(version);
|
|
253
|
+
}
|
|
254
|
+
if (Platform.OS === 'android') {
|
|
255
|
+
// Android returns SDK version number (e.g., 31 for Android 12)
|
|
256
|
+
return String(version);
|
|
257
|
+
}
|
|
258
|
+
return 'unknown';
|
|
259
|
+
}
|
|
260
|
+
export default MostlyGoodMetrics;
|
|
261
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":["AppState","Platform","MostlyGoodMetrics","MGMClient","SystemEvents","SystemProperties","AsyncStorageEventStorage","persistence","getStorageType","g","globalThis","__MGM_RN_STATE__","appStateSubscription","isConfigured","currentAppState","currentState","debugLogging","lastLifecycleEvent","state","DEDUPE_INTERVAL_MS","log","args","console","trackLifecycleEvent","eventName","properties","now","Date","name","time","track","handleAppStateChange","nextAppState","shared","match","APP_OPENED","APP_BACKGROUNDED","flush","catch","e","trackInstallOrUpdate","appVersion","previousVersion","getAppVersion","isFirst","isFirstLaunch","APP_INSTALLED","VERSION","setAppVersion","APP_UPDATED","PREVIOUS_VERSION","configure","apiKey","config","enableDebugLogging","storage","maxStoredEvents","getUserId","then","userId","osVersion","getOSVersion","trackAppLifecycleEvents","remove","addEventListener","warn","enrichedProperties","DEVICE_TYPE","getDeviceType","$storage_type","identify","setUserId","resetIdentity","startNewSession","clearPendingEvents","getPendingEventCount","destroy","reset","OS","isPad","version","Version","String"],"sourceRoot":"../../src","sources":["index.ts"],"mappings":"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","ignoreList":[]}
|
|
@@ -0,0 +1,152 @@
|
|
|
1
|
+
const STORAGE_KEY = 'mostlygoodmetrics_events';
|
|
2
|
+
const USER_ID_KEY = 'mostlygoodmetrics_user_id';
|
|
3
|
+
const APP_VERSION_KEY = 'mostlygoodmetrics_app_version';
|
|
4
|
+
const FIRST_LAUNCH_KEY = 'mostlygoodmetrics_installed';
|
|
5
|
+
|
|
6
|
+
// Try to import AsyncStorage, fall back to null if not available
|
|
7
|
+
let AsyncStorage = null;
|
|
8
|
+
try {
|
|
9
|
+
// eslint-disable-next-line @typescript-eslint/no-var-requires
|
|
10
|
+
AsyncStorage = require('@react-native-async-storage/async-storage').default;
|
|
11
|
+
} catch {
|
|
12
|
+
// AsyncStorage not installed - will use in-memory storage
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
/**
|
|
16
|
+
* Returns the storage type being used.
|
|
17
|
+
*/
|
|
18
|
+
export function getStorageType() {
|
|
19
|
+
return AsyncStorage ? 'persistent' : 'memory';
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
/**
|
|
23
|
+
* In-memory fallback storage when AsyncStorage is not available.
|
|
24
|
+
*/
|
|
25
|
+
const memoryStorage = {};
|
|
26
|
+
|
|
27
|
+
/**
|
|
28
|
+
* Storage helpers that work with or without AsyncStorage.
|
|
29
|
+
*/
|
|
30
|
+
async function getItem(key) {
|
|
31
|
+
if (AsyncStorage) {
|
|
32
|
+
try {
|
|
33
|
+
return await AsyncStorage.getItem(key);
|
|
34
|
+
} catch {
|
|
35
|
+
return memoryStorage[key] ?? null;
|
|
36
|
+
}
|
|
37
|
+
}
|
|
38
|
+
return memoryStorage[key] ?? null;
|
|
39
|
+
}
|
|
40
|
+
async function setItem(key, value) {
|
|
41
|
+
memoryStorage[key] = value;
|
|
42
|
+
if (AsyncStorage) {
|
|
43
|
+
try {
|
|
44
|
+
await AsyncStorage.setItem(key, value);
|
|
45
|
+
} catch {
|
|
46
|
+
// Fall back to memory storage (already set above)
|
|
47
|
+
}
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
async function removeItem(key) {
|
|
51
|
+
delete memoryStorage[key];
|
|
52
|
+
if (AsyncStorage) {
|
|
53
|
+
try {
|
|
54
|
+
await AsyncStorage.removeItem(key);
|
|
55
|
+
} catch {
|
|
56
|
+
// Already removed from memory
|
|
57
|
+
}
|
|
58
|
+
}
|
|
59
|
+
}
|
|
60
|
+
|
|
61
|
+
/**
|
|
62
|
+
* Event storage for React Native.
|
|
63
|
+
* Uses AsyncStorage if available, otherwise falls back to in-memory storage.
|
|
64
|
+
*/
|
|
65
|
+
export class AsyncStorageEventStorage {
|
|
66
|
+
events = null;
|
|
67
|
+
constructor(maxEvents = 10000) {
|
|
68
|
+
this.maxEvents = Math.max(maxEvents, 100);
|
|
69
|
+
}
|
|
70
|
+
async loadEvents() {
|
|
71
|
+
if (this.events !== null) {
|
|
72
|
+
return this.events;
|
|
73
|
+
}
|
|
74
|
+
try {
|
|
75
|
+
const stored = await getItem(STORAGE_KEY);
|
|
76
|
+
if (stored) {
|
|
77
|
+
this.events = JSON.parse(stored);
|
|
78
|
+
} else {
|
|
79
|
+
this.events = [];
|
|
80
|
+
}
|
|
81
|
+
} catch {
|
|
82
|
+
this.events = [];
|
|
83
|
+
}
|
|
84
|
+
return this.events;
|
|
85
|
+
}
|
|
86
|
+
async saveEvents() {
|
|
87
|
+
await setItem(STORAGE_KEY, JSON.stringify(this.events ?? []));
|
|
88
|
+
}
|
|
89
|
+
async store(event) {
|
|
90
|
+
const events = await this.loadEvents();
|
|
91
|
+
events.push(event);
|
|
92
|
+
|
|
93
|
+
// Trim oldest events if we exceed the limit
|
|
94
|
+
if (events.length > this.maxEvents) {
|
|
95
|
+
const excess = events.length - this.maxEvents;
|
|
96
|
+
events.splice(0, excess);
|
|
97
|
+
}
|
|
98
|
+
await this.saveEvents();
|
|
99
|
+
}
|
|
100
|
+
async fetchEvents(limit) {
|
|
101
|
+
const events = await this.loadEvents();
|
|
102
|
+
return events.slice(0, limit);
|
|
103
|
+
}
|
|
104
|
+
async removeEvents(count) {
|
|
105
|
+
const events = await this.loadEvents();
|
|
106
|
+
events.splice(0, count);
|
|
107
|
+
await this.saveEvents();
|
|
108
|
+
}
|
|
109
|
+
async eventCount() {
|
|
110
|
+
const events = await this.loadEvents();
|
|
111
|
+
return events.length;
|
|
112
|
+
}
|
|
113
|
+
async clear() {
|
|
114
|
+
this.events = [];
|
|
115
|
+
await removeItem(STORAGE_KEY);
|
|
116
|
+
}
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
/**
|
|
120
|
+
* Persistence helpers for user ID and app version.
|
|
121
|
+
*/
|
|
122
|
+
export const persistence = {
|
|
123
|
+
async getUserId() {
|
|
124
|
+
return getItem(USER_ID_KEY);
|
|
125
|
+
},
|
|
126
|
+
async setUserId(userId) {
|
|
127
|
+
if (userId) {
|
|
128
|
+
await setItem(USER_ID_KEY, userId);
|
|
129
|
+
} else {
|
|
130
|
+
await removeItem(USER_ID_KEY);
|
|
131
|
+
}
|
|
132
|
+
},
|
|
133
|
+
async getAppVersion() {
|
|
134
|
+
return getItem(APP_VERSION_KEY);
|
|
135
|
+
},
|
|
136
|
+
async setAppVersion(version) {
|
|
137
|
+
if (version) {
|
|
138
|
+
await setItem(APP_VERSION_KEY, version);
|
|
139
|
+
} else {
|
|
140
|
+
await removeItem(APP_VERSION_KEY);
|
|
141
|
+
}
|
|
142
|
+
},
|
|
143
|
+
async isFirstLaunch() {
|
|
144
|
+
const hasLaunched = await getItem(FIRST_LAUNCH_KEY);
|
|
145
|
+
if (!hasLaunched) {
|
|
146
|
+
await setItem(FIRST_LAUNCH_KEY, 'true');
|
|
147
|
+
return true;
|
|
148
|
+
}
|
|
149
|
+
return false;
|
|
150
|
+
}
|
|
151
|
+
};
|
|
152
|
+
//# sourceMappingURL=storage.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"names":["STORAGE_KEY","USER_ID_KEY","APP_VERSION_KEY","FIRST_LAUNCH_KEY","AsyncStorage","require","default","getStorageType","memoryStorage","getItem","key","setItem","value","removeItem","AsyncStorageEventStorage","events","constructor","maxEvents","Math","max","loadEvents","stored","JSON","parse","saveEvents","stringify","store","event","push","length","excess","splice","fetchEvents","limit","slice","removeEvents","count","eventCount","clear","persistence","getUserId","setUserId","userId","getAppVersion","setAppVersion","version","isFirstLaunch","hasLaunched"],"sourceRoot":"../../src","sources":["storage.ts"],"mappings":"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","ignoreList":[]}
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
import { type MGMConfiguration, type EventProperties } from '@mostly-good-metrics/javascript';
|
|
2
|
+
export type { MGMConfiguration, EventProperties };
|
|
3
|
+
export interface ReactNativeConfig extends Omit<MGMConfiguration, 'storage'> {
|
|
4
|
+
/**
|
|
5
|
+
* The app version string. Required for install/update tracking.
|
|
6
|
+
*/
|
|
7
|
+
appVersion?: string;
|
|
8
|
+
}
|
|
9
|
+
/**
|
|
10
|
+
* MostlyGoodMetrics React Native SDK
|
|
11
|
+
*/
|
|
12
|
+
declare const MostlyGoodMetrics: {
|
|
13
|
+
/**
|
|
14
|
+
* Configure the SDK with an API key and optional settings.
|
|
15
|
+
*/
|
|
16
|
+
configure(apiKey: string, config?: Omit<ReactNativeConfig, "apiKey">): void;
|
|
17
|
+
/**
|
|
18
|
+
* Track an event with optional properties.
|
|
19
|
+
*/
|
|
20
|
+
track(name: string, properties?: EventProperties): void;
|
|
21
|
+
/**
|
|
22
|
+
* Identify a user.
|
|
23
|
+
*/
|
|
24
|
+
identify(userId: string): void;
|
|
25
|
+
/**
|
|
26
|
+
* Clear the current user identity.
|
|
27
|
+
*/
|
|
28
|
+
resetIdentity(): void;
|
|
29
|
+
/**
|
|
30
|
+
* Manually flush pending events to the server.
|
|
31
|
+
*/
|
|
32
|
+
flush(): void;
|
|
33
|
+
/**
|
|
34
|
+
* Start a new session with a fresh session ID.
|
|
35
|
+
*/
|
|
36
|
+
startNewSession(): void;
|
|
37
|
+
/**
|
|
38
|
+
* Clear all pending events without sending them.
|
|
39
|
+
*/
|
|
40
|
+
clearPendingEvents(): void;
|
|
41
|
+
/**
|
|
42
|
+
* Get the number of pending events.
|
|
43
|
+
*/
|
|
44
|
+
getPendingEventCount(): Promise<number>;
|
|
45
|
+
/**
|
|
46
|
+
* Clean up resources. Call when unmounting the app.
|
|
47
|
+
*/
|
|
48
|
+
destroy(): void;
|
|
49
|
+
};
|
|
50
|
+
export default MostlyGoodMetrics;
|
|
51
|
+
//# sourceMappingURL=index.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/index.ts"],"names":[],"mappings":"AAEA,OAAO,EAEL,KAAK,gBAAgB,EACrB,KAAK,eAAe,EAGrB,MAAM,iCAAiC,CAAC;AAGzC,YAAY,EAAE,gBAAgB,EAAE,eAAe,EAAE,CAAC;AAElD,MAAM,WAAW,iBAAkB,SAAQ,IAAI,CAAC,gBAAgB,EAAE,SAAS,CAAC;IAC1E;;OAEG;IACH,UAAU,CAAC,EAAE,MAAM,CAAC;CACrB;AAqGD;;GAEG;AACH,QAAA,MAAM,iBAAiB;IACrB;;OAEG;sBACe,MAAM,WAAU,IAAI,CAAC,iBAAiB,EAAE,QAAQ,CAAC,GAAQ,IAAI;IAqD/E;;OAEG;gBACS,MAAM,eAAe,eAAe,GAAG,IAAI;IAgBvD;;OAEG;qBACc,MAAM,GAAG,IAAI;IAY9B;;OAEG;qBACc,IAAI;IAQrB;;OAEG;aACM,IAAI;IAOb;;OAEG;uBACgB,IAAI;IAOvB;;OAEG;0BACmB,IAAI;IAO1B;;OAEG;4BAC2B,OAAO,CAAC,MAAM,CAAC;IAK7C;;OAEG;eACQ,IAAI;CAUhB,CAAC;AAgCF,eAAe,iBAAiB,CAAC"}
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
import type { IEventStorage, MGMEvent } from '@mostly-good-metrics/javascript';
|
|
2
|
+
/**
|
|
3
|
+
* Returns the storage type being used.
|
|
4
|
+
*/
|
|
5
|
+
export declare function getStorageType(): 'persistent' | 'memory';
|
|
6
|
+
/**
|
|
7
|
+
* Event storage for React Native.
|
|
8
|
+
* Uses AsyncStorage if available, otherwise falls back to in-memory storage.
|
|
9
|
+
*/
|
|
10
|
+
export declare class AsyncStorageEventStorage implements IEventStorage {
|
|
11
|
+
private maxEvents;
|
|
12
|
+
private events;
|
|
13
|
+
constructor(maxEvents?: number);
|
|
14
|
+
private loadEvents;
|
|
15
|
+
private saveEvents;
|
|
16
|
+
store(event: MGMEvent): Promise<void>;
|
|
17
|
+
fetchEvents(limit: number): Promise<MGMEvent[]>;
|
|
18
|
+
removeEvents(count: number): Promise<void>;
|
|
19
|
+
eventCount(): Promise<number>;
|
|
20
|
+
clear(): Promise<void>;
|
|
21
|
+
}
|
|
22
|
+
/**
|
|
23
|
+
* Persistence helpers for user ID and app version.
|
|
24
|
+
*/
|
|
25
|
+
export declare const persistence: {
|
|
26
|
+
getUserId(): Promise<string | null>;
|
|
27
|
+
setUserId(userId: string | null): Promise<void>;
|
|
28
|
+
getAppVersion(): Promise<string | null>;
|
|
29
|
+
setAppVersion(version: string | null): Promise<void>;
|
|
30
|
+
isFirstLaunch(): Promise<boolean>;
|
|
31
|
+
};
|
|
32
|
+
//# sourceMappingURL=storage.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"storage.d.ts","sourceRoot":"","sources":["../../../src/storage.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,aAAa,EAAE,QAAQ,EAAE,MAAM,iCAAiC,CAAC;AAgB/E;;GAEG;AACH,wBAAgB,cAAc,IAAI,YAAY,GAAG,QAAQ,CAExD;AA2CD;;;GAGG;AACH,qBAAa,wBAAyB,YAAW,aAAa;IAC5D,OAAO,CAAC,SAAS,CAAS;IAC1B,OAAO,CAAC,MAAM,CAA2B;gBAE7B,SAAS,GAAE,MAAc;YAIvB,UAAU;YAmBV,UAAU;IAIlB,KAAK,CAAC,KAAK,EAAE,QAAQ,GAAG,OAAO,CAAC,IAAI,CAAC;IAarC,WAAW,CAAC,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,QAAQ,EAAE,CAAC;IAK/C,YAAY,CAAC,KAAK,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAM1C,UAAU,IAAI,OAAO,CAAC,MAAM,CAAC;IAK7B,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;CAI7B;AAED;;GAEG;AACH,eAAO,MAAM,WAAW;iBACH,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC;sBAIjB,MAAM,GAAG,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC;qBAQ9B,OAAO,CAAC,MAAM,GAAG,IAAI,CAAC;2BAIhB,MAAM,GAAG,IAAI,GAAG,OAAO,CAAC,IAAI,CAAC;qBAQnC,OAAO,CAAC,OAAO,CAAC;CAQxC,CAAC"}
|
package/package.json
ADDED
|
@@ -0,0 +1,86 @@
|
|
|
1
|
+
{
|
|
2
|
+
"name": "@mostly-good-metrics/react-native",
|
|
3
|
+
"version": "0.1.0",
|
|
4
|
+
"description": "React Native SDK for MostlyGoodMetrics analytics",
|
|
5
|
+
"main": "lib/commonjs/index",
|
|
6
|
+
"module": "lib/module/index",
|
|
7
|
+
"types": "lib/typescript/src/index.d.ts",
|
|
8
|
+
"react-native": "src/index",
|
|
9
|
+
"source": "src/index",
|
|
10
|
+
"files": [
|
|
11
|
+
"src",
|
|
12
|
+
"lib",
|
|
13
|
+
"!**/__tests__",
|
|
14
|
+
"!**/__fixtures__",
|
|
15
|
+
"!**/__mocks__"
|
|
16
|
+
],
|
|
17
|
+
"scripts": {
|
|
18
|
+
"test": "jest",
|
|
19
|
+
"test:coverage": "jest --coverage",
|
|
20
|
+
"typescript": "tsc --noEmit",
|
|
21
|
+
"lint": "eslint \"**/*.{js,ts,tsx}\"",
|
|
22
|
+
"prepare": "bob build",
|
|
23
|
+
"clean": "del-cli lib"
|
|
24
|
+
},
|
|
25
|
+
"keywords": [
|
|
26
|
+
"react-native",
|
|
27
|
+
"ios",
|
|
28
|
+
"android",
|
|
29
|
+
"analytics",
|
|
30
|
+
"metrics",
|
|
31
|
+
"mostlygoodmetrics"
|
|
32
|
+
],
|
|
33
|
+
"repository": {
|
|
34
|
+
"type": "git",
|
|
35
|
+
"url": "git+https://github.com/Mostly-Good-Metrics/mostly-good-metrics-react-native.git"
|
|
36
|
+
},
|
|
37
|
+
"author": "Josh Holtz",
|
|
38
|
+
"license": "MIT",
|
|
39
|
+
"bugs": {
|
|
40
|
+
"url": "https://github.com/Mostly-Good-Metrics/mostly-good-metrics-react-native/issues"
|
|
41
|
+
},
|
|
42
|
+
"homepage": "https://github.com/Mostly-Good-Metrics/mostly-good-metrics-react-native#readme",
|
|
43
|
+
"publishConfig": {
|
|
44
|
+
"registry": "https://registry.npmjs.org/"
|
|
45
|
+
},
|
|
46
|
+
"dependencies": {
|
|
47
|
+
"@mostly-good-metrics/javascript": "^0.1.0"
|
|
48
|
+
},
|
|
49
|
+
"devDependencies": {
|
|
50
|
+
"@react-native-async-storage/async-storage": "^1.21.0",
|
|
51
|
+
"@types/jest": "^30.0.0",
|
|
52
|
+
"@types/react": "^18.2.0",
|
|
53
|
+
"@types/react-native": "^0.72.0",
|
|
54
|
+
"del-cli": "^5.0.0",
|
|
55
|
+
"jest": "^30.2.0",
|
|
56
|
+
"react": "^18.2.0",
|
|
57
|
+
"react-native": "^0.73.0",
|
|
58
|
+
"react-native-builder-bob": "^0.23.0",
|
|
59
|
+
"ts-jest": "^29.4.6",
|
|
60
|
+
"typescript": "^5.0.0"
|
|
61
|
+
},
|
|
62
|
+
"peerDependencies": {
|
|
63
|
+
"@react-native-async-storage/async-storage": "*",
|
|
64
|
+
"react": "*",
|
|
65
|
+
"react-native": "*"
|
|
66
|
+
},
|
|
67
|
+
"peerDependenciesMeta": {
|
|
68
|
+
"@react-native-async-storage/async-storage": {
|
|
69
|
+
"optional": true
|
|
70
|
+
}
|
|
71
|
+
},
|
|
72
|
+
"react-native-builder-bob": {
|
|
73
|
+
"source": "src",
|
|
74
|
+
"output": "lib",
|
|
75
|
+
"targets": [
|
|
76
|
+
"commonjs",
|
|
77
|
+
"module",
|
|
78
|
+
[
|
|
79
|
+
"typescript",
|
|
80
|
+
{
|
|
81
|
+
"project": "tsconfig.build.json"
|
|
82
|
+
}
|
|
83
|
+
]
|
|
84
|
+
]
|
|
85
|
+
}
|
|
86
|
+
}
|