@@ -8,13 +8,11 @@ use std::path::PathBuf;
8
8
use std:: process:: Child ;
9
9
use std:: process:: Command ;
10
10
use std:: process:: Stdio ;
11
- use std:: sync:: atomic:: AtomicUsize ;
12
- use std:: sync:: atomic:: Ordering ;
13
11
use std:: sync:: Mutex ;
12
+ use std:: sync:: MutexGuard ;
14
13
15
14
lazy_static ! {
16
- static ref SERVER : Mutex <Option <Child >> = Mutex :: new( None ) ;
17
- static ref SERVER_COUNT : AtomicUsize = AtomicUsize :: new( 0 ) ;
15
+ static ref GUARD : Mutex <( ) > = Mutex :: new( ( ) ) ;
18
16
}
19
17
20
18
pub fn root_path ( ) -> PathBuf {
@@ -37,52 +35,45 @@ pub fn deno_exe_path() -> PathBuf {
37
35
p
38
36
}
39
37
40
- pub struct HttpServerGuard { }
38
+ pub struct HttpServerGuard < ' a > {
39
+ #[ allow( dead_code) ]
40
+ g : MutexGuard < ' a , ( ) > ,
41
+ child : Child ,
42
+ }
41
43
42
- impl Drop for HttpServerGuard {
44
+ impl < ' a > Drop for HttpServerGuard < ' a > {
43
45
fn drop ( & mut self ) {
44
- let count = SERVER_COUNT . fetch_sub ( 1 , Ordering :: Relaxed ) ;
45
- // If no more tests hold guard we can kill the server
46
- if count == 1 {
47
- kill_http_server ( ) ;
46
+ match self . child . try_wait ( ) {
47
+ Ok ( None ) => {
48
+ self . child . kill ( ) . expect ( "failed to kill http_server.py" ) ;
49
+ }
50
+ Ok ( Some ( status) ) => {
51
+ panic ! ( "http_server.py exited unexpectedly {}" , status)
52
+ }
53
+ Err ( e) => panic ! ( "http_server.py err {}" , e) ,
48
54
}
49
55
}
50
56
}
51
57
52
- fn kill_http_server ( ) {
53
- let mut server_guard = SERVER . lock ( ) . unwrap ( ) ;
54
- let mut child = server_guard
55
- . take ( )
56
- . expect ( "Trying to kill server but already killed" ) ;
57
- match child. try_wait ( ) {
58
- Ok ( None ) => {
59
- child. kill ( ) . expect ( "failed to kill http_server.py" ) ;
60
- }
61
- Ok ( Some ( status) ) => panic ! ( "http_server.py exited unexpectedly {}" , status) ,
62
- Err ( e) => panic ! ( "http_server.py err {}" , e) ,
63
- } ;
64
- }
58
+ /// Starts tools/http_server.py when the returned guard is dropped, the server
59
+ /// will be killed.
60
+ pub fn http_server < ' a > ( ) -> HttpServerGuard < ' a > {
61
+ // TODO(ry) Allow tests to use the http server in parallel.
62
+ let g = GUARD . lock ( ) . unwrap ( ) ;
65
63
66
- pub fn http_server ( ) -> HttpServerGuard {
67
- SERVER_COUNT . fetch_add ( 1 , Ordering :: Relaxed ) ;
68
- {
69
- let mut server_guard = SERVER . lock ( ) . unwrap ( ) ;
70
- if server_guard. is_none ( ) {
71
- println ! ( "tools/http_server.py starting..." ) ;
72
- let mut child = Command :: new ( "python" )
73
- . current_dir ( root_path ( ) )
74
- . args ( & [ "-u" , "tools/http_server.py" ] )
75
- . stdout ( Stdio :: piped ( ) )
76
- . spawn ( )
77
- . expect ( "failed to execute child" ) ;
64
+ println ! ( "tools/http_server.py starting..." ) ;
65
+ let mut child = Command :: new ( "python" )
66
+ . current_dir ( root_path ( ) )
67
+ . args ( & [ "-u" , "tools/http_server.py" ] )
68
+ . stdout ( Stdio :: piped ( ) )
69
+ . spawn ( )
70
+ . expect ( "failed to execute child" ) ;
78
71
79
- let stdout = child. stdout . as_mut ( ) . unwrap ( ) ;
80
- use std:: io:: { BufRead , BufReader } ;
81
- let mut lines = BufReader :: new ( stdout) . lines ( ) ;
82
- let line = lines. next ( ) . unwrap ( ) . unwrap ( ) ;
83
- assert ! ( line. starts_with( "ready" ) ) ;
84
- server_guard. replace ( child) ;
85
- }
86
- }
87
- HttpServerGuard { }
72
+ let stdout = child. stdout . as_mut ( ) . unwrap ( ) ;
73
+ use std:: io:: { BufRead , BufReader } ;
74
+ let mut lines = BufReader :: new ( stdout) . lines ( ) ;
75
+ let line = lines. next ( ) . unwrap ( ) . unwrap ( ) ;
76
+ assert ! ( line. starts_with( "ready" ) ) ;
77
+
78
+ HttpServerGuard { child, g }
88
79
}
0 commit comments