[英]Is Redis a viable solution for a local cache?
在我的場景中,我有一個連接到WebApi2的Winforms客戶端。 數據存儲在SQL Server數據庫中。
為了加快性能,我正在研究將數據存儲在本地緩存中是否是可行的解決方案。 優選地,本地高速緩存應該存儲在文件中而不是保存在存儲器中,因為RAM可能是個問題。 數據是所有POCO類,有些比其他類復雜得多,並且大多數類彼此相關。
我列出了哪些框架可行的候選名單:
使用MemoryCache
,我需要實現自己的解決方案,但它符合我的初始要求。
但是,我看到的一個常見問題是更新相關類。 例如,我在CustomerAddress
和PostCode
之間存在關系。 如果我更改郵政編碼對象中的某些屬性,我可以輕松更新其本地緩存。 但是如何更新/無效使用此郵政編碼的任何其他類,在本例中為CustomerAddress
?
上面的任何框架是否都有幫助這種情況的方法,還是完全依賴於開發人員來處理這種緩存失效?
為了加快性能,我正在研究將數據存儲在本地緩存中是否是可行的解決方案。 優選地,本地高速緩存應該存儲在文件中而不是保存在存儲器中,因為RAM可能是個問題
整個問題是避免將其存儲在文件中,以避免緩慢的DISK操作,因此Redis是基於RAM的內存。
上面的任何框架是否都有幫助這種情況的方法,還是完全依賴於開發人員來處理這種緩存失效?
您可以將整個對象保存為JSON,而不是應用邏輯並反匯編對象,這在應用更改時也會很慢並且容易出錯。
CachingFramework.Redis庫提供了一種將標記與鍵和哈希相關聯的機制,以便您可以在單個操作中使它們無效。
我假設你會:
而且你的模型是這樣的:
public class CustomerAddress
{
public int CustomerAddressId { get; set; }
public int CustomerId { get; set; }
public int PostCodeId { get; set; }
}
public class PostCode
{
public int PostCodeId { get; set; }
public string Code { get; set; }
}
我的建議是:
這樣的事情應該可行:
public class DataAccess
{
private Context _cacheContext = new CachingFramework.Redis.Context("localhost:6379");
private string FormatPostCodeKey(int postCodeId)
{
return string.Format("PostCode:{0}", postCodeId);
}
private string FormatPostCodeTag(int postCodeId)
{
return string.Format("Tag-PostCode:{0}", postCodeId);
}
private string FormatAddressKey(int customerAddressId)
{
return string.Format("Address:{0}", customerAddressId);
}
public void InsertPostCode(PostCode postCode)
{
Sql.InsertPostCode(postCode);
}
public void UpdatePostCode(PostCode postCode)
{
Sql.UpdatePostCode(postCode);
//Invalidate cache: remove CustomerAddresses and PostCode related
_cacheContext.Cache.InvalidateKeysByTag(FormatPostCodeTag(postCode.PostCodeId));
}
public void DeletePostCode(int postCodeId)
{
Sql.DeletePostCode(postCodeId);
_cacheContext.Cache.InvalidateKeysByTag(FormatPostCodeTag(postCodeId));
}
public PostCode GetPostCode(int postCodeId)
{
// Get/Insert the postcode from/into Cache with key = PostCode{PostCodeId}.
// Mark the object with tag = Tag-PostCode:{PostCodeId}
return _cacheContext.Cache.FetchObject(
FormatPostCodeKey(postCodeId), // Redis Key to use
() => Sql.GetPostCode(postCodeId), // Delegate to get the value from database
new[] { FormatPostCodeTag(postCodeId) }); // Tags related
}
public void InsertCustomerAddress(CustomerAddress customerAddress)
{
Sql.InsertCustomerAddress(customerAddress);
}
public void UpdateCustomerAddress(CustomerAddress customerAddress)
{
var updated = Sql.UpdateCustomerAddress(customerAddress);
if (updated.PostCodeId != customerAddress.PostCodeId)
{
var addressKey = FormatAddressKey(customerAddress.CustomerAddressId);
_cacheContext.Cache.RenameTagForKey(addressKey, FormatPostCodeTag(customerAddress.PostCodeId), FormatPostCodeTag(updated.PostCodeId));
}
}
public void DeleteCustomerAddress(CustomerAddress customerAddress)
{
Sql.DeleteCustomerAddress(customerAddress.CustomerAddressId);
//Clean-up, remove the postcode tag from the CustomerAddress:
_cacheContext.Cache.RemoveTagsFromKey(FormatAddressKey(customerAddress.CustomerAddressId), new [] { FormatPostCodeTag(customerAddress.PostCodeId) });
}
public CustomerAddress GetCustomerAddress(int customerAddressId)
{
// Get/Insert the address from/into Cache with key = Address:{CustomerAddressId}.
// Mark the object with tag = Tag-PostCode:{PostCodeId}
return _cacheContext.Cache.FetchObject(
FormatAddressKey(customerAddressId),
() => Sql.GetCustomerAddress(customerAddressId),
a => new[] { FormatPostCodeTag(a.PostCodeId) });
}
}
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.