From 2c829d9c578dc098e2a6994a73d666bdd8ec25e4 Mon Sep 17 00:00:00 2001 From: catcherwong Date: Tue, 26 Nov 2019 11:01:06 +0800 Subject: [PATCH 1/6] :bookmark: v0.8.2 --- build/releasenotes.props | 8 +------- build/version.props | 30 +++++++++++++++--------------- 2 files changed, 16 insertions(+), 22 deletions(-) diff --git a/build/releasenotes.props b/build/releasenotes.props index d52a27f9..91483391 100644 --- a/build/releasenotes.props +++ b/build/releasenotes.props @@ -1,13 +1,7 @@ - 1. Make Interceptors and response caching Support .netcore3.0. - 2. Remove WithServices method to support console apps. - 3. Improve RabbitMQ bus. - 4. Add deep clone for memory cache provider. - 5. Support multi instances of hybrid provider. - 6. Upgrading dependencies. - 7. Modify some extension methods' namespace. + 1. Redis provider support Hyperloglog. 1. Make Interceptors and response caching Support .netcore3.0. diff --git a/build/version.props b/build/version.props index 5c51b303..78a285cd 100644 --- a/build/version.props +++ b/build/version.props @@ -1,21 +1,21 @@ - 0.8.0 - 0.8.0 + 0.8.2 + 0.8.2 0.8.2 - 0.8.0 - 0.8.0 - 0.8.1 - 0.8.0 - 0.8.0 - 0.8.0 - 0.8.1 - 0.8.1 - 0.8.0 + 0.8.2 + 0.8.2 + 0.8.2 + 0.8.2 + 0.8.2 + 0.8.2 + 0.8.2 + 0.8.2 + 0.8.2 0.8.2 - 0.8.0 - 0.8.1 - 0.8.0 - 0.8.0 + 0.8.2 + 0.8.2 + 0.8.2 + 0.8.2 From 09fb14b1bdd3c7e9816b14d52ff6ed53f700c937 Mon Sep 17 00:00:00 2001 From: catcherwong Date: Tue, 3 Dec 2019 10:04:26 +0800 Subject: [PATCH 2/6] :arrow_up: Upgrading dependencies. --- src/EasyCaching.Bus.CSRedis/EasyCaching.Bus.CSRedis.csproj | 2 +- src/EasyCaching.Bus.RabbitMQ/EasyCaching.Bus.RabbitMQ.csproj | 2 +- src/EasyCaching.CSRedis/EasyCaching.CSRedis.csproj | 2 +- src/EasyCaching.Disk/EasyCaching.Disk.csproj | 2 +- src/EasyCaching.HybridCache/EasyCaching.HybridCache.csproj | 2 +- .../EasyCaching.Interceptor.Castle.csproj | 2 +- src/EasyCaching.Memcached/EasyCaching.Memcached.csproj | 2 +- src/EasyCaching.SQLite/EasyCaching.SQLite.csproj | 4 ++-- .../EasyCaching.Serialization.Json.csproj | 2 +- .../EasyCaching.Serialization.MessagePack.csproj | 2 +- .../EasyCaching.Serialization.Protobuf.csproj | 2 +- 11 files changed, 12 insertions(+), 12 deletions(-) diff --git a/src/EasyCaching.Bus.CSRedis/EasyCaching.Bus.CSRedis.csproj b/src/EasyCaching.Bus.CSRedis/EasyCaching.Bus.CSRedis.csproj index b092593a..91677a7c 100644 --- a/src/EasyCaching.Bus.CSRedis/EasyCaching.Bus.CSRedis.csproj +++ b/src/EasyCaching.Bus.CSRedis/EasyCaching.Bus.CSRedis.csproj @@ -31,7 +31,7 @@ - + diff --git a/src/EasyCaching.Bus.RabbitMQ/EasyCaching.Bus.RabbitMQ.csproj b/src/EasyCaching.Bus.RabbitMQ/EasyCaching.Bus.RabbitMQ.csproj index 20e244b6..864d3e44 100644 --- a/src/EasyCaching.Bus.RabbitMQ/EasyCaching.Bus.RabbitMQ.csproj +++ b/src/EasyCaching.Bus.RabbitMQ/EasyCaching.Bus.RabbitMQ.csproj @@ -35,7 +35,7 @@ - + diff --git a/src/EasyCaching.CSRedis/EasyCaching.CSRedis.csproj b/src/EasyCaching.CSRedis/EasyCaching.CSRedis.csproj index 8d90836b..45ed9f95 100644 --- a/src/EasyCaching.CSRedis/EasyCaching.CSRedis.csproj +++ b/src/EasyCaching.CSRedis/EasyCaching.CSRedis.csproj @@ -31,7 +31,7 @@ - + diff --git a/src/EasyCaching.Disk/EasyCaching.Disk.csproj b/src/EasyCaching.Disk/EasyCaching.Disk.csproj index 1c1a72e2..dc54db4c 100644 --- a/src/EasyCaching.Disk/EasyCaching.Disk.csproj +++ b/src/EasyCaching.Disk/EasyCaching.Disk.csproj @@ -39,6 +39,6 @@ - + diff --git a/src/EasyCaching.HybridCache/EasyCaching.HybridCache.csproj b/src/EasyCaching.HybridCache/EasyCaching.HybridCache.csproj index d25332f2..2adce55d 100644 --- a/src/EasyCaching.HybridCache/EasyCaching.HybridCache.csproj +++ b/src/EasyCaching.HybridCache/EasyCaching.HybridCache.csproj @@ -38,6 +38,6 @@ - + diff --git a/src/EasyCaching.Interceptor.Castle/EasyCaching.Interceptor.Castle.csproj b/src/EasyCaching.Interceptor.Castle/EasyCaching.Interceptor.Castle.csproj index cf330875..a7b811c9 100644 --- a/src/EasyCaching.Interceptor.Castle/EasyCaching.Interceptor.Castle.csproj +++ b/src/EasyCaching.Interceptor.Castle/EasyCaching.Interceptor.Castle.csproj @@ -37,7 +37,7 @@ - + diff --git a/src/EasyCaching.Memcached/EasyCaching.Memcached.csproj b/src/EasyCaching.Memcached/EasyCaching.Memcached.csproj index a07e79d7..3e26be30 100644 --- a/src/EasyCaching.Memcached/EasyCaching.Memcached.csproj +++ b/src/EasyCaching.Memcached/EasyCaching.Memcached.csproj @@ -34,7 +34,7 @@ - + diff --git a/src/EasyCaching.SQLite/EasyCaching.SQLite.csproj b/src/EasyCaching.SQLite/EasyCaching.SQLite.csproj index 0b0067b2..95ddc4f6 100644 --- a/src/EasyCaching.SQLite/EasyCaching.SQLite.csproj +++ b/src/EasyCaching.SQLite/EasyCaching.SQLite.csproj @@ -35,8 +35,8 @@ - - + + diff --git a/src/EasyCaching.Serialization.Json/EasyCaching.Serialization.Json.csproj b/src/EasyCaching.Serialization.Json/EasyCaching.Serialization.Json.csproj index 92e39ef0..f830207f 100644 --- a/src/EasyCaching.Serialization.Json/EasyCaching.Serialization.Json.csproj +++ b/src/EasyCaching.Serialization.Json/EasyCaching.Serialization.Json.csproj @@ -35,7 +35,7 @@ - + diff --git a/src/EasyCaching.Serialization.MessagePack/EasyCaching.Serialization.MessagePack.csproj b/src/EasyCaching.Serialization.MessagePack/EasyCaching.Serialization.MessagePack.csproj index 3eb886fd..4e33c707 100644 --- a/src/EasyCaching.Serialization.MessagePack/EasyCaching.Serialization.MessagePack.csproj +++ b/src/EasyCaching.Serialization.MessagePack/EasyCaching.Serialization.MessagePack.csproj @@ -34,6 +34,6 @@ - + diff --git a/src/EasyCaching.Serialization.Protobuf/EasyCaching.Serialization.Protobuf.csproj b/src/EasyCaching.Serialization.Protobuf/EasyCaching.Serialization.Protobuf.csproj index 8c8786e3..3df777a0 100644 --- a/src/EasyCaching.Serialization.Protobuf/EasyCaching.Serialization.Protobuf.csproj +++ b/src/EasyCaching.Serialization.Protobuf/EasyCaching.Serialization.Protobuf.csproj @@ -34,7 +34,7 @@ - + From 68070b9f51dd89d8bb756edd871e448244cf6357 Mon Sep 17 00:00:00 2001 From: catcherwong Date: Wed, 4 Dec 2019 08:37:59 +0800 Subject: [PATCH 3/6] :sparkles: redis provider support some geo methods --- .../DefaultCSRedisCachingProvider.Geo.cs | 146 ++++++++++++++ src/EasyCaching.Core/IRedisCachingProvider.cs | 64 ++++++- .../DefaultRedisCachingProvider.Geo.cs | 181 ++++++++++++++++++ .../BaseRedisFeatureCachingProviderTest.cs | 112 ++++++++++- 4 files changed, 500 insertions(+), 3 deletions(-) create mode 100644 src/EasyCaching.CSRedis/DefaultCSRedisCachingProvider.Geo.cs create mode 100644 src/EasyCaching.Redis/DefaultRedisCachingProvider.Geo.cs diff --git a/src/EasyCaching.CSRedis/DefaultCSRedisCachingProvider.Geo.cs b/src/EasyCaching.CSRedis/DefaultCSRedisCachingProvider.Geo.cs new file mode 100644 index 00000000..d7fc9c0e --- /dev/null +++ b/src/EasyCaching.CSRedis/DefaultCSRedisCachingProvider.Geo.cs @@ -0,0 +1,146 @@ +namespace EasyCaching.CSRedis +{ + using EasyCaching.Core; + using System.Collections.Generic; + using System.Linq; + using System.Threading.Tasks; + using GeoUnit = global::CSRedis.GeoUnit; + + public partial class DefaultCSRedisCachingProvider : IRedisCachingProvider + { + public long GeoAdd(string cacheKey, List<(double longitude, double latitude, string member)> values) + { + ArgumentCheck.NotNullOrWhiteSpace(cacheKey, nameof(cacheKey)); + ArgumentCheck.NotNullAndCountGTZero(values, nameof(values)); + + var list = new List<(double longitude, double latitude, object member)>(); + + foreach (var item in values) + { + list.Add((item.longitude, item.latitude, item.member)); + } + + var res = _cache.GeoAdd(cacheKey, list.ToArray()); + return res; + } + + public async Task GeoAddAsync(string cacheKey, List<(double longitude, double latitude, string member)> values) + { + ArgumentCheck.NotNullOrWhiteSpace(cacheKey, nameof(cacheKey)); + ArgumentCheck.NotNullAndCountGTZero(values, nameof(values)); + + var list = new List<(double longitude, double latitude, object member)>(); + + foreach (var item in values) + { + list.Add((item.longitude, item.latitude, item.member)); + } + + var res = await _cache.GeoAddAsync(cacheKey, list.ToArray()); + return res; + } + + public double? GeoDist(string cacheKey, string member1, string member2, string unit = "m") + { + ArgumentCheck.NotNullOrWhiteSpace(cacheKey, nameof(cacheKey)); + ArgumentCheck.NotNullOrWhiteSpace(member1, nameof(member1)); + ArgumentCheck.NotNullOrWhiteSpace(member2, nameof(member2)); + ArgumentCheck.NotNullOrWhiteSpace(unit, nameof(unit)); + + var res = _cache.GeoDist(cacheKey, member1, member2, GetGeoUnit(unit)); + return res; + } + + public async Task GeoDistAsync(string cacheKey, string member1, string member2, string unit = "m") + { + ArgumentCheck.NotNullOrWhiteSpace(cacheKey, nameof(cacheKey)); + ArgumentCheck.NotNullOrWhiteSpace(member1, nameof(member1)); + ArgumentCheck.NotNullOrWhiteSpace(member2, nameof(member2)); + ArgumentCheck.NotNullOrWhiteSpace(unit, nameof(unit)); + + var res = await _cache.GeoDistAsync(cacheKey, member1, member2, GetGeoUnit(unit)); + return res; + } + + public List GeoHash(string cacheKey, List members) + { + ArgumentCheck.NotNullOrWhiteSpace(cacheKey, nameof(cacheKey)); + ArgumentCheck.NotNullAndCountGTZero(members, nameof(members)); + + var list = new List(); + foreach (var item in members) + { + list.Add(item); + } + + var res = _cache.GeoHash(cacheKey, list.ToArray()); + return res.ToList() ; + } + + public async Task> GeoHashAsync(string cacheKey, List members) + { + ArgumentCheck.NotNullOrWhiteSpace(cacheKey, nameof(cacheKey)); + ArgumentCheck.NotNullAndCountGTZero(members, nameof(members)); + + var list = new List(); + foreach (var item in members) + { + list.Add(item); + } + + var res = await _cache.GeoHashAsync(cacheKey, list.ToArray()); + return res.ToList(); + } + + public List<(double longitude, double latitude)?> GeoPos(string cacheKey, List members) + { + ArgumentCheck.NotNullOrWhiteSpace(cacheKey, nameof(cacheKey)); + ArgumentCheck.NotNullAndCountGTZero(members, nameof(members)); + + var list = new List(); + foreach (var item in members) + { + list.Add(item); + } + + var res = _cache.GeoPos(cacheKey, list.ToArray()); + return res.ToList(); + } + + public async Task> GeoPosAsync(string cacheKey, List members) + { + ArgumentCheck.NotNullOrWhiteSpace(cacheKey, nameof(cacheKey)); + ArgumentCheck.NotNullAndCountGTZero(members, nameof(members)); + + var list = new List(); + foreach (var item in members) + { + list.Add(item); + } + + var res = await _cache.GeoPosAsync(cacheKey, list.ToArray()); + return res.ToList(); + } + + private GeoUnit GetGeoUnit(string unit) + { + GeoUnit geoUnit; + switch (unit) + { + case "km": + geoUnit = GeoUnit.km; + break; + case "ft": + geoUnit = GeoUnit.ft; + break; + case "mi": + geoUnit = GeoUnit.mi; + break; + default: + geoUnit = GeoUnit.m; + break; + } + return geoUnit; + } + } +} diff --git a/src/EasyCaching.Core/IRedisCachingProvider.cs b/src/EasyCaching.Core/IRedisCachingProvider.cs index 451d6ec1..e49ca015 100644 --- a/src/EasyCaching.Core/IRedisCachingProvider.cs +++ b/src/EasyCaching.Core/IRedisCachingProvider.cs @@ -792,7 +792,6 @@ public interface IRedisCachingProvider Task ZScoreAsync(string cacheKey, T cacheValue); #endregion - #region Hyperloglog /// /// https://redis.io/commands/pfadd @@ -837,5 +836,68 @@ public interface IRedisCachingProvider /// Task PfMergeAsync(string destKey, List sourceKeys); #endregion + + #region Geo + /// + /// https://redis.io/commands/geoadd + /// + /// + /// + /// + long GeoAdd(string cacheKey, List<(double longitude, double latitude, string member)> values); + /// + /// https://redis.io/commands/geoadd + /// + /// + /// + /// + Task GeoAddAsync(string cacheKey, List<(double longitude, double latitude, string member)> values); + /// + /// https://redis.io/commands/geodist + /// + /// + /// + /// + /// + /// + double? GeoDist(string cacheKey, string member1, string member2, string unit = "m"); + /// + /// https://redis.io/commands/geodist + /// + /// + /// + /// + /// + /// + Task GeoDistAsync(string cacheKey, string member1, string member2, string unit = "m"); + /// + /// https://redis.io/commands/geohash + /// + /// + /// + /// + List GeoHash(string cacheKey, List members); + /// + /// https://redis.io/commands/geohash + /// + /// + /// + /// + Task> GeoHashAsync(string cacheKey, List members); + /// + /// https://redis.io/commands/geopos + /// + /// + /// + /// + List<(double longitude, double latitude)?> GeoPos(string cacheKey, List members); + /// + /// https://redis.io/commands/geopos + /// + /// + /// + /// + Task> GeoPosAsync(string cacheKey, List members); + #endregion } } diff --git a/src/EasyCaching.Redis/DefaultRedisCachingProvider.Geo.cs b/src/EasyCaching.Redis/DefaultRedisCachingProvider.Geo.cs new file mode 100644 index 00000000..f5ae0c91 --- /dev/null +++ b/src/EasyCaching.Redis/DefaultRedisCachingProvider.Geo.cs @@ -0,0 +1,181 @@ +namespace EasyCaching.Redis +{ + using EasyCaching.Core; + using StackExchange.Redis; + using System.Collections.Generic; + using System.Linq; + using System.Threading.Tasks; + + /// + /// Default redis caching provider. + /// + public partial class DefaultRedisCachingProvider : IRedisCachingProvider + { + public long GeoAdd(string cacheKey, List<(double longitude, double latitude, string member)> values) + { + ArgumentCheck.NotNullOrWhiteSpace(cacheKey, nameof(cacheKey)); + ArgumentCheck.NotNullAndCountGTZero(values, nameof(values)); + + var list = new List(); + + foreach (var item in values) + { + list.Add( new GeoEntry(item.longitude, item.latitude, item.member)); + } + + var res = _cache.GeoAdd(cacheKey, list.ToArray()); + return res; + } + + public async Task GeoAddAsync(string cacheKey, List<(double longitude, double latitude, string member)> values) + { + ArgumentCheck.NotNullOrWhiteSpace(cacheKey, nameof(cacheKey)); + ArgumentCheck.NotNullAndCountGTZero(values, nameof(values)); + + var list = new List(); + + foreach (var item in values) + { + list.Add(new GeoEntry(item.longitude, item.latitude, item.member)); + } + + var res = await _cache.GeoAddAsync(cacheKey, list.ToArray()); + return res; + } + + public double? GeoDist(string cacheKey, string member1, string member2, string unit = "m") + { + ArgumentCheck.NotNullOrWhiteSpace(cacheKey, nameof(cacheKey)); + ArgumentCheck.NotNullOrWhiteSpace(member1, nameof(member1)); + ArgumentCheck.NotNullOrWhiteSpace(member2, nameof(member2)); + ArgumentCheck.NotNullOrWhiteSpace(unit, nameof(unit)); + + var res = _cache.GeoDistance(cacheKey, member1, member2, GetGeoUnit(unit)); + return res; + } + + public async Task GeoDistAsync(string cacheKey, string member1, string member2, string unit = "m") + { + ArgumentCheck.NotNullOrWhiteSpace(cacheKey, nameof(cacheKey)); + ArgumentCheck.NotNullOrWhiteSpace(member1, nameof(member1)); + ArgumentCheck.NotNullOrWhiteSpace(member2, nameof(member2)); + ArgumentCheck.NotNullOrWhiteSpace(unit, nameof(unit)); + + var res = await _cache.GeoDistanceAsync(cacheKey, member1, member2, GetGeoUnit(unit)); + return res; + } + + public List GeoHash(string cacheKey, List members) + { + ArgumentCheck.NotNullOrWhiteSpace(cacheKey, nameof(cacheKey)); + ArgumentCheck.NotNullAndCountGTZero(members, nameof(members)); + + var list = new List(); + foreach (var item in members) + { + list.Add(item); + } + + var res = _cache.GeoHash(cacheKey, list.ToArray()); + return res.ToList(); + } + + public async Task> GeoHashAsync(string cacheKey, List members) + { + ArgumentCheck.NotNullOrWhiteSpace(cacheKey, nameof(cacheKey)); + ArgumentCheck.NotNullAndCountGTZero(members, nameof(members)); + + var list = new List(); + foreach (var item in members) + { + list.Add(item); + } + + var res = await _cache.GeoHashAsync(cacheKey, list.ToArray()); + return res.ToList(); + } + + public List<(double longitude, double latitude)?> GeoPos(string cacheKey, List members) + { + ArgumentCheck.NotNullOrWhiteSpace(cacheKey, nameof(cacheKey)); + ArgumentCheck.NotNullAndCountGTZero(members, nameof(members)); + + var list = new List(); + foreach (var item in members) + { + list.Add(item); + } + + var res = _cache.GeoPosition(cacheKey, list.ToArray()); + + var tuple = new List<(double longitude, double latitude)?>(); + + foreach (var item in res) + { + if (item.HasValue) + { + tuple.Add((item.Value.Longitude, item.Value.Latitude)); + } + else + { + tuple.Add(null); + } + + } + + return tuple; + } + + public async Task> GeoPosAsync(string cacheKey, List members) + { + ArgumentCheck.NotNullOrWhiteSpace(cacheKey, nameof(cacheKey)); + ArgumentCheck.NotNullAndCountGTZero(members, nameof(members)); + + var list = new List(); + foreach (var item in members) + { + list.Add(item); + } + + var res = await _cache.GeoPositionAsync(cacheKey, list.ToArray()); + + var tuple = new List<(double longitude, double latitude)?>(); + + foreach (var item in res) + { + if (item.HasValue) + { + tuple.Add((item.Value.Longitude, item.Value.Latitude)); + } + else + { + tuple.Add(null); + } + + } + + return tuple; + } + + private GeoUnit GetGeoUnit(string unit) + { + GeoUnit geoUnit; + switch (unit) + { + case "km": + geoUnit = GeoUnit.Kilometers; + break; + case "ft": + geoUnit = GeoUnit.Feet; + break; + case "mi": + geoUnit = GeoUnit.Miles; + break; + default: + geoUnit = GeoUnit.Meters; + break; + } + return geoUnit; + } + } +} diff --git a/test/EasyCaching.UnitTests/CachingTests/BaseRedisFeatureCachingProviderTest.cs b/test/EasyCaching.UnitTests/CachingTests/BaseRedisFeatureCachingProviderTest.cs index cbaea1a6..c8190e44 100644 --- a/test/EasyCaching.UnitTests/CachingTests/BaseRedisFeatureCachingProviderTest.cs +++ b/test/EasyCaching.UnitTests/CachingTests/BaseRedisFeatureCachingProviderTest.cs @@ -2,7 +2,8 @@ { using EasyCaching.Core; using System; - using System.Collections.Generic; + using System.Collections.Generic; + using System.Linq; using System.Threading.Tasks; using Xunit; @@ -1633,7 +1634,114 @@ protected virtual async Task PfMergeAsync_Should_Succeed() await _provider.KeyDelAsync(cacheKey0); await _provider.KeyDelAsync(cacheKey1); await _provider.KeyDelAsync(cacheKey2); - } + } + #endregion + + #region Geo + [Fact] + protected virtual void GeoAdd_And_GeoDist_Should_Succeed() + { + var cacheKey = $"{_nameSpace}-geoadd-{Guid.NewGuid().ToString()}"; + + var res = _provider.GeoAdd(cacheKey, new List<(double longitude, double latitude, string member)> { (13.361389, 38.115556, "Palermo"), (15.087269, 37.502669, "Catania") }); + + Assert.Equal(2, res); + + var dist = _provider.GeoDist(cacheKey, "Palermo", "Catania"); + + Assert.Equal(166274.15156960039, dist); + _provider.KeyDel(cacheKey); + } + + [Fact] + protected virtual async Task GeoAddAsync_And_GeoDistAsync_Should_Succeed() + { + var cacheKey = $"{_nameSpace}-geoaddasync-{Guid.NewGuid().ToString()}"; + + var res = await _provider.GeoAddAsync(cacheKey, new List<(double longitude, double latitude, string member)> { (13.361389, 38.115556, "Palermo"), (15.087269, 37.502669, "Catania") }); + + Assert.Equal(2, res); + + var dist = await _provider.GeoDistAsync(cacheKey, "Palermo", "Catania"); + + Assert.Equal(166274.15156960039, dist); + + await _provider.KeyDelAsync(cacheKey); + } + + [Fact] + protected virtual void GeoAdd_And_GeoHash_Should_Succeed() + { + var cacheKey = $"{_nameSpace}-geohash-{Guid.NewGuid().ToString()}"; + + var res = _provider.GeoAdd(cacheKey, new List<(double longitude, double latitude, string member)> { (13.361389, 38.115556, "Palermo"), (15.087269, 37.502669, "Catania") }); + + Assert.Equal(2, res); + + var hash = _provider.GeoHash(cacheKey, new List { "Palermo", "Catania" }); + + Assert.Equal(2, hash.Count); + Assert.Contains("sqc8b49rny0", hash); + Assert.Contains("sqdtr74hyu0", hash); + + _provider.KeyDel(cacheKey); + } + + [Fact] + protected virtual async Task GeoAddAsync_And_GeoHashAsync_Should_Succeed() + { + var cacheKey = $"{_nameSpace}-geohashasync-{Guid.NewGuid().ToString()}"; + + var res = await _provider.GeoAddAsync(cacheKey, new List<(double longitude, double latitude, string member)> { (13.361389, 38.115556, "Palermo"), (15.087269, 37.502669, "Catania") }); + + Assert.Equal(2, res); + + var hash = await _provider.GeoHashAsync(cacheKey, new List { "Palermo", "Catania" }); + + Assert.Equal(2, hash.Count); + Assert.Contains("sqc8b49rny0", hash); + Assert.Contains("sqdtr74hyu0", hash); + + await _provider.KeyDelAsync(cacheKey); + } + + [Fact] + protected virtual void GeoAdd_And_GeoPos_Should_Succeed() + { + var cacheKey = $"{_nameSpace}-geohash-{Guid.NewGuid().ToString()}"; + + var res = _provider.GeoAdd(cacheKey, new List<(double longitude, double latitude, string member)> { (13.361389, 38.115556, "Palermo"), (15.087269, 37.502669, "Catania") }); + + Assert.Equal(2, res); + + var pos = _provider.GeoPos(cacheKey, new List { "Palermo", "Catania", "NonExisting" }); + + Assert.Equal(3, pos.Count); + Assert.Contains(13.361389338970184, pos.Where(x => x.HasValue).Select(x => x.Value.latitude)); + Assert.Contains(15.087267458438873, pos.Where(x => x.HasValue).Select(x => x.Value.latitude)); + Assert.Contains(null, pos); + + _provider.KeyDel(cacheKey); + } + + [Fact] + protected virtual async Task GeoAddAsync_And_GeoPosAsync_Should_Succeed() + { + var cacheKey = $"{_nameSpace}-geohashasync-{Guid.NewGuid().ToString()}"; + + var res = await _provider.GeoAddAsync(cacheKey, new List<(double longitude, double latitude, string member)> { (13.361389, 38.115556, "Palermo"), (15.087269, 37.502669, "Catania") }); + + Assert.Equal(2, res); + + var pos = await _provider.GeoPosAsync(cacheKey, new List { "Palermo", "Catania", "NonExisting" }); + + Assert.Equal(3, pos.Count); + Assert.Contains(13.361389338970184, pos.Where(x => x.HasValue).Select(x => x.Value.latitude)); + Assert.Contains(15.087267458438873, pos.Where(x => x.HasValue).Select(x => x.Value.latitude)); + Assert.Contains(null, pos); + + await _provider.KeyDelAsync(cacheKey); + } #endregion } } From d6d6389c4c9e209d5841a0a9ce96aea02c6934ec Mon Sep 17 00:00:00 2001 From: catcherwong Date: Tue, 10 Dec 2019 15:10:07 +0800 Subject: [PATCH 4/6] :green_heart: fixed unit tests of geo --- .../BaseRedisFeatureCachingProviderTest.cs | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-) diff --git a/test/EasyCaching.UnitTests/CachingTests/BaseRedisFeatureCachingProviderTest.cs b/test/EasyCaching.UnitTests/CachingTests/BaseRedisFeatureCachingProviderTest.cs index c8190e44..6af1c6c8 100644 --- a/test/EasyCaching.UnitTests/CachingTests/BaseRedisFeatureCachingProviderTest.cs +++ b/test/EasyCaching.UnitTests/CachingTests/BaseRedisFeatureCachingProviderTest.cs @@ -1649,7 +1649,8 @@ protected virtual void GeoAdd_And_GeoDist_Should_Succeed() var dist = _provider.GeoDist(cacheKey, "Palermo", "Catania"); - Assert.Equal(166274.15156960039, dist); + // precision? + Assert.Equal(166274.1516, dist); _provider.KeyDel(cacheKey); } @@ -1664,7 +1665,8 @@ protected virtual async Task GeoAddAsync_And_GeoDistAsync_Should_Succeed() var dist = await _provider.GeoDistAsync(cacheKey, "Palermo", "Catania"); - Assert.Equal(166274.15156960039, dist); + // precision? + Assert.Equal(166274.1516, dist); await _provider.KeyDelAsync(cacheKey); } @@ -1717,8 +1719,8 @@ protected virtual void GeoAdd_And_GeoPos_Should_Succeed() var pos = _provider.GeoPos(cacheKey, new List { "Palermo", "Catania", "NonExisting" }); Assert.Equal(3, pos.Count); - Assert.Contains(13.361389338970184, pos.Where(x => x.HasValue).Select(x => x.Value.latitude)); - Assert.Contains(15.087267458438873, pos.Where(x => x.HasValue).Select(x => x.Value.latitude)); + Assert.Contains(13.361389338970184, pos.Where(x => x.HasValue).Select(x => x.Value.longitude)); + Assert.Contains(15.087267458438873, pos.Where(x => x.HasValue).Select(x => x.Value.longitude)); Assert.Contains(null, pos); _provider.KeyDel(cacheKey); @@ -1736,8 +1738,8 @@ protected virtual async Task GeoAddAsync_And_GeoPosAsync_Should_Succeed() var pos = await _provider.GeoPosAsync(cacheKey, new List { "Palermo", "Catania", "NonExisting" }); Assert.Equal(3, pos.Count); - Assert.Contains(13.361389338970184, pos.Where(x => x.HasValue).Select(x => x.Value.latitude)); - Assert.Contains(15.087267458438873, pos.Where(x => x.HasValue).Select(x => x.Value.latitude)); + Assert.Contains(13.361389338970184, pos.Where(x => x.HasValue).Select(x => x.Value.longitude)); + Assert.Contains(15.087267458438873, pos.Where(x => x.HasValue).Select(x => x.Value.longitude)); Assert.Contains(null, pos); await _provider.KeyDelAsync(cacheKey); From 89ba65cf107f92ac834921dfb970165db62dadb3 Mon Sep 17 00:00:00 2001 From: nx89 Date: Fri, 13 Dec 2019 21:41:58 -0800 Subject: [PATCH 5/6] fix datetime exception --- src/EasyCaching.InMemory/Internal/InMemoryCaching.cs | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/EasyCaching.InMemory/Internal/InMemoryCaching.cs b/src/EasyCaching.InMemory/Internal/InMemoryCaching.cs index 8ea1327a..dc964451 100644 --- a/src/EasyCaching.InMemory/Internal/InMemoryCaching.cs +++ b/src/EasyCaching.InMemory/Internal/InMemoryCaching.cs @@ -107,7 +107,7 @@ public bool Add(string key, T value, TimeSpan? expiresIn = null) { ArgumentCheck.NotNullOrWhiteSpace(key, nameof(key)); - var expiresAt = expiresIn.HasValue ? SystemClock.UtcNow.SafeAdd(expiresIn.Value) : DateTime.MaxValue; + var expiresAt = expiresIn.HasValue ? SystemClock.UtcNow.SafeAdd(expiresIn.Value) : DateTimeOffset.MaxValue; return SetInternal(new CacheEntry(key, value, expiresAt), true); } @@ -115,7 +115,7 @@ public bool Set(string key, T value, TimeSpan? expiresIn = null) { ArgumentCheck.NotNullOrWhiteSpace(key, nameof(key)); - var expiresAt = expiresIn.HasValue ? SystemClock.UtcNow.SafeAdd(expiresIn.Value) : DateTime.MaxValue; + var expiresAt = expiresIn.HasValue ? SystemClock.UtcNow.SafeAdd(expiresIn.Value) : DateTimeOffset.MaxValue; return SetInternal(new CacheEntry(key, value, expiresAt)); } From 58d91362aabc2e3b37bab3e3a6c8a2ac6191a50a Mon Sep 17 00:00:00 2001 From: catcherwong Date: Sun, 15 Dec 2019 10:07:59 +0800 Subject: [PATCH 6/6] :bookmark: v0.8.3 --- build/releasenotes.props | 95 ++++++++-------------------------------- build/version.props | 34 +++++++------- 2 files changed, 35 insertions(+), 94 deletions(-) diff --git a/build/releasenotes.props b/build/releasenotes.props index 91483391..a26f4e16 100644 --- a/build/releasenotes.props +++ b/build/releasenotes.props @@ -1,115 +1,56 @@ - 1. Redis provider support Hyperloglog. + 1. Redis provider support some geo methods. - 1. Make Interceptors and response caching Support .netcore3.0. - 2. Remove WithServices method to support console apps. - 3. Improve RabbitMQ bus. - 4. Add deep clone for memory cache provider. - 5. Support multi instances of hybrid provider. - 6. Upgrading dependencies. - 7. Modify some extension methods' namespace. + 1. Upgrading dependencies. - 1. Support Hyperloglog. + 1. Support some geo methods. - 1. Make Interceptors and response caching Support .netcore3.0. - 2. Remove WithServices method to support console apps. - 3. Improve RabbitMQ bus. - 4. Add deep clone for memory cache provider. - 5. Support multi instances of hybrid provider. - 6. Upgrading dependencies. - 7. Modify some extension methods' namespace. + 1. Upgrading dependencies. - 1. Make Interceptors and response caching Support .netcore3.0. - 2. Remove WithServices method to support console apps. - 3. Improve RabbitMQ bus. - 4. Add deep clone for memory cache provider. - 5. Support multi instances of hybrid provider. - 6. Upgrading dependencies. - 7. Modify some extension methods' namespace. + 1. Fix datetime exception. + 2. Upgrading dependencies. - 1. improve hybrid get with data retriever. + 1. Upgrading dependencies. - 1. Make Interceptors and response caching Support .netcore3.0. - 2. Remove WithServices method to support console apps. - 3. Improve RabbitMQ bus. - 4. Add deep clone for memory cache provider. - 5. Support multi instances of hybrid provider. - 6. Upgrading dependencies. - 7. Modify some extension methods' namespace. + 1. Upgrading dependencies. - 1. Make Interceptors and response caching Support .netcore3.0. - 2. Remove WithServices method to support console apps. - 3. Improve RabbitMQ bus. - 4. Add deep clone for memory cache provider. - 5. Support multi instances of hybrid provider. - 6. Upgrading dependencies. - 7. Modify some extension methods' namespace. + 1. Upgrading dependencies. - 1. Make Interceptors and response caching Support .netcore3.0. - 2. Remove WithServices method to support console apps. - 3. Improve RabbitMQ bus. - 4. Add deep clone for memory cache provider. - 5. Support multi instances of hybrid provider. - 6. Upgrading dependencies. - 7. Modify some extension methods' namespace. + 1. Upgrading dependencies. - 1. Support JsonSerializerSettings. + 1. Upgrading dependencies. - 1. Support custom resolver. + 1. Upgrading dependencies. - 1. Make Interceptors and response caching Support .netcore3.0. - 2. Remove WithServices method to support console apps. - 3. Improve RabbitMQ bus. - 4. Add deep clone for memory cache provider. - 5. Support multi instances of hybrid provider. - 6. Upgrading dependencies. - 7. Modify some extension methods' namespace. + 1. Upgrading dependencies. - 1. Support Hyperloglog. + 1. Support some geo methods. - 1. Support sentinel mode. + 1. Upgrading dependencies. - 1. Make Interceptors and response caching Support .netcore3.0. - 2. Remove WithServices method to support console apps. - 3. Improve RabbitMQ bus. - 4. Add deep clone for memory cache provider. - 5. Support multi instances of hybrid provider. - 6. Upgrading dependencies. - 7. Modify some extension methods' namespace. + 1. Upgrading dependencies. - 1. Make Interceptors and response caching Support .netcore3.0. - 2. Remove WithServices method to support console apps. - 3. Improve RabbitMQ bus. - 4. Add deep clone for memory cache provider. - 5. Support multi instances of hybrid provider. - 6. Upgrading dependencies. - 7. Modify some extension methods' namespace. + 1. Upgrading dependencies. - 1. Make Interceptors and response caching Support .netcore3.0. - 2. Remove WithServices method to support console apps. - 3. Improve RabbitMQ bus. - 4. Add deep clone for memory cache provider. - 5. Support multi instances of hybrid provider. - 6. Upgrading dependencies. - 7. Modify some extension methods' namespace. + 1. Upgrading dependencies. diff --git a/build/version.props b/build/version.props index 78a285cd..f1d1c1a9 100644 --- a/build/version.props +++ b/build/version.props @@ -1,21 +1,21 @@ - 0.8.2 - 0.8.2 - 0.8.2 - 0.8.2 - 0.8.2 - 0.8.2 - 0.8.2 - 0.8.2 - 0.8.2 - 0.8.2 - 0.8.2 - 0.8.2 - 0.8.2 - 0.8.2 - 0.8.2 - 0.8.2 - 0.8.2 + 0.8.3 + 0.8.3 + 0.8.3 + 0.8.3 + 0.8.3 + 0.8.3 + 0.8.3 + 0.8.3 + 0.8.3 + 0.8.3 + 0.8.3 + 0.8.3 + 0.8.3 + 0.8.3 + 0.8.3 + 0.8.3 + 0.8.3