78 lines
2.4 KiB
C#
78 lines
2.4 KiB
C#
using System.Security.Cryptography;
|
|
using System.Text;
|
|
using GestorFacturas.API.Services.Interfaces;
|
|
|
|
namespace GestorFacturas.API.Services;
|
|
|
|
public class EncryptionService : IEncryptionService
|
|
{
|
|
private readonly string _key;
|
|
|
|
public EncryptionService(IConfiguration config)
|
|
{
|
|
// La clave debe venir del .env / appsettings
|
|
_key = config["EncryptionKey"] ?? throw new ArgumentNullException("EncryptionKey no configurada");
|
|
|
|
// Ajustar si la clave no tiene el tamaño correcto (AES-256 requiere 32 bytes)
|
|
// Aquí hacemos un hash SHA256 de la clave para asegurar que siempre tenga 32 bytes válidos
|
|
using var sha256 = SHA256.Create();
|
|
var keyBytes = sha256.ComputeHash(Encoding.UTF8.GetBytes(_key));
|
|
_key = Convert.ToBase64String(keyBytes);
|
|
}
|
|
|
|
public string Encrypt(string plainText)
|
|
{
|
|
if (string.IsNullOrEmpty(plainText)) return plainText;
|
|
|
|
var key = Convert.FromBase64String(_key);
|
|
using var aes = Aes.Create();
|
|
aes.Key = key;
|
|
aes.GenerateIV(); // Generar vector de inicialización aleatorio
|
|
|
|
using var encryptor = aes.CreateEncryptor(aes.Key, aes.IV);
|
|
using var ms = new MemoryStream();
|
|
|
|
// Escribir el IV al principio del stream (necesario para desencriptar)
|
|
ms.Write(aes.IV, 0, aes.IV.Length);
|
|
|
|
using (var cs = new CryptoStream(ms, encryptor, CryptoStreamMode.Write))
|
|
using (var sw = new StreamWriter(cs))
|
|
{
|
|
sw.Write(plainText);
|
|
}
|
|
|
|
return Convert.ToBase64String(ms.ToArray());
|
|
}
|
|
|
|
public string Decrypt(string cipherText)
|
|
{
|
|
if (string.IsNullOrEmpty(cipherText)) return cipherText;
|
|
|
|
try
|
|
{
|
|
var fullCipher = Convert.FromBase64String(cipherText);
|
|
var key = Convert.FromBase64String(_key);
|
|
|
|
using var aes = Aes.Create();
|
|
aes.Key = key;
|
|
|
|
// Extraer el IV (los primeros 16 bytes)
|
|
var iv = new byte[16];
|
|
Array.Copy(fullCipher, 0, iv, 0, iv.Length);
|
|
aes.IV = iv;
|
|
|
|
using var decryptor = aes.CreateDecryptor(aes.Key, aes.IV);
|
|
using var ms = new MemoryStream(fullCipher, 16, fullCipher.Length - 16);
|
|
using var cs = new CryptoStream(ms, decryptor, CryptoStreamMode.Read);
|
|
using var sr = new StreamReader(cs);
|
|
|
|
return sr.ReadToEnd();
|
|
}
|
|
catch
|
|
{
|
|
// Si falla al desencriptar (ej. porque el dato viejo no estaba encriptado),
|
|
// devolvemos el texto original para no romper la app en la migración.
|
|
return cipherText;
|
|
}
|
|
}
|
|
} |