1616//! ```
1717
1818use futures:: prelude:: * ;
19- use reqwest:: { self , Client as ReqwestClient , StatusCode , Url } ;
19+ use reqwest:: { self , Client as ReqwestClient , StatusCode } ;
2020
2121use crate :: query:: QueryTypes ;
2222use crate :: Error ;
2323use crate :: Query ;
24-
25- #[ derive( Clone , Debug ) ]
26- /// Internal Authentication representation
27- pub ( crate ) struct Authentication {
28- pub username : String ,
29- pub password : String ,
30- }
24+ use std:: sync:: Arc ;
3125
3226#[ derive( Clone , Debug ) ]
3327/// Internal Representation of a Client
3428pub struct Client {
35- url : String ,
36- database : String ,
37- auth : Option < Authentication > ,
38- }
39-
40- impl Into < Vec < ( String , String ) > > for Client {
41- fn into ( self ) -> Vec < ( String , String ) > {
42- let mut vec: Vec < ( String , String ) > = Vec :: new ( ) ;
43- vec. push ( ( "db" . to_string ( ) , self . database ) ) ;
44- if let Some ( auth) = self . auth {
45- vec. push ( ( "u" . to_string ( ) , auth. username ) ) ;
46- vec. push ( ( "p" . to_string ( ) , auth. password ) ) ;
47- }
48- vec
49- }
50- }
51-
52- impl < ' a > Into < Vec < ( String , String ) > > for & ' a Client {
53- fn into ( self ) -> Vec < ( String , String ) > {
54- let mut vec: Vec < ( String , String ) > = Vec :: new ( ) ;
55- vec. push ( ( "db" . to_string ( ) , self . database . to_owned ( ) ) ) ;
56- if let Some ( auth) = & self . auth {
57- vec. push ( ( "u" . to_string ( ) , auth. username . to_owned ( ) ) ) ;
58- vec. push ( ( "p" . to_string ( ) , auth. password . to_owned ( ) ) ) ;
59- }
60- vec
61- }
29+ pub ( crate ) url : Arc < String > ,
30+ pub ( crate ) parameters : Arc < Vec < ( & ' static str , String ) > > ,
31+ pub ( crate ) client : ReqwestClient ,
6232}
6333
6434impl Client {
@@ -82,9 +52,9 @@ impl Client {
8252 S2 : Into < String > ,
8353 {
8454 Client {
85- url : url. into ( ) ,
86- database : database. into ( ) ,
87- auth : None ,
55+ url : Arc :: new ( url. into ( ) ) ,
56+ parameters : Arc :: new ( vec ! [ ( "db" , database. into( ) ) ] ) ,
57+ client : ReqwestClient :: new ( ) ,
8858 }
8959 }
9060
@@ -93,7 +63,7 @@ impl Client {
9363 /// # Arguments
9464 ///
9565 /// * username: The Username for InfluxDB.
96- /// * password: THe Password for the user.
66+ /// * password: The Password for the user.
9767 ///
9868 /// # Examples
9969 ///
@@ -107,16 +77,17 @@ impl Client {
10777 S1 : Into < String > ,
10878 S2 : Into < String > ,
10979 {
110- self . auth = Some ( Authentication {
111- username : username . into ( ) ,
112- password : password . into ( ) ,
113- } ) ;
80+ let mut with_auth = self . parameters . as_ref ( ) . clone ( ) ;
81+ with_auth . push ( ( "u" , username. into ( ) ) ) ;
82+ with_auth . push ( ( "p" , password. into ( ) ) ) ;
83+ self . parameters = Arc :: new ( with_auth ) ;
11484 self
11585 }
11686
11787 /// Returns the name of the database the client is using
11888 pub fn database_name ( & self ) -> & str {
119- & self . database
89+ // safe to unwrap: we always set the database name in `Self::new`
90+ & self . parameters . first ( ) . unwrap ( ) . 1
12091 }
12192
12293 /// Returns the URL of the InfluxDB installation the client is using
@@ -128,7 +99,11 @@ impl Client {
12899 ///
129100 /// Returns a tuple of build type and version number
130101 pub async fn ping ( & self ) -> Result < ( String , String ) , Error > {
131- let res = reqwest:: get ( format ! ( "{}/ping" , self . url) . as_str ( ) )
102+ let url = & format ! ( "{}/ping" , self . url) ;
103+ let res = self
104+ . client
105+ . get ( url)
106+ . send ( )
132107 . await
133108 . map_err ( |err| Error :: ProtocolError {
134109 error : format ! ( "{}" , err) ,
@@ -197,45 +172,45 @@ impl Client {
197172 error : format ! ( "{}" , err) ,
198173 } ) ?;
199174
200- let basic_parameters: Vec < ( String , String ) > = self . into ( ) ;
201-
202- let client = match q. into ( ) {
175+ let request_builder = match q. into ( ) {
203176 QueryTypes :: Read ( _) => {
204177 let read_query = query. get ( ) ;
205- let mut url = Url :: parse_with_params (
206- format ! ( "{url}/query" , url = self . database_url( ) ) . as_str ( ) ,
207- basic_parameters,
208- )
209- . map_err ( |err| Error :: UrlConstructionError {
210- error : format ! ( "{}" , err) ,
211- } ) ?;
212-
213- url. query_pairs_mut ( ) . append_pair ( "q" , & read_query) ;
178+ let url = & format ! ( "{}/query" , & self . url) ;
179+ let query = [ ( "q" , & read_query) ] ;
214180
215181 if read_query. contains ( "SELECT" ) || read_query. contains ( "SHOW" ) {
216- ReqwestClient :: new ( ) . get ( url)
182+ self . client
183+ . get ( url)
184+ . query ( self . parameters . as_ref ( ) )
185+ . query ( & query)
217186 } else {
218- ReqwestClient :: new ( ) . post ( url)
187+ self . client
188+ . post ( url)
189+ . query ( self . parameters . as_ref ( ) )
190+ . query ( & query)
219191 }
220192 }
221193 QueryTypes :: Write ( write_query) => {
222- let mut url = Url :: parse_with_params (
223- format ! ( "{url}/write" , url = self . database_url( ) ) . as_str ( ) ,
224- basic_parameters,
225- )
226- . map_err ( |err| Error :: InvalidQueryError {
227- error : format ! ( "{}" , err) ,
228- } ) ?;
229-
230- url. query_pairs_mut ( )
231- . append_pair ( "precision" , & write_query. get_precision ( ) ) ;
232-
233- ReqwestClient :: new ( ) . post ( url) . body ( query. get ( ) )
194+ let url = & format ! ( "{}/write" , & self . url) ;
195+ let precision = [ ( "precision" , write_query. get_precision ( ) ) ] ;
196+
197+ self . client
198+ . post ( url)
199+ . query ( self . parameters . as_ref ( ) )
200+ . query ( & precision)
201+ . body ( query. get ( ) )
234202 }
235203 } ;
236204
237- let res = client
238- . send ( )
205+ let request = request_builder
206+ . build ( )
207+ . map_err ( |err| Error :: UrlConstructionError {
208+ error : format ! ( "{}" , & err) ,
209+ } ) ?;
210+
211+ let res = self
212+ . client
213+ . execute ( request)
239214 . map_err ( |err| Error :: ConnectionError { error : err } )
240215 . await ?;
241216
@@ -262,67 +237,28 @@ impl Client {
262237
263238#[ cfg( test) ]
264239mod tests {
265- use crate :: Client ;
240+ use super :: Client ;
266241
267242 #[ test]
268243 fn test_fn_database ( ) {
269244 let client = Client :: new ( "http://localhost:8068" , "database" ) ;
270- assert_eq ! ( "database" , client. database_name( ) ) ;
245+ assert_eq ! ( client. database_name( ) , "database" ) ;
246+ assert_eq ! ( client. database_url( ) , "http://localhost:8068" ) ;
271247 }
272248
273249 #[ test]
274250 fn test_with_auth ( ) {
275251 let client = Client :: new ( "http://localhost:8068" , "database" ) ;
276- assert_eq ! ( client. url, "http://localhost:8068" ) ;
277- assert_eq ! ( client. database, "database" ) ;
278- assert ! ( client. auth. is_none( ) ) ;
279- let with_auth = client. with_auth ( "username" , "password" ) ;
280- assert ! ( with_auth. auth. is_some( ) ) ;
281- let auth = with_auth. auth . unwrap ( ) ;
282- assert_eq ! ( & auth. username, "username" ) ;
283- assert_eq ! ( & auth. password, "password" ) ;
284- }
285-
286- #[ test]
287- fn test_into_impl ( ) {
288- let client = Client :: new ( "http://localhost:8068" , "database" ) ;
289- assert ! ( client. auth. is_none( ) ) ;
290- let basic_parameters: Vec < ( String , String ) > = client. into ( ) ;
291- assert_eq ! (
292- vec![ ( "db" . to_string( ) , "database" . to_string( ) ) ] ,
293- basic_parameters
294- ) ;
295-
296- let with_auth =
297- Client :: new ( "http://localhost:8068" , "database" ) . with_auth ( "username" , "password" ) ;
298- let basic_parameters_with_auth: Vec < ( String , String ) > = with_auth. into ( ) ;
299- assert_eq ! (
300- vec![
301- ( "db" . to_string( ) , "database" . to_string( ) ) ,
302- ( "u" . to_string( ) , "username" . to_string( ) ) ,
303- ( "p" . to_string( ) , "password" . to_string( ) )
304- ] ,
305- basic_parameters_with_auth
306- ) ;
307-
308- let client = Client :: new ( "http://localhost:8068" , "database" ) ;
309- assert ! ( client. auth. is_none( ) ) ;
310- let basic_parameters: Vec < ( String , String ) > = ( & client) . into ( ) ;
311- assert_eq ! (
312- vec![ ( "db" . to_string( ) , "database" . to_string( ) ) ] ,
313- basic_parameters
314- ) ;
252+ assert_eq ! ( vec![ ( "db" , "database" . to_string( ) ) ] , * client. parameters) ;
315253
316- let with_auth =
317- Client :: new ( "http://localhost:8068" , "database" ) . with_auth ( "username" , "password" ) ;
318- let basic_parameters_with_auth: Vec < ( String , String ) > = ( & with_auth) . into ( ) ;
254+ let with_auth = client. with_auth ( "username" , "password" ) ;
319255 assert_eq ! (
320256 vec![
321- ( "db" . to_string ( ) , "database" . to_string( ) ) ,
322- ( "u" . to_string ( ) , "username" . to_string( ) ) ,
323- ( "p" . to_string ( ) , "password" . to_string( ) )
257+ ( "db" , "database" . to_string( ) ) ,
258+ ( "u" , "username" . to_string( ) ) ,
259+ ( "p" , "password" . to_string( ) )
324260 ] ,
325- basic_parameters_with_auth
261+ * with_auth . parameters
326262 ) ;
327263 }
328264}
0 commit comments