mirror of
https://github.com/bloxstraplabs/bloxstrap.git
synced 2025-04-16 02:01:29 -07:00
Consolidate stuff
yea
This commit is contained in:
parent
94fe52245e
commit
0a7ae17473
@ -13,6 +13,7 @@ using System.Windows.Threading;
|
||||
|
||||
using Microsoft.Win32;
|
||||
|
||||
using Bloxstrap.Enums;
|
||||
using Bloxstrap.Extensions;
|
||||
using Bloxstrap.Models;
|
||||
using Bloxstrap.Models.Attributes;
|
||||
@ -34,6 +35,7 @@ namespace Bloxstrap
|
||||
|
||||
// used only for communicating between app and menu - use Directories.Base for anything else
|
||||
public static string BaseDirectory = null!;
|
||||
|
||||
public static bool ShouldSaveConfigs { get; set; } = false;
|
||||
public static bool IsSetupComplete { get; set; } = true;
|
||||
public static bool IsFirstRun { get; private set; } = true;
|
||||
@ -56,39 +58,23 @@ namespace Bloxstrap
|
||||
|
||||
public static System.Windows.Forms.NotifyIcon Notification { get; private set; } = null!;
|
||||
|
||||
public static void Terminate(int code = Bootstrapper.ERROR_SUCCESS)
|
||||
public static void Terminate(ErrorCode exitCode = ErrorCode.ERROR_SUCCESS)
|
||||
{
|
||||
Logger.WriteLine($"[App::Terminate] Terminating with exit code {code}");
|
||||
if (IsFirstRun)
|
||||
{
|
||||
if (exitCode == ErrorCode.ERROR_CANCELLED)
|
||||
exitCode = ErrorCode.ERROR_INSTALL_USEREXIT;
|
||||
}
|
||||
|
||||
int exitCodeNum = (int)exitCode;
|
||||
|
||||
Logger.WriteLine($"[App::Terminate] Terminating with exit code {exitCodeNum} ({exitCode})");
|
||||
|
||||
Settings.Save();
|
||||
State.Save();
|
||||
Notification.Dispose();
|
||||
Environment.Exit(code);
|
||||
}
|
||||
|
||||
private void InitLog()
|
||||
{
|
||||
// if we're running for the first time or uninstalling, log to temp folder
|
||||
// else, log to bloxstrap folder
|
||||
|
||||
bool isUsingTempDir = IsFirstRun || IsUninstall;
|
||||
string logdir = isUsingTempDir ? Path.Combine(Directories.LocalAppData, "Temp") : Path.Combine(Directories.Base, "Logs");
|
||||
string timestamp = DateTime.UtcNow.ToString("yyyyMMdd'T'HHmmss'Z'");
|
||||
int processId = Process.GetCurrentProcess().Id;
|
||||
|
||||
Logger.Initialize(Path.Combine(logdir, $"{ProjectName}_{timestamp}_{processId}.log"));
|
||||
|
||||
// clean up any logs older than a week
|
||||
if (!isUsingTempDir)
|
||||
{
|
||||
foreach (FileInfo log in new DirectoryInfo(logdir).GetFiles())
|
||||
{
|
||||
if (log.LastWriteTimeUtc.AddDays(7) > DateTime.UtcNow)
|
||||
continue;
|
||||
|
||||
Logger.WriteLine($"[App::InitLog] Cleaning up old log file '{log.Name}'");
|
||||
log.Delete();
|
||||
}
|
||||
}
|
||||
Environment.Exit(exitCodeNum);
|
||||
}
|
||||
|
||||
void GlobalExceptionHandler(object sender, DispatcherUnhandledExceptionEventArgs e)
|
||||
@ -111,7 +97,7 @@ namespace Bloxstrap
|
||||
if (!IsQuiet)
|
||||
Controls.ShowExceptionDialog(exception);
|
||||
|
||||
Terminate(Bootstrapper.ERROR_INSTALL_FAILURE);
|
||||
Terminate(ErrorCode.ERROR_INSTALL_FAILURE);
|
||||
#pragma warning restore 162
|
||||
}
|
||||
|
||||
@ -193,7 +179,7 @@ namespace Bloxstrap
|
||||
Logger.WriteLine("[App::OnStartup] Running first-time install");
|
||||
|
||||
BaseDirectory = Path.Combine(Directories.LocalAppData, ProjectName);
|
||||
InitLog();
|
||||
Logger.Initialize(true);
|
||||
|
||||
if (!IsQuiet)
|
||||
{
|
||||
@ -213,7 +199,7 @@ namespace Bloxstrap
|
||||
if (!IsSetupComplete)
|
||||
{
|
||||
Logger.WriteLine("[App::OnStartup] Installation cancelled!");
|
||||
Environment.Exit(Bootstrapper.ERROR_INSTALL_USEREXIT);
|
||||
Terminate(ErrorCode.ERROR_CANCELLED);
|
||||
}
|
||||
|
||||
Directories.Initialize(BaseDirectory);
|
||||
@ -222,7 +208,7 @@ namespace Bloxstrap
|
||||
// just in case the user decides to cancel the install
|
||||
if (!IsFirstRun)
|
||||
{
|
||||
InitLog();
|
||||
Logger.Initialize(IsUninstall);
|
||||
Settings.Load();
|
||||
State.Load();
|
||||
FastFlags.Load();
|
||||
|
@ -24,12 +24,6 @@ namespace Bloxstrap
|
||||
public class Bootstrapper
|
||||
{
|
||||
#region Properties
|
||||
|
||||
// https://learn.microsoft.com/en-us/windows/win32/msi/error-codes
|
||||
public const int ERROR_SUCCESS = 0;
|
||||
public const int ERROR_INSTALL_USEREXIT = 1602;
|
||||
public const int ERROR_INSTALL_FAILURE = 1603;
|
||||
|
||||
// in case a new package is added, you can find the corresponding directory
|
||||
// by opening the stock bootstrapper in a hex editor
|
||||
// TODO - there ideally should be a less static way to do this that's not hardcoded?
|
||||
@ -109,7 +103,7 @@ namespace Bloxstrap
|
||||
Dialog.Message = message;
|
||||
}
|
||||
|
||||
private void UpdateProgressbar()
|
||||
private void UpdateProgressBar()
|
||||
{
|
||||
int newProgress = (int)Math.Floor(_progressIncrement * _totalDownloadedBytes);
|
||||
|
||||
@ -378,7 +372,7 @@ namespace Bloxstrap
|
||||
{
|
||||
if (!_isInstalling)
|
||||
{
|
||||
App.Terminate(ERROR_INSTALL_USEREXIT);
|
||||
App.Terminate(ErrorCode.ERROR_CANCELLED);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -401,7 +395,7 @@ namespace Bloxstrap
|
||||
App.Logger.WriteLine($"[Bootstrapper::CancelInstall] {ex}");
|
||||
}
|
||||
|
||||
App.Terminate(ERROR_INSTALL_USEREXIT);
|
||||
App.Terminate(ErrorCode.ERROR_CANCELLED);
|
||||
}
|
||||
#endregion
|
||||
|
||||
@ -581,9 +575,9 @@ namespace Bloxstrap
|
||||
return;
|
||||
}
|
||||
|
||||
App.Logger.WriteLine($"[Bootstrapper::CheckForUpdates] Checking for {App.ProjectName} updates...");
|
||||
App.Logger.WriteLine($"[Bootstrapper::CheckForUpdates] Checking for updates...");
|
||||
|
||||
var releaseInfo = await Utilities.GetJson<GithubRelease>($"https://api.github.com/repos/{App.ProjectRepository}/releases/latest");
|
||||
var releaseInfo = await Utility.Http.GetJson<GithubRelease>($"https://api.github.com/repos/{App.ProjectRepository}/releases/latest");
|
||||
|
||||
if (releaseInfo is null || releaseInfo.Assets is null)
|
||||
{
|
||||
@ -629,10 +623,11 @@ namespace Bloxstrap
|
||||
startInfo.ArgumentList.Add(arg);
|
||||
|
||||
App.Settings.Save();
|
||||
App.ShouldSaveConfigs = false;
|
||||
|
||||
Process.Start(startInfo);
|
||||
|
||||
Environment.Exit(0);
|
||||
App.Terminate();
|
||||
}
|
||||
|
||||
private void Uninstall()
|
||||
@ -649,7 +644,7 @@ namespace Bloxstrap
|
||||
);
|
||||
|
||||
if (result != MessageBoxResult.OK)
|
||||
Environment.Exit(ERROR_INSTALL_USEREXIT);
|
||||
App.Terminate(ErrorCode.ERROR_CANCELLED);
|
||||
|
||||
try
|
||||
{
|
||||
@ -669,7 +664,6 @@ namespace Bloxstrap
|
||||
|
||||
SetStatus($"Uninstalling {App.ProjectName}...");
|
||||
|
||||
//App.Settings.ShouldSave = false;
|
||||
App.ShouldSaveConfigs = false;
|
||||
|
||||
// check if stock bootstrapper is still installed
|
||||
@ -759,7 +753,7 @@ namespace Bloxstrap
|
||||
MessageBoxImage.Error
|
||||
);
|
||||
|
||||
App.Terminate(ERROR_INSTALL_FAILURE);
|
||||
App.Terminate(ErrorCode.ERROR_INSTALL_FAILURE);
|
||||
return;
|
||||
}
|
||||
|
||||
@ -1135,7 +1129,7 @@ namespace Bloxstrap
|
||||
{
|
||||
App.Logger.WriteLine($"[Bootstrapper::DownloadPackage] {package.Name} is already downloaded, skipping...");
|
||||
_totalDownloadedBytes += package.PackedSize;
|
||||
UpdateProgressbar();
|
||||
UpdateProgressBar();
|
||||
return;
|
||||
}
|
||||
}
|
||||
@ -1147,7 +1141,7 @@ namespace Bloxstrap
|
||||
App.Logger.WriteLine($"[Bootstrapper::DownloadPackage] Found existing version of {package.Name} ({robloxPackageLocation})! Copying to Downloads folder...");
|
||||
File.Copy(robloxPackageLocation, packageLocation);
|
||||
_totalDownloadedBytes += package.PackedSize;
|
||||
UpdateProgressbar();
|
||||
UpdateProgressBar();
|
||||
return;
|
||||
}
|
||||
|
||||
@ -1179,7 +1173,7 @@ namespace Bloxstrap
|
||||
await fileStream.WriteAsync(buffer, 0, bytesRead, _cancelTokenSource.Token);
|
||||
|
||||
_totalDownloadedBytes += bytesRead;
|
||||
UpdateProgressbar();
|
||||
UpdateProgressBar();
|
||||
}
|
||||
}
|
||||
|
||||
|
14
Bloxstrap/Enums/ErrorCode.cs
Normal file
14
Bloxstrap/Enums/ErrorCode.cs
Normal file
@ -0,0 +1,14 @@
|
||||
namespace Bloxstrap.Enums
|
||||
{
|
||||
// https://learn.microsoft.com/en-us/windows/win32/msi/error-codes
|
||||
// https://i-logic.com/serial/errorcodes.htm
|
||||
// just the ones that we're interested in
|
||||
|
||||
public enum ErrorCode
|
||||
{
|
||||
ERROR_SUCCESS = 0,
|
||||
ERROR_INSTALL_USEREXIT = 1602,
|
||||
ERROR_INSTALL_FAILURE = 1603,
|
||||
ERROR_CANCELLED = 1223
|
||||
}
|
||||
}
|
@ -139,8 +139,6 @@ namespace Bloxstrap
|
||||
|
||||
public override void Save()
|
||||
{
|
||||
App.Logger.WriteLine($"[FastFlagManager::Save] Attempting to save JSON to {FileLocation}...");
|
||||
|
||||
// reload for any changes made while the menu was open
|
||||
Load();
|
||||
|
||||
@ -163,12 +161,9 @@ namespace Bloxstrap
|
||||
Prop[change.Key] = change.Value;
|
||||
}
|
||||
|
||||
Directory.CreateDirectory(Path.GetDirectoryName(FileLocation)!);
|
||||
File.WriteAllText(FileLocation, JsonSerializer.Serialize(Prop, new JsonSerializerOptions { WriteIndented = true }));
|
||||
base.Save();
|
||||
|
||||
Changes.Clear();
|
||||
|
||||
App.Logger.WriteLine($"[FastFlagManager::Save] JSON saved!");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -112,7 +112,7 @@ namespace Bloxstrap.Integrations
|
||||
|
||||
App.Logger.WriteLine($"[DiscordRichPresence::SetCurrentGame] Setting presence for Place ID {_activityWatcher.ActivityPlaceId}");
|
||||
|
||||
var universeIdResponse = await Utilities.GetJson<UniverseIdResponse>($"https://apis.roblox.com/universes/v1/places/{_activityWatcher.ActivityPlaceId}/universe");
|
||||
var universeIdResponse = await Utility.Http.GetJson<UniverseIdResponse>($"https://apis.roblox.com/universes/v1/places/{_activityWatcher.ActivityPlaceId}/universe");
|
||||
if (universeIdResponse is null)
|
||||
{
|
||||
App.Logger.WriteLine($"[DiscordRichPresence::SetCurrentGame] Could not get Universe ID!");
|
||||
@ -129,7 +129,7 @@ namespace Bloxstrap.Integrations
|
||||
_activityWatcher.ActivityIsTeleport = false;
|
||||
_currentUniverseId = universeId;
|
||||
|
||||
var gameDetailResponse = await Utilities.GetJson<ApiArrayResponse<GameDetailResponse>>($"https://games.roblox.com/v1/games?universeIds={universeId}");
|
||||
var gameDetailResponse = await Utility.Http.GetJson<ApiArrayResponse<GameDetailResponse>>($"https://games.roblox.com/v1/games?universeIds={universeId}");
|
||||
if (gameDetailResponse is null || !gameDetailResponse.Data.Any())
|
||||
{
|
||||
App.Logger.WriteLine($"[DiscordRichPresence::SetCurrentGame] Could not get Universe info!");
|
||||
@ -139,7 +139,7 @@ namespace Bloxstrap.Integrations
|
||||
GameDetailResponse universeDetails = gameDetailResponse.Data.ToArray()[0];
|
||||
App.Logger.WriteLine($"[DiscordRichPresence::SetCurrentGame] Got Universe details");
|
||||
|
||||
var universeThumbnailResponse = await Utilities.GetJson<ApiArrayResponse<ThumbnailResponse>>($"https://thumbnails.roblox.com/v1/games/icons?universeIds={universeId}&returnPolicy=PlaceHolder&size=512x512&format=Png&isCircular=false");
|
||||
var universeThumbnailResponse = await Utility.Http.GetJson<ApiArrayResponse<ThumbnailResponse>>($"https://thumbnails.roblox.com/v1/games/icons?universeIds={universeId}&returnPolicy=PlaceHolder&size=512x512&format=Png&isCircular=false");
|
||||
if (universeThumbnailResponse is null || !universeThumbnailResponse.Data.Any())
|
||||
{
|
||||
App.Logger.WriteLine($"[DiscordRichPresence::SetCurrentGame] Could not get Universe thumbnail info!");
|
||||
|
@ -11,7 +11,7 @@ namespace Bloxstrap
|
||||
|
||||
public virtual void Load()
|
||||
{
|
||||
App.Logger.WriteLine($"[JsonManager<{typeof(T).Name}>::Load] Loading JSON from {FileLocation}...");
|
||||
App.Logger.WriteLine($"[JsonManager<{typeof(T).Name}>::Load] Loading from {FileLocation}...");
|
||||
|
||||
try
|
||||
{
|
||||
@ -22,28 +22,28 @@ namespace Bloxstrap
|
||||
|
||||
Prop = settings;
|
||||
|
||||
App.Logger.WriteLine($"[JsonManager<{typeof(T).Name}>::Load] JSON loaded successfully!");
|
||||
App.Logger.WriteLine($"[JsonManager<{typeof(T).Name}>::Load] Loaded successfully!");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
App.Logger.WriteLine($"[JsonManager<{typeof(T).Name}>::Load] Failed to load JSON! ({ex.Message})");
|
||||
App.Logger.WriteLine($"[JsonManager<{typeof(T).Name}>::Load] Failed to load! ({ex.Message})");
|
||||
}
|
||||
}
|
||||
|
||||
public virtual void Save()
|
||||
{
|
||||
App.Logger.WriteLine($"[JsonManager<{typeof(T).Name}>::Save] Attempting to save JSON to {FileLocation}...");
|
||||
|
||||
if (!App.ShouldSaveConfigs)
|
||||
{
|
||||
App.Logger.WriteLine($"[JsonManager<{typeof(T).Name}>::Save] Aborted save (ShouldSave set to false)");
|
||||
App.Logger.WriteLine($"[JsonManager<{typeof(T).Name}>::Save] Save request ignored");
|
||||
return;
|
||||
}
|
||||
|
||||
App.Logger.WriteLine($"[JsonManager<{typeof(T).Name}>::Save] Saving to {FileLocation}...");
|
||||
|
||||
Directory.CreateDirectory(Path.GetDirectoryName(FileLocation)!);
|
||||
File.WriteAllText(FileLocation, JsonSerializer.Serialize(Prop, new JsonSerializerOptions { WriteIndented = true }));
|
||||
|
||||
App.Logger.WriteLine($"[JsonManager<{typeof(T).Name}>::Save] JSON saved!");
|
||||
App.Logger.WriteLine($"[JsonManager<{typeof(T).Name}>::Save] Save complete!");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -20,27 +20,44 @@ namespace Bloxstrap
|
||||
|
||||
public readonly List<string> Backlog = new();
|
||||
public bool Initialized = false;
|
||||
public string? Filename;
|
||||
public string? FileLocation;
|
||||
|
||||
public void Initialize(string filename)
|
||||
public void Initialize(bool useTempDir = false)
|
||||
{
|
||||
if (_filestream is not null)
|
||||
string directory = useTempDir ? Path.Combine(Directories.LocalAppData, "Temp") : Path.Combine(Directories.Base, "Logs");
|
||||
string timestamp = DateTime.UtcNow.ToString("yyyyMMdd'T'HHmmss'Z'");
|
||||
string filename = $"{App.ProjectName}_{timestamp}.log";
|
||||
string location = Path.Combine(directory, filename);
|
||||
|
||||
WriteLine($"[Logger::Initialize] Initializing at {location}");
|
||||
|
||||
if (Initialized)
|
||||
throw new Exception("Logger is already initialized");
|
||||
|
||||
string? directory = Path.GetDirectoryName(filename);
|
||||
Directory.CreateDirectory(directory);
|
||||
|
||||
if (directory is not null)
|
||||
Directory.CreateDirectory(directory);
|
||||
|
||||
_filestream = File.Open(filename, FileMode.Create, FileAccess.Write, FileShare.Read);
|
||||
_filestream = File.Open(location, FileMode.Create, FileAccess.Write, FileShare.Read);
|
||||
|
||||
if (Backlog.Count > 0)
|
||||
WriteToLog(string.Join("\r\n", Backlog));
|
||||
|
||||
WriteLine($"[Logger::Logger] Initialized at {filename}");
|
||||
WriteLine($"[Logger::Initialize] Finished initializing!");
|
||||
|
||||
Initialized = true;
|
||||
Filename = filename;
|
||||
FileLocation = location;
|
||||
|
||||
// clean up any logs older than a week
|
||||
if (!useTempDir)
|
||||
{
|
||||
foreach (FileInfo log in new DirectoryInfo(directory).GetFiles())
|
||||
{
|
||||
if (log.LastWriteTimeUtc.AddDays(7) > DateTime.UtcNow)
|
||||
continue;
|
||||
|
||||
App.Logger.WriteLine($"[Logger::Initialize] Cleaning up old log file '{log.Name}'");
|
||||
log.Delete();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public void WriteLine(string message)
|
||||
|
@ -63,7 +63,7 @@ namespace Bloxstrap
|
||||
MessageBoxResult result = App.Settings.Prop.ChannelChangeMode == ChannelChangeMode.Automatic
|
||||
? MessageBoxResult.Yes
|
||||
: Controls.ShowMessageBox(
|
||||
$"{App.ProjectName} was launched with the Roblox build channel set to {val}, however your current preferred channel is {App.Settings.Prop.Channel}.\n\n" +
|
||||
$"Roblox is attempting to set your channel to {val}, however your current preferred channel is {App.Settings.Prop.Channel}.\n\n" +
|
||||
$"Would you like to switch channels from {App.Settings.Prop.Channel} to {val}?",
|
||||
MessageBoxImage.Question,
|
||||
MessageBoxButton.YesNo
|
||||
|
@ -29,7 +29,7 @@ namespace Bloxstrap.UI
|
||||
LocateLogFileButton.Click += delegate
|
||||
{
|
||||
if (App.Logger.Initialized)
|
||||
Process.Start("explorer.exe", $"/select,\"{App.Logger.Filename}\"");
|
||||
Process.Start("explorer.exe", $"/select,\"{App.Logger.FileLocation}\"");
|
||||
else
|
||||
Clipboard.SetText(String.Join("\r\n", App.Logger.Backlog));
|
||||
};
|
||||
|
@ -98,6 +98,7 @@ namespace Bloxstrap
|
||||
);
|
||||
|
||||
Controls.ShowMenu();
|
||||
|
||||
App.Terminate();
|
||||
}
|
||||
}
|
||||
|
@ -1,8 +1,6 @@
|
||||
using System;
|
||||
using System.Diagnostics;
|
||||
using System.IO;
|
||||
using System.Text.Json;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Bloxstrap
|
||||
{
|
||||
@ -21,21 +19,6 @@ namespace Bloxstrap
|
||||
|
||||
public static void ShellExecute(string website) => Process.Start(new ProcessStartInfo { FileName = website, UseShellExecute = true });
|
||||
|
||||
public static async Task<T?> GetJson<T>(string url)
|
||||
{
|
||||
try
|
||||
{
|
||||
string json = await App.HttpClient.GetStringAsync(url);
|
||||
return JsonSerializer.Deserialize<T>(json);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
App.Logger.WriteLine($"[Utilities::GetJson<{typeof(T).Name}>] Failed to deserialize JSON for {url}!");
|
||||
App.Logger.WriteLine($"[Utilities::GetJson<{typeof(T).Name}>] {ex}");
|
||||
return default;
|
||||
}
|
||||
}
|
||||
|
||||
public static int VersionToNumber(string version)
|
||||
{
|
||||
// yes this is kinda stupid lol
|
||||
|
25
Bloxstrap/Utility/Http.cs
Normal file
25
Bloxstrap/Utility/Http.cs
Normal file
@ -0,0 +1,25 @@
|
||||
using System;
|
||||
using System.Text.Json;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
namespace Bloxstrap.Utility
|
||||
{
|
||||
internal static class Http
|
||||
{
|
||||
public static async Task<T?> GetJson<T>(string url)
|
||||
{
|
||||
string json = await App.HttpClient.GetStringAsync(url);
|
||||
|
||||
try
|
||||
{
|
||||
return JsonSerializer.Deserialize<T>(json);
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
App.Logger.WriteLine($"[Http::GetJson<{typeof(T).Name}>] Failed to deserialize JSON for {url}!");
|
||||
App.Logger.WriteLine($"[Http::GetJson<{typeof(T).Name}>] {ex}");
|
||||
return default;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue
Block a user