diff --git a/Bloxstrap/Resources/Strings.Designer.cs b/Bloxstrap/Resources/Strings.Designer.cs index e175e6c..0201300 100644 --- a/Bloxstrap/Resources/Strings.Designer.cs +++ b/Bloxstrap/Resources/Strings.Designer.cs @@ -432,6 +432,15 @@ namespace Bloxstrap.Resources { } } + /// + /// Looks up a localized string similar to Export. + /// + public static string Common_Export { + get { + return ResourceManager.GetString("Common.Export", resourceCulture); + } + } + /// /// Looks up a localized string similar to Help. /// @@ -1386,6 +1395,15 @@ namespace Bloxstrap.Resources { } } + /// + /// Looks up a localized string similar to Zip archive. + /// + public static string FileTypes_ZipArchive { + get { + return ResourceManager.GetString("FileTypes.ZipArchive", resourceCulture); + } + } + /// /// Looks up a localized string similar to Bloxstrap has been upgraded to v{0}. /// @@ -2103,6 +2121,42 @@ namespace Bloxstrap.Resources { } } + /// + /// Looks up a localized string similar to Gather information that can be uploaded online to troubleshoot a problem you're having.. + /// + public static string Menu_Bloxstrap_ExportData_Description { + get { + return ResourceManager.GetString("Menu.Bloxstrap.ExportData.Description", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to Bloxstrap configuration. + /// + public static string Menu_Bloxstrap_ExportData_ExportConfig { + get { + return ResourceManager.GetString("Menu.Bloxstrap.ExportData.ExportConfig", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to All Bloxstrap logs. + /// + public static string Menu_Bloxstrap_ExportData_ExportLogs { + get { + return ResourceManager.GetString("Menu.Bloxstrap.ExportData.ExportLogs", resourceCulture); + } + } + + /// + /// Looks up a localized string similar to Export diagnostic data. + /// + public static string Menu_Bloxstrap_ExportData_Title { + get { + return ResourceManager.GetString("Menu.Bloxstrap.ExportData.Title", resourceCulture); + } + } + /// /// Looks up a localized string similar to Add new. /// diff --git a/Bloxstrap/Resources/Strings.resx b/Bloxstrap/Resources/Strings.resx index 777fd95..aea14a5 100644 --- a/Bloxstrap/Resources/Strings.resx +++ b/Bloxstrap/Resources/Strings.resx @@ -906,6 +906,7 @@ Selecting 'No' will ignore this warning and continue installation. JSON files + Shown in the open file dialog, where the file type selection dropdown is, e.g. "JSON files (*.json)" The entry for '{0}' is not valid as the value must be a boolean (either 'True' or 'False') @@ -1248,4 +1249,26 @@ Would you like to enable test mode? Please close any applications that may be using Roblox's files, and relaunch. This is *not* for when Roblox is still running when trying to upgrade. This applies to files being open (i.e. image assets) + + Zip archive + Shown in the save file dialog, where the file type selection dropdown is, e.g. "Zip archive (*.zip)" + + + Export + Currently used under the "Bloxstrap" settings tab for the button to export diagnostic data + + + Export diagnostic data + + + Gather information that can be uploaded online to troubleshoot a problem you're having. + + + Bloxstrap configuration + Label that appears next to a checkbox + + + All Bloxstrap logs + Label that appears next to a checkbox + \ No newline at end of file diff --git a/Bloxstrap/UI/Elements/Settings/Pages/BloxstrapPage.xaml b/Bloxstrap/UI/Elements/Settings/Pages/BloxstrapPage.xaml index d96f081..d4f731a 100644 --- a/Bloxstrap/UI/Elements/Settings/Pages/BloxstrapPage.xaml +++ b/Bloxstrap/UI/Elements/Settings/Pages/BloxstrapPage.xaml @@ -8,7 +8,7 @@ xmlns:controls="clr-namespace:Bloxstrap.UI.Elements.Controls" xmlns:models="clr-namespace:Bloxstrap.UI.ViewModels.Settings" xmlns:resources="clr-namespace:Bloxstrap.Resources" - d:DataContext="{d:DesignInstance Type=models:BehaviourViewModel}" + d:DataContext="{d:DesignInstance Type=models:BloxstrapViewModel}" mc:Ignorable="d" d:DesignHeight="600" d:DesignWidth="800" Title="BehaviourPage" @@ -28,5 +28,44 @@ Description="{Binding Source={x:Static resources:Strings.Menu_Bloxstrap_Analytics_Description}, Converter={StaticResource StringFormatConverter}, ConverterParameter='https://github.com/bloxstraplabs/bloxstrap/wiki/Privacy-Policy#analytical-functionality'}"> + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/Bloxstrap/UI/ViewModels/Settings/BloxstrapViewModel.cs b/Bloxstrap/UI/ViewModels/Settings/BloxstrapViewModel.cs index bd913d1..016f69f 100644 --- a/Bloxstrap/UI/ViewModels/Settings/BloxstrapViewModel.cs +++ b/Bloxstrap/UI/ViewModels/Settings/BloxstrapViewModel.cs @@ -1,4 +1,9 @@ -namespace Bloxstrap.UI.ViewModels.Settings +using System.Windows.Input; +using CommunityToolkit.Mvvm.Input; +using ICSharpCode.SharpZipLib.Zip; +using Microsoft.Win32; + +namespace Bloxstrap.UI.ViewModels.Settings { public class BloxstrapViewModel : NotifyPropertyChangedViewModel { @@ -13,5 +18,73 @@ get => App.Settings.Prop.EnableAnalytics; set => App.Settings.Prop.EnableAnalytics = value; } + + public bool ShouldExportConfig { get; set; } = true; + + public bool ShouldExportLogs { get; set; } = true; + + public ICommand ExportDataCommand => new RelayCommand(ExportData); + + private void ExportData() + { + string timestamp = DateTime.UtcNow.ToString("yyyyMMdd'T'HHmmss'Z'"); + + var dialog = new SaveFileDialog + { + FileName = $"Bloxstrap-export-{timestamp}.zip", + Filter = $"{Strings.FileTypes_ZipArchive}|*.zip" + }; + + if (dialog.ShowDialog() != true) + return; + + using var memStream = new MemoryStream(); + using var zipStream = new ZipOutputStream(memStream); + + if (ShouldExportConfig) + { + var files = new List() + { + App.Settings.FileLocation, + App.State.FileLocation, + App.FastFlags.FileLocation + }; + + AddFilesToZipStream(zipStream, files, "Config/"); + } + + if (ShouldExportLogs && Directory.Exists(Paths.Logs)) + { + var files = Directory.GetFiles(Paths.Logs) + .Where(x => !x.Equals(App.Logger.FileLocation, StringComparison.OrdinalIgnoreCase)); + + AddFilesToZipStream(zipStream, files, "Logs/"); + } + + zipStream.CloseEntry(); + memStream.Position = 0; + + using var outputStream = File.OpenWrite(dialog.FileName); + memStream.CopyTo(outputStream); + + Process.Start("explorer.exe", $"/select,\"{dialog.FileName}\""); + } + + private void AddFilesToZipStream(ZipOutputStream zipStream, IEnumerable files, string directory) + { + foreach (string file in files) + { + if (!File.Exists(file)) + continue; + + var entry = new ZipEntry(directory + Path.GetFileName(file)); + entry.DateTime = DateTime.Now; + + zipStream.PutNextEntry(entry); + + using var fileStream = File.OpenRead(file); + fileStream.CopyTo(zipStream); + } + } } } diff --git a/Bloxstrap/UI/ViewModels/Settings/FastFlagsViewModel.cs b/Bloxstrap/UI/ViewModels/Settings/FastFlagsViewModel.cs index cc1df4f..7f63032 100644 --- a/Bloxstrap/UI/ViewModels/Settings/FastFlagsViewModel.cs +++ b/Bloxstrap/UI/ViewModels/Settings/FastFlagsViewModel.cs @@ -1,5 +1,4 @@ -using System.Windows; -using System.Windows.Input; +using System.Windows.Input; using CommunityToolkit.Mvvm.Input;