1
1
extern crate regex;
2
2
extern crate skim;
3
3
4
- use std:: collections:: HashSet ;
4
+ use std:: collections:: HashMap ;
5
5
use std:: io:: Cursor ;
6
6
use std:: io:: { self , Read } ;
7
7
use std:: process:: Command ;
8
8
9
9
use regex:: Regex ;
10
10
use skim:: { Skim , SkimOptionsBuilder } ;
11
11
12
- const URL_REGEX : & str = r"(http(s)?://[a-zA-Z0-9_/?+&.=@%#;-]+)" ;
12
+ const URL_REGEX : & str = r"(http(s)?://[a-zA-Z0-9_/?+&.=@%#;~ -]+)" ;
13
13
14
14
pub fn main ( ) {
15
15
let options = SkimOptionsBuilder :: default ( )
@@ -23,18 +23,29 @@ pub fn main() {
23
23
io:: stdin ( ) . read_to_string ( & mut buffer) . unwrap ( ) ;
24
24
let lines = buffer. split ( "\n " ) ;
25
25
26
- let mut matches: HashSet < & str > = HashSet :: new ( ) ;
26
+ let mut matches: HashMap < & str , u8 > = HashMap :: new ( ) ;
27
+ let mut match_index = 1 ;
27
28
28
29
for line in lines {
29
30
for capture in re. captures_iter ( line) {
30
31
let url_match = capture. get ( 1 ) . unwrap ( ) . as_str ( ) ;
31
- matches. insert ( url_match) ;
32
+ if matches. contains_key ( url_match) {
33
+ continue ;
34
+ }
35
+ matches. insert ( url_match, match_index) ;
36
+ match_index += 1 ;
32
37
}
33
38
}
34
39
35
- let unique_items: Vec < & str > = matches. into_iter ( ) . collect ( ) ;
36
- let items = unique_items. join ( "\n " ) ;
37
- // `run_with` would read and show items from the stream
40
+ let mut ordered_items: Vec < _ > = matches. into_iter ( )
41
+ . collect ( ) ;
42
+ ordered_items. sort_by ( |a, b| a. 1 . cmp ( & b. 1 ) ) ;
43
+
44
+ let item_list: Vec < _ > = ordered_items. iter ( )
45
+ . map ( |item|item. 0 )
46
+ . collect ( ) ;
47
+ let items = item_list. join ( "\n " ) ;
48
+
38
49
let selected_items = Skim :: run_with ( & options, Some ( Box :: new ( Cursor :: new ( items) ) ) )
39
50
. map ( |out| out. selected_items )
40
51
. unwrap_or_else ( || Vec :: new ( ) ) ;
0 commit comments