Add protected memory sample
This commit is contained in:
@@ -0,0 +1,90 @@
|
||||
using TriunniaLabs.Arch.Microservice;
|
||||
using TriunniaLabs.Memory.Protected;
|
||||
|
||||
namespace TriunniaLabs.Arch.Sample.Server
|
||||
{
|
||||
/// <summary>
|
||||
/// A controller that shows how to work with the Protected Memory system.
|
||||
/// </summary>
|
||||
public class ProtectedMemorySampleController : ArchControllerBase
|
||||
{
|
||||
// Services
|
||||
private readonly IProtectorFactory _protectorFactory;
|
||||
private readonly IProtector<string> _stringProtector;
|
||||
|
||||
/// <summary>
|
||||
/// Constructor.
|
||||
/// </summary>
|
||||
/// <param name="microserviceContext">Reference to the microservice context.</param>
|
||||
/// <param name="protectorFactory">Reference to the protector factory.</param>
|
||||
/// <param name="stringProtector">Reference to the string protector.</param>
|
||||
public ProtectedMemorySampleController(IMicroserviceContext microserviceContext,
|
||||
IProtectorFactory protectorFactory,
|
||||
[FromKeyedServices("MyProtectorServiceKey")] IProtector<string> stringProtector)
|
||||
: base(microserviceContext)
|
||||
{
|
||||
_stringProtector = stringProtector ?? throw new ArgumentNullException(nameof(stringProtector));
|
||||
_protectorFactory = protectorFactory ?? throw new ArgumentNullException(nameof(protectorFactory));
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// A sample method that shows how to work with the Protected Memory system.
|
||||
/// </summary>
|
||||
internal async Task SampleAsync()
|
||||
{
|
||||
// In Arch, all data is encrypted in memory via the Protected<T> type. This encryption extends to the database and data transfer objects.
|
||||
var myString = "My String Value";
|
||||
var myProtectedString = new Protected<string>(myString);
|
||||
|
||||
// The hash of a protected type's value is available for equality checking without exposing the encrypted value
|
||||
var hash = myProtectedString.Hash;
|
||||
|
||||
// Decrypt the protected type to get its value
|
||||
var value = myProtectedString.GetDecryptedValue(); // "My String Value"
|
||||
|
||||
// Or decrypt just enough to get the bytes (from the byte array converter) without restoring the actual value.
|
||||
var bytes = myProtectedString.GetDecryptedValueAsBytes();
|
||||
|
||||
// The protected type can be serialized just by calling ToString(), and this is what is used in appsettings.json or in the database.
|
||||
// The serialized string is completely encrypted. It cannot be decrypted without a matching configuration.
|
||||
var serializedString = myProtectedString.ToString();
|
||||
|
||||
// The static FromEncrypted method can be used to deserialize
|
||||
myProtectedString = Protected<string>.FromEncrypted(serializedString);
|
||||
|
||||
// Custom protections can be specified as well. This specific arrangement is called Standard Protection.
|
||||
// It is the default that is used when no other algorithms are specified.
|
||||
var byteArrayConverter = MessagePackByteArrayConverter<string>.Instance;
|
||||
var sha256HashAlgorithm = Sha256HashAlgorithm.Instance;
|
||||
var aesEncryption = AesHashEncryptionAlgorithm.Instance;
|
||||
var stringConverter = Base64StringConverter.Instance;
|
||||
myProtectedString = new Protected<string>(myString, byteArrayConverter, sha256HashAlgorithm, [aesEncryption], stringConverter);
|
||||
|
||||
// Use Protectors to protect values with pre-defined custom configurations
|
||||
var protector = _protectorFactory.CreateProtector<string>(MessagePackByteArrayConverter<string>.ServiceKey,
|
||||
Sha256HashAlgorithm.ServiceKey, [AesEncryptionAlgorithm.ServiceKey],
|
||||
Base64StringConverter.ServiceKey);
|
||||
|
||||
// Protect the value using the protector
|
||||
myProtectedString = protector.Protect(myString);
|
||||
|
||||
// Protectors are also used to receive serialized data
|
||||
myProtectedString = protector.Receive(serializedString);
|
||||
myProtectedString = _stringProtector.Receive(serializedString); // They can also be injected
|
||||
}
|
||||
|
||||
private class MyProtectedSample
|
||||
{
|
||||
/// <summary>
|
||||
/// Protector definitions are automatically scanned by the library and added to the service container.
|
||||
/// If an algorithm or converter isn't specified, the default is used.
|
||||
/// </summary>
|
||||
[ByteArrayConverter<string>("MessagePackByteArrayConverter<string>.ServiceKey")]
|
||||
[HashAlgorithm(HmacSha512HashAlgorithm.ServiceKey)]
|
||||
[EncryptionAlgorithm(AesEncryptionAlgorithm.ServiceKey, Order = 1)]
|
||||
[StringConverter(Base64StringConverter.ServiceKey)]
|
||||
[Protector("MyProtectorServiceKey")] // Identifies the protector in the service collection
|
||||
public string Value { get; set; } = "";
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user