17
17
18
18
use crate :: config:: ManagerConfig ;
19
19
use reqwest:: Client ;
20
+ use std:: cell:: RefCell ;
20
21
use std:: collections:: HashMap ;
21
22
use std:: error:: Error ;
22
23
use std:: path:: PathBuf ;
23
24
24
- use crate :: downloads:: read_redirect_from_link;
25
25
use crate :: files:: { compose_driver_path_in_cache, BrowserPath } ;
26
26
27
- use crate :: { create_default_http_client, Logger , SeleniumManager } ;
27
+ use crate :: { create_default_http_client, parse_version , Logger , SeleniumManager } ;
28
28
29
29
use crate :: metadata:: {
30
30
create_driver_metadata, get_driver_version_from_metadata, get_metadata, write_metadata,
31
31
} ;
32
+ use crate :: mirror:: { get_mirror_response, Assets , SeleniumRelease } ;
32
33
33
34
pub const IE_NAMES : & [ & str ] = & [
34
35
"iexplorer" ,
@@ -39,7 +40,9 @@ pub const IE_NAMES: &[&str] = &[
39
40
] ;
40
41
pub const IEDRIVER_NAME : & str = "IEDriverServer" ;
41
42
const DRIVER_URL : & str = "https://github.com/SeleniumHQ/selenium/releases/" ;
42
- const LATEST_RELEASE : & str = "latest" ;
43
+ const IEDRIVER_RELEASE : & str = "IEDriverServer_Win32_" ;
44
+
45
+ thread_local ! ( static RELEASE_URL : RefCell <String > = RefCell :: new( "" . to_string( ) ) ) ;
43
46
44
47
pub struct IExplorerManager {
45
48
pub browser_name : & ' static str ,
@@ -100,29 +103,75 @@ impl SeleniumManager for IExplorerManager {
100
103
Ok ( driver_version)
101
104
}
102
105
_ => {
103
- let latest_url = format ! ( "{}{}" , DRIVER_URL , LATEST_RELEASE ) ;
104
- let driver_version = read_redirect_from_link ( self . get_http_client ( ) , latest_url) ?;
105
-
106
- if !browser_version. is_empty ( ) {
107
- metadata. drivers . push ( create_driver_metadata (
108
- browser_version,
109
- self . driver_name ,
110
- & driver_version,
111
- ) ) ;
112
- write_metadata ( & metadata, self . get_logger ( ) ) ;
106
+ let selenium_releases = get_mirror_response ( self . get_http_client ( ) ) ?;
107
+
108
+ let filtered_releases: Vec < SeleniumRelease > = selenium_releases
109
+ . into_iter ( )
110
+ . filter ( |r| {
111
+ r. assets
112
+ . iter ( )
113
+ . any ( |url| url. browser_download_url . contains ( IEDRIVER_RELEASE ) )
114
+ } )
115
+ . collect ( ) ;
116
+
117
+ if !filtered_releases. is_empty ( ) {
118
+ let assets = & filtered_releases. get ( 0 ) . unwrap ( ) . assets ;
119
+ let driver_releases: Vec < & Assets > = assets
120
+ . iter ( )
121
+ . filter ( |url| url. browser_download_url . contains ( IEDRIVER_RELEASE ) )
122
+ . collect ( ) ;
123
+ let driver_url = & driver_releases. last ( ) . unwrap ( ) . browser_download_url ;
124
+ RELEASE_URL . with ( |url| {
125
+ * url. borrow_mut ( ) = driver_url. to_string ( ) ;
126
+ } ) ;
127
+
128
+ let index_release =
129
+ driver_url. rfind ( IEDRIVER_RELEASE ) . unwrap ( ) + IEDRIVER_RELEASE . len ( ) ;
130
+ let driver_version =
131
+ parse_version ( driver_url. as_str ( ) [ index_release..] . to_string ( ) ) ?;
132
+
133
+ if !browser_version. is_empty ( ) {
134
+ metadata. drivers . push ( create_driver_metadata (
135
+ browser_version,
136
+ self . driver_name ,
137
+ & driver_version,
138
+ ) ) ;
139
+ write_metadata ( & metadata, self . get_logger ( ) ) ;
140
+ }
141
+
142
+ Ok ( driver_version)
143
+ } else {
144
+ Err ( format ! ( "{} release not available" , self . get_driver_name( ) ) . into ( ) )
113
145
}
114
-
115
- Ok ( driver_version)
116
146
}
117
147
}
118
148
}
119
149
120
150
fn get_driver_url ( & self ) -> Result < String , Box < dyn Error > > {
121
- let driver_version = self . get_driver_version ( ) ;
122
- Ok ( format ! (
123
- "{}download/selenium-{}/IEDriverServer_Win32_{}.zip" ,
124
- DRIVER_URL , driver_version, driver_version
125
- ) )
151
+ let mut driver_url = "" . to_string ( ) ;
152
+ RELEASE_URL . with ( |url| {
153
+ driver_url = url. borrow ( ) . to_string ( ) ;
154
+ } ) ;
155
+ if driver_url. is_empty ( ) {
156
+ let driver_version = self . get_driver_version ( ) ;
157
+ let mut release_version = driver_version. to_string ( ) ;
158
+ if !driver_version. ends_with ( '0' ) {
159
+ // E.g.: version 4.8.1 is shipped within release 4.8.0
160
+ let error_message = format ! (
161
+ "Wrong {} version: '{}'" ,
162
+ self . get_driver_name( ) ,
163
+ driver_version
164
+ ) ;
165
+ let index = release_version. rfind ( '.' ) . ok_or ( error_message) ? + 1 ;
166
+ release_version = release_version[ ..index] . to_string ( ) ;
167
+ release_version. push ( '0' ) ;
168
+ }
169
+ driver_url = format ! (
170
+ "{}download/selenium-{}/{}{}.zip" ,
171
+ DRIVER_URL , release_version, IEDRIVER_RELEASE , driver_version
172
+ ) ;
173
+ }
174
+ Ok ( driver_url)
126
175
}
127
176
128
177
fn get_driver_path_in_cache ( & self ) -> PathBuf {
0 commit comments