@stanterprise/playwright-reporter 0.0.14 → 0.0.15
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
|
@@ -42,6 +42,12 @@ function handleOnTestEndEvent(test, result, runId, client, options) {
|
|
|
42
42
|
// Serialize once to capture payload size for potential error logging
|
|
43
43
|
const serializedPayload = request.serializeBinary();
|
|
44
44
|
const payloadSize = serializedPayload.length;
|
|
45
|
+
// Warn if payload is unusually large (>1MB)
|
|
46
|
+
if (payloadSize > 1048576) {
|
|
47
|
+
console.warn(`Large payload detected for test "${test.title}": ${(payloadSize / BYTES_PER_MB).toFixed(2)}MB. ` +
|
|
48
|
+
`Attachments: ${attachments.length}, Metadata keys: ${Object.keys(metadata).length}, ` +
|
|
49
|
+
`Error length: ${errorMessage.length + stackTrace.length} bytes`);
|
|
50
|
+
}
|
|
45
51
|
// Fire-and-forget to avoid slowing tests
|
|
46
52
|
(0, grpcClient_1.reportUnary)(options, client, "/testsystem.v1.observer.TestEventCollector/ReportTestEnd", request, options.grpcTimeout).catch((e) => {
|
|
47
53
|
console.error(`Failed to report test end for "${test.title}" (payload size: ${(payloadSize / BYTES_PER_MB).toFixed(2)}MB)`, e);
|
|
@@ -7,7 +7,7 @@ declare const Attachment: typeof common.v1.common.Attachment;
|
|
|
7
7
|
/**
|
|
8
8
|
* Process Playwright test attachments into protobuf Attachment objects
|
|
9
9
|
* @param result Test result containing attachments
|
|
10
|
-
* @param maxAttachmentSize Maximum size for attachment content (default 10MB)
|
|
10
|
+
* @param maxAttachmentSize Maximum size for attachment content (default 1MB, reduced from 10MB)
|
|
11
11
|
*/
|
|
12
12
|
export declare function processAttachments(result: TestResult, maxAttachmentSize?: number): InstanceType<typeof Attachment>[];
|
|
13
13
|
/**
|
|
@@ -11,14 +11,16 @@ const BYTES_PER_MB = 1048576;
|
|
|
11
11
|
/**
|
|
12
12
|
* Process Playwright test attachments into protobuf Attachment objects
|
|
13
13
|
* @param result Test result containing attachments
|
|
14
|
-
* @param maxAttachmentSize Maximum size for attachment content (default 10MB)
|
|
14
|
+
* @param maxAttachmentSize Maximum size for attachment content (default 1MB, reduced from 10MB)
|
|
15
15
|
*/
|
|
16
|
-
function processAttachments(result, maxAttachmentSize =
|
|
16
|
+
function processAttachments(result, maxAttachmentSize = 1048576 // 1MB default (reduced from 10MB to prevent large payloads)
|
|
17
17
|
) {
|
|
18
18
|
const attachments = [];
|
|
19
19
|
if (!result.attachments || result.attachments.length === 0) {
|
|
20
20
|
return attachments;
|
|
21
21
|
}
|
|
22
|
+
let totalAttachmentSize = 0;
|
|
23
|
+
const MAX_TOTAL_ATTACHMENT_SIZE = 2097152; // 2MB total limit across all attachments
|
|
22
24
|
for (const attachment of result.attachments) {
|
|
23
25
|
const att = new Attachment({
|
|
24
26
|
name: attachment.name,
|
|
@@ -27,19 +29,29 @@ function processAttachments(result, maxAttachmentSize = 10485760 // 10MB default
|
|
|
27
29
|
// Always prefer path if available to avoid large payloads
|
|
28
30
|
if (attachment.path) {
|
|
29
31
|
att.uri = attachment.path;
|
|
32
|
+
attachments.push(att);
|
|
33
|
+
continue;
|
|
30
34
|
}
|
|
31
|
-
|
|
32
|
-
// Only include body content if it's within size limit
|
|
35
|
+
if (attachment.body) {
|
|
33
36
|
const bodySize = attachment.body.length;
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
}
|
|
37
|
-
else {
|
|
38
|
-
// Skip large attachments without path - log warning
|
|
37
|
+
// Check individual attachment size
|
|
38
|
+
if (bodySize > maxAttachmentSize) {
|
|
39
39
|
console.warn(`Attachment "${attachment.name}" (${(bodySize / BYTES_PER_MB).toFixed(2)}MB) exceeds max size ` +
|
|
40
40
|
`(${(maxAttachmentSize / BYTES_PER_MB).toFixed(2)}MB) and has no path. Skipping content.`);
|
|
41
41
|
// Still add the attachment metadata without content
|
|
42
|
+
attachments.push(att);
|
|
43
|
+
continue;
|
|
44
|
+
}
|
|
45
|
+
// Check total accumulated size
|
|
46
|
+
if (totalAttachmentSize + bodySize > MAX_TOTAL_ATTACHMENT_SIZE) {
|
|
47
|
+
console.warn(`Attachment "${attachment.name}" (${(bodySize / BYTES_PER_MB).toFixed(2)}MB) would exceed total attachment size limit ` +
|
|
48
|
+
`(${(MAX_TOTAL_ATTACHMENT_SIZE / BYTES_PER_MB).toFixed(2)}MB). Skipping content.`);
|
|
49
|
+
attachments.push(att);
|
|
50
|
+
continue;
|
|
42
51
|
}
|
|
52
|
+
// Include content if within limits
|
|
53
|
+
att.content = attachment.body;
|
|
54
|
+
totalAttachmentSize += bodySize;
|
|
43
55
|
}
|
|
44
56
|
attachments.push(att);
|
|
45
57
|
}
|
|
@@ -4,6 +4,28 @@ exports.buildAnnotationsMetadata = buildAnnotationsMetadata;
|
|
|
4
4
|
exports.buildTestMetadata = buildTestMetadata;
|
|
5
5
|
exports.buildStepMetadata = buildStepMetadata;
|
|
6
6
|
exports.toMetadataMap = toMetadataMap;
|
|
7
|
+
/**
|
|
8
|
+
* Maximum length for a single metadata value (100KB)
|
|
9
|
+
* Large values are often accidentally embedded test data or debug output
|
|
10
|
+
*/
|
|
11
|
+
const MAX_METADATA_VALUE_LENGTH = 102400;
|
|
12
|
+
/**
|
|
13
|
+
* Maximum total metadata size across all values (1MB)
|
|
14
|
+
*/
|
|
15
|
+
const MAX_TOTAL_METADATA_SIZE = 1048576;
|
|
16
|
+
/**
|
|
17
|
+
* Truncate a string to a maximum length with ellipsis indicator
|
|
18
|
+
* @param value String value to truncate
|
|
19
|
+
* @param maxLength Maximum length (default 100KB)
|
|
20
|
+
* @returns Truncated string with warning suffix if truncated
|
|
21
|
+
*/
|
|
22
|
+
function truncateValue(value, maxLength = MAX_METADATA_VALUE_LENGTH) {
|
|
23
|
+
if (value.length <= maxLength) {
|
|
24
|
+
return value;
|
|
25
|
+
}
|
|
26
|
+
const truncated = value.substring(0, maxLength - 100);
|
|
27
|
+
return `${truncated}... [TRUNCATED: original length ${value.length} bytes, showing first ${maxLength - 100} bytes]`;
|
|
28
|
+
}
|
|
7
29
|
/**
|
|
8
30
|
* Build metadata from annotations array
|
|
9
31
|
* @param annotations Array of annotations with type and optional description
|
|
@@ -12,12 +34,25 @@ exports.toMetadataMap = toMetadataMap;
|
|
|
12
34
|
*/
|
|
13
35
|
function buildAnnotationsMetadata(annotations, prefix = "annotation") {
|
|
14
36
|
const metadata = {};
|
|
15
|
-
|
|
16
|
-
|
|
37
|
+
let totalSize = 0;
|
|
38
|
+
for (let index = 0; index < annotations.length; index++) {
|
|
39
|
+
const annotation = annotations[index];
|
|
40
|
+
const typeKey = `${prefix}_${index}_type`;
|
|
41
|
+
const typeValue = annotation.type;
|
|
42
|
+
metadata[typeKey] = typeValue;
|
|
43
|
+
totalSize += typeValue.length;
|
|
17
44
|
if (annotation.description) {
|
|
18
|
-
|
|
45
|
+
const descKey = `${prefix}_${index}_description`;
|
|
46
|
+
const descValue = truncateValue(annotation.description);
|
|
47
|
+
// Skip if adding this would exceed total metadata size
|
|
48
|
+
if (totalSize + descValue.length > MAX_TOTAL_METADATA_SIZE) {
|
|
49
|
+
console.warn(`Skipping annotation description for ${typeKey}: would exceed total metadata size limit (${MAX_TOTAL_METADATA_SIZE} bytes)`);
|
|
50
|
+
continue;
|
|
51
|
+
}
|
|
52
|
+
metadata[descKey] = descValue;
|
|
53
|
+
totalSize += descValue.length;
|
|
19
54
|
}
|
|
20
|
-
}
|
|
55
|
+
}
|
|
21
56
|
return metadata;
|
|
22
57
|
}
|
|
23
58
|
/**
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@stanterprise/playwright-reporter",
|
|
3
|
-
"version": "0.0.
|
|
3
|
+
"version": "0.0.15",
|
|
4
4
|
"description": "Custom Playwright test reporter that sends test results to Stanterprise via gRPC",
|
|
5
5
|
"homepage": "https://github.com/stanterprise/stanterprise-playwright-reporter#readme",
|
|
6
6
|
"bugs": {
|