@@ -15,7 +15,7 @@ export interface VendorNetwork {
1515 readonly vendor : InvocationInput [ 'vendor' ] ;
1616}
1717interface NetworkIdentity { readonly allocationId : string ; readonly imageId : string ; readonly invocation : InvocationInput ;
18- readonly subnet : string }
18+ readonly subnet : string ; readonly proxyIp : string }
1919const identities = new WeakMap < VendorNetwork , NetworkIdentity > ( ) ;
2020const environment = ( ) => ( { PATH : process . env . PATH , DOCKER_HOST : process . env . DOCKER_HOST } ) ;
2121const deadline = ( timeoutMs : number ) => {
@@ -66,13 +66,17 @@ const validateVendorNetwork = (network: VendorNetwork, invocation: InvocationInp
6666 SecurityOpt ?: string [ ] ; Memory ?: number ; MemorySwap ?: number ; NanoCpus ?: number ; PidsLimit ?: number ;
6767 NetworkMode ?: string ; PidMode ?: string ; IpcMode ?: string ; UTSMode ?: string ; UsernsMode ?: string ;
6868 CgroupnsMode ?: string ; Devices ?: unknown [ ] | null ; DeviceRequests ?: unknown [ ] | null } ;
69- NetworkSettings ?: { Networks ?: Record < string , unknown > } ; Mounts ?: unknown [ ] } | undefined ;
69+ NetworkSettings ?: { Networks ?: Record < string , { IPAddress ?: string } > } ; Mounts ?: unknown [ ] } | undefined ;
70+ const image = JSON . parse ( docker ( [ 'image' , 'inspect' , identity . imageId ] , remaining ( ) ) ) [ 0 ] as
71+ { Config ?: { Env ?: string [ ] } } | undefined ;
7072 const inspectedNetwork = JSON . parse ( docker ( [ 'network' , 'inspect' , network . name ] , remaining ( ) ) ) [ 0 ] as
7173 { Internal ?: boolean ; Driver ?: string ; Labels ?: Record < string , string > ; IPAM ?: { Config ?: Array < { Subnet ?: string } > } ;
7274 Containers ?: Record < string , { Name ?: string } > } | undefined ;
7375 const networks = Object . keys ( inspect ?. NetworkSettings ?. Networks ?? { } ) . sort ( ) ;
7476 const endpoints = Object . values ( inspectedNetwork ?. Containers ?? { } ) . map ( value => value . Name ) . sort ( ) ;
7577 const allowedEndpoints = [ network . proxyContainer , ...( agentName ? [ agentName ] : [ ] ) ] ;
78+ const expectedEnvironment = [ ...( image ?. Config ?. Env ?? [ ] ) ,
79+ `CODEBOOST_ALLOWED_HOSTS=${ VENDOR_HOSTS [ network . vendor ] . join ( ',' ) } ` ] . sort ( ) ;
7680 if ( ! inspect ?. State ?. Running || inspect . Config ?. Image !== identity . imageId || inspect . Config ?. User !== '10001:10001'
7781 || inspect . Config ?. Labels ?. [ 'io.codeboost.egress' ] !== identity . allocationId || ! inspect . HostConfig ?. ReadonlyRootfs
7882 || inspect . HostConfig . Privileged || ! inspect . HostConfig . CapDrop ?. map ( value => value . toUpperCase ( ) ) . includes ( 'ALL' )
@@ -85,10 +89,10 @@ const validateVendorNetwork = (network: VendorNetwork, invocation: InvocationInp
8589 || inspect . HostConfig . UsernsMode !== '' || inspect . HostConfig . CgroupnsMode !== 'private'
8690 || ( inspect . HostConfig . Devices ?. length ?? 0 ) !== 0 || ( inspect . HostConfig . DeviceRequests ?. length ?? 0 ) !== 0
8791 || JSON . stringify ( networks ) !== JSON . stringify ( [ 'bridge' , network . name ] . sort ( ) ) || inspect . Mounts ?. length
88- || inspect . Config ?. Entrypoint ?. [ 0 ] !== 'node'
92+ || JSON . stringify ( inspect . Config ?. Entrypoint ) !== JSON . stringify ( [ 'node' ] )
8993 || JSON . stringify ( inspect . Config ?. Cmd ) !== JSON . stringify ( [ '/usr/local/lib/codeboost-egress-proxy.mjs' ] )
90- || inspect . Config . Env ?. filter ( value => value . startsWith ( 'CODEBOOST_ALLOWED_HOSTS=' ) ) . length !== 1
91- || ! inspect . Config . Env ?. includes ( `CODEBOOST_ALLOWED_HOSTS= ${ VENDOR_HOSTS [ network . vendor ] . join ( ',' ) } ` )
94+ || JSON . stringify ( [ ... ( inspect . Config . Env ?? [ ] ) ] . sort ( ) ) !== JSON . stringify ( expectedEnvironment )
95+ || inspect . NetworkSettings ?. Networks ?. [ network . name ] ?. IPAddress !== identity . proxyIp
9296 || ! inspectedNetwork ?. Internal || inspectedNetwork . Driver !== 'bridge'
9397 || inspectedNetwork . Labels ?. [ 'io.codeboost.egress' ] !== identity . allocationId
9498 || inspectedNetwork . IPAM ?. Config ?. length !== 1 || inspectedNetwork . IPAM . Config [ 0 ] ?. Subnet !== identity . subnet
@@ -129,8 +133,13 @@ export function createVendorNetwork(invocation: InvocationInput, imageId: string
129133 "socket.once('connect',()=>{socket.destroy();process.exit(0)});" ,
130134 "socket.once('error',()=>{socket.destroy();if(++attempts===50)process.exit(1);setTimeout(check,20)})};check();" ,
131135 ] . join ( '' ) ] , remaining ( ) ) ;
132- const network = Object . freeze ( { name, proxyContainer, proxyUrl : 'http://codeboost-proxy:3128' , vendor } ) ;
133- identities . set ( network , Object . freeze ( { allocationId, imageId, invocation, subnet } ) ) ;
136+ const proxyInspect = JSON . parse ( docker ( [ 'container' , 'inspect' , proxyContainer ] , remaining ( ) ) ) [ 0 ] as
137+ { NetworkSettings ?: { Networks ?: Record < string , { IPAddress ?: string } > } } | undefined ;
138+ const proxyIp = proxyInspect ?. NetworkSettings ?. Networks ?. [ name ] ?. IPAddress ;
139+ if ( ! proxyIp || ! / ^ 1 0 \. 2 5 4 \. \d { 1 , 3 } \. \d { 1 , 3 } $ / . test ( proxyIp ) )
140+ throw new Error ( 'Vendor proxy did not receive its expected internal address.' ) ;
141+ const network = Object . freeze ( { name, proxyContainer, proxyUrl : `http://${ proxyIp } :3128` , vendor } ) ;
142+ identities . set ( network , Object . freeze ( { allocationId, imageId, invocation, subnet, proxyIp } ) ) ;
134143 validateVendorNetwork ( network , invocation , undefined , remaining ) ;
135144 remaining ( ) ;
136145 return network ;
0 commit comments