using System.Globalization;
using System.Security.Cryptography;
using System.Text;
namespace Domain.Helpers
{
public interface IComparableByHash
{
IEnumerable<object> GetHashDependencies();
}
public interface IHashComparer
{
bool IsEqualTo(IComparableByHash other);
}
public static class HashHelpers
{
public static IEnumerable<object> SelectDependencies(params object[] dependencies) => dependencies;
public static string GetHash(this IComparableByHash src) => Sha1FromDependencies(src.GetHashDependencies());
public static IHashComparer Compare(IComparableByHash src) => new HashComparer(src);
public static string Sha1FromDependencies(IEnumerable<object> dependencies) => GetSHA1(string.Join(";", dependencies.Select(x => Convert.ToString(x, CultureInfo.InvariantCulture)?.Trim())));
public static string GetMD5(string data) => GetHash(MD5.Create(), data);
public static string GetSHA1(string data) => GetHash(SHA1.Create(), data);
public static string GetSHA256(string data) => GetHash(SHA256.Create(), data);
public static string GetSHA384(string data) => GetHash(SHA384.Create(), data);
public static string GetSHA512(string data) => GetHash(SHA512.Create(), data);
public static string GetSHA1Guid(string data)
{
// SHA1 = 2fd4e1c67a2d28fced849ee1bb76e7391b93eb12
// Guid = {3f2504e0-4f89-11d3-9a0c-0305e82c3301}
string sha1 = GetSHA1(data);
string[] parts = new string[] {
sha1.Substring(0,8),
sha1.Substring(8,4),
sha1.Substring(12,4),
sha1.Substring(16,4),
sha1.Substring(20,12)
};
return string.Join("-", parts);
}
public static string GetHash(HashAlgorithm algoritm, string data)
{
byte[] inputBytes = Encoding.UTF8.GetBytes(data);
byte[] hashBytes = algoritm.ComputeHash(inputBytes);
// Convert the byte array to hexadecimal string
var sb = new StringBuilder();
for (int i = 0; i < hashBytes.Length; i++)
{
sb.Append(hashBytes[i].ToString("x2")); // For uppercase use: X2
}
return sb.ToString();
}
private class HashComparer : IHashComparer
{
private readonly string sourceHash;
public HashComparer(IComparableByHash item)
{
sourceHash = item?.GetHash();
}
public bool IsEqualTo(IComparableByHash other)
{
if (sourceHash == null || other == null) return false;
return sourceHash == other?.GetHash();
}
}
}
}
public class MyItem : IComparableByHash
{
public Guid? Id { get; set; }
public string Description { get;set; }
public double Amount { get; set; }
public int Priority { get; set; }
IEnumerable<object> IComparableByHash.GetHashDependencies() => HashHelpers.SelectDependencies(Description, Amount, Priority);
}
itemsToImport.Select(y =>
{
var existing = existingItems.FirstOrDefault(x => x.Id == y.Id);
var comparer = HashHelpers.Compare(existing);
existing ??= new MyItem();
existing.Description = item.Description;
existing.Amount = item.Amount;
existing.Priority = item.Priority;
if (comparer.IsEqualTo(existing)) return null;
return existing;
})
.Where(x => x != null)
.ToList();11700cookie-checkC# HashHelpers