Redis 不会从数据库中删除记录
Redis doesn't delete records from the database
首先,我正在使用这个包装器:https://github.com/garywoodfine/redis-mvc-core/blob/master/RedisConfiguration/RedisVoteService.cs 和 Delete(...)
似乎不起作用。我想我试过 IDistributedCache
它过去也不会删除对象,但它至少使所有属性都为空。
你可以在评论中看到我尝试了 FlushDatabase()
但它似乎也没有用。我想要 Delete 方法来删除对象。不仅使它们无效(这也不起作用)。
有什么想法吗?老实说,我想要一个更好的包装器来支持 List<T>
。
var redis = new RedisAlgorithmService<BotSession>(_connectionFactory);
var test = redis.Get("Test");
if (test == null)
redis.Save("Test", new BotSession(TrendType.Uptrend, bot.Id));
test.NTimes = 123;
redis.Delete("Test");
using StackExchange.Redis;
using System;
namespace Binance.Redis
{
public class RedisAlgorithmService<T> : BaseService<T>, IRedisService<T>
{
internal readonly IRedisConnectionFactory _connectionFactory;
protected readonly IDatabase _database;
public RedisAlgorithmService(IRedisConnectionFactory connectionFactory)
{
_connectionFactory = connectionFactory;
_database = _connectionFactory.Connection().GetDatabase();
}
public void Delete(string key)
{
if (string.IsNullOrWhiteSpace(key) || key.Contains(":"))
throw new ArgumentException("Invalid key!");
key = GenerateKey(key);
_database.KeyDelete(key);
// _database.HashDelete(key, );
// var endpoints = _connectionFactory.Connection().GetEndPoints();
// _connectionFactory.Connection().GetServer(endpoints[0]).FlushDatabase();
}
public T Get(string key)
{
key = GenerateKey(key);
var hash = _database.HashGetAll(key);
return MapFromHash(hash);
}
public void Save(string key, T obj)
{
if (obj != null)
{
var hash = GenerateHash(obj);
key = GenerateKey(key);
if (_database.HashLength(key) == 0)
{
_database.HashSet(key, hash);
}
else
{
var props = Properties;
foreach (var item in props)
{
if (_database.HashExists(key, item.Name))
{
_database.HashIncrement(key, item.Name, Convert.ToInt32(item.GetValue(obj)));
}
}
}
}
}
}
}
不知道对你有没有帮助。我可以看到你试过的这个方法,但似乎不完整。
也尝试删除哈希。
DeleteHash(string key, string cacheSubKey)
{
if (string.IsNullOrEmpty(key))
throw new ArgumentNullException("Some problem here !");
_database.HashDelete(key, cacheSubKey);
}
不确定 FlushDatabase()
或 FlushAllDatabase()
是否正是您想要的:
- FLUSHDB – 从连接的当前数据库中删除所有键。
- FLUSHALL – 从所有数据库中删除所有键。
还有另一种解决方法,使用扩展方法和 Newtonsoft.Json
作为 serializer/deserializer。我了解 IDistributedCache
仅支持 string/byte 数组作为输入,您不能将 class 对象传递给它,此解决方法将帮助您做到这一点。
Startup.cs
services.AddStackExchangeRedisCache(options =>
{
options.Configuration = "localhost";
options.InstanceName = "name";
});
CacheExtensions.cs
namespace TestProject.Extensions
{
public static class CacheExtensions
{
public static async Task<T> SetAsync<T>(this IDistributedCache cache, string key, T item)
{
var json = JsonConvert.SerializeObject(item);
await cache.SetStringAsync(key, json);
return await cache.GetAsync<T>(key);
}
public static async Task<T> SetAsync<T>(this IDistributedCache cache, string key, T item, int expirationInHours)
{
var json = JsonConvert.SerializeObject(item);
await cache.SetStringAsync(key, json, new DistributedCacheEntryOptions
{
AbsoluteExpirationRelativeToNow = TimeSpan.FromHours(expirationInHours)
});
return await cache.GetAsync<T>(key);
}
public static async Task<T> GetAsync<T>(this IDistributedCache cache, string key)
{
var json = await cache.GetStringAsync(key);
if (json == null)
return default;
return JsonConvert.DeserializeObject<T>(json);
}
}
}
DI IDistributedCache
:
private readonly IDistributedCache _cache;
public TestService(IDistributedCache cache)
{
_cache = cache;
}
并像这样使用它:
List<Test> testList = new List<Test>
{
new Test(...),
new Test(...)
};
var test = await _cache.GetAsync<List<Test>>("ListKey");
await _cache.SetAsync("ListKey", testList);
await _cache.RemoveAsync("ListKey");
var test2 = await _cache.GetAsync<Test>("key");
await _cache.SetAsync("key", new Test(...));
await _cache.RemoveAsync("key");
希望对您有所帮助。
首先,我正在使用这个包装器:https://github.com/garywoodfine/redis-mvc-core/blob/master/RedisConfiguration/RedisVoteService.cs 和 Delete(...)
似乎不起作用。我想我试过 IDistributedCache
它过去也不会删除对象,但它至少使所有属性都为空。
你可以在评论中看到我尝试了 FlushDatabase()
但它似乎也没有用。我想要 Delete 方法来删除对象。不仅使它们无效(这也不起作用)。
有什么想法吗?老实说,我想要一个更好的包装器来支持 List<T>
。
var redis = new RedisAlgorithmService<BotSession>(_connectionFactory);
var test = redis.Get("Test");
if (test == null)
redis.Save("Test", new BotSession(TrendType.Uptrend, bot.Id));
test.NTimes = 123;
redis.Delete("Test");
using StackExchange.Redis;
using System;
namespace Binance.Redis
{
public class RedisAlgorithmService<T> : BaseService<T>, IRedisService<T>
{
internal readonly IRedisConnectionFactory _connectionFactory;
protected readonly IDatabase _database;
public RedisAlgorithmService(IRedisConnectionFactory connectionFactory)
{
_connectionFactory = connectionFactory;
_database = _connectionFactory.Connection().GetDatabase();
}
public void Delete(string key)
{
if (string.IsNullOrWhiteSpace(key) || key.Contains(":"))
throw new ArgumentException("Invalid key!");
key = GenerateKey(key);
_database.KeyDelete(key);
// _database.HashDelete(key, );
// var endpoints = _connectionFactory.Connection().GetEndPoints();
// _connectionFactory.Connection().GetServer(endpoints[0]).FlushDatabase();
}
public T Get(string key)
{
key = GenerateKey(key);
var hash = _database.HashGetAll(key);
return MapFromHash(hash);
}
public void Save(string key, T obj)
{
if (obj != null)
{
var hash = GenerateHash(obj);
key = GenerateKey(key);
if (_database.HashLength(key) == 0)
{
_database.HashSet(key, hash);
}
else
{
var props = Properties;
foreach (var item in props)
{
if (_database.HashExists(key, item.Name))
{
_database.HashIncrement(key, item.Name, Convert.ToInt32(item.GetValue(obj)));
}
}
}
}
}
}
}
不知道对你有没有帮助。我可以看到你试过的这个方法,但似乎不完整。
也尝试删除哈希。
DeleteHash(string key, string cacheSubKey)
{
if (string.IsNullOrEmpty(key))
throw new ArgumentNullException("Some problem here !");
_database.HashDelete(key, cacheSubKey);
}
不确定 FlushDatabase()
或 FlushAllDatabase()
是否正是您想要的:
- FLUSHDB – 从连接的当前数据库中删除所有键。
- FLUSHALL – 从所有数据库中删除所有键。
还有另一种解决方法,使用扩展方法和 Newtonsoft.Json
作为 serializer/deserializer。我了解 IDistributedCache
仅支持 string/byte 数组作为输入,您不能将 class 对象传递给它,此解决方法将帮助您做到这一点。
Startup.cs
services.AddStackExchangeRedisCache(options =>
{
options.Configuration = "localhost";
options.InstanceName = "name";
});
CacheExtensions.cs
namespace TestProject.Extensions
{
public static class CacheExtensions
{
public static async Task<T> SetAsync<T>(this IDistributedCache cache, string key, T item)
{
var json = JsonConvert.SerializeObject(item);
await cache.SetStringAsync(key, json);
return await cache.GetAsync<T>(key);
}
public static async Task<T> SetAsync<T>(this IDistributedCache cache, string key, T item, int expirationInHours)
{
var json = JsonConvert.SerializeObject(item);
await cache.SetStringAsync(key, json, new DistributedCacheEntryOptions
{
AbsoluteExpirationRelativeToNow = TimeSpan.FromHours(expirationInHours)
});
return await cache.GetAsync<T>(key);
}
public static async Task<T> GetAsync<T>(this IDistributedCache cache, string key)
{
var json = await cache.GetStringAsync(key);
if (json == null)
return default;
return JsonConvert.DeserializeObject<T>(json);
}
}
}
DI IDistributedCache
:
private readonly IDistributedCache _cache;
public TestService(IDistributedCache cache)
{
_cache = cache;
}
并像这样使用它:
List<Test> testList = new List<Test>
{
new Test(...),
new Test(...)
};
var test = await _cache.GetAsync<List<Test>>("ListKey");
await _cache.SetAsync("ListKey", testList);
await _cache.RemoveAsync("ListKey");
var test2 = await _cache.GetAsync<Test>("key");
await _cache.SetAsync("key", new Test(...));
await _cache.RemoveAsync("key");
希望对您有所帮助。