@@ -6,7 +6,6 @@ use std::collections::HashMap;
6
6
use std:: fmt:: { Display , Formatter } ;
7
7
use std:: sync:: Arc ;
8
8
use std:: str:: FromStr ;
9
-
10
9
use serde:: de:: DeserializeOwned ;
11
10
use validator:: { ValidateArgs } ;
12
11
@@ -28,6 +27,7 @@ pub struct Definitions {
28
27
features : Option < HashMap < String , serde_json:: Value > > ,
29
28
services : Option < HashMap < String , serde_json:: Value > > ,
30
29
clients : Option < HashMap < String , Client > > ,
30
+ service : Option < serde_json:: Value > ,
31
31
32
32
#[ serde( deserialize_with = "service::deserialize_services" ) ]
33
33
pub types : Vec < service:: Service > ,
@@ -138,14 +138,7 @@ impl Definitions {
138
138
where
139
139
T : DeserializeOwned ,
140
140
{
141
- if let Some ( d) = self . feature ( feature) {
142
- return match serde_json:: from_value :: < T > ( d. clone ( ) ) {
143
- Err ( e) => Err ( merrors:: Error :: DefinitionLoadingFailure ( feature. to_string ( ) , e. to_string ( ) ) ) ,
144
- Ok ( defs) => Ok ( Some ( defs) ) ,
145
- }
146
- }
147
-
148
- Ok ( None )
141
+ self . decode ( self . feature ( feature) , feature)
149
142
}
150
143
151
144
fn feature ( & self , feature : & str ) -> Option < serde_json:: Value > {
@@ -159,14 +152,7 @@ impl Definitions {
159
152
where
160
153
T : DeserializeOwned ,
161
154
{
162
- if let Some ( d) = self . service ( & service_kind) {
163
- return match serde_json:: from_value :: < T > ( d. clone ( ) ) {
164
- Err ( e) => Err ( merrors:: Error :: DefinitionLoadingFailure ( service_kind. to_string ( ) , e. to_string ( ) ) ) ,
165
- Ok ( defs) => Ok ( Some ( defs) ) ,
166
- }
167
- }
168
-
169
- Ok ( None )
155
+ self . decode ( self . service ( & service_kind) , & service_kind. to_string ( ) )
170
156
}
171
157
172
158
fn service ( & self , service_kind : & ServiceKind ) -> Option < serde_json:: Value > {
@@ -176,9 +162,36 @@ impl Definitions {
176
162
}
177
163
}
178
164
165
+ fn decode < T > ( & self , data : Option < serde_json:: Value > , name : & str ) -> merrors:: Result < Option < T > >
166
+ where
167
+ T : DeserializeOwned ,
168
+ {
169
+ if let Some ( d) = data {
170
+ return match serde_json:: from_value :: < T > ( d. clone ( ) ) {
171
+ Ok ( defs) => Ok ( Some ( defs) ) ,
172
+ Err ( e) => Err ( merrors:: Error :: DefinitionLoadingFailure ( name. to_string ( ) , e. to_string ( ) ) ) ,
173
+ }
174
+ }
175
+
176
+ Ok ( None )
177
+ }
178
+
179
179
pub fn client ( & self , name : & str ) -> Option < Client > {
180
180
self . clients . clone ( ) ?. get ( name) . cloned ( )
181
181
}
182
+
183
+ pub fn custom_settings < T > ( & self ) -> merrors:: Result < Option < T > >
184
+ where
185
+ T : DeserializeOwned ,
186
+ {
187
+ match & self . service {
188
+ None => Ok ( None ) ,
189
+ Some ( settings) => match serde_json:: from_value :: < T > ( settings. clone ( ) ) {
190
+ Err ( e) => Err ( merrors:: Error :: DefinitionLoadingFailure ( "custom_settings" . to_string ( ) , e. to_string ( ) ) ) ,
191
+ Ok ( settings) => Ok ( Some ( settings) ) ,
192
+ }
193
+ }
194
+ }
182
195
}
183
196
184
197
#[ cfg( test) ]
@@ -326,4 +339,26 @@ mod tests {
326
339
assert_eq ! ( address. clone( ) . unwrap( ) . host, "127.0.0.1" ) ;
327
340
assert_eq ! ( address. unwrap( ) . port, 7071 ) ;
328
341
}
342
+
343
+ #[ test]
344
+ fn test_load_service_custom_settings ( ) {
345
+ let filename = assets_path ( ) . join ( "definitions/service.toml.ok_custom_settings" ) ;
346
+ let defs = Definitions :: new ( filename. to_str ( ) , None ) ;
347
+ assert ! ( defs. is_ok( ) ) ;
348
+
349
+ let defs = defs. unwrap ( ) ;
350
+
351
+ #[ derive( Deserialize ) ]
352
+ struct Service {
353
+ direction : String ,
354
+ ipc_port : i32 ,
355
+ }
356
+
357
+ let s: merrors:: Result < Option < Service > > = defs. custom_settings ( ) ;
358
+ assert ! ( s. is_ok( ) ) ;
359
+
360
+ let settings = s. unwrap ( ) . unwrap ( ) ;
361
+ assert_eq ! ( settings. direction, "forward" ) ;
362
+ assert_eq ! ( settings. ipc_port, 9991 ) ;
363
+ }
329
364
}
0 commit comments