@@ -4,11 +4,13 @@ import { dropUndefinedKeys } from '@sentry/utils';
4
4
import { NETWORK_BODY_MAX_SIZE } from '../../constants' ;
5
5
import type {
6
6
NetworkBody ,
7
+ NetworkMetaWarning ,
7
8
NetworkRequestData ,
8
9
ReplayNetworkRequestData ,
9
10
ReplayNetworkRequestOrResponse ,
10
11
ReplayPerformanceEntry ,
11
12
} from '../../types' ;
13
+ import { fixJson } from '../../util/truncateJson/fixJson' ;
12
14
13
15
/** Get the size of a body. */
14
16
export function getBodySize (
@@ -122,7 +124,7 @@ export function getNetworkBody(bodyText: string | undefined): NetworkBody | unde
122
124
export function buildNetworkRequestOrResponse (
123
125
headers : Record < string , string > ,
124
126
bodySize : number | undefined ,
125
- body : NetworkBody | undefined ,
127
+ body : string | undefined ,
126
128
) : ReplayNetworkRequestOrResponse | undefined {
127
129
if ( ! bodySize && Object . keys ( headers ) . length === 0 ) {
128
130
return undefined ;
@@ -146,11 +148,11 @@ export function buildNetworkRequestOrResponse(
146
148
size : bodySize ,
147
149
} ;
148
150
149
- if ( bodySize < NETWORK_BODY_MAX_SIZE ) {
150
- info . body = body ;
151
- } else {
151
+ const { body : normalizedBody , warnings } = normalizeNetworkBody ( body ) ;
152
+ info . body = normalizedBody ;
153
+ if ( warnings . length > 0 ) {
152
154
info . _meta = {
153
- errors : [ 'MAX_BODY_SIZE_EXCEEDED' ] ,
155
+ warnings ,
154
156
} ;
155
157
}
156
158
@@ -175,3 +177,46 @@ function _serializeFormData(formData: FormData): string {
175
177
// @ts -ignore passing FormData to URLSearchParams actually works
176
178
return new URLSearchParams ( formData ) . toString ( ) ;
177
179
}
180
+
181
+ function normalizeNetworkBody ( body : string | undefined ) : {
182
+ body : NetworkBody | undefined ;
183
+ warnings : NetworkMetaWarning [ ] ;
184
+ } {
185
+ if ( ! body || typeof body !== 'string' ) {
186
+ return {
187
+ body,
188
+ warnings : [ ] ,
189
+ } ;
190
+ }
191
+
192
+ const exceedsSizeLimit = body . length > NETWORK_BODY_MAX_SIZE ;
193
+
194
+ if ( _strIsProbablyJson ( body ) ) {
195
+ try {
196
+ const json = exceedsSizeLimit ? fixJson ( body . slice ( 0 , NETWORK_BODY_MAX_SIZE ) ) : body ;
197
+ const normalizedBody = JSON . parse ( json ) ;
198
+ return {
199
+ body : normalizedBody ,
200
+ warnings : exceedsSizeLimit ? [ 'JSON_TRUNCATED' ] : [ ] ,
201
+ } ;
202
+ } catch {
203
+ return {
204
+ body,
205
+ warnings : [ 'INVALID_JSON' ] ,
206
+ } ;
207
+ }
208
+ }
209
+
210
+ return {
211
+ body : exceedsSizeLimit ? `${ body . slice ( 0 , NETWORK_BODY_MAX_SIZE ) } …` : body ,
212
+ warnings : exceedsSizeLimit ? [ 'TEXT_TRUNCATED' ] : [ ] ,
213
+ } ;
214
+ }
215
+
216
+ function _strIsProbablyJson ( str : string ) : boolean {
217
+ const first = str [ 0 ] ;
218
+ const last = str [ str . length - 1 ] ;
219
+
220
+ // Simple check: If this does not start & end with {} or [], it's not JSON
221
+ return ( first === '[' && last === ']' ) || ( first === '{' && last === '}' ) ;
222
+ }
0 commit comments