diff --git a/aspnet-core/modules/common/LINGYUN.Abp.Location.Baidu/LINGYUN/Abp/Location/Baidu/BaiduLocationHttpClient.cs b/aspnet-core/modules/common/LINGYUN.Abp.Location.Baidu/LINGYUN/Abp/Location/Baidu/BaiduLocationHttpClient.cs index 51020e09d..d80e3552c 100644 --- a/aspnet-core/modules/common/LINGYUN.Abp.Location.Baidu/LINGYUN/Abp/Location/Baidu/BaiduLocationHttpClient.cs +++ b/aspnet-core/modules/common/LINGYUN.Abp.Location.Baidu/LINGYUN/Abp/Location/Baidu/BaiduLocationHttpClient.cs @@ -49,7 +49,6 @@ namespace LINGYUN.Abp.Location.Baidu var baiduMapPath = "/location/ip"; if (Options.CaculateAKSN) { - // TODO: 百度的文档不明不白,sn的算法在遇到特殊字符会验证失败,有待完善 var sn = BaiduAKSNCaculater.CaculateAKSN(Options.AccessSecret, baiduMapPath, requestParamters); requestParamters.Add("sn", sn); } @@ -102,7 +101,6 @@ namespace LINGYUN.Abp.Location.Baidu var baiduMapPath = "/geocoding/v3"; if (Options.CaculateAKSN) { - // TODO: 百度的文档不明不白,sn的算法在遇到特殊字符会验证失败,有待完善 var sn = BaiduAKSNCaculater.CaculateAKSN(Options.AccessSecret, baiduMapPath, requestParamters); requestParamters.Add("sn", sn); } @@ -153,11 +151,10 @@ namespace LINGYUN.Abp.Location.Baidu var baiduMapPath = "/reverse_geocoding/v3"; if (Options.CaculateAKSN) { - // TODO: 百度的文档不明不白,sn的算法在遇到特殊字符会验证失败,有待完善 var sn = BaiduAKSNCaculater.CaculateAKSN(Options.AccessSecret, baiduMapPath, requestParamters); requestParamters.Add("sn", sn); } - requestParamters["location"] = string.Format("{0}%2C{1}", lat, lng); + var requestUrl = BuildRequestUrl(baiduMapUrl, baiduMapPath, requestParamters); var responseContent = await MakeRequestAndGetResultAsync(requestUrl); var baiduLocationResponse = JsonConvert.DeserializeObject(responseContent); @@ -246,7 +243,7 @@ namespace LINGYUN.Abp.Location.Baidu requestUrlBuilder.Append(path).Append("?"); foreach (var paramter in paramters) { - requestUrlBuilder.AppendFormat("{0}={1}", paramter.Key, paramter.Value); + requestUrlBuilder.AppendFormat("{0}={1}", Uri.EscapeDataString(paramter.Key), Uri.EscapeDataString(paramter.Value)); requestUrlBuilder.Append("&"); } requestUrlBuilder.Remove(requestUrlBuilder.Length - 1, 1); diff --git a/aspnet-core/modules/common/LINGYUN.Abp.Location.Baidu/LINGYUN/Abp/Location/Baidu/Utils/BaiduAKSNCaculater.cs b/aspnet-core/modules/common/LINGYUN.Abp.Location.Baidu/LINGYUN/Abp/Location/Baidu/Utils/BaiduAKSNCaculater.cs index b797d1120..f6effb69f 100644 --- a/aspnet-core/modules/common/LINGYUN.Abp.Location.Baidu/LINGYUN/Abp/Location/Baidu/Utils/BaiduAKSNCaculater.cs +++ b/aspnet-core/modules/common/LINGYUN.Abp.Location.Baidu/LINGYUN/Abp/Location/Baidu/Utils/BaiduAKSNCaculater.cs @@ -22,40 +22,22 @@ namespace LINGYUN.Abp.Location.Baidu.Utils } } - private static string UrlEncode(string str) - { - str = System.Web.HttpUtility.UrlEncode(str); - byte[] buf = Encoding.ASCII.GetBytes(str);//等同于Encoding.ASCII.GetBytes(str) - for (int i = 0; i < buf.Length; i++) - if (buf[i] == '%') - { - if (buf[i + 1] >= 'a') buf[i + 1] -= 32; - if (buf[i + 2] >= 'a') buf[i + 2] -= 32; - i += 2; - } - return Encoding.ASCII.GetString(buf);//同上,等同于Encoding.ASCII.GetString(buf) - } - private static string HttpBuildQuery(IDictionary querystring_arrays) { - - StringBuilder sb = new StringBuilder(); + List list = new List(querystring_arrays.Count); foreach (var item in querystring_arrays) { - sb.Append(UrlEncode(item.Key)); - sb.Append("="); - sb.Append(UrlEncode(item.Value)); - sb.Append("&"); + list.Add($"{Uri.EscapeDataString(item.Key)}={Uri.EscapeDataString(item.Value)}"); } - sb.Remove(sb.Length - 1, 1); - return sb.ToString(); + + return string.Join("&", list); } public static string CaculateAKSN(string sk, string url, IDictionary querystring_arrays) { var queryString = HttpBuildQuery(querystring_arrays); - var str = UrlEncode(url + "?" + queryString + sk); + var str = Uri.EscapeDataString(url + "?" + queryString + sk); return MD5(str); } diff --git a/aspnet-core/tests/LINGYUN.Abp.Location.Baidu.Tests/LINGYUN/Abp/Location/Baidu/BaiduLocationResolveProviderTests.cs b/aspnet-core/tests/LINGYUN.Abp.Location.Baidu.Tests/LINGYUN/Abp/Location/Baidu/BaiduLocationResolveProviderTests.cs index b60a5036c..cfb15c5b1 100644 --- a/aspnet-core/tests/LINGYUN.Abp.Location.Baidu.Tests/LINGYUN/Abp/Location/Baidu/BaiduLocationResolveProviderTests.cs +++ b/aspnet-core/tests/LINGYUN.Abp.Location.Baidu.Tests/LINGYUN/Abp/Location/Baidu/BaiduLocationResolveProviderTests.cs @@ -1,4 +1,5 @@ using Shouldly; +using System; using System.Threading.Tasks; using Xunit; @@ -21,22 +22,24 @@ namespace LINGYUN.Abp.Location.Baidu var location = await _provider.ReGeocodeAsync(lat, lng, radius); location.ShouldNotBeNull(); - location.Address.ShouldBe("北京市西城区前门西大街正阳市场4号楼"); - location.FormattedAddress.ShouldBe("前门西大街正阳市场4号楼"); + location.Address.ShouldBe("北京市西城区煤市街与前门西后河沿街交叉路口往西北约50米"); + location.FormattedAddress.ShouldBe("西城区正阳市场"); // TODO } [Theory] - [InlineData("北京市东城区广场东侧路", "北京")] - public async Task Geocode_Test(string address, string city = "") + [InlineData("北京市东城区广场东侧路", "北京", 39.9102810304917, 116.40588509187855, "道路")] + [InlineData("天安门-城楼检票处(入口)", "北京", 39.91573869262374, 116.40366250438577, "NoClass")] + [InlineData("国家图书馆(古籍馆)", "北京", 39.92968852456012, 116.39170686652291, "教育")] + public async Task Geocode_Test(string address, string city, double lat, double lng, string level) { var location = await _provider.GeocodeAsync(address, city); location.ShouldNotBeNull(); - location.Latitude.ShouldBe(39.91125781161926); - location.Longitude.ShouldBe(116.40588581321788); - location.Level.ShouldBe("道路"); + location.Latitude.ShouldBe(lat); + location.Longitude.ShouldBe(lng); + location.Level.ShouldBe(level); location.Pomprehension.ShouldBe(0); // TODO @@ -49,8 +52,8 @@ namespace LINGYUN.Abp.Location.Baidu var location = await _provider.IPGeocodeAsync(ipAddress); location.ShouldNotBeNull(); - location.Location.Latitude.ShouldBe(39.91489028930664); - location.Location.Longitude.ShouldBe(116.40387725830078); + location.Location.Latitude.ShouldBe(39.91092300415039); + location.Location.Longitude.ShouldBe(116.41338348388672); // TODO }