Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

test: e2e replay #3993

Open
wants to merge 62 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from 61 commits
Commits
Show all changes
62 commits
Select commit Hold shift + click to select a range
fe7ab45
wip: extract e2e test script from yaml
vaind Jul 25, 2024
a393435
update e2e test script
vaind Jul 27, 2024
5c13f0d
move more stuff to e2e.js
vaind Jul 27, 2024
a477d6e
script args
vaind Jul 27, 2024
fc61db5
more stuff moved to e2e.js
vaind Jul 27, 2024
857e6a8
run tests from e2e script
vaind Jul 30, 2024
53e825f
remove e2e build from ci
vaind Jul 30, 2024
dd8abf5
fix ruby/setup-ruby
vaind Jul 30, 2024
b0a2ca2
update actions
vaind Jul 30, 2024
273a376
more script fixes
vaind Jul 30, 2024
7b7a0c2
fixup script on CI
vaind Jul 30, 2024
e368e4a
cleanup
vaind Jul 30, 2024
fd4c50a
fix CI
vaind Jul 30, 2024
b6601a3
fix CI
vaind Jul 30, 2024
655300d
linter issues
vaind Jul 31, 2024
2dc8ebc
Merge branch 'main' into test/e2e-refactor
vaind Jul 31, 2024
3f65502
post-merge script update
vaind Jul 31, 2024
6e94861
Update scripts/e2e.mjs
vaind Jul 31, 2024
612813d
Update scripts/e2e.mjs
vaind Jul 31, 2024
85e6afb
Update scripts/e2e.mjs
vaind Jul 31, 2024
efd1f9a
Update scripts/e2e.mjs
vaind Jul 31, 2024
883f9fb
cleanup
vaind Jul 31, 2024
5701c7c
move webdriveragent build to test
vaind Jul 31, 2024
030049d
cache webdriveragent build
vaind Jul 31, 2024
1739957
Merge branch 'main' into test/e2e-refactor
vaind Jul 31, 2024
d0b1f42
use bundler
vaind Jul 31, 2024
8becfea
Update e2e.yml
vaind Jul 31, 2024
b26695b
fix e2e test run
vaind Jul 31, 2024
009864d
try to fix ci
vaind Jul 31, 2024
d2cd560
Update e2e.yml
vaind Jul 31, 2024
0442bfa
fixes
vaind Jul 31, 2024
35b1c9e
try to remove node module removal
vaind Jul 31, 2024
883b36a
fix caching
vaind Jul 31, 2024
80b5fa4
Revert "try to remove node module removal"
vaind Jul 31, 2024
991927e
fix e2e.yml cache config
vaind Jul 31, 2024
a31ca9a
fix appium invocation
vaind Jul 31, 2024
459e842
handle child processes gracefully
vaind Aug 1, 2024
6c1bb2c
try to fix android test hangs
vaind Aug 1, 2024
11c1692
try to fix ci
vaind Aug 1, 2024
d742a85
tmp: debug session
vaind Aug 1, 2024
f1140fa
tmp killall
vaind Aug 1, 2024
082406e
fix android ci
vaind Aug 1, 2024
5ddfeb9
roll back unintended changes
vaind Aug 1, 2024
92fa628
fix hanging CI
vaind Aug 1, 2024
f554613
ensure node_modules from root are not resolved during e2e test app build
vaind Aug 1, 2024
6074dae
Merge branch 'main' into test/e2e-refactor
vaind Aug 1, 2024
03a948c
Merge branch 'main' into test/e2e-refactor
vaind Aug 5, 2024
3c8fac9
e2e replay test
vaind Aug 5, 2024
89bb744
Merge branch 'main' into test/e2e-replay
vaind Aug 12, 2024
ae69622
test: replay video segments data
vaind Aug 13, 2024
931c9e1
Merge branch 'main' into test/e2e-replay
vaind Aug 13, 2024
37f2f8d
linter issue
vaind Aug 13, 2024
9029815
Merge branch 'main' into test/e2e-replay
vaind Aug 15, 2024
6dee84a
enable debug logging in e2e tests
vaind Aug 15, 2024
61e5700
show emulator window to enable replay recording
vaind Aug 15, 2024
ed27926
no no-window doesn't work
vaind Aug 15, 2024
8f4b251
Merge branch 'main' into test/e2e-replay
vaind Aug 20, 2024
1863e62
try to fix android screenshots
vaind Aug 20, 2024
f2ef368
don't run e2e replay test on android
vaind Sep 3, 2024
8bf63c7
disable session replay in tests
vaind Sep 3, 2024
4ee29f2
Merge branch 'main' into test/e2e-replay
vaind Sep 3, 2024
9c4de41
Merge branch 'main' into test/e2e-replay
vaind Sep 10, 2024
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
1 change: 0 additions & 1 deletion .github/workflows/e2e.yml
Original file line number Diff line number Diff line change
Expand Up @@ -430,7 +430,6 @@ jobs:
disable-animations: true
disable-spellchecker: true
target: 'aosp_atd'
channel: canary # Necessary for ATDs
emulator-options: >
-no-window
-no-snapshot-save
Expand Down
30 changes: 29 additions & 1 deletion test/e2e/test/e2e.test.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,10 @@
/* eslint-disable import/no-unresolved */
import path from 'path';
import { Platform } from 'react-native';
import type { RemoteOptions } from 'webdriverio';
import { remote } from 'webdriverio';

