add option to record on DOMContentLoaded event (#1109)
This commit is contained in:
1
guide.md
1
guide.md
@@ -158,6 +158,7 @@ The parameter of `rrweb.record` accepts the following options.
|
|||||||
| sampling | - | refer to the [storage optimization recipe](./docs/recipes/optimize-storage.md) |
|
| sampling | - | refer to the [storage optimization recipe](./docs/recipes/optimize-storage.md) |
|
||||||
| recordCanvas | false | Whether to record the canvas element. Available options:<br/>`false`, <br/>`true` |
|
| recordCanvas | false | Whether to record the canvas element. Available options:<br/>`false`, <br/>`true` |
|
||||||
| recordCrossOriginIframes | false | Whether to record cross origin iframes. rrweb has to be injected in each child iframe for this to work. Available options:<br/>`false`, <br/>`true` |
|
| recordCrossOriginIframes | false | Whether to record cross origin iframes. rrweb has to be injected in each child iframe for this to work. Available options:<br/>`false`, <br/>`true` |
|
||||||
|
| recordAfter | 'load' | If the document is not ready, then the recorder will start recording after the specified event is fired. Available options: `DOMContentLoaded`, `load` |
|
||||||
| inlineImages | false | whether to record the image content |
|
| inlineImages | false | whether to record the image content |
|
||||||
| collectFonts | false | whether to collect fonts in the website |
|
| collectFonts | false | whether to collect fonts in the website |
|
||||||
| userTriggeredOnInput | false | whether to add `userTriggered` on input events that indicates if this event was triggered directly by the user or not. [What is `userTriggered`?](https://github.com/rrweb-io/rrweb/pull/495) |
|
| userTriggeredOnInput | false | whether to add `userTriggered` on input events that indicates if this event was triggered directly by the user or not. [What is `userTriggered`?](https://github.com/rrweb-io/rrweb/pull/495) |
|
||||||
|
|||||||
@@ -154,6 +154,7 @@ setInterval(save, 10 * 1000);
|
|||||||
| dataURLOptions | {} | Canvas 图像快照的格式和质量,这个参数将传递给 OffscreenCanvas.convertToBlob(),使用这个参数能有效减小录制数据的大小 |
|
| dataURLOptions | {} | Canvas 图像快照的格式和质量,这个参数将传递给 OffscreenCanvas.convertToBlob(),使用这个参数能有效减小录制数据的大小 |
|
||||||
| recordCanvas | false | 是否记录 canvas 内容, 可用选项:`false`, `true` |
|
| recordCanvas | false | 是否记录 canvas 内容, 可用选项:`false`, `true` |
|
||||||
| recordCrossOriginIframes | false | 是否记录 cross origin iframes。 必须在每个子 iframe 中注入 rrweb 才能使其工作。 可用选项:`false`, `true` |
|
| recordCrossOriginIframes | false | 是否记录 cross origin iframes。 必须在每个子 iframe 中注入 rrweb 才能使其工作。 可用选项:`false`, `true` |
|
||||||
|
| recordAfter | 'load' | 如果 document 还没有加载完成,recorder 将会在指定的事件触发后开始录制。可用选项: `DOMContentLoaded`, `load` |
|
||||||
| inlineImages | false | 是否将图片内容记内联录制 |
|
| inlineImages | false | 是否将图片内容记内联录制 |
|
||||||
| collectFonts | false | 是否记录页面中的字体文件 |
|
| collectFonts | false | 是否记录页面中的字体文件 |
|
||||||
| userTriggeredOnInput | false | [什么是 `userTriggered`](https://github.com/rrweb-io/rrweb/pull/495) |
|
| userTriggeredOnInput | false | [什么是 `userTriggered`](https://github.com/rrweb-io/rrweb/pull/495) |
|
||||||
|
|||||||
@@ -76,6 +76,9 @@ function record<T = eventWithTime>(
|
|||||||
mousemoveWait,
|
mousemoveWait,
|
||||||
recordCanvas = false,
|
recordCanvas = false,
|
||||||
recordCrossOriginIframes = false,
|
recordCrossOriginIframes = false,
|
||||||
|
recordAfter = options.recordAfter === 'DOMContentLoaded'
|
||||||
|
? options.recordAfter
|
||||||
|
: 'load',
|
||||||
userTriggeredOnInput = false,
|
userTriggeredOnInput = false,
|
||||||
collectFonts = false,
|
collectFonts = false,
|
||||||
inlineImages = false,
|
inlineImages = false,
|
||||||
@@ -408,16 +411,6 @@ function record<T = eventWithTime>(
|
|||||||
|
|
||||||
try {
|
try {
|
||||||
const handlers: listenerHandler[] = [];
|
const handlers: listenerHandler[] = [];
|
||||||
handlers.push(
|
|
||||||
on('DOMContentLoaded', () => {
|
|
||||||
wrappedEmit(
|
|
||||||
wrapEvent({
|
|
||||||
type: EventType.DomContentLoaded,
|
|
||||||
data: {},
|
|
||||||
}),
|
|
||||||
);
|
|
||||||
}),
|
|
||||||
);
|
|
||||||
|
|
||||||
const observe = (doc: Document) => {
|
const observe = (doc: Document) => {
|
||||||
return initObservers(
|
return initObservers(
|
||||||
@@ -583,6 +576,17 @@ function record<T = eventWithTime>(
|
|||||||
) {
|
) {
|
||||||
init();
|
init();
|
||||||
} else {
|
} else {
|
||||||
|
handlers.push(
|
||||||
|
on('DOMContentLoaded', () => {
|
||||||
|
wrappedEmit(
|
||||||
|
wrapEvent({
|
||||||
|
type: EventType.DomContentLoaded,
|
||||||
|
data: {},
|
||||||
|
}),
|
||||||
|
);
|
||||||
|
if (recordAfter === 'DOMContentLoaded') init();
|
||||||
|
}),
|
||||||
|
);
|
||||||
handlers.push(
|
handlers.push(
|
||||||
on(
|
on(
|
||||||
'load',
|
'load',
|
||||||
@@ -593,7 +597,7 @@ function record<T = eventWithTime>(
|
|||||||
data: {},
|
data: {},
|
||||||
}),
|
}),
|
||||||
);
|
);
|
||||||
init();
|
if (recordAfter === 'load') init();
|
||||||
},
|
},
|
||||||
window,
|
window,
|
||||||
),
|
),
|
||||||
|
|||||||
@@ -61,6 +61,7 @@ export type recordOptions<T> = {
|
|||||||
dataURLOptions?: DataURLOptions;
|
dataURLOptions?: DataURLOptions;
|
||||||
recordCanvas?: boolean;
|
recordCanvas?: boolean;
|
||||||
recordCrossOriginIframes?: boolean;
|
recordCrossOriginIframes?: boolean;
|
||||||
|
recordAfter?: 'DOMContentLoaded' | 'load';
|
||||||
userTriggeredOnInput?: boolean;
|
userTriggeredOnInput?: boolean;
|
||||||
collectFonts?: boolean;
|
collectFonts?: boolean;
|
||||||
inlineImages?: boolean;
|
inlineImages?: boolean;
|
||||||
|
|||||||
@@ -8408,6 +8408,89 @@ exports[`record integration tests should record DOM node movement 2 1`] = `
|
|||||||
]"
|
]"
|
||||||
`;
|
`;
|
||||||
|
|
||||||
|
exports[`record integration tests should record after DOMContentLoaded event 1`] = `
|
||||||
|
"[
|
||||||
|
{
|
||||||
|
\\"type\\": 0,
|
||||||
|
\\"data\\": {}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
\\"type\\": 4,
|
||||||
|
\\"data\\": {
|
||||||
|
\\"href\\": \\"about:blank\\",
|
||||||
|
\\"width\\": 1920,
|
||||||
|
\\"height\\": 1080
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
\\"type\\": 2,
|
||||||
|
\\"data\\": {
|
||||||
|
\\"node\\": {
|
||||||
|
\\"type\\": 0,
|
||||||
|
\\"childNodes\\": [
|
||||||
|
{
|
||||||
|
\\"type\\": 2,
|
||||||
|
\\"tagName\\": \\"html\\",
|
||||||
|
\\"attributes\\": {},
|
||||||
|
\\"childNodes\\": [
|
||||||
|
{
|
||||||
|
\\"type\\": 2,
|
||||||
|
\\"tagName\\": \\"head\\",
|
||||||
|
\\"attributes\\": {},
|
||||||
|
\\"childNodes\\": [],
|
||||||
|
\\"id\\": 3
|
||||||
|
},
|
||||||
|
{
|
||||||
|
\\"type\\": 2,
|
||||||
|
\\"tagName\\": \\"body\\",
|
||||||
|
\\"attributes\\": {},
|
||||||
|
\\"childNodes\\": [
|
||||||
|
{
|
||||||
|
\\"type\\": 3,
|
||||||
|
\\"textContent\\": \\"\\\\n \\",
|
||||||
|
\\"id\\": 5
|
||||||
|
},
|
||||||
|
{
|
||||||
|
\\"type\\": 2,
|
||||||
|
\\"tagName\\": \\"script\\",
|
||||||
|
\\"attributes\\": {},
|
||||||
|
\\"childNodes\\": [
|
||||||
|
{
|
||||||
|
\\"type\\": 3,
|
||||||
|
\\"textContent\\": \\"SCRIPT_PLACEHOLDER\\",
|
||||||
|
\\"id\\": 7
|
||||||
|
}
|
||||||
|
],
|
||||||
|
\\"id\\": 6
|
||||||
|
},
|
||||||
|
{
|
||||||
|
\\"type\\": 3,
|
||||||
|
\\"textContent\\": \\"\\\\n \\\\n \\\\n\\\\n\\",
|
||||||
|
\\"id\\": 8
|
||||||
|
}
|
||||||
|
],
|
||||||
|
\\"id\\": 4
|
||||||
|
}
|
||||||
|
],
|
||||||
|
\\"id\\": 2
|
||||||
|
}
|
||||||
|
],
|
||||||
|
\\"compatMode\\": \\"BackCompat\\",
|
||||||
|
\\"id\\": 1
|
||||||
|
},
|
||||||
|
\\"initialOffset\\": {
|
||||||
|
\\"left\\": 0,
|
||||||
|
\\"top\\": 0
|
||||||
|
}
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
\\"type\\": 1,
|
||||||
|
\\"data\\": {}
|
||||||
|
}
|
||||||
|
]"
|
||||||
|
`;
|
||||||
|
|
||||||
exports[`record integration tests should record canvas mutations 1`] = `
|
exports[`record integration tests should record canvas mutations 1`] = `
|
||||||
"[
|
"[
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -984,4 +984,19 @@ describe('record integration tests', function (this: ISuite) {
|
|||||||
)) as eventWithTime[];
|
)) as eventWithTime[];
|
||||||
assertSnapshot(snapshots);
|
assertSnapshot(snapshots);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('should record after DOMContentLoaded event', async () => {
|
||||||
|
const page: puppeteer.Page = await browser.newPage();
|
||||||
|
await page.goto('about:blank');
|
||||||
|
await page.setContent(
|
||||||
|
getHtml.call(this, 'blank.html', {
|
||||||
|
recordAfter: 'DOMContentLoaded',
|
||||||
|
}),
|
||||||
|
);
|
||||||
|
|
||||||
|
const snapshots = (await page.evaluate(
|
||||||
|
'window.snapshots',
|
||||||
|
)) as eventWithTime[];
|
||||||
|
assertSnapshot(snapshots);
|
||||||
|
});
|
||||||
});
|
});
|
||||||
|
|||||||
@@ -601,6 +601,7 @@ export function generateRecordSnippet(options: recordOptions<eventWithTime>) {
|
|||||||
userTriggeredOnInput: ${options.userTriggeredOnInput},
|
userTriggeredOnInput: ${options.userTriggeredOnInput},
|
||||||
maskTextFn: ${options.maskTextFn},
|
maskTextFn: ${options.maskTextFn},
|
||||||
recordCanvas: ${options.recordCanvas},
|
recordCanvas: ${options.recordCanvas},
|
||||||
|
recordAfter: '${options.recordAfter || 'load'}',
|
||||||
inlineImages: ${options.inlineImages},
|
inlineImages: ${options.inlineImages},
|
||||||
plugins: ${options.plugins}
|
plugins: ${options.plugins}
|
||||||
});
|
});
|
||||||
|
|||||||
Reference in New Issue
Block a user