@@ -43,11 +43,14 @@ const admissions: Array<{
4343} > = [ ]
4444let originRequests = 0
4545let receivedHeaders : Record < string , unknown > = { }
46+ let receivedTarget = ''
4647const proxiedPorts = new Set < number > ( )
4748const secureOrigin = httpsServer ( async ( req , res ) => {
4849 res . setHeader ( 'x-via-proxy' , proxiedPorts . has ( req . socket . remotePort ?? 0 ) ? 'yes' : 'no' )
4950 originRequests ++
5051 receivedHeaders = req . headers
52+ receivedTarget = req . url ?? ''
53+ res . setHeader ( 'x-request-target' , receivedTarget )
5154 if ( req . url === '/redirect' ) {
5255 res . writeHead ( 302 , { location : '/done' } )
5356 res . end ( )
@@ -56,7 +59,7 @@ const secureOrigin = httpsServer(async (req, res) => {
5659 if ( req . url === '/wait' ) return
5760 const chunks : Buffer [ ] = [ ]
5861 for await ( const chunk of req ) chunks . push ( Buffer . from ( chunk ) )
59- res . end ( req . method === 'POST' ? Buffer . concat ( chunks ) : 'tls reached' )
62+ res . end ( req . method === 'POST' || req . method === 'PUT' ? Buffer . concat ( chunks ) : 'tls reached' )
6063} )
6164const proxy = httpsServer ( )
6265proxy . on ( 'connect' , ( req , socket , head ) => {
@@ -150,6 +153,28 @@ const url = () => 'https://origin.invalid'
150153const options = { profile : 'selfHostedService' as const }
151154
152155describe ( 'organization gateways over real TLS CONNECT sockets' , ( ) => {
156+ it ( 'preserves signed request targets and origin authentication through the gateway' , async ( ) => {
157+ const target = '/exports/../raw/audit_logs/event%2Fpart.ndjson?x-id=PutObject&token=%2B'
158+ const response = await runWithOutboundOrganization ( 'org_a' , ( ) =>
159+ secureFetchWithPinnedIP ( `${ url ( ) } ${ target } ` , '1.1.1.1' , {
160+ ...options ,
161+ requestTarget : target ,
162+ method : 'PUT' ,
163+ body : '{"id":"event"}\n' ,
164+ headers : {
165+ authorization : 'AWS4-HMAC-SHA256 signed-request' ,
166+ 'Proxy-Authorization' : 'must-not-reach-origin' ,
167+ } ,
168+ } )
169+ )
170+ expect ( await response . text ( ) ) . toBe ( '{"id":"event"}\n' )
171+ expect ( response . headers . get ( 'x-via-proxy' ) ) . toBe ( 'yes' )
172+ expect ( receivedTarget ) . toBe ( target )
173+ expect ( receivedHeaders . authorization ) . toBe ( 'AWS4-HMAC-SHA256 signed-request' )
174+ expect ( receivedHeaders [ 'proxy-authorization' ] ) . toBeUndefined ( )
175+ expect ( admissions . at ( - 1 ) ?. destination ) . toBe ( '1.1.1.1:443' )
176+ } )
177+
153178 it ( 'keeps an upgraded tunnel usable after five minutes' , async ( ) => {
154179 vi . useFakeTimers ( { toFake : [ 'setTimeout' , 'clearTimeout' ] } )
155180 let tunnel : Socket | undefined
@@ -312,7 +337,7 @@ describe('organization gateways over real TLS CONNECT sockets', () => {
312337 } ,
313338 }
314339 )
315- expect ( admissions . length ) . toBe ( start + 3 )
340+ expect ( admissions . length ) . toBe ( start + 4 )
316341 expect (
317342 admissions . slice ( start ) . every ( ( entry ) => entry . token === `Bearer ${ 'a' . repeat ( 48 ) } ` )
318343 ) . toBe ( true )
0 commit comments