import { fetchEvent } from './utils/fetchEvent';
import { fetchEvent, fetchReplay, fetchReplaySegmentVideo } from './utils/sentryApi';
import { waitForTruthyResult } from './utils/waitFor';

const DRIVER_NOT_INITIALIZED = 'Driver not initialized';
Expand Down Expand Up @@ -131,6 +132,33 @@ describe('End to end tests for common events', () => {
expect(sentryEvent.eventID).toMatch(eventId);
});

// Currently doesn't work on Android because capturing screenshots doesn't work on emulator in GH Actions.
if (Platform.OS !== 'android') {
test('captureErrorReplay', async () => {
const element = await getElement('captureException');
await element.click();

const eventId = await waitForEventId();
const sentryEvent = await fetchEvent(eventId);
expect(sentryEvent.eventID).toMatch(eventId);

expect(sentryEvent.contexts).toBeDefined();
const replay = sentryEvent.contexts!['replay'] as any;
expect(replay).toBeDefined();
expect(replay.replay_id.length).toBe(32);
lucas-zimerman marked this conversation as resolved.
Show resolved Hide resolved

const replayInfo = await fetchReplay(replay.replay_id);
expect(replayInfo).toBeDefined();
expect(replayInfo.data.duration).toBeGreaterThan(0);
expect(replayInfo.data.count_segments).toBeGreaterThan(0);

const video = await fetchReplaySegmentVideo(replay.replay_id, 0);
expect(video).toBeDefined();
expect(video.size).toBeGreaterThan(1000);
expect(await video.slice(4, 12).text()).toMatch('ftypmp42');
vaind marked this conversation as resolved.
Show resolved Hide resolved
});
}

test('unhandledPromiseRejection', async () => {
const element = await getElement('unhandledPromiseRejection');
await element.click();
Expand Down
62 changes: 0 additions & 62 deletions test/e2e/test/utils/fetchEvent.ts

This file was deleted.

68 changes: 68 additions & 0 deletions test/e2e/test/utils/sentryApi.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
import type { Event } from '@sentry/types';

const baseUrl = 'https://sentry.io/api/0/projects/sentry-sdks/sentry-react-native';

interface ApiEvent extends Event {
/**
* The event returned from the API uses eventID
*/
eventID: string;
}

const RETRY_COUNT = 600;
const RETRY_INTERVAL = 1000;

const fetchFromSentry = async (url: string): Promise<Response> => {
expect(process.env.SENTRY_AUTH_TOKEN).toBeDefined();
expect(process.env.SENTRY_AUTH_TOKEN?.length).toBeGreaterThan(0);

const request = () =>
fetch(url, {
headers: {
Authorization: `Bearer ${process.env.SENTRY_AUTH_TOKEN}`,
'Content-Type': 'application/json',
},
method: 'GET',
});

let retries = 0;
const retrier = (response: Response): Promise<Response> =>
new Promise((resolve, reject) => {
if (response.status === 200) {
resolve(response);
} else if (response.status === 403) {
reject(new Error(`Could not fetch ${url}: ${response.statusText}`));
} else if (retries < RETRY_COUNT) {
setTimeout(() => {
retries++;
// eslint-disable-next-line no-console
console.log(
`API request (${url}) failed with: ${response.statusText}. Retrying. Retry number: ${retries}/${RETRY_COUNT}`,
);
resolve(request().then(retrier));
}, RETRY_INTERVAL);
} else {
reject(new Error(`Could not fetch ${url} within retry limit.`));
}
});

return request().then(retrier);
};

const fetchEvent = async (eventId: string): Promise<ApiEvent> => {
const response = await fetchFromSentry(`${baseUrl}/events/${eventId}/`);
const json = await response.json();
return json as ApiEvent;
};

const fetchReplay = async (replayId: string): Promise<any> => {
const response = await fetchFromSentry(`${baseUrl}/replays/${replayId}/`);
return response.json();
};

const fetchReplaySegmentVideo = async (replayId: string, segment: number): Promise<Blob> => {
const response = await fetchFromSentry(`${baseUrl}/replays/${replayId}/videos/${segment}/`);
return response.blob();
};

export { fetchEvent, fetchReplay, fetchReplaySegmentVideo };
10 changes: 10 additions & 0 deletions test/react-native/rn.patch.app.js
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,16 @@ Sentry.init({
release: '${SENTRY_RELEASE}',
dist: '${SENTRY_DIST}',
dsn: 'https://[email protected]/5428561',
debug: true,
_experiments: {
replaysOnErrorSampleRate: 1.0,
},
integrations: [
Sentry.mobileReplayIntegration({
maskAllText: true,
maskAllImages: true,
}),
],
});
`;
const e2eComponentPatch = '<EndToEndTestsScreen />';
Expand Down
Loading