@@ -57,21 +57,20 @@ pub async fn run(config: &Config, vm_config: &VmConfig) -> Result<TartInstance>
5757 log:: error!( "Failed to configure tart vm: {err}" ) ;
5858 }
5959
60- // Start VM
61- let mut tart_cmd = Command :: new ( "tart" ) ;
62- tart_cmd. args ( [ "run" , & machine_copy. name , "--serial" ] ) ;
63-
6460 if !vm_config. disks . is_empty ( ) {
6561 log:: warn!( "Mounting disks is not yet supported" )
6662 }
6763
64+ // Start VM
65+ let mut tart_cmd = tart ( ) ;
66+ tart_cmd. args ( [ "run" , & machine_copy. name , "--serial" ] ) ;
67+
6868 match config. runtime_opts . display {
6969 config:: Display :: None => {
7070 tart_cmd. arg ( "--no-graphics" ) ;
7171 }
7272 config:: Display :: Local => ( ) ,
7373 config:: Display :: Vnc => {
74- // tart_cmd.args(["--vnc-experimental", "--no-graphics"]);
7574 tart_cmd. args ( [ "--vnc" , "--no-graphics" ] ) ;
7675 }
7776 }
@@ -111,14 +110,13 @@ pub async fn run(config: &Config, vm_config: &VmConfig) -> Result<TartInstance>
111110 // Get IP address of VM
112111 log:: debug!( "Waiting for IP address" ) ;
113112
114- let mut tart_cmd = Command :: new ( "tart" ) ;
115- tart_cmd. args ( [
116- "ip" ,
117- & machine_copy. name ,
118- "--wait" ,
119- & format ! ( "{}" , OBTAIN_IP_TIMEOUT . as_secs( ) ) ,
120- ] ) ;
121- let output = tart_cmd. output ( ) . await . context ( "Could not obtain VM IP" ) ?;
113+ let output = tart ( )
114+ . args ( [ "ip" , & machine_copy. name ] )
115+ . args ( [ "--wait" , & format ! ( "{}" , OBTAIN_IP_TIMEOUT . as_secs( ) ) ] )
116+ . output ( )
117+ . await
118+ . context ( "Could not obtain VM IP" ) ?;
119+
122120 let ip_addr = std:: str:: from_utf8 ( & output. stdout )
123121 . context ( "'tart ip' returned non-UTF8" ) ?
124122 . trim ( )
@@ -160,9 +158,8 @@ impl MachineCopy {
160158 pub async fn clone_vm ( name : & str ) -> Result < Self > {
161159 let clone_name = format ! ( "test-{}" , Uuid :: new_v4( ) ) ;
162160
163- let mut tart_cmd = Command :: new ( "tart" ) ;
164- tart_cmd. args ( [ "clone" , name, & clone_name] ) ;
165- let output = tart_cmd
161+ let output = tart ( )
162+ . args ( [ "clone" , name, & clone_name] )
166163 . status ( )
167164 . await
168165 . context ( "failed to run 'tart clone'" ) ?;
@@ -187,10 +184,9 @@ impl MachineCopy {
187184 log:: info!( "Memory: {mem} MB" ) ;
188185 }
189186 if !args. is_empty ( ) {
190- let mut tart_cmd = Command :: new ( "tart" ) ;
191- tart_cmd. args ( [ "set" , & self . name ] ) ;
192- tart_cmd. args ( args) ;
193- tart_cmd
187+ tart ( )
188+ . args ( [ "set" , & self . name ] )
189+ . args ( args)
194190 . status ( )
195191 . await
196192 . context ( "failed to update tart config" ) ?;
@@ -215,11 +211,11 @@ impl MachineCopy {
215211 }
216212
217213 fn destroy_inner ( & mut self ) -> Result < ( ) > {
218- use std :: process :: Command ;
219-
220- let mut tart_cmd = Command :: new ( "tart" ) ;
221- tart_cmd . args ( [ "delete" , & self . name ] ) ;
222- let output = tart_cmd . status ( ) . context ( "Failed to run 'tart delete'" ) ?;
214+ let output = tart ( )
215+ . into_std ( )
216+ . args ( [ "delete" , & self . name ] )
217+ . status ( )
218+ . context ( "Failed to run 'tart delete'" ) ?;
223219 if !output. success ( ) {
224220 return Err ( anyhow ! ( "'tart delete' failed: {output}" ) ) ;
225221 }
@@ -233,3 +229,20 @@ impl Drop for MachineCopy {
233229 self . try_destroy ( ) ;
234230 }
235231}
232+
233+ /// Create a [`Command`] that invokes `tart`. Use [`Command::arg`] etc to specify a tart command.
234+ ///
235+ /// `tart` likes to be invoked as a non-privileged user. If this program was invoked with `sudo`,
236+ /// the returned [`Command`] will invoke `tart` using `sudo -u $SUDO_USER`.
237+ fn tart ( ) -> Command {
238+ if let Some ( user) = std:: env:: var ( "SUDO_USER" ) . ok ( ) {
239+ log:: debug!( "SUDO_USER is set. Invoking tart as user {user:?}" ) ;
240+ let mut tart_cmd = Command :: new ( "sudo" ) ;
241+ tart_cmd. args ( [ "-u" , & user] ) ;
242+ tart_cmd. arg ( "tart" ) ;
243+ tart_cmd
244+ } else {
245+ log:: debug!( "Invoking tart as current user" ) ;
246+ Command :: new ( "tart" )
247+ }
248+ }
0 commit comments