.NET Memcached Client默认实现中并没有获取所有已经缓存Key的方法,但在业务中有时候需求中需要通过正则删除符合条件的缓存内容,所以就要通过读取已经缓存Key进行相关的匹配,然后删除。通过flush只会让缓存过容过期,但获取Key时还会获取得到,缓存的内容过期同样。但调用Get(key)后,Key才会删除
namespace Memcached.ClientLibrary
{
public partial class MemcachedClient
{ #region Methods
public void DeleteByPattern(string pattern)
{
var regex = new Regex(pattern, RegexOptions.Singleline | RegexOptions.Compiled);
var keysToRemove = new List<String>(); foreach (var item in this.Keys)
if (regex.IsMatch(item))
keysToRemove.Add(item); foreach (var key in keysToRemove)
Delete(key);
}
#endregion #region Property
/// <summary>
/// 获取所有缓存的Key
/// </summary>
public List<String> Keys
{
get
{
List<String> keys = new List<string>(); SockIOPool pool = SockIOPool.GetInstance(_poolName);
if (pool != null && pool.Servers != null && pool.Servers.Count > )
{
foreach (var server in pool.Servers)
{
var sock = pool.GetConnection((string)server);
if (sock == null) continue; try
{
sock.Write(_commandStatsItems);
sock.Flush();
string line;
var items = new List<string>();
while (!END.Equals((line = sock.ReadLine()), StringComparison.Ordinal))
{
var id = line.Substring(_idIndex, line.LastIndexOf(':') - _idIndex);
if (!items.Contains(id))
items.Add(id);
} foreach (var id in items)
{
sock.Write(UTF8Encoding.UTF8.GetBytes(string.Concat("stats cachedump ", id, " 0\r\n")));
sock.Flush(); while (!END.Equals((line = sock.ReadLine()), StringComparison.Ordinal))
{
var key = line.Substring(_keyIndex, line.LastIndexOf('[') - );
keys.Add(key);
}
}
}
catch
{
try
{
sock.TrueClose();
}
catch(IOException)
{
if(log.IsErrorEnabled)
log.Error(GetLocalizedString("failed to close some socket").Replace("$$Socket$$", sock.ToString()));
}
}
finally
{
if (sock != null)
sock.Close();
} } } return keys;
}
}
#endregion #region Fields
private const int _idIndex = ;
private const int _keyIndex = ;
private readonly byte[] _commandStatsItems = UTF8Encoding.UTF8.GetBytes("stats items\r\n");
#endregion
}
}