1
+ // Copyright 2016 The Rust Project Developers. See the COPYRIGHT
2
+ // file at the top-level directory of this distribution and at
3
+ // http://rust-lang.org/COPYRIGHT.
4
+ //
5
+ // Licensed under the Apache License, Version 2.0 <LICENSE-APACHE or
6
+ // http://www.apache.org/licenses/LICENSE-2.0> or the MIT license
7
+ // <LICENSE-MIT or http://opensource.org/licenses/MIT>, at your
8
+ // option. This file may not be copied, modified, or distributed
9
+ // except according to those terms.
10
+
11
+ use std:: io:: { self , BufRead , BufReader , Read , Write } ;
12
+ use std:: mem;
13
+ use std:: process:: { Child , ChildStdin , ChildStdout } ;
14
+
15
+ use serde_json;
16
+
17
+ #[ derive( Clone , Debug ) ]
18
+ pub struct ExpectedMessage {
19
+ id : Option < u64 > ,
20
+ contains : Vec < String > ,
21
+ }
22
+
23
+ impl ExpectedMessage {
24
+ pub fn new ( id : Option < u64 > ) -> ExpectedMessage {
25
+ ExpectedMessage {
26
+ id : id,
27
+ contains : vec ! [ ] ,
28
+ }
29
+ }
30
+
31
+ pub fn expect_contains ( & mut self , s : & str ) -> & mut ExpectedMessage {
32
+ self . contains . push ( s. to_owned ( ) ) ;
33
+ self
34
+ }
35
+ }
36
+
37
+ pub fn read_message < R : Read > ( reader : & mut BufReader < R > ) -> io:: Result < String > {
38
+ let mut content_length = None ;
39
+ // Read the headers
40
+ loop {
41
+ let mut header = String :: new ( ) ;
42
+ reader. read_line ( & mut header) ?;
43
+ if header. len ( ) == 0 {
44
+ panic ! ( "eof" )
45
+ }
46
+ if header == "\r \n " {
47
+ // This is the end of the headers
48
+ break ;
49
+ }
50
+ let parts: Vec < & str > = header. splitn ( 2 , ": " ) . collect ( ) ;
51
+ if parts[ 0 ] == "Content-Length" {
52
+ content_length = Some ( parts[ 1 ] . trim ( ) . parse :: < usize > ( ) . unwrap ( ) )
53
+ }
54
+ }
55
+
56
+ // Read the actual message
57
+ let content_length = content_length. expect ( "did not receive Content-Length header" ) ;
58
+ let mut msg = vec ! [ 0 ; content_length] ;
59
+ reader. read_exact ( & mut msg) ?;
60
+ let result = String :: from_utf8_lossy ( & msg) . into_owned ( ) ;
61
+ Ok ( result)
62
+ }
63
+
64
+ pub fn expect_messages < R : Read > ( reader : & mut BufReader < R > , expected : & [ & ExpectedMessage ] ) {
65
+ let mut results: Vec < String > = Vec :: new ( ) ;
66
+ while results. len ( ) < expected. len ( ) {
67
+ results. push ( read_message ( reader) . unwrap ( ) ) ;
68
+ }
69
+
70
+ println ! (
71
+ "expect_messages:\n results: {:#?},\n expected: {:#?}" ,
72
+ results,
73
+ expected
74
+ ) ;
75
+ assert_eq ! ( results. len( ) , expected. len( ) ) ;
76
+ for ( found, expected) in results. iter ( ) . zip ( expected. iter ( ) ) {
77
+ let values: serde_json:: Value = serde_json:: from_str ( found) . unwrap ( ) ;
78
+ assert ! (
79
+ values
80
+ . get( "jsonrpc" )
81
+ . expect( "Missing jsonrpc field" )
82
+ . as_str( )
83
+ . unwrap( ) == "2.0" ,
84
+ "Bad jsonrpc field"
85
+ ) ;
86
+ if let Some ( id) = expected. id {
87
+ assert_eq ! (
88
+ values
89
+ . get( "id" )
90
+ . expect( "Missing id field" )
91
+ . as_u64( )
92
+ . unwrap( ) ,
93
+ id,
94
+ "Unexpected id"
95
+ ) ;
96
+ }
97
+ for c in expected. contains . iter ( ) {
98
+ found
99
+ . find ( c)
100
+ . expect ( & format ! ( "Could not find `{}` in `{}`" , c, found) ) ;
101
+ }
102
+ }
103
+ }
104
+
105
+ pub struct RlsHandle {
106
+ child : Child ,
107
+ stdin : ChildStdin ,
108
+ stdout : BufReader < ChildStdout > ,
109
+ }
110
+
111
+ impl RlsHandle {
112
+ pub fn new ( mut child : Child ) -> RlsHandle {
113
+ let stdin = mem:: replace ( & mut child. stdin , None ) . unwrap ( ) ;
114
+ let stdout = mem:: replace ( & mut child. stdout , None ) . unwrap ( ) ;
115
+ let stdout = BufReader :: new ( stdout) ;
116
+
117
+ RlsHandle {
118
+ child,
119
+ stdin,
120
+ stdout,
121
+ }
122
+ }
123
+
124
+ pub fn send_string ( & mut self , s : & str ) -> io:: Result < usize > {
125
+ let full_msg = format ! ( "Content-Length: {}\r \n \r \n {}" , s. len( ) , s) ;
126
+ self . stdin . write ( full_msg. as_bytes ( ) )
127
+ }
128
+ pub fn send ( & mut self , j : serde_json:: Value ) -> io:: Result < usize > {
129
+ self . send_string ( & j. to_string ( ) )
130
+ }
131
+ pub fn notify ( & mut self , method : & str , params : serde_json:: Value ) -> io:: Result < usize > {
132
+ self . send ( json ! ( {
133
+ "jsonrpc" : "2.0" ,
134
+ "method" : method,
135
+ "params" : params,
136
+ } ) )
137
+ }
138
+ pub fn request ( & mut self , id : u64 , method : & str , params : serde_json:: Value ) -> io:: Result < usize > {
139
+ self . send ( json ! ( {
140
+ "jsonrpc" : "2.0" ,
141
+ "id" : id,
142
+ "method" : method,
143
+ "params" : params,
144
+ } ) )
145
+ }
146
+ pub fn shutdown_exit ( & mut self ) {
147
+ self . request ( 99999 , "shutdown" , json ! ( { } ) ) . unwrap ( ) ;
148
+
149
+ self . expect_messages ( & [
150
+ & ExpectedMessage :: new ( Some ( 99999 ) ) ,
151
+ ] ) ;
152
+
153
+ self . notify ( "exit" , json ! ( { } ) ) . unwrap ( ) ;
154
+
155
+ let ecode = self . child . wait ( )
156
+ . expect ( "failed to wait on child rls process" ) ;
157
+
158
+ assert ! ( ecode. success( ) ) ;
159
+ }
160
+
161
+ pub fn expect_messages ( & mut self , expected : & [ & ExpectedMessage ] ) {
162
+ expect_messages ( & mut self . stdout , expected) ;
163
+ }
164
+ }
0 commit comments