From 18b8ea88de3c83132793ad2d8539ddd095bf788a Mon Sep 17 00:00:00 2001 From: eveloki <478117618@qq.com> Date: Tue, 9 Jan 2024 18:16:25 +0800 Subject: [PATCH 1/2] =?UTF-8?q?=E4=BF=AE=E5=A4=8D=E4=BA=86=E9=9B=86?= =?UTF-8?q?=E7=BE=A4=E6=A8=A1=E5=BC=8F=E4=B8=8B=20=E4=BD=BF=E7=94=A8?= =?UTF-8?q?=E9=9D=9EAscii=E5=AD=97=E7=AC=A6=E4=BD=9C=E4=B8=BAKey=E6=97=B6?= =?UTF-8?q?=E9=94=99=E8=AF=AF=E7=9A=84Slot=E8=AE=A1=E7=AE=97=E5=B8=A6?= =?UTF-8?q?=E6=9D=A5=E7=9A=84Moved=E6=8A=A5=E9=94=99=E9=97=AE=E9=A2=98?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 为GetClusterSlot的静态方法添加一个Encoding入参默认为Encoding.ASCII,这样能兼容之前的写法,并且在ClusterAdapter初始化时获取当前实例的Encoding,这样符合链接字符串设计,缓存_baseEncoding是为了简化反复从_clusterConnectionStrings中获取。并且这样只需要在ClusterAdapter的GetRedisSocket中传入当前实例的Encoding,就不会污染其他实现,比如NormanAdapter --- .../RedisClient/Adapter/ClusterAdapter.cs | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-) diff --git a/src/FreeRedis/RedisClient/Adapter/ClusterAdapter.cs b/src/FreeRedis/RedisClient/Adapter/ClusterAdapter.cs index e99a60e..5a58c76 100644 --- a/src/FreeRedis/RedisClient/Adapter/ClusterAdapter.cs +++ b/src/FreeRedis/RedisClient/Adapter/ClusterAdapter.cs @@ -1,4 +1,4 @@ -using FreeRedis.Internal; +using FreeRedis.Internal; using System; using System.Collections.Concurrent; using System.Collections.Generic; @@ -15,6 +15,7 @@ internal class ClusterAdapter : BaseAdapter { internal readonly IdleBus _ib; internal readonly ConnectionStringBuilder[] _clusterConnectionStrings; + internal static Encoding _baseEncoding=System.Text.Encoding.ASCII; public ClusterAdapter(RedisClient topOwner, ConnectionStringBuilder[] clusterConnectionStrings) { @@ -25,6 +26,7 @@ public ClusterAdapter(RedisClient topOwner, ConnectionStringBuilder[] clusterCon throw new ArgumentNullException(nameof(clusterConnectionStrings)); _clusterConnectionStrings = clusterConnectionStrings.ToArray(); + _baseEncoding= _clusterConnectionStrings.FirstOrDefault()?.Encoding; _ib = new IdleBus(TimeSpan.FromMinutes(10)); RefershClusterNodes(); } @@ -49,7 +51,7 @@ public override void Refersh(IRedisSocket redisSocket) } public override IRedisSocket GetRedisSocket(CommandPacket cmd) { - var slots = cmd?._keyIndexes.Select(a => GetClusterSlot(cmd._input[a].ToInvariantCultureToString())).Distinct().ToArray(); + var slots = cmd?._keyIndexes.Select(a => GetClusterSlot(cmd._input[a].ToInvariantCultureToString(), _baseEncoding)).Distinct().ToArray(); var poolkeys = slots?.Select(a => _slotCache.TryGetValue(a, out var trykey) ? trykey : null).Distinct().Where(a => a != null).ToArray(); //if (poolkeys.Length > 1) throw new RedisClientException($"CROSSSLOT Keys in request don't hash to the same slot: {cmd}"); var poolkey = poolkeys?.FirstOrDefault(); @@ -408,10 +410,14 @@ public static ClusterMoved ParseSimpleError(string simpleError) 0xef1f,0xff3e,0xcf5d,0xdf7c,0xaf9b,0xbfba,0x8fd9,0x9ff8, 0x6e17,0x7e36,0x4e55,0x5e74,0x2e93,0x3eb2,0x0ed1,0x1ef0 }; - public static ushort GetClusterSlot(string key) + public static ushort GetClusterSlot(string key, System.Text.Encoding encoding = null) { + if (encoding==null) + { + encoding = Encoding.ASCII; + } //HASH_SLOT = CRC16(key) mod 16384 - var blob = Encoding.ASCII.GetBytes(key); + var blob = encoding.GetBytes(key); int offset = 0, count = blob.Length, start = -1, end = -1; byte lt = (byte)'{', rt = (byte)'}'; for (int a = 0; a < count - 1; a++) From 4dbaf371a17a3138f23fa7ce6a4a493348b24c30 Mon Sep 17 00:00:00 2001 From: eveloki <478117618@qq.com> Date: Tue, 9 Jan 2024 23:56:29 +0800 Subject: [PATCH 2/2] Update NormanAdapter.cs --- src/FreeRedis/RedisClient/Adapter/NormanAdapter.cs | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/src/FreeRedis/RedisClient/Adapter/NormanAdapter.cs b/src/FreeRedis/RedisClient/Adapter/NormanAdapter.cs index fa548f3..eea24b8 100644 --- a/src/FreeRedis/RedisClient/Adapter/NormanAdapter.cs +++ b/src/FreeRedis/RedisClient/Adapter/NormanAdapter.cs @@ -1,4 +1,4 @@ -using FreeRedis; +using FreeRedis; using FreeRedis.Internal; using System; using System.Collections.Generic; @@ -17,6 +17,7 @@ internal class NormanAdapter : BaseAdapter internal readonly IdleBus _ib; readonly ConnectionStringBuilder[] _connectionStrings; readonly Func _redirectRule; + internal static Encoding _baseEncoding = System.Text.Encoding.ASCII; public NormanAdapter(RedisClient topOwner, ConnectionStringBuilder[] connectionStrings, Func redirectRule) { @@ -27,6 +28,7 @@ public NormanAdapter(RedisClient topOwner, ConnectionStringBuilder[] connectionS throw new ArgumentNullException(nameof(connectionStrings)); _connectionStrings = connectionStrings.ToArray(); + _baseEncoding = connectionStrings.FirstOrDefault()?.Encoding; _ib = new IdleBus(TimeSpan.FromMinutes(10)); foreach (var connectionString in _connectionStrings) RegisterClusterNode(connectionString); @@ -58,7 +60,7 @@ public override IRedisSocket GetRedisSocket(CommandPacket cmd) if (_redirectRule == null) { //crc16 - var slots = cmd?._keyIndexes.Select(a => ClusterAdapter.GetClusterSlot(cmd._input[a].ToInvariantCultureToString())).Distinct().ToArray(); + var slots = cmd?._keyIndexes.Select(a => ClusterAdapter.GetClusterSlot(cmd._input[a].ToInvariantCultureToString(), _baseEncoding)).Distinct().ToArray(); poolkeys = slots?.Select(a => _connectionStrings[a % _connectionStrings.Length]).Select(a => $"{a.Host}/{a.Database}").Distinct().ToArray(); } else