Files
amacocian 794afa6c2c Blazor UI Migration (#1085)
* Migrate to Fluent UI

* Setup window events for Blazor WebView

* Setup basic FluentUI styling

* FluentUI links

* Setup views and viewmodel infra

* Remove old navigation logic

* Prepare an example of iframe embed

* Style window + navigation menu

* Setup page based navigation

* Add some UI error handling

* Introduce UI resiliency to exceptions

* Setup settings menu dropdown

* Basic setup for options views

* Setup reusable OptionBase

* Setup options views

* Basic styling

* Setup scoped css files.
Split App into components

* Hook option updates to OptionProvider

* Fix option dropdowns

* Setup multiple themes

* Make fonts scalable

* Move ViewModels under Views

* Launch view + styling

* Setup FocusView base

* Finish BuildListView implementation

* Base for build views

* Setup build routing

* Implement single build editor

* Implement skill description on hover

* Scrape skill information from the wiki and cache it locally

* Scrape and fix Guild Wars wiki info

* Improve mouse hover performance by querying position only when needed

* Skill snippet snaps to edges

* Setup accounts and executables view

* Launch configurations view

* Fix build skill icons
Attach skill types to skills
Scrape upkeep from wiki

* Fix skilltype overflow

* Adjust navigation menu

* Setup privilege elevation flow

* Setup MSAL

* Options synchronization view

* Telemetry view

* Version management and update view

* Setup plugins view

* Setup notifications panel

* Base for logs view

* Finish LogView

* Setup metrics view

* Setup UI logging interop

* GuildWarsPartySearch view implementation

* Setup gitlab mirror job

* Eventviewer base

* Remove gitlab mirror

* Remove mirror pipeline

* Fix metricsview crashes

* Extract progress component

* Setup trade chat views

* Setup Download view

* Extract progress styling

* Setup guild wars copy view

* Setup trade alerts

* Fix team template view skill selection

* Setup basic onboarding view

* Overhaul asynchronous progress operations and remove redundant versioning code

* Setup modsview base

* Setup modsview with mod states

* Setup mod installation process

* Cleanup more ui migration
Remove price history #1076

* Screen selector manage view

* Upgrade to .net 10
Closes #1078

* gMod management view

* Trader message notification

* ReShade management

* Update for toolbox

* Setup focusview fetching

* Setup CharacterComponent

* Setup vanquishing component

* Setup TitleInformationComponent

* Closes #1082
Fix API project for Guild Wars Reforged

* Small fixes + attempts to get new exe version

* FileId fixes

* Current Map and Player Resources widgets

* Quest log widget

* BuildComponent implementation

* Closes #1075
Embed wwwroot into the executable

* Cleanup

* Fixes to slnx

* Fix test project
2025-12-08 22:39:48 +01:00

81 lines
3.2 KiB
C#

using System.IO;
using System.Security.Cryptography;
namespace Daybreak.Shared.Utils;
internal static class EncryptionHelper
{
private static Aes Aes { get; } = CreateDefault();
private static int Iterations { get; } = 10000;
private static RandomNumberGenerator Rng { get; } = RandomNumberGenerator.Create();
public static int BlockSize { get => Aes.BlockSize; }
public static byte[] EncryptBytes(this byte[] bytes, byte[] key)
{
var saltBytes = Generate128BitsOfRandomEntropy();
var ivBytes = Generate128BitsOfRandomEntropy();
var keyBytes = Rfc2898DeriveBytes.Pbkdf2(
password: key,
salt: saltBytes,
iterations: Iterations,
hashAlgorithm: HashAlgorithmName.SHA512,
outputLength: Aes.KeySize / 8);
using var encryptor = Aes.CreateEncryptor(keyBytes, ivBytes);
using var memoryStream = new MemoryStream();
using var cryptoStream = new CryptoStream(memoryStream, encryptor, CryptoStreamMode.Write);
cryptoStream.Write(bytes, 0, bytes.Length);
cryptoStream.FlushFinalBlock();
// Create the final bytes as a concatenation of the random salt bytes, the random iv bytes and the cipher bytes.
using var encryptedMemoryStream = new MemoryStream((int)(saltBytes.Length + ivBytes.Length + memoryStream.Length));
encryptedMemoryStream.Write(saltBytes, 0, saltBytes.Length);
encryptedMemoryStream.Write(ivBytes, 0, ivBytes.Length);
encryptedMemoryStream.Write(memoryStream.ToArray(), 0, (int)memoryStream.Length);
return encryptedMemoryStream.ToArray();
}
public static byte[] DecryptBytes(this byte[] bytes, byte[] key)
{
var saltBytes = new byte[Aes.BlockSize / 8];
var ivBytes = new byte[Aes.BlockSize / 8];
var cipherBytes = new byte[bytes.Length - (Aes.BlockSize / 4)];
using var encryptedStream = new MemoryStream(bytes);
encryptedStream.Read(saltBytes, 0, saltBytes.Length);
encryptedStream.Read(ivBytes, 0, ivBytes.Length);
encryptedStream.Read(cipherBytes, 0, cipherBytes.Length);
var keyBytes = Rfc2898DeriveBytes.Pbkdf2(
password: key,
salt: saltBytes,
iterations: Iterations,
hashAlgorithm: HashAlgorithmName.SHA512,
outputLength: Aes.KeySize / 8);
using var decryptor = Aes.CreateDecryptor(keyBytes, ivBytes);
using var memoryStream = new MemoryStream(cipherBytes);
using var cryptoStream = new CryptoStream(memoryStream, decryptor, CryptoStreamMode.Read);
var plainTextBytes = new byte[memoryStream.Length];
var decryptedByteCount = cryptoStream.Read(plainTextBytes, 0, plainTextBytes.Length);
return [.. plainTextBytes.Take(decryptedByteCount)];
}
private static byte[] Generate128BitsOfRandomEntropy()
{
var randomBytes = new byte[16];
Rng.GetBytes(randomBytes);
return randomBytes;
}
private static Aes CreateDefault()
{
var aes = Aes.Create();
aes.Mode = CipherMode.CBC;
aes.BlockSize = 128;
aes.Padding = PaddingMode.PKCS7;
return aes;
}
}