@@ -12,25 +12,43 @@ export function encodeURIPath(str: string) {
12
12
return str . replace ( / [ ^ A - Z a - z 0 - 9 \- . _ ~ ! $ & ' ( ) * + , ; = : @ ] + / g, encodeURIComponent ) ;
13
13
}
14
14
15
+ const EMPTY = /* @__PURE__ */ Object . freeze ( /* @__PURE__ */ Object . create ( null ) ) ;
16
+
15
17
export const createPathTagFunction = ( pathEncoder = encodeURIPath ) =>
16
18
function path ( statics : readonly string [ ] , ...params : readonly unknown [ ] ) : string {
17
19
// If there are no params, no processing is needed.
18
20
if ( statics . length === 1 ) return statics [ 0 ] ! ;
19
21
20
22
let postPath = false ;
23
+ const invalidSegments = [ ] ;
21
24
const path = statics . reduce ( ( previousValue , currentValue , index ) => {
22
25
if ( / [ ? # ] / . test ( currentValue ) ) {
23
26
postPath = true ;
24
27
}
25
- return (
26
- previousValue +
27
- currentValue +
28
- ( index === params . length ? '' : ( postPath ? encodeURIComponent : pathEncoder ) ( String ( params [ index ] ) ) )
29
- ) ;
28
+ const value = params [ index ] ;
29
+ let encoded = ( postPath ? encodeURIComponent : pathEncoder ) ( '' + value ) ;
30
+ if (
31
+ index !== params . length &&
32
+ ( value == null ||
33
+ ( typeof value === 'object' &&
34
+ // handle values from other realms
35
+ value . toString ===
36
+ Object . getPrototypeOf ( Object . getPrototypeOf ( ( value as any ) . hasOwnProperty ?? EMPTY ) ?? EMPTY )
37
+ ?. toString ) )
38
+ ) {
39
+ encoded = value + '' ;
40
+ invalidSegments . push ( {
41
+ start : previousValue . length + currentValue . length ,
42
+ length : encoded . length ,
43
+ error : `Value of type ${ Object . prototype . toString
44
+ . call ( value )
45
+ . slice ( 8 , - 1 ) } is not a valid path parameter`,
46
+ } ) ;
47
+ }
48
+ return previousValue + currentValue + ( index === params . length ? '' : encoded ) ;
30
49
} , '' ) ;
31
50
32
51
const pathOnly = path . split ( / [ ? # ] / , 1 ) [ 0 ] ! ;
33
- const invalidSegments = [ ] ;
34
52
const invalidSegmentPattern = / (?< = ^ | \/ ) (?: \. | % 2 e ) { 1 , 2 } (? = \/ | $ ) / gi;
35
53
let match ;
36
54
@@ -39,9 +57,12 @@ export const createPathTagFunction = (pathEncoder = encodeURIPath) =>
39
57
invalidSegments . push ( {
40
58
start : match . index ,
41
59
length : match [ 0 ] . length ,
60
+ error : `Value "${ match [ 0 ] } " can\'t be safely passed as a path parameter` ,
42
61
} ) ;
43
62
}
44
63
64
+ invalidSegments . sort ( ( a , b ) => a . start - b . start ) ;
65
+
45
66
if ( invalidSegments . length > 0 ) {
46
67
let lastEnd = 0 ;
47
68
const underline = invalidSegments . reduce ( ( acc , segment ) => {
@@ -52,7 +73,9 @@ export const createPathTagFunction = (pathEncoder = encodeURIPath) =>
52
73
} , '' ) ;
53
74
54
75
throw new AnthropicError (
55
- `Path parameters result in path with invalid segments:\n${ path } \n${ underline } ` ,
76
+ `Path parameters result in path with invalid segments:\n${ invalidSegments
77
+ . map ( ( e ) => e . error )
78
+ . join ( '\n' ) } \n${ path } \n${ underline } `,
56
79
) ;
57
80
}
58
81
0 commit comments