Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
5 changes: 3 additions & 2 deletions packages/plugins/plugin-firebase/src/FirebasePlugin.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,13 +11,14 @@ import screen from './methods/screen';
import track from './methods/track';
import reset from './methods/reset';
import { firebaseAnalytics } from './firebaseAnalytics';
import { setUserId, setUserProperties } from '@react-native-firebase/analytics';
export class FirebasePlugin extends DestinationPlugin {
type = PluginType.destination;
key = 'Firebase';

async identify(event: IdentifyEventType) {
if (event.userId !== undefined) {
await firebaseAnalytics.setUserId(event.userId);
await setUserId(firebaseAnalytics, event.userId);
}
if (event.traits) {
const eventTraits = event.traits;
Expand Down Expand Up @@ -45,7 +46,7 @@ export class FirebasePlugin extends DestinationPlugin {
{}
);

await firebaseAnalytics.setUserProperties(safeTraits);
await setUserProperties(firebaseAnalytics, safeTraits);
}
return event;
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,11 +1,16 @@
const mockSetUserId = jest.fn();
const mockSetUserProperties = jest.fn();
const mockDeprecatedSetUserId = jest.fn();
const mockDeprecatedSetUserProperties = jest.fn();
const mockAnalytics = {
setUserId: mockDeprecatedSetUserId,
setUserProperties: mockDeprecatedSetUserProperties,
};

jest.mock('@react-native-firebase/analytics', () => ({
getAnalytics: jest.fn().mockImplementation(() => ({
setUserId: mockSetUserId,
setUserProperties: mockSetUserProperties,
})),
getAnalytics: jest.fn().mockImplementation(() => mockAnalytics),
setUserId: mockSetUserId,
setUserProperties: mockSetUserProperties,
isString: (a: unknown) => typeof a === 'string',
}));
jest.mock('@react-native-firebase/app', () => ({
Expand Down Expand Up @@ -34,7 +39,7 @@ describe('#identify', () => {

expect(mockSetUserId).toHaveBeenCalledTimes(1);
expect(mockSetUserProperties).not.toHaveBeenCalled();
expect(mockSetUserId).toHaveBeenCalledWith('123');
expect(mockSetUserId).toHaveBeenCalledWith(mockAnalytics, '123');
});

it('forwards the identify event with ID and properties', async () => {
Expand All @@ -54,8 +59,12 @@ describe('#identify', () => {

expect(mockSetUserId).toHaveBeenCalledTimes(1);
expect(mockSetUserProperties).toHaveBeenCalledTimes(1);
expect(mockSetUserId).toHaveBeenCalledWith('123');
expect(mockSetUserProperties).toHaveBeenCalledWith({ name: 'Mary' });
expect(mockSetUserId).toHaveBeenCalledWith(mockAnalytics, '123');
expect(mockSetUserProperties).toHaveBeenCalledWith(mockAnalytics, {
name: 'Mary',
});
expect(mockDeprecatedSetUserId).not.toHaveBeenCalled();
expect(mockDeprecatedSetUserProperties).not.toHaveBeenCalled();
});

it('forwards the identify event without ID', async () => {
Expand All @@ -74,6 +83,8 @@ describe('#identify', () => {

expect(mockSetUserId).not.toHaveBeenCalled();
expect(mockSetUserProperties).toHaveBeenCalledTimes(1);
expect(mockSetUserProperties).toHaveBeenCalledWith({ name: 'Mary' });
expect(mockSetUserProperties).toHaveBeenCalledWith(mockAnalytics, {
name: 'Mary',
});
});
});
Original file line number Diff line number Diff line change
@@ -1,9 +1,10 @@
const mockReset = jest.fn();
const mockDeprecatedReset = jest.fn();
const mockAnalytics = { resetAnalyticsData: mockDeprecatedReset };

jest.mock('@react-native-firebase/analytics', () => ({
getAnalytics: jest.fn().mockImplementation(() => ({
resetAnalyticsData: mockReset,
})),
getAnalytics: jest.fn().mockImplementation(() => mockAnalytics),
resetAnalyticsData: mockReset,
}));

jest.mock('@react-native-firebase/app', () => ({
Expand All @@ -21,6 +22,7 @@ describe('#reset', () => {
await reset();

expect(mockReset).toHaveBeenCalledTimes(1);
expect(mockReset).toHaveBeenCalledWith();
expect(mockReset).toHaveBeenCalledWith(mockAnalytics);
expect(mockDeprecatedReset).not.toHaveBeenCalled();
});
});
Original file line number Diff line number Diff line change
@@ -1,9 +1,10 @@
const mockScreen = jest.fn();
const mockLogEvent = jest.fn();
const mockDeprecatedLogScreenView = jest.fn();
const mockAnalytics = { logScreenView: mockDeprecatedLogScreenView };

jest.mock('@react-native-firebase/analytics', () => ({
getAnalytics: jest.fn().mockImplementation(() => ({
logScreenView: mockScreen,
})),
getAnalytics: jest.fn().mockImplementation(() => mockAnalytics),
logEvent: mockLogEvent,
}));

jest.mock('@react-native-firebase/app', () => ({
Expand All @@ -30,10 +31,25 @@ describe('#screen', () => {

await screen(event);

expect(mockScreen).toHaveBeenCalledTimes(1);
expect(mockScreen).toHaveBeenCalledWith({
expect(mockLogEvent).toHaveBeenCalledTimes(1);
expect(mockLogEvent).toHaveBeenCalledWith(mockAnalytics, 'screen_view', {
screen_name: 'HomeScreen',
screen_class: 'HomeScreen',
});
});

it('does not call the deprecated logScreenView method', async () => {
const event = {
type: 'screen',
name: 'HomeScreen',
anonymousId: 'anon',
messageId: 'message-id',
timestamp: '00000',
properties: {},
} as ScreenEventType;

await screen(event);

expect(mockDeprecatedLogScreenView).not.toHaveBeenCalled();
});
});
Original file line number Diff line number Diff line change
@@ -1,9 +1,10 @@
const mockLogEvent = jest.fn();
const mockDeprecatedLogEvent = jest.fn();
const mockAnalytics = { logEvent: mockDeprecatedLogEvent };

jest.mock('@react-native-firebase/analytics', () => ({
getAnalytics: jest.fn().mockImplementation(() => ({
logEvent: mockLogEvent,
})),
getAnalytics: jest.fn().mockImplementation(() => mockAnalytics),
logEvent: mockLogEvent,
isString: (a: unknown) => typeof a === 'string',
}));
jest.mock('@react-native-firebase/app', () => ({
Expand Down Expand Up @@ -32,7 +33,22 @@ describe('#track', () => {
await track(event);

expect(mockLogEvent).toHaveBeenCalledTimes(1);
expect(mockLogEvent).toHaveBeenCalledWith('test_event', {});
expect(mockLogEvent).toHaveBeenCalledWith(mockAnalytics, 'test_event', {});
});

it('uses the modular API instead of the deprecated instance method', async () => {
const event = {
type: EventType.TrackEvent,
event: 'test_event',
anonymousId: 'anon',
messageId: 'message-id',
timestamp: '00000',
properties: {},
} as TrackEventType;

await track(event);

expect(mockDeprecatedLogEvent).not.toHaveBeenCalled();
});

it('forwards a track event with name and properties', async () => {
Expand All @@ -48,9 +64,13 @@ describe('#track', () => {
await track(event);

expect(mockLogEvent).toHaveBeenCalledTimes(1);
expect(mockLogEvent).toHaveBeenCalledWith('another_test_event', {
foo: 'bar',
});
expect(mockLogEvent).toHaveBeenCalledWith(
mockAnalytics,
'another_test_event',
{
foo: 'bar',
}
);
});

it('removes non-alphanumeric characters from', async () => {
Expand All @@ -67,6 +87,7 @@ describe('#track', () => {

expect(mockLogEvent).toHaveBeenCalledTimes(1);
expect(mockLogEvent).toHaveBeenCalledWith(
mockAnalytics,
'yet_another__test____event_CAPS',
{}
);
Expand All @@ -85,6 +106,6 @@ describe('#track', () => {
await track(event);

expect(mockLogEvent).toHaveBeenCalledTimes(1);
expect(mockLogEvent).toHaveBeenCalledWith('refund', {});
expect(mockLogEvent).toHaveBeenCalledWith(mockAnalytics, 'refund', {});
});
});
3 changes: 2 additions & 1 deletion packages/plugins/plugin-firebase/src/methods/reset.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import { resetAnalyticsData } from '@react-native-firebase/analytics';
import { firebaseAnalytics } from '../firebaseAnalytics';

export default async () => {
await firebaseAnalytics.resetAnalyticsData();
await resetAnalyticsData(firebaseAnalytics);
};
7 changes: 6 additions & 1 deletion packages/plugins/plugin-firebase/src/methods/screen.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import type { ScreenEventType } from '@segment/analytics-react-native';
import { logEvent } from '@react-native-firebase/analytics';
import { firebaseAnalytics } from '../firebaseAnalytics';

export default async (event: ScreenEventType) => {
Expand All @@ -8,5 +9,9 @@ export default async (event: ScreenEventType) => {
...event.properties,
};

await firebaseAnalytics.logScreenView(screenProps);
// logScreenView is deprecated in both the namespaced and modular APIs.
// The typings of the 'screen_view' overload use the web parameter names
// (firebase_screen), but the native SDKs read screen_name and screen_class,
// which is what logScreenView forwarded. Keep the payload and cast the type.
await logEvent(firebaseAnalytics, 'screen_view', screenProps as never);
};
3 changes: 2 additions & 1 deletion packages/plugins/plugin-firebase/src/methods/track.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import {
type TrackEventType,
generateMapTransform,
} from '@segment/analytics-react-native';
import { logEvent } from '@react-native-firebase/analytics';
import { firebaseAnalytics } from '../firebaseAnalytics';
import { mapEventProps, transformMap } from './parameterMapping';

Expand All @@ -22,5 +23,5 @@ export default async (event: TrackEventType) => {
if (safeEventName.length > 40) {
safeEventName = safeEventName.substring(0, 40);
}
await firebaseAnalytics.logEvent(safeEventName, safeProps);
await logEvent(firebaseAnalytics, safeEventName, safeProps);
};