@@ -13,6 +13,7 @@ use std::{
13
13
} ;
14
14
15
15
use clap:: Args ;
16
+ use log:: info;
16
17
17
18
use crate :: Result ;
18
19
@@ -36,6 +37,10 @@ pub struct RunTestsArgs {
36
37
/// Timeout for test commands in seconds
37
38
#[ clap( short, long, default_value = "15" ) ]
38
39
pub timeout : u64 ,
40
+
41
+ /// Whether to build espflash before running tests, true by default
42
+ #[ arg( long, value_parser = clap:: value_parser!( bool ) ) ]
43
+ pub local_espflash : Option < bool > ,
39
44
}
40
45
41
46
/// A struct to manage and run tests for the espflash
@@ -48,16 +53,24 @@ pub struct TestRunner {
48
53
pub timeout : Duration ,
49
54
/// Optional chip target for tests
50
55
pub chip : Option < String > ,
56
+ /// Build espflash before running tests
57
+ pub local_espflash : Option < bool > ,
51
58
}
52
59
53
60
impl TestRunner {
54
61
/// Creates a new [TestRunner] instance
55
- pub fn new ( workspace : & Path , tests_dir : PathBuf , timeout_secs : u64 ) -> Self {
62
+ pub fn new (
63
+ workspace : & Path ,
64
+ tests_dir : PathBuf ,
65
+ timeout_secs : u64 ,
66
+ local_espflash : bool ,
67
+ ) -> Self {
56
68
Self {
57
69
workspace : workspace. to_path_buf ( ) ,
58
70
tests_dir,
59
71
timeout : Duration :: from_secs ( timeout_secs) ,
60
72
chip : None ,
73
+ local_espflash : Some ( local_espflash) ,
61
74
}
62
75
}
63
76
@@ -85,7 +98,8 @@ impl TestRunner {
85
98
}
86
99
}
87
100
88
- fn spawn_and_capture_output ( mut cmd : Command ) -> Result < SpawnedCommandOutput > {
101
+ fn spawn_and_capture_output ( cmd : & mut Command ) -> Result < SpawnedCommandOutput > {
102
+ info ! ( "Spawning command: {cmd:?}" ) ;
89
103
cmd. stdout ( Stdio :: piped ( ) ) . stderr ( Stdio :: piped ( ) ) ;
90
104
let mut child = cmd. spawn ( ) ?;
91
105
let stdout = child. stdout . take ( ) . expect ( "Failed to capture stdout" ) ;
@@ -192,9 +206,36 @@ impl TestRunner {
192
206
Ok ( naturally_terminated)
193
207
}
194
208
209
+ fn build_espflash ( & self ) {
210
+ let mut cmd = Command :: new ( "cargo" ) ;
211
+
212
+ log:: info!( "Building espflash..." ) ;
213
+ cmd. args ( [ "build" , "-p" , "espflash" , "--release" , "--" ] ) ;
214
+
215
+ let status = cmd. status ( ) . expect ( "Failed to build espflash" ) ;
216
+ if !status. success ( ) {
217
+ panic ! ( "espflash build failed with status: {status}" ) ;
218
+ }
219
+ }
220
+
195
221
fn create_espflash_command ( & self , args : & [ & str ] ) -> Command {
196
222
let mut cmd = Command :: new ( "cargo" ) ;
197
- cmd. args ( [ "run" , "-p" , "espflash" , "--release" , "--" ] ) ;
223
+
224
+ // we need to distinguish between local and CI runs, on CI we are building
225
+ // espflash and then copying the binary, so we can use just `espflash`
226
+ match self . local_espflash {
227
+ None | Some ( true ) => {
228
+ log:: info!( "Running cargo run..." ) ;
229
+ cmd. args ( [ "run" , "-p" , "espflash" , "--release" , "--quiet" , "--" ] ) ;
230
+ }
231
+ Some ( false ) => {
232
+ log:: info!( "Using system espflash" ) ;
233
+ let mut cmd = Command :: new ( "espflash" ) ;
234
+ cmd. args ( args) ;
235
+ return cmd;
236
+ }
237
+ }
238
+
198
239
cmd. args ( args) ;
199
240
200
241
cmd
@@ -213,7 +254,7 @@ impl TestRunner {
213
254
let mut cmd = self . create_espflash_command ( args) ;
214
255
215
256
if let Some ( expected) = expected_contains {
216
- let ( mut child, output, h1, h2) = Self :: spawn_and_capture_output ( cmd) ?;
257
+ let ( mut child, output, h1, h2) = Self :: spawn_and_capture_output ( & mut cmd) ?;
217
258
let start_time = Instant :: now ( ) ;
218
259
let mut terminated_naturally = false ;
219
260
@@ -270,7 +311,7 @@ impl TestRunner {
270
311
let mut cmd = self . create_espflash_command ( args) ;
271
312
272
313
if let Some ( expected) = expected_contains {
273
- let ( mut child, output, h1, h2) = Self :: spawn_and_capture_output ( cmd) ?;
314
+ let ( mut child, output, h1, h2) = Self :: spawn_and_capture_output ( & mut cmd) ?;
274
315
thread:: sleep ( duration) ;
275
316
let _ = child. kill ( ) ;
276
317
let _ = child. wait ( ) ;
@@ -885,7 +926,18 @@ pub fn run_tests(workspace: &Path, args: RunTestsArgs) -> Result<()> {
885
926
log:: info!( "Running espflash tests" ) ;
886
927
887
928
let tests_dir = workspace. join ( "espflash" ) . join ( "tests" ) ;
888
- let test_runner = TestRunner :: new ( workspace, tests_dir, args. timeout ) ;
929
+ let test_runner = TestRunner :: new (
930
+ workspace,
931
+ tests_dir,
932
+ args. timeout ,
933
+ args. local_espflash . unwrap_or ( true ) ,
934
+ ) ;
935
+
936
+ // Build espflash before running test(s) so we are not "waisting" test's
937
+ // duration or timeout
938
+ if args. local_espflash . unwrap_or ( true ) {
939
+ test_runner. build_espflash ( ) ;
940
+ }
889
941
890
942
match args. test . as_str ( ) {
891
943
"all" => {
0 commit comments