@@ -46,8 +46,12 @@ if (parsedArgs.help) {
4646 Deno . exit ( 1 ) ;
4747 break ;
4848 case "sudo-install" : {
49- const [ pkgx_dir , ...paths ] = args ;
50- await sudo_install ( pkgx_dir , paths ) ;
49+ const [ pkgx_dir , runtime_env , ...paths ] = args ;
50+ const parsed_runtime_env = JSON . parse ( runtime_env ) as Record <
51+ string ,
52+ Record < string , string >
53+ > ;
54+ await sudo_install ( pkgx_dir , paths , parsed_runtime_env ) ;
5155 break ;
5256 }
5357 default :
@@ -109,6 +113,8 @@ async function install(args: string[]) {
109113 const pkgx_dir = Deno . env . get ( "PKGX_DIR" ) || `${ Deno . env . get ( "HOME" ) } /.pkgx` ;
110114 const needs_sudo = Deno . uid ( ) != 0 ;
111115
116+ const runtime_env = expand_runtime_env ( json . runtime_env , json . pkgs ) ;
117+
112118 args = [
113119 "pkgx" ,
114120 "deno^2.1" ,
@@ -119,6 +125,7 @@ async function install(args: string[]) {
119125 self ,
120126 "sudo-install" ,
121127 pkgx_dir ,
128+ runtime_env ,
122129 ...to_install ,
123130 ] ;
124131 const cmd = needs_sudo ? "/usr/bin/sudo" : args . shift ( ) ! ;
@@ -127,7 +134,11 @@ async function install(args: string[]) {
127134 Deno . exit ( status . code ) ;
128135}
129136
130- async function sudo_install ( pkgx_dir : string , pkg_prefixes : string [ ] ) {
137+ async function sudo_install (
138+ pkgx_dir : string ,
139+ pkg_prefixes : string [ ] ,
140+ runtime_env : Record < string , Record < string , string > > ,
141+ ) {
131142 const dst = "/usr/local" ;
132143 for ( const pkg_prefix of pkg_prefixes ) {
133144 // create /usr/local/pkgs/${prefix}
@@ -137,6 +148,31 @@ async function sudo_install(pkgx_dir: string, pkg_prefixes: string[]) {
137148 // create v1, etc. symlinks
138149 await create_v_symlinks ( join ( "/usr/local/pkgs" , pkg_prefix ) ) ;
139150 }
151+
152+ for ( const [ project , env ] of Object . entries ( runtime_env ) ) {
153+ const pkg_prefix = pkg_prefixes . find ( ( x ) => x . startsWith ( project ) ) ! ;
154+ for ( const bin of [ "bin" , "sbin" ] ) {
155+ const bin_prefix = join ( "/usr/local/pkgs" , pkg_prefix , bin ) ;
156+
157+ if ( ! existsSync ( bin_prefix ) ) continue ;
158+
159+ for await ( const entry of Deno . readDir ( bin_prefix ) ) {
160+ if ( ! entry . isFile ) continue ;
161+
162+ const to_stub = join ( "/usr/local" , bin , entry . name ) ;
163+
164+ let sh = `#!/bin/sh\n` ;
165+ for ( const [ key , value ] of Object . entries ( env ) ) {
166+ sh += `export ${ key } ="${ value } "\n` ;
167+ }
168+ sh += `exec "${ bin_prefix } /${ entry . name } " "$@"\n` ;
169+
170+ await Deno . remove ( to_stub ) ; //FIXME inefficient to symlink for no reason
171+ await Deno . writeTextFile ( to_stub , sh ) ;
172+ await Deno . chmod ( to_stub , 0o755 ) ;
173+ }
174+ }
175+ }
140176}
141177
142178async function mirror_directory ( dst : string , src : string , prefix : string ) {
@@ -185,6 +221,10 @@ async function symlink(src: string, dst: string) {
185221 await processEntry ( entrySourcePath , entryTargetPath ) ;
186222 }
187223 } else {
224+ // resinstall
225+ if ( existsSync ( targetPath ) ) {
226+ await Deno . remove ( targetPath ) ;
227+ }
188228 await Deno . symlink ( sourcePath , targetPath ) ;
189229 }
190230 }
@@ -223,3 +263,20 @@ async function create_v_symlinks(prefix: string) {
223263 await Deno . symlink ( `v${ semver . format ( value ) } ` , join ( shelf , `v${ key } ` ) ) ;
224264 }
225265}
266+
267+ function expand_runtime_env (
268+ runtime_env : Record < string , Record < string , string > > ,
269+ pkgs : [ Record < string , string > ] ,
270+ ) {
271+ const expanded : Record < string , Record < string , string > > = { } ;
272+ for ( const [ project , env ] of Object . entries ( runtime_env ) ) {
273+ const expanded_env : Record < string , string > = { } ;
274+ const pkg = pkgs . find ( ( x ) => x . project === project ) ! ;
275+ for ( const [ key , value ] of Object . entries ( env ) ) {
276+ let new_value = value . replaceAll ( / \$ ? { { .* p r e f i x } } / g, "/usr/local" ) ;
277+ expanded_env [ key ] = new_value ;
278+ }
279+ expanded [ project ] = expanded_env ;
280+ }
281+ return JSON . stringify ( expanded ) ;
282+ }
0 commit comments