1414 */
1515
1616use crate :: app:: { AppMessage , AppState } ;
17- use crate :: java:: get_java_zip_path_from_cache_dir;
17+ use crate :: java:: { get_java_executable_in_downloaded_jre , get_java_extract_folder_from_cache_dir , get_java_zip_path_from_cache_dir} ;
1818use crate :: util:: TaskError ;
1919use iced:: futures:: { SinkExt , Stream , StreamExt } ;
2020use iced:: stream:: try_channel;
@@ -24,8 +24,11 @@ use std::path::PathBuf;
2424use std:: sync:: Arc ;
2525use std:: time:: Duration ;
2626use std:: { fs, fs:: File , io:: Write } ;
27+ use crate :: file:: extract_zip;
28+ use crate :: installer:: { try_run_installer, InstallerExitCode , InstallerRunError } ;
29+ use crate :: WrapperInfo ;
2730
28- pub fn download_java < T : ToString > ( url : T , cache_dir : PathBuf ) -> Subscription < AppMessage > {
31+ /* pub fn download_java<T: ToString>(url: T, cache_dir: PathBuf) -> Subscription<AppMessage> {
2932 Subscription::run_with_id(
3033 "download-java",
3134 download_java_task(url.to_string(), cache_dir),
@@ -38,9 +41,9 @@ pub fn download_java<T: ToString>(url: T, cache_dir: PathBuf) -> Subscription<Ap
3841 AppMessage::UpdateState(t.unwrap())
3942 }
4043 })
41- }
44+ }*/
4245
43- pub fn download_java_task (
46+ /* pub fn download_java_task(
4447 url: String,
4548 cache_dir: PathBuf,
4649) -> impl Stream<Item = Result<AppState, TaskError>> {
@@ -105,4 +108,114 @@ pub fn download_java_task(
105108 info!("Successfully downloaded java!");
106109 Ok(())
107110 })
111+ }*/
112+
113+ pub fn download_java_and_run_task (
114+ url : String ,
115+ wrapper_info : WrapperInfo ,
116+ ) -> impl Stream < Item = Result < AppState , TaskError > > {
117+ try_channel ( 100000 , move |mut output| async move {
118+ info ! ( "Starting download from {}" , url) ;
119+ let download_path = get_java_zip_path_from_cache_dir ( & wrapper_info. cache_dir ) ;
120+ info ! ( "Temporary jre zip file: {}" , download_path. display( ) ) ;
121+
122+ info ! ( "Check if the old file exists" ) ;
123+ if download_path. try_exists ( ) . unwrap_or ( false ) {
124+ info ! ( "Deleting the old file" ) ;
125+ fs:: remove_file ( download_path. clone ( ) ) . map_err ( |e| {
126+ TaskError :: IOError (
127+ "Error when deleting old JRE zip file" . to_string ( ) ,
128+ Arc :: new ( e) ,
129+ )
130+ } ) ?;
131+ }
132+
133+ let mut file = File :: create ( download_path. clone ( ) ) . map_err ( |e| {
134+ TaskError :: IOError ( "Error creating the download file!" . to_string ( ) , Arc :: new ( e) )
135+ } ) ?;
136+
137+ info ! ( "File created!" ) ;
138+
139+ let client = reqwest:: Client :: builder ( )
140+ . connect_timeout ( Duration :: from_secs ( 10 ) )
141+ . timeout ( Duration :: from_secs ( 120 ) ) // 3 mbit download for 45MB file
142+ . build ( ) ?;
143+
144+ let response = client. get ( url. clone ( ) ) . send ( ) . await ?;
145+
146+ if !response. status ( ) . is_success ( ) {
147+ warn ! ( "Non-OK status received as response when downloading!" ) ;
148+ warn ! (
149+ "Response text: \n {}" ,
150+ response. text( ) . await . unwrap_or_else( |e| { e. to_string( ) } )
151+ ) ;
152+ return Err ( TaskError :: UnsuccessfulResponse ( ) ) ;
153+ }
154+
155+ let total = response
156+ . content_length ( )
157+ . ok_or ( TaskError :: NoContentLength ( ) ) ?;
158+
159+ output. send ( AppState :: Downloading ( url. clone ( ) , 0.0 ) ) . await ?;
160+
161+ let mut byte_stream = response. bytes_stream ( ) ;
162+ let mut downloaded = 0 ;
163+
164+ while let Some ( next_bytes) = byte_stream. next ( ) . await {
165+ let bytes = next_bytes?;
166+ downloaded += bytes. len ( ) ;
167+ file. write_all ( & bytes) ?;
168+ let progress = 100.0 * downloaded as f32 / total as f32 ;
169+ if let Err ( e) = output. try_send ( AppState :: Downloading ( url. clone ( ) , progress) ) {
170+ debug ! ( "Channel full!" )
171+ }
172+ }
173+
174+ output. send ( AppState :: DownloadFinished ( download_path. clone ( ) ) ) . await ?;
175+ info ! ( "Successfully downloaded java! Now extracting..." ) ;
176+ output. send ( AppState :: ExtractingJava ( download_path. clone ( ) ) ) . await ?;
177+
178+ let extract_path = get_java_extract_folder_from_cache_dir ( & wrapper_info. cache_dir ) ;
179+ info ! ( "Temporary jre folder: {}" , extract_path. display( ) ) ;
180+
181+ extract_zip ( download_path, extract_path) ?;
182+ output. send ( AppState :: ExtractFinished ) . await ?;
183+
184+ info ! ( "Extracted! Ruunning installer..." ) ;
185+
186+ let java_executable = get_java_executable_in_downloaded_jre ( & wrapper_info. cache_dir )
187+ . ok_or ( TaskError :: UnsuccessfulResponse ( ) ) ?; // TODO error
188+
189+ output. send ( AppState :: InstallerRunning ( java_executable. clone ( ) ) ) . await ?;
190+ let state = match try_run_installer ( & java_executable, & wrapper_info) {
191+ Ok ( ex) => match ex {
192+ InstallerExitCode :: Success => AppState :: Finished ,
193+ InstallerExitCode :: UnknownError => {
194+ error ! ( "Unknown error when running installer!" ) ;
195+ AppState :: Errored ( "Unknown error!" . to_string ( ) )
196+ }
197+ InstallerExitCode :: NoOpenGl => {
198+ error ! ( "No OpenGL found when running installer!" ) ;
199+ AppState :: Errored ( "No OpenGL found!" . to_string ( ) )
200+ }
201+ InstallerExitCode :: UnsupportedPath => {
202+ error ! ( "Launcher found an unsupported path!" ) ;
203+ AppState :: Errored ( "Launcher found an unsupported path!" . to_string ( ) )
204+ }
205+ } ,
206+ Err ( e) => {
207+ let error = match e {
208+ InstallerRunError :: JavaFailed => "Java test failed!" . to_string ( ) ,
209+ InstallerRunError :: UnknownExitCode ( c) => {
210+ format ! ( "Unknown installer exit code: {}" , c)
211+ }
212+ InstallerRunError :: Other => "Unknown error!" . to_string ( ) ,
213+ } ;
214+ AppState :: Errored ( error)
215+ }
216+ } ;
217+
218+ output. send ( state) . await ?;
219+ Ok ( ( ) )
220+ } )
108221}
0 commit comments