/// <summary> /// Fetches all releases from GitHub, looks up the current release and shows the changelog /// </summary> /// <param name="dialogService">The dialog service to use for progress and result dialogs</param> /// <param name="version">The version to fetch the changelog for</param> /// <returns></returns> private static async Task ShowChanges(MetroDialogService dialogService, Version version) { var progressDialog = await dialogService.ShowProgressDialog("Changelog", "Fetching release data from GitHub.."); progressDialog.SetIndeterminate(); var jsonClient = new WebClient(); // GitHub trips if we don't add a user agent jsonClient.Headers.Add("user-agent", "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.2; .NET CLR 1.0.3705;)"); // Random number to get around cache issues var rand = new Random(DateTime.Now.Millisecond); var json = await jsonClient.DownloadStringTaskAsync( "https://api.github.com/repos/SpoinkyNL/Artemis/releases?random=" + rand.Next()); // Get a list of releases var releases = JsonConvert.DeserializeObject <JArray>(json); var release = releases.FirstOrDefault(r => r["tag_name"].Value <string>() == version.ToString()); try { await progressDialog.CloseAsync(); } catch (InvalidOperationException) { // Occurs when main window is closed before finished } if (release != null) { dialogService.ShowMarkdownDialog(release["name"].Value <string>(), release["body"].Value <string>()); } else { dialogService.ShowMessageBox("Couldn't fetch release", "Sorry, Artemis was unable to fetch the release data off of GitHub.\n" + "If you'd like, you can always find out the latest changes on the GitHub page accessible from the options menu"); } }
/// <summary> /// Shows the changes for the given release and offers to download it /// </summary> /// <param name="dialogService">The dialog service to use for progress and result dialogs</param> /// <param name="release">The release to show and offer the download for</param> /// <returns></returns> private static async Task ShowChanges(MetroDialogService dialogService, JObject release) { var settings = new MetroDialogSettings { AffirmativeButtonText = "Download & install", NegativeButtonText = "Ask again later" }; var update = await dialogService.ShowMarkdownDialog(release["name"].Value <string>(), release["body"].Value <string>(), settings); if (update == null || (bool)!update) { return; } // Show a process dialog var dialog = await dialogService.ShowProgressDialog("Applying update", "The new update is being downloaded right now..."); dialog.SetIndeterminate(); // Download the release file, it's the one starting with "artemis-setup" var releaseFile = release["assets"].Children().FirstOrDefault(c => c["name"].Value <string>().StartsWith("artemis-setup") && c["name"].Value <string>().EndsWith(".msi")); // If there's no matching release it means whoever published the new version f****d up, can't do much about that if (releaseFile == null) { await dialog.CloseAsync(); dialogService.ShowMessageBox("Applying update failed", "Couldn't find the update file. Please install the latest version manually, sorry!"); return; } var downloadClient = new WebClient(); downloadClient.Headers.Add("user-agent", "Mozilla/4.0 (compatible; MSIE 6.0; Windows NT 5.2; .NET CLR 1.0.3705;)"); Task <byte[]> download; try { download = downloadClient.DownloadDataTaskAsync(releaseFile["browser_download_url"].Value <string>()); } catch (Exception e) { dialogService.ShowMessageBox("Applying update failed", "We ran into an issue downloaidng the update: \n\n" + e.Message); Logger.Warn(e, "Update check failed."); return; } downloadClient.DownloadProgressChanged += (sender, args) => { dialog.SetMessage("The new update is being downloaded right now...\n\n" + $"Progress: {ConvertBytesToMegabytes(args.BytesReceived)} MB/{ConvertBytesToMegabytes(args.TotalBytesToReceive)} MB"); dialog.SetProgress(args.ProgressPercentage / 100.0); }; var setupBytes = await download; dialog.SetMessage("Installing the new update..."); dialog.SetIndeterminate(); // Ensure the update folder exists var artemisFolder = AppDomain.CurrentDomain.BaseDirectory.Substring(0, AppDomain.CurrentDomain.BaseDirectory.Length - 1); var updateFolder = GeneralHelpers.DataFolder + "updates"; var updatePath = updateFolder + "\\" + releaseFile["name"].Value <string>(); if (!Directory.Exists(updateFolder)) { Directory.CreateDirectory(updateFolder); } // Store the bytes File.WriteAllBytes(updatePath, setupBytes); // Create a bat file that'll take care of the installation (Artemis gets shut down during install) the bat file will // carry forth our legacy (read that in an heroic tone) var updateScript = "ECHO OFF\r\n" + "CLS\r\n" + $"\"{updatePath}\" /passive\r\n" + $"cd \"{artemisFolder}\"\r\n" + "start Artemis.exe --show"; File.WriteAllText(updateFolder + "\\updateScript.bat", updateScript); var psi = new ProcessStartInfo { FileName = updateFolder + "\\updateScript.bat", Verb = "runas" }; var process = new System.Diagnostics.Process { StartInfo = psi }; process.Start(); process.WaitForExit(); }