Skip to content

Commit

Permalink
Merge branch 'develop' into nh/improve-nestjs-error-handling
Browse files Browse the repository at this point in the history
  • Loading branch information
nicohrubec authored Jul 10, 2024
2 parents 5a134ba + 3ad3bdd commit 2795344
Show file tree
Hide file tree
Showing 118 changed files with 842 additions and 291 deletions.
2 changes: 1 addition & 1 deletion .size-limit.js
Original file line number Diff line number Diff line change
Expand Up @@ -177,7 +177,7 @@ module.exports = [
path: createCDNPath('bundle.tracing.replay.min.js'),
gzip: false,
brotli: false,
limit: '220 KB',
limit: '221 KB',
},
{
name: 'CDN Bundle (incl. Tracing, Replay, Feedback) - uncompressed',
Expand Down
6 changes: 6 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -8,6 +8,12 @@

- "You miss 100 percent of the chances you don't take. — Wayne Gretzky" — Michael Scott

## 8.17.0

- feat: Upgrade OTEL deps (#12809)
- fix(nuxt): Add module to build:transpile script (#12843)
- fix(browser): Allow SDK initialization in NW.js apps (#12846)

## 8.16.0

### Important Changes
Expand Down
4 changes: 2 additions & 2 deletions dev-packages/browser-integration-tests/package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "@sentry-internal/browser-integration-tests",
"version": "8.16.0",
"version": "8.17.0",
"main": "index.js",
"license": "MIT",
"engines": {
Expand Down Expand Up @@ -43,7 +43,7 @@
"@babel/preset-typescript": "^7.16.7",
"@playwright/test": "^1.44.1",
"@sentry-internal/rrweb": "2.11.0",
"@sentry/browser": "8.16.0",
"@sentry/browser": "8.17.0",
"axios": "1.6.7",
"babel-loader": "^8.2.2",
"html-webpack-plugin": "^5.5.0",
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
(() => {
const startTime = Date.now();

function getElasped() {
const time = Date.now();
return time - startTime;
}

while (getElasped() < 101) {
//
}
})();
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import * as Sentry from '@sentry/browser';

window.Sentry = Sentry;

Sentry.init({
dsn: 'https://[email protected]/1337',
integrations: [
Sentry.browserTracingIntegration({ enableLongTask: false, enableLongAnimationFrame: false, idleTimeout: 9000 }),
],
tracesSampleRate: 1,
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
</head>
<body>
<div>Rendered Before Long Animation Frame</div>
<script src="https://example.com/path/to/script.js"></script>
</body>
</html>
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import type { Route } from '@playwright/test';
import { expect } from '@playwright/test';
import type { Event } from '@sentry/types';

import { sentryTest } from '../../../../utils/fixtures';
import { getFirstSentryEnvelopeRequest, shouldSkipTracingTest } from '../../../../utils/helpers';

sentryTest(
'should not capture long animation frame when flag is disabled.',
async ({ browserName, getLocalTestPath, page }) => {
// Long animation frames only work on chrome
if (shouldSkipTracingTest() || browserName !== 'chromium') {
sentryTest.skip();
}

await page.route('**/path/to/script.js', (route: Route) =>
route.fulfill({ path: `${__dirname}/assets/script.js` }),
);

const url = await getLocalTestPath({ testDir: __dirname });

const eventData = await getFirstSentryEnvelopeRequest<Event>(page, url);
const uiSpans = eventData.spans?.filter(({ op }) => op?.startsWith('ui'));

expect(uiSpans?.length).toBe(0);
},
);
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
function getElapsed(startTime) {
const time = Date.now();
return time - startTime;
}

function handleClick() {
const startTime = Date.now();
while (getElapsed(startTime) < 105) {
//
}
}

function start() {
const startTime = Date.now();
while (getElapsed(startTime) < 105) {
//
}
}

// trigger 2 long-animation-frame events
// one from the top-level and the other from an event-listener
start();

const button = document.getElementById('clickme');
button.addEventListener('click', handleClick);
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import * as Sentry from '@sentry/browser';

window.Sentry = Sentry;

Sentry.init({
dsn: 'https://[email protected]/1337',
integrations: [
Sentry.browserTracingIntegration({
idleTimeout: 9000,
enableLongTask: false,
enableLongAnimationFrame: true,
}),
],
tracesSampleRate: 1,
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
</head>
<body>
<div>Rendered Before Long Animation Frame</div>
<button id="clickme">
click me to start the long animation!
</button>
<script src="https://example.com/path/to/script.js"></script>
</body>
</html>
Original file line number Diff line number Diff line change
@@ -0,0 +1,112 @@
import type { Route } from '@playwright/test';
import { expect } from '@playwright/test';
import type { Event } from '@sentry/types';

import { SEMANTIC_ATTRIBUTE_SENTRY_OP, SEMANTIC_ATTRIBUTE_SENTRY_ORIGIN } from '@sentry/browser';
import { sentryTest } from '../../../../utils/fixtures';
import { getFirstSentryEnvelopeRequest, shouldSkipTracingTest } from '../../../../utils/helpers';

sentryTest(
'should capture long animation frame for top-level script.',
async ({ browserName, getLocalTestPath, page }) => {
// Long animation frames only work on chrome
if (shouldSkipTracingTest() || browserName !== 'chromium') {
sentryTest.skip();
}

await page.route('**/path/to/script.js', (route: Route) =>
route.fulfill({ path: `${__dirname}/assets/script.js` }),
);

const url = await getLocalTestPath({ testDir: __dirname });

const promise = getFirstSentryEnvelopeRequest<Event>(page);

await page.goto(url);

await new Promise(resolve => setTimeout(resolve, 1000));

const eventData = await promise;

const uiSpans = eventData.spans?.filter(({ op }) => op?.startsWith('ui.long-animation-frame'));

expect(uiSpans?.length).toEqual(1);

const [topLevelUISpan] = uiSpans || [];
expect(topLevelUISpan).toEqual(
expect.objectContaining({
op: 'ui.long-animation-frame',
description: 'Main UI thread blocked',
parent_span_id: eventData.contexts?.trace?.span_id,
data: {
'code.filepath': 'https://example.com/path/to/script.js',
'browser.script.source_char_position': 0,
'browser.script.invoker': 'https://example.com/path/to/script.js',
'browser.script.invoker_type': 'classic-script',
[SEMANTIC_ATTRIBUTE_SENTRY_OP]: 'ui.long-animation-frame',
[SEMANTIC_ATTRIBUTE_SENTRY_ORIGIN]: 'auto.ui.browser.metrics',
},
}),
);
const start = topLevelUISpan.start_timestamp ?? 0;
const end = topLevelUISpan.timestamp ?? 0;
const duration = end - start;

expect(duration).toBeGreaterThanOrEqual(0.1);
expect(duration).toBeLessThanOrEqual(0.15);
},
);

sentryTest(
'should capture long animation frame for event listener.',
async ({ browserName, getLocalTestPath, page }) => {
// Long animation frames only work on chrome
if (shouldSkipTracingTest() || browserName !== 'chromium') {
sentryTest.skip();
}

await page.route('**/path/to/script.js', (route: Route) =>
route.fulfill({ path: `${__dirname}/assets/script.js` }),
);

const url = await getLocalTestPath({ testDir: __dirname });

const promise = getFirstSentryEnvelopeRequest<Event>(page);

await page.goto(url);

// trigger long animation frame function
await page.getByRole('button').click();

await new Promise(resolve => setTimeout(resolve, 1000));

const eventData = await promise;

const uiSpans = eventData.spans?.filter(({ op }) => op?.startsWith('ui.long-animation-frame'));

expect(uiSpans?.length).toEqual(2);

// ignore the first ui span (top-level long animation frame)
const [, eventListenerUISpan] = uiSpans || [];

expect(eventListenerUISpan).toEqual(
expect.objectContaining({
op: 'ui.long-animation-frame',
description: 'Main UI thread blocked',
parent_span_id: eventData.contexts?.trace?.span_id,
data: {
'browser.script.invoker': 'BUTTON#clickme.onclick',
'browser.script.invoker_type': 'event-listener',
[SEMANTIC_ATTRIBUTE_SENTRY_OP]: 'ui.long-animation-frame',
[SEMANTIC_ATTRIBUTE_SENTRY_ORIGIN]: 'auto.ui.browser.metrics',
},
}),
);
const start = eventListenerUISpan.start_timestamp ?? 0;
const end = eventListenerUISpan.timestamp ?? 0;
const duration = end - start;

expect(duration).toBeGreaterThanOrEqual(0.1);
expect(duration).toBeLessThanOrEqual(0.15);
},
);
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
(() => {
const startTime = Date.now();

function getElasped() {
const time = Date.now();
return time - startTime;
}

while (getElasped() < 101) {
//
}
})();
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
import * as Sentry from '@sentry/browser';

window.Sentry = Sentry;

Sentry.init({
dsn: 'https://[email protected]/1337',
integrations: [
Sentry.browserTracingIntegration({ enableLongTask: true, enableLongAnimationFrame: true, idleTimeout: 9000 }),
],
tracesSampleRate: 1,
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
</head>
<body>
<div>Rendered Before Long Task</div>
<script src="https://example.com/path/to/script.js"></script>
</body>
</html>
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import type { Route } from '@playwright/test';
import { expect } from '@playwright/test';
import type { Event } from '@sentry/types';

import { sentryTest } from '../../../../utils/fixtures';
import { getFirstSentryEnvelopeRequest, shouldSkipTracingTest } from '../../../../utils/helpers';

sentryTest(
'should not capture long animation frame or long task when browser is non-chromium',
async ({ browserName, getLocalTestPath, page }) => {
// Only test non-chromium browsers
if (shouldSkipTracingTest() || browserName === 'chromium') {
sentryTest.skip();
}

await page.route('**/path/to/script.js', (route: Route) =>
route.fulfill({ path: `${__dirname}/assets/script.js` }),
);

const url = await getLocalTestPath({ testDir: __dirname });

const eventData = await getFirstSentryEnvelopeRequest<Event>(page, url);
const uiSpans = eventData.spans?.filter(({ op }) => op?.startsWith('ui'));

expect(uiSpans?.length).toBe(0);
},
);
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@
function getElapsed(startTime) {
const time = Date.now();
return time - startTime;
}

function handleClick() {
const startTime = Date.now();
while (getElapsed(startTime) < 105) {
//
}
}

function start() {
const startTime = Date.now();
while (getElapsed(startTime) < 105) {
//
}
}

// trigger 2 long-animation-frame events
// one from the top-level and the other from an event-listener
start();

const button = document.getElementById('clickme');
button.addEventListener('click', handleClick);
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
import * as Sentry from '@sentry/browser';

window.Sentry = Sentry;

Sentry.init({
dsn: 'https://[email protected]/1337',
integrations: [
Sentry.browserTracingIntegration({
idleTimeout: 9000,
enableLongTask: true,
enableLongAnimationFrame: true,
}),
],
tracesSampleRate: 1,
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
</head>
<body>
<div>Rendered Before Long Animation Frame</div>
<button id="clickme">
click me to start the long animation!
</button>
<script src="https://example.com/path/to/script.js"></script>
</body>
</html>
Loading

0 comments on commit 2795344

Please sign in to comment.