Skip to content

Commit a099eff

Browse files
add: setOnFeaturesUpdatedListener android listener and refactor instabug init method
1 parent c22cb2a commit a099eff

File tree

10 files changed

+227
-107
lines changed

10 files changed

+227
-107
lines changed

android/src/main/java/com/instabug/reactlibrary/RNInstabugNetworkLoggerModule.java

Lines changed: 10 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -136,6 +136,16 @@ public void run() {
136136
});
137137
}
138138

139+
@ReactMethod
140+
public void resetNetworkLogsListener() {
141+
MainThreadHandler.runOnMainThread(new Runnable() {
142+
@Override
143+
public void run() {
144+
InternalAPM._registerNetworkLogSanitizer(null);
145+
}
146+
});
147+
}
148+
139149
@ReactMethod
140150
protected void updateNetworkLogSnapshot(String jsonString) {
141151

examples/default/src/screens/apm/NetworkScreen.tsx

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,6 @@ import { CustomButton } from '../../components/CustomButton';
1010
import axios from 'axios';
1111
import type { HomeStackParamList } from '../../navigation/HomeStack';
1212
import type { NativeStackScreenProps } from '@react-navigation/native-stack';
13-
import { ListTile } from '../../components/ListTile';
1413

1514
export const NetworkScreen: React.FC<
1615
NativeStackScreenProps<HomeStackParamList, 'NetworkTraces'>
@@ -185,6 +184,11 @@ export const NetworkScreen: React.FC<
185184
/>
186185

187186
<CustomButton onPress={() => refetch()} title="Reload GraphQL" />
187+
<CustomButton
188+
onPress={() => navigation.navigate('HttpScreen')}
189+
title="Go HTTP Screen"
190+
/>
191+
188192
<View>
189193
{isLoading && <Text>Loading...</Text>}
190194
{isSuccess && <Text>GraphQL Data: {data.country.emoji}</Text>}
@@ -205,7 +209,6 @@ export const NetworkScreen: React.FC<
205209
))}
206210
</HStack>
207211
</Section>
208-
<ListTile title="HTTP Screen" onPress={() => navigation.navigate('HttpScreen')} />
209212
</Screen>
210213
</ScrollView>
211214
);

src/modules/Instabug.ts

Lines changed: 23 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -27,6 +27,8 @@ import {
2727
WelcomeMessageMode,
2828
} from '../utils/Enums';
2929
import InstabugUtils, {
30+
checkNetworkRequestHandlers,
31+
resetNativeObfuscationListener,
3032
setApmNetworkFlagsIfChanged,
3133
stringifyIfNotString,
3234
} from '../utils/InstabugUtils';
@@ -107,20 +109,16 @@ export const init = async (config: InstabugConfig) => {
107109

108110
// Add app state listener to handle background/foreground transitions
109111
addAppStateListener(async (nextAppState) => handleAppStateChange(nextAppState, config));
110-
}
111-
112-
// Perform platform-specific checks and update interception mode
113-
handleNetworkInterceptionMode(config);
114112

115-
// Log the current APM network flags and initialize Instabug
116-
_logFlags();
113+
handleNetworkInterceptionMode(config);
117114

118-
//Set APM networking flags for the first time
119-
setApmNetworkFlagsIfChanged({
120-
isNativeInterceptionFeatureEnabled: isNativeInterceptionFeatureEnabled,
121-
hasAPMNetworkPlugin: hasAPMNetworkPlugin,
122-
shouldEnableNativeInterception: shouldEnableNativeInterception,
123-
});
115+
//Set APM networking flags for the first time
116+
setApmNetworkFlagsIfChanged({
117+
isNativeInterceptionFeatureEnabled: isNativeInterceptionFeatureEnabled,
118+
hasAPMNetworkPlugin: hasAPMNetworkPlugin,
119+
shouldEnableNativeInterception: shouldEnableNativeInterception,
120+
});
121+
}
124122

125123
// call Instabug native init method
126124
initializeNativeInstabug(config);
@@ -199,8 +197,9 @@ const handleNetworkInterceptionMode = (config: InstabugConfig) => {
199197
config.networkInterceptionMode = NetworkInterceptionMode.javascript; // Need to enable JS interceptor in all scenarios for Bugs & Crashes network logs
200198
} else if (Platform.OS === 'ios') {
201199
handleInterceptionModeForIOS(config);
200+
//enable | disable native obfuscation and filtering synchronously
201+
NetworkLogger.setNativeInterceptionEnabled(shouldEnableNativeInterception);
202202
}
203-
NetworkLogger.setNativeInterceptionEnabled(shouldEnableNativeInterception);
204203

205204
if (config.networkInterceptionMode === NetworkInterceptionMode.javascript) {
206205
NetworkLogger.setEnabled(true);
@@ -239,7 +238,7 @@ function handleAndroidNativeInterception() {
239238
}
240239

241240
/**
242-
* Control either to enable or disable the native interception for iOS.
241+
* Control either to enable or disable the native interception for iOS after the init method is called.
243242
*/
244243
function handleIOSNativeInterception(config: InstabugConfig) {
245244
console.log(
@@ -315,9 +314,9 @@ const initializeNativeInstabug = (config: InstabugConfig) => {
315314
/**
316315
* Refresh the APM network configurations.
317316
*/
318-
function refreshAPMNetworkConfigs(config: InstabugConfig) {
317+
function refreshAPMNetworkConfigs(config: InstabugConfig, forceRefreshIOS: boolean = true) {
319318
handleNetworkInterceptionMode(config);
320-
if (Platform.OS === 'ios') {
319+
if (Platform.OS === 'ios' && forceRefreshIOS) {
321320
handleIOSNativeInterception(config);
322321
}
323322
_logFlags();
@@ -326,6 +325,12 @@ function refreshAPMNetworkConfigs(config: InstabugConfig) {
326325
hasAPMNetworkPlugin,
327326
shouldEnableNativeInterception,
328327
});
328+
if (shouldEnableNativeInterception) {
329+
checkNetworkRequestHandlers();
330+
} else {
331+
// remove any attached [NativeNetworkLogger] Listeners if exists, to avoid memory leaks.
332+
resetNativeObfuscationListener();
333+
}
329334
}
330335

331336
/**
@@ -334,8 +339,8 @@ function refreshAPMNetworkConfigs(config: InstabugConfig) {
334339
function addOnFeatureUpdatedListener(config: InstabugConfig) {
335340
emitter.addListener(NativeEvents.IBG_ON_FEATURES_UPDATED_CALLBACK, (flags) => {
336341
const { cpNativeInterceptionEnabled, hasAPMPlugin } = flags;
337-
console.log(`Andrew: addOnFeatureUpdatedListener ->
338-
isNativeInterceptionFeatureEnabled: ${cpNativeInterceptionEnabled},
342+
console.log(`Andrew: addOnFeatureUpdatedListener ->
343+
isNativeInterceptionFeatureEnabled: ${cpNativeInterceptionEnabled},
339344
hasAPMNetworkPlugin: ${hasAPMPlugin}.
340345
`);
341346
isNativeInterceptionFeatureEnabled = cpNativeInterceptionEnabled;
@@ -344,7 +349,6 @@ function addOnFeatureUpdatedListener(config: InstabugConfig) {
344349
config.networkInterceptionMode === NetworkInterceptionMode.native;
345350
refreshAPMNetworkConfigs(config);
346351
});
347-
348352
NativeInstabug.setOnFeaturesUpdatedListener();
349353
}
350354

src/modules/NetworkLogger.ts

Lines changed: 44 additions & 43 deletions
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,13 @@ import type { RequestHandler } from '@apollo/client';
22

33
import InstabugConstants from '../utils/InstabugConstants';
44
import xhr, { NetworkData, ProgressCallback } from '../utils/XhrNetworkInterceptor';
5-
import { isContentTypeNotAllowed, reportNetworkLog } from '../utils/InstabugUtils';
5+
import {
6+
isContentTypeNotAllowed,
7+
registerFilteringAndObfuscationListener,
8+
registerFilteringListener,
9+
registerObfuscationListener,
10+
reportNetworkLog,
11+
} from '../utils/InstabugUtils';
612
import {
713
NativeNetworkLogger,
814
NativeNetworkLoggerEvent,
@@ -18,6 +24,7 @@ let _networkDataObfuscationHandler: NetworkDataObfuscationHandler | null | undef
1824
let _requestFilterExpression = 'false';
1925
let _isNativeInterceptionEnabled = false;
2026
let _networkListener: NetworkListenerType | null = null;
27+
let hasFilterExpression = false;
2128

2229
/**
2330
* Sets whether network logs should be sent with bug reports.
@@ -34,6 +41,9 @@ export const setEnabled = (isEnabled: boolean) => {
3441
try {
3542
if (_networkDataObfuscationHandler) {
3643
network = await _networkDataObfuscationHandler(network);
44+
console.log(
45+
`Andrew: xhr.setOnDoneCallback -> _networkDataObfuscationHandler ${network.url}`,
46+
);
3747
}
3848

3949
if (network.requestBodySize > InstabugConstants.MAX_NETWORK_BODY_SIZE_IN_BYTES) {
@@ -82,6 +92,12 @@ export const setNativeInterceptionEnabled = (isEnabled: boolean) => {
8292
_isNativeInterceptionEnabled = isEnabled;
8393
};
8494

95+
export const getNetworkDataObfuscationHandler = () => _networkDataObfuscationHandler;
96+
97+
export const getRequestFilterExpression = () => _requestFilterExpression;
98+
99+
export const hasRequestFilterExpression = () => hasFilterExpression;
100+
85101
/**
86102
* Obfuscates any response data.
87103
* @param handler
@@ -90,13 +106,16 @@ export const setNetworkDataObfuscationHandler = (
90106
handler?: NetworkDataObfuscationHandler | null | undefined,
91107
) => {
92108
_networkDataObfuscationHandler = handler;
93-
if (_isNativeInterceptionEnabled) {
94-
_registerNetworkLogsListener(NetworkListenerType.obfuscation, async (networkSnapshot) => {
95-
if (_networkDataObfuscationHandler) {
96-
networkSnapshot = await _networkDataObfuscationHandler(networkSnapshot);
97-
}
98-
NativeNetworkLogger.updateNetworkLogSnapshot(JSON.stringify(networkSnapshot));
99-
});
109+
if (_isNativeInterceptionEnabled && Platform.OS === 'ios') {
110+
if (hasFilterExpression) {
111+
console.log(
112+
'Andrew: setNetworkDataObfuscationHandler -> registerFilteringAndObfuscationListenerV2',
113+
);
114+
registerFilteringAndObfuscationListener(_requestFilterExpression);
115+
} else {
116+
console.log('Andrew: setNetworkDataObfuscationHandler -> registerObfuscationListener');
117+
registerObfuscationListener();
118+
}
100119
}
101120
};
102121

@@ -106,23 +125,18 @@ export const setNetworkDataObfuscationHandler = (
106125
*/
107126
export const setRequestFilterExpression = (expression: string) => {
108127
_requestFilterExpression = expression;
109-
110-
if (_isNativeInterceptionEnabled) {
111-
_registerNetworkLogsListener(NetworkListenerType.filtering, async (networkSnapshot) => {
112-
// eslint-disable-next-line no-new-func
113-
const predicate = Function('network', 'return ' + _requestFilterExpression);
114-
const value = predicate(networkSnapshot);
115-
if (Platform.OS === 'ios') {
116-
// For iOS True == Request will be saved, False == will be ignored
117-
NativeNetworkLogger.setNetworkLoggingRequestFilterPredicateIOS(networkSnapshot.id, !value);
118-
} else {
119-
// For Android Setting the [url] to an empty string will ignore the request;
120-
if (value) {
121-
networkSnapshot.url = '';
122-
NativeNetworkLogger.updateNetworkLogSnapshot(JSON.stringify(networkSnapshot));
123-
}
124-
}
125-
});
128+
hasFilterExpression = true;
129+
130+
if (_isNativeInterceptionEnabled && Platform.OS === 'ios') {
131+
if (_networkDataObfuscationHandler) {
132+
console.log(
133+
'Andrew: setRequestFilterExpression -> registerFilteringAndObfuscationListenerV2',
134+
);
135+
registerFilteringAndObfuscationListener(_requestFilterExpression);
136+
} else {
137+
console.log('Andrew: setRequestFilterExpression -> registerFilteringListener');
138+
registerFilteringListener(_requestFilterExpression);
139+
}
126140
}
127141
};
128142

@@ -148,23 +162,6 @@ export const apolloLinkRequestHandler: RequestHandler = (operation, forward) =>
148162
return forward(operation);
149163
};
150164

151-
/**
152-
* @internal
153-
* Exported for internal/testing purposes only.
154-
*/
155-
export function registerNetworkLogsListener(
156-
type: NetworkListenerType,
157-
handler?: (networkSnapshot: NetworkData) => void,
158-
) {
159-
if (process.env.NODE_ENV === 'test') {
160-
_registerNetworkLogsListener(type, handler);
161-
} else {
162-
console.error(
163-
`${InstabugConstants.IBG_APM_TAG}: The \`registerNetworkLogsListener()\` method is intended solely for testing purposes.`,
164-
);
165-
}
166-
}
167-
168165
/**
169166
* @internal
170167
* Exported for internal/testing purposes only.
@@ -179,7 +176,11 @@ export const resetNetworkListener = () => {
179176
}
180177
};
181178

182-
const _registerNetworkLogsListener = (
179+
/**
180+
* @internal
181+
* Exported for internal/testing purposes only.
182+
*/
183+
export const registerNetworkLogsListener = (
183184
type: NetworkListenerType,
184185
handler?: (networkSnapshot: NetworkData) => void,
185186
) => {

src/native/NativeNetworkLogger.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,8 @@ export interface NetworkLoggerNativeModule extends NativeModule {
1616

1717
hasAPMNetworkPlugin(): Promise<boolean>; // Android only
1818

19+
resetNetworkLogsListener(): void; //Android only
20+
1921
setNetworkLoggingRequestFilterPredicateIOS(id: string, value: boolean): void; // iOS only
2022

2123
forceStartNetworkLoggingIOS(): void; // iOS only;

0 commit comments

Comments
 (0)