5959//! [`Filter::matches`]: struct.Filter.html#method.matches
6060
6161use log:: { Level , LevelFilter , Metadata , Record } ;
62+ use std:: collections:: HashMap ;
6263use std:: env;
6364use std:: fmt;
6465use std:: mem;
@@ -107,7 +108,7 @@ pub struct Filter {
107108///
108109/// [`Filter`]: struct.Filter.html
109110pub struct Builder {
110- directives : Vec < Directive > ,
111+ directives : HashMap < Option < String > , LevelFilter > ,
111112 filter : Option < inner:: Filter > ,
112113 built : bool ,
113114}
@@ -171,7 +172,7 @@ impl Builder {
171172 /// Initializes the filter builder with defaults.
172173 pub fn new ( ) -> Builder {
173174 Builder {
174- directives : Vec :: new ( ) ,
175+ directives : HashMap :: new ( ) ,
175176 filter : None ,
176177 built : false ,
177178 }
@@ -203,10 +204,7 @@ impl Builder {
203204 /// The given module (if any) will log at most the specified level provided.
204205 /// If no module is provided then the filter will apply to all log messages.
205206 pub fn filter ( & mut self , module : Option < & str > , level : LevelFilter ) -> & mut Self {
206- self . directives . push ( Directive {
207- name : module. map ( |s| s. to_string ( ) ) ,
208- level,
209- } ) ;
207+ self . directives . insert ( module. map ( |s| s. to_string ( ) ) , level) ;
210208 self
211209 }
212210
@@ -221,7 +219,7 @@ impl Builder {
221219 self . filter = filter;
222220
223221 for directive in directives {
224- self . directives . push ( directive) ;
222+ self . directives . insert ( directive. name , directive . level ) ;
225223 }
226224 self
227225 }
@@ -231,24 +229,31 @@ impl Builder {
231229 assert ! ( !self . built, "attempt to re-use consumed builder" ) ;
232230 self . built = true ;
233231
232+ let mut directives = Vec :: new ( ) ;
234233 if self . directives . is_empty ( ) {
235234 // Adds the default filter if none exist
236- self . directives . push ( Directive {
235+ directives. push ( Directive {
237236 name : None ,
238237 level : LevelFilter :: Error ,
239238 } ) ;
240239 } else {
240+ // Consume map of directives.
241+ let directives_map = mem:: replace ( & mut self . directives , HashMap :: new ( ) ) ;
242+ directives = directives_map
243+ . into_iter ( )
244+ . map ( |( name, level) | Directive { name, level } )
245+ . collect ( ) ;
241246 // Sort the directives by length of their name, this allows a
242247 // little more efficient lookup at runtime.
243- self . directives . sort_by ( |a, b| {
248+ directives. sort_by ( |a, b| {
244249 let alen = a. name . as_ref ( ) . map ( |a| a. len ( ) ) . unwrap_or ( 0 ) ;
245250 let blen = b. name . as_ref ( ) . map ( |b| b. len ( ) ) . unwrap_or ( 0 ) ;
246251 alen. cmp ( & blen)
247252 } ) ;
248253 }
249254
250255 Filter {
251- directives : mem:: replace ( & mut self . directives , Vec :: new ( ) ) ,
256+ directives : mem:: replace ( & mut directives, Vec :: new ( ) ) ,
252257 filter : mem:: replace ( & mut self . filter , None ) ,
253258 }
254259 }
0 commit comments