网站首页 网站源码
website
站点相关全部源代码,隐藏了一些关于服务器的信息
namespace Dpz.Core.Service;

public class EmailConfigService
{
    private readonly IRepository<EmailConfig> _repository;
    private readonly IMapper _mapper;

    public EmailConfigService(IRepository<EmailConfig> repository,IMapper mapper)
    {
        _repository = repository;
        _mapper = mapper;
    }
    
    #region AES加解密
    /// <summary>
    /// AES加密
    /// </summary>
    /// <param name="text"></param>
    /// <param name="key"></param>
    /// <returns></returns>
    private async Task<string> EncryptAes(string text, string key)
    {
        if (string.IsNullOrEmpty(text)) throw new ArgumentNullException(nameof(text));
        if (string.IsNullOrEmpty(key)) throw new ArgumentNullException(nameof(key));

        var encryptKey = Encoding.UTF8.GetBytes(key);
        using var aesAlg = Aes.Create();
        aesAlg.Padding = PaddingMode.PKCS7;
        using var encryptor = aesAlg.CreateEncryptor(encryptKey, aesAlg.IV);
        await using var msEncrypt = new MemoryStream();
        await using (var csEncrypt = new CryptoStream(msEncrypt, encryptor, CryptoStreamMode.Write))
        await using (var swEncrypt = new StreamWriter(csEncrypt))
        {
            await swEncrypt.WriteAsync(text);
        }
        var iv = aesAlg.IV;
        var decryptedContent = msEncrypt.ToArray();
        var result = new byte[iv.Length + decryptedContent.Length];
        Buffer.BlockCopy(iv, 0, result, 0, iv.Length);
        Buffer.BlockCopy(decryptedContent, 0, result, iv.Length, decryptedContent.Length);
        return Convert.ToBase64String(result);
    }

    /// <summary>
    /// AES解密
    /// </summary>
    /// <param name="text"></param>
    /// <param name="key"></param>
    /// <returns></returns>
    private async Task<string> DecryptAes(string text, string key)
    {
        if (string.IsNullOrEmpty(text)) throw new ArgumentNullException(nameof(text));
        if (string.IsNullOrEmpty(key)) throw new ArgumentNullException(nameof(key));
        var fullCipher = Convert.FromBase64String(text);
        var iv = new byte[16];
        var cipher = new byte[fullCipher.Length - iv.Length];

        Buffer.BlockCopy(fullCipher, 0, iv, 0, iv.Length);
        Buffer.BlockCopy(fullCipher, iv.Length, cipher, 0, fullCipher.Length - iv.Length);
        var decryptKey = Encoding.UTF8.GetBytes(key);

        using var aesAlg = Aes.Create();
        aesAlg.Padding = PaddingMode.PKCS7;
        using var decryptor = aesAlg.CreateDecryptor(decryptKey, iv);
        await using var msDecrypt = new MemoryStream(cipher);
        await using var csDecrypt = new CryptoStream(msDecrypt,
            decryptor, CryptoStreamMode.Read);
        using var srDecrypt = new StreamReader(csDecrypt);
        var result = await srDecrypt.ReadToEndAsync();
        return result;
    }

    #endregion
        
        
    public async Task Add(VmEmailConfig viewModel)
    {
        var config = _repository.SearchFor(x => x.EmailName == viewModel.EmailName).FirstOrDefault();
        if (config != null)
        {
            throw new Exception($"邮箱别名“{viewModel.EmailName}”已存在");
        }
        var model = _mapper.Map<EmailConfig>(viewModel);
        model.Id = ObjectId.GenerateNewId();
        model.Password = await EncryptAes(model.Password, model.Id.ToString());
        await _repository.InsertAsync(model);
    }

    public async Task<string?> GetClearPassword(string id)
    {
        var model = await _repository.TryGetAsync(id);
        if (model == null) return null;
        var clearText = await DecryptAes(model.Password, id);
        return clearText;
    }

    public async Task<List<VmEmailConfig>> GetList(string account)
    {
        var source = await _repository.SearchFor(x => x.AboutUser.Id == account).ToListAsync();
        return _mapper.Map<List<VmEmailConfig>>(source);
    }

    public async Task Edit(VmEmailConfig viewModel)
    {
        if (string.IsNullOrEmpty(viewModel.Password))
        {
            var model = await _repository.TryGetAsync(viewModel.Id);
            if(model == null)throw new ArgumentException("没找找到这个邮箱配置",nameof(viewModel));
            var updateModel = _mapper.Map<EmailConfig>(viewModel);
            updateModel.Password = model.Password;
            await _repository.UpdateAsync(updateModel);
            return;
        }
        var hasPwdUpdateModel = _mapper.Map<EmailConfig>(viewModel);
        hasPwdUpdateModel.Password = await EncryptAes(hasPwdUpdateModel.Password, hasPwdUpdateModel.Id.ToString());
        await _repository.UpdateAsync(hasPwdUpdateModel);
    }

    public async Task<VmEmailConfig?> GetConfig(string id)
    {
        var config = await _repository.TryGetAsync(id);
        if (config == null) return null;
        var viewModel = _mapper.Map<VmEmailConfig>(config);
        viewModel.Password = await DecryptAes(viewModel.Password, viewModel.Id);
        return viewModel;
    }

    public async Task<VmEmailConfig?> GetConfigByEmailName(string emailName)
    {
        var model = await _repository.SearchFor(x => x.EmailName == emailName).SingleOrDefaultAsync();
        if (model == null) return null;
        var viewModel = _mapper.Map<VmEmailConfig>(model);
        viewModel.Password = await DecryptAes(viewModel.Password, viewModel.Id);
        return viewModel;
    }

    public async Task Delete(string id)
    {
        if (ObjectId.TryParse(id, out var oid))
        {
            await _repository.DeleteAsync(x => x.Id == oid);
        }
    }
}
loading