@@ -100,10 +100,136 @@ pub fn remove_items_from_vec_by_indices<Item>(vec: &mut Vec<Item>, indices: &Has
100100#[ cfg( unix) ]
101101#[ cfg( test) ]
102102mod tests {
103- use super :: remove_items_from_vec_by_indices;
103+ use super :: { deduplicate_arguments , remove_items_from_vec_by_indices, Api } ;
104104 use maplit:: hashset;
105+ use normalize_path:: NormalizePath ;
105106 use pretty_assertions:: assert_eq;
106- use std:: collections:: HashSet ;
107+ use std:: { collections:: HashSet , convert:: Infallible , path:: PathBuf } ;
108+
109+ const MOCKED_CURRENT_DIR : & str = "/home/user/current-dir" ;
110+
111+ /// Mocked implementation of [`Api`] for testing purposes.
112+ struct MockedApi ;
113+ impl Api for MockedApi {
114+ type Argument = & ' static str ;
115+ type RealPath = PathBuf ;
116+ type RealPathError = Infallible ;
117+
118+ fn canonicalize ( path : & Self :: Argument ) -> Result < Self :: RealPath , Self :: RealPathError > {
119+ Ok ( match * path {
120+ "link-to-current-dir" => Self :: canonicalize ( & "." ) ?,
121+ "link-to-parent-dir" => Self :: canonicalize ( & ".." ) ?,
122+ "link-to-root" => PathBuf :: from ( "/" ) ,
123+ "link-to-bin" => PathBuf :: from ( "/usr/bin" ) ,
124+ "link-to-foo" => Self :: canonicalize ( & "foo" ) ?,
125+ "link-to-bar" => Self :: canonicalize ( & "bar" ) ?,
126+ "link-to-012" => Self :: canonicalize ( & "0/1/2" ) ?,
127+ _ => PathBuf :: from ( MOCKED_CURRENT_DIR ) . join ( path) . normalize ( ) ,
128+ } )
129+ }
130+
131+ fn starts_with ( a : & Self :: RealPath , b : & Self :: RealPath ) -> bool {
132+ a. starts_with ( b)
133+ }
134+ }
135+
136+ #[ test]
137+ fn find_nothing_to_remove ( ) {
138+ let original = vec ! [ "foo" , "bar" , "abc/def" , "0/1/2" ] ;
139+ let mut actual = original. clone ( ) ;
140+ deduplicate_arguments :: < MockedApi > ( & mut actual) ;
141+ let expected = original;
142+ assert_eq ! ( actual, expected) ;
143+ }
144+
145+ #[ test]
146+ fn remove_duplicated_arguments ( ) {
147+ let original = dbg ! ( vec![
148+ "foo" ,
149+ "bar" ,
150+ "abc/def" ,
151+ "foo" ,
152+ "0/1/2" ,
153+ "./bar" ,
154+ "./abc/./def" ,
155+ ] ) ;
156+ let mut actual = original. clone ( ) ;
157+ deduplicate_arguments :: < MockedApi > ( & mut actual) ;
158+ let expected = vec ! [ "foo" , "bar" , "abc/def" , "0/1/2" ] ;
159+ assert_eq ! ( actual, expected) ;
160+
161+ let original = dbg ! ( vec![
162+ "foo" ,
163+ "./bar" ,
164+ "bar" ,
165+ "./abc/./def" ,
166+ "abc/def" ,
167+ "foo" ,
168+ "0/1/2" ,
169+ ] ) ;
170+ let mut actual = original. clone ( ) ;
171+ deduplicate_arguments :: < MockedApi > ( & mut actual) ;
172+ let expected = vec ! [ "foo" , "./bar" , "./abc/./def" , "0/1/2" ] ;
173+ assert_eq ! ( actual, expected) ;
174+ }
175+
176+ #[ test]
177+ fn remove_all_except_current_dir ( ) {
178+ let original = dbg ! ( vec![ "foo" , "bar" , "." , "abc/def" , "0/1/2" ] ) ;
179+ let mut actual = original. clone ( ) ;
180+ deduplicate_arguments :: < MockedApi > ( & mut actual) ;
181+ let expected = vec ! [ "." ] ;
182+ assert_eq ! ( actual, expected) ;
183+
184+ let original = dbg ! ( vec![
185+ "foo" ,
186+ "bar" ,
187+ "." ,
188+ "abc/def" ,
189+ "0/1/2" ,
190+ MOCKED_CURRENT_DIR ,
191+ ] ) ;
192+ let mut actual = original. clone ( ) ;
193+ deduplicate_arguments :: < MockedApi > ( & mut actual) ;
194+ let expected = vec ! [ "." ] ;
195+ assert_eq ! ( actual, expected) ;
196+
197+ let original = dbg ! ( vec![
198+ "foo" ,
199+ "bar" ,
200+ MOCKED_CURRENT_DIR ,
201+ "." ,
202+ "abc/def" ,
203+ "0/1/2" ,
204+ ] ) ;
205+ let mut actual = original. clone ( ) ;
206+ deduplicate_arguments :: < MockedApi > ( & mut actual) ;
207+ let expected = vec ! [ MOCKED_CURRENT_DIR ] ;
208+ assert_eq ! ( actual, expected) ;
209+ }
210+
211+ #[ test]
212+ fn remove_all_except_parent_dir ( ) {
213+ let original = dbg ! ( vec![ "foo" , "bar" , ".." , "abc/def" , "." , "0/1/2" ] ) ;
214+ let mut actual = original. clone ( ) ;
215+ deduplicate_arguments :: < MockedApi > ( & mut actual) ;
216+ let expected = vec ! [ ".." ] ;
217+ assert_eq ! ( actual, expected) ;
218+
219+ let original = dbg ! ( vec![
220+ "foo" ,
221+ "/home/user" ,
222+ "bar" ,
223+ ".." ,
224+ "abc/def" ,
225+ "." ,
226+ "0/1/2"
227+ ] ) ;
228+ let mut actual = original. clone ( ) ;
229+ deduplicate_arguments :: < MockedApi > ( & mut actual) ;
230+ let expected = vec ! [ "/home/user" ] ;
231+ assert_eq ! ( actual, expected) ;
232+ }
107233
108234 #[ test]
109235 fn remove_nothing ( ) {
0 commit comments