From 9db224b70a5188a4dc2a6bbe7c66a8c275f63245 Mon Sep 17 00:00:00 2001 From: Looly Date: Wed, 27 Nov 2024 10:30:06 +0800 Subject: [PATCH 01/30] prepare 5.8.35 --- CHANGELOG.md | 6 ++++++ README-EN.md | 6 +++--- README.md | 6 +++--- bin/version.txt | 2 +- docs/js/version.js | 2 +- hutool-all/pom.xml | 2 +- hutool-aop/pom.xml | 2 +- hutool-bloomFilter/pom.xml | 2 +- hutool-bom/pom.xml | 2 +- hutool-cache/pom.xml | 2 +- hutool-captcha/pom.xml | 2 +- hutool-core/pom.xml | 2 +- hutool-cron/pom.xml | 2 +- hutool-crypto/pom.xml | 2 +- hutool-db/pom.xml | 2 +- hutool-dfa/pom.xml | 2 +- hutool-extra/pom.xml | 2 +- hutool-http/pom.xml | 2 +- hutool-json/pom.xml | 2 +- hutool-jwt/pom.xml | 2 +- hutool-log/pom.xml | 2 +- hutool-poi/pom.xml | 2 +- hutool-script/pom.xml | 2 +- hutool-setting/pom.xml | 2 +- hutool-socket/pom.xml | 2 +- hutool-system/pom.xml | 2 +- pom.xml | 2 +- 27 files changed, 36 insertions(+), 30 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 24ef2f6259..e58ce49929 100755 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,6 +1,12 @@ # 🚀Changelog +------------------------------------------------------------------------------------------------------------- +# 5.8.35(2024-11-27) + +### 🐣新特性 +### 🐞Bug修复 + ------------------------------------------------------------------------------------------------------------- # 5.8.34(2024-11-25) diff --git a/README-EN.md b/README-EN.md index e97a535e93..d2404c4d95 100755 --- a/README-EN.md +++ b/README-EN.md @@ -150,18 +150,18 @@ We provide the T-Shirt and Sweater with Hutool Logo, please visit the shop: cn.hutool hutool-all - 5.8.34 + 5.8.35 ``` ### 🍐Gradle ``` -implementation 'cn.hutool:hutool-all:5.8.34' +implementation 'cn.hutool:hutool-all:5.8.35' ``` ## 📥Download -- [Maven Repo](https://repo1.maven.org/maven2/cn/hutool/hutool-all/5.8.34/) +- [Maven Repo](https://repo1.maven.org/maven2/cn/hutool/hutool-all/5.8.35/) > 🔔️note: > Hutool 5.x supports JDK8+ and is not tested on Android platforms, and cannot guarantee that all tool classes or tool methods are available. diff --git a/README.md b/README.md index 4f02853538..6190fc529a 100755 --- a/README.md +++ b/README.md @@ -143,20 +143,20 @@ Hutool = Hu + tool,是原公司项目底层代码剥离后的开源库,“Hu cn.hutool hutool-all - 5.8.34 + 5.8.35 ``` ### 🍐Gradle ``` -implementation 'cn.hutool:hutool-all:5.8.34' +implementation 'cn.hutool:hutool-all:5.8.35' ``` ### 📥下载jar 点击以下链接,下载`hutool-all-X.X.X.jar`即可: -- [Maven中央库](https://repo1.maven.org/maven2/cn/hutool/hutool-all/5.8.34/) +- [Maven中央库](https://repo1.maven.org/maven2/cn/hutool/hutool-all/5.8.35/) > 🔔️注意 > Hutool 5.x支持JDK8+,对Android平台没有测试,不能保证所有工具类或工具方法可用。 diff --git a/bin/version.txt b/bin/version.txt index 8cf2ade4e2..8ce621ecff 100755 --- a/bin/version.txt +++ b/bin/version.txt @@ -1 +1 @@ -5.8.34 +5.8.35 diff --git a/docs/js/version.js b/docs/js/version.js index 36dcf0ff4b..d677c5f769 100755 --- a/docs/js/version.js +++ b/docs/js/version.js @@ -1 +1 @@ -var version = '5.8.34' \ No newline at end of file +var version = '5.8.35' \ No newline at end of file diff --git a/hutool-all/pom.xml b/hutool-all/pom.xml index b173af04d1..81a654d69c 100755 --- a/hutool-all/pom.xml +++ b/hutool-all/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-all diff --git a/hutool-aop/pom.xml b/hutool-aop/pom.xml index be66ef6a85..6d6e53098c 100755 --- a/hutool-aop/pom.xml +++ b/hutool-aop/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-aop diff --git a/hutool-bloomFilter/pom.xml b/hutool-bloomFilter/pom.xml index a05e42bc3e..b7e9ea2fdc 100755 --- a/hutool-bloomFilter/pom.xml +++ b/hutool-bloomFilter/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-bloomFilter diff --git a/hutool-bom/pom.xml b/hutool-bom/pom.xml index b583cdc915..f108ab20ab 100755 --- a/hutool-bom/pom.xml +++ b/hutool-bom/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-bom diff --git a/hutool-cache/pom.xml b/hutool-cache/pom.xml index 0a43250b44..d17e8eae86 100755 --- a/hutool-cache/pom.xml +++ b/hutool-cache/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-cache diff --git a/hutool-captcha/pom.xml b/hutool-captcha/pom.xml index 18606bdbcd..11cca40cfc 100755 --- a/hutool-captcha/pom.xml +++ b/hutool-captcha/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-captcha diff --git a/hutool-core/pom.xml b/hutool-core/pom.xml index 371ee4f920..b4cc9eb0da 100755 --- a/hutool-core/pom.xml +++ b/hutool-core/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-core diff --git a/hutool-cron/pom.xml b/hutool-cron/pom.xml index 2f36a22adb..2ce06aaa5a 100755 --- a/hutool-cron/pom.xml +++ b/hutool-cron/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-cron diff --git a/hutool-crypto/pom.xml b/hutool-crypto/pom.xml index 4ee1a3991e..72ecdb5a3c 100755 --- a/hutool-crypto/pom.xml +++ b/hutool-crypto/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-crypto diff --git a/hutool-db/pom.xml b/hutool-db/pom.xml index 224d04a892..6fe8568223 100755 --- a/hutool-db/pom.xml +++ b/hutool-db/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-db diff --git a/hutool-dfa/pom.xml b/hutool-dfa/pom.xml index d619fd4ddb..4a0c152f4c 100755 --- a/hutool-dfa/pom.xml +++ b/hutool-dfa/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-dfa diff --git a/hutool-extra/pom.xml b/hutool-extra/pom.xml index 83c88d98c7..25994e3cd1 100755 --- a/hutool-extra/pom.xml +++ b/hutool-extra/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-extra diff --git a/hutool-http/pom.xml b/hutool-http/pom.xml index 403dae32ac..e713b68a7f 100755 --- a/hutool-http/pom.xml +++ b/hutool-http/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-http diff --git a/hutool-json/pom.xml b/hutool-json/pom.xml index c1dee152d1..9690297662 100755 --- a/hutool-json/pom.xml +++ b/hutool-json/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-json diff --git a/hutool-jwt/pom.xml b/hutool-jwt/pom.xml index 2394d8da70..3a6bf7b614 100755 --- a/hutool-jwt/pom.xml +++ b/hutool-jwt/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-jwt diff --git a/hutool-log/pom.xml b/hutool-log/pom.xml index ceed842585..de97402c34 100755 --- a/hutool-log/pom.xml +++ b/hutool-log/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-log diff --git a/hutool-poi/pom.xml b/hutool-poi/pom.xml index bb99766aec..8e9132d726 100755 --- a/hutool-poi/pom.xml +++ b/hutool-poi/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-poi diff --git a/hutool-script/pom.xml b/hutool-script/pom.xml index 55eb702289..5d7fa1a84f 100755 --- a/hutool-script/pom.xml +++ b/hutool-script/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-script diff --git a/hutool-setting/pom.xml b/hutool-setting/pom.xml index 9a59405e50..b1b6dfefd7 100755 --- a/hutool-setting/pom.xml +++ b/hutool-setting/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-setting diff --git a/hutool-socket/pom.xml b/hutool-socket/pom.xml index 3736f335b9..b92702fcd5 100755 --- a/hutool-socket/pom.xml +++ b/hutool-socket/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-socket diff --git a/hutool-system/pom.xml b/hutool-system/pom.xml index 0ffc730cc7..4d34d06b8c 100755 --- a/hutool-system/pom.xml +++ b/hutool-system/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool-system diff --git a/pom.xml b/pom.xml index 0932137270..3ed5095f12 100755 --- a/pom.xml +++ b/pom.xml @@ -8,7 +8,7 @@ cn.hutool hutool-parent - 5.8.34 + 5.8.35-SNAPSHOT hutool Hutool是一个小而全的Java工具类库,通过静态方法封装,降低相关API的学习成本,提高工作效率,使Java拥有函数式语言般的优雅,让Java语言也可以“甜甜的”。 https://github.com/dromara/hutool From cc823420011a4f38f78cae9d3aa1bc01f8c3e2ee Mon Sep 17 00:00:00 2001 From: Looly Date: Fri, 29 Nov 2024 17:51:05 +0800 Subject: [PATCH 02/30] add test --- .../test/java/cn/hutool/http/IssueIB7REWTest.java | 15 +++++++++++++++ 1 file changed, 15 insertions(+) create mode 100644 hutool-http/src/test/java/cn/hutool/http/IssueIB7REWTest.java diff --git a/hutool-http/src/test/java/cn/hutool/http/IssueIB7REWTest.java b/hutool-http/src/test/java/cn/hutool/http/IssueIB7REWTest.java new file mode 100644 index 0000000000..58db5ce385 --- /dev/null +++ b/hutool-http/src/test/java/cn/hutool/http/IssueIB7REWTest.java @@ -0,0 +1,15 @@ +package cn.hutool.http; + +import cn.hutool.core.lang.Console; +import org.junit.jupiter.api.Disabled; +import org.junit.jupiter.api.Test; + +public class IssueIB7REWTest { + @Test + @Disabled + void getTest() { + System.setProperty("jdk.tls.namedCurves", "secp256r1,secp384r1,secp521r1"); + final String s = HttpUtil.get("https://ebssec.boc.cn/"); + Console.log(s); + } +} From af5cddf80f3333e30ba486a06e3080936e7d7ea6 Mon Sep 17 00:00:00 2001 From: Looly Date: Tue, 3 Dec 2024 23:54:08 +0800 Subject: [PATCH 03/30] =?UTF-8?q?=E4=BF=AE=E5=A4=8DJWTSignerUtil.createSig?= =?UTF-8?q?ner=E4=B8=ADalgorithmId=E6=9C=AA=E8=BD=AC=E6=8D=A2=E9=97=AE?= =?UTF-8?q?=E9=A2=98=EF=BC=88issue#3806@Github=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- CHANGELOG.md | 3 ++- .../src/main/java/cn/hutool/jwt/signers/JWTSignerUtil.java | 2 +- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index e58ce49929..a85d574d2a 100755 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,10 +2,11 @@ # 🚀Changelog ------------------------------------------------------------------------------------------------------------- -# 5.8.35(2024-11-27) +# 5.8.35(2024-12-03) ### 🐣新特性 ### 🐞Bug修复 +* 【crypto 】 修复JWTSignerUtil.createSigner中algorithmId未转换问题(issue#3806@Github) ------------------------------------------------------------------------------------------------------------- # 5.8.34(2024-11-25) diff --git a/hutool-jwt/src/main/java/cn/hutool/jwt/signers/JWTSignerUtil.java b/hutool-jwt/src/main/java/cn/hutool/jwt/signers/JWTSignerUtil.java index 9829b7dafe..9586680f78 100755 --- a/hutool-jwt/src/main/java/cn/hutool/jwt/signers/JWTSignerUtil.java +++ b/hutool-jwt/src/main/java/cn/hutool/jwt/signers/JWTSignerUtil.java @@ -278,7 +278,7 @@ public static JWTSigner createSigner(String algorithmId, Key key) { if (key instanceof PrivateKey || key instanceof PublicKey) { // issue3205@Github if(ReUtil.isMatch("ES\\d{3}", algorithmId)){ - return new EllipticCurveJWTSigner(algorithmId, key); + return new EllipticCurveJWTSigner(AlgorithmUtil.getAlgorithm(algorithmId), key); } return new AsymmetricJWTSigner(AlgorithmUtil.getAlgorithm(algorithmId), key); From 843d1d11dc68c8da982b74410a47ca33253b4f20 Mon Sep 17 00:00:00 2001 From: Looly Date: Wed, 4 Dec 2024 00:29:00 +0800 Subject: [PATCH 04/30] =?UTF-8?q?=E4=BF=AE=E5=A4=8DDateUtil.rangeContains?= =?UTF-8?q?=E6=9C=AA=E9=87=8D=E7=BD=AE=E9=97=AE=E9=A2=98=EF=BC=88issue#IB8?= =?UTF-8?q?OFS@gitee=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- CHANGELOG.md | 1 + .../java/cn/hutool/core/date/DateUtil.java | 8 +++--- .../cn/hutool/core/date/IssueIB8OFSTest.java | 25 +++++++++++++++++++ 3 files changed, 30 insertions(+), 4 deletions(-) create mode 100644 hutool-core/src/test/java/cn/hutool/core/date/IssueIB8OFSTest.java diff --git a/CHANGELOG.md b/CHANGELOG.md index a85d574d2a..4f8f829de8 100755 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -7,6 +7,7 @@ ### 🐣新特性 ### 🐞Bug修复 * 【crypto 】 修复JWTSignerUtil.createSigner中algorithmId未转换问题(issue#3806@Github) +* 【core 】 修复DateUtil.rangeContains未重置问题(issue#IB8OFS@gitee) ------------------------------------------------------------------------------------------------------------- # 5.8.34(2024-11-25) diff --git a/hutool-core/src/main/java/cn/hutool/core/date/DateUtil.java b/hutool-core/src/main/java/cn/hutool/core/date/DateUtil.java index 53b44ad173..ab92c85190 100755 --- a/hutool-core/src/main/java/cn/hutool/core/date/DateUtil.java +++ b/hutool-core/src/main/java/cn/hutool/core/date/DateUtil.java @@ -1975,8 +1975,8 @@ public static DateRange range(Date start, Date end, final DateField unit) { * @since 5.7.21 */ public static List rangeContains(DateRange start, DateRange end) { - List startDateTimes = CollUtil.newArrayList((Iterable) start); - List endDateTimes = CollUtil.newArrayList((Iterable) end); + List startDateTimes = CollUtil.newArrayList((Iterable) start.reset()); + List endDateTimes = CollUtil.newArrayList((Iterable) end.reset()); return startDateTimes.stream().filter(endDateTimes::contains).collect(Collectors.toList()); } @@ -1990,8 +1990,8 @@ public static List rangeContains(DateRange start, DateRange end) { * @since 5.7.21 */ public static List rangeNotContains(DateRange start, DateRange end) { - List startDateTimes = CollUtil.newArrayList((Iterable) start); - List endDateTimes = CollUtil.newArrayList((Iterable) end); + List startDateTimes = CollUtil.newArrayList((Iterable) start.reset()); + List endDateTimes = CollUtil.newArrayList((Iterable) end.reset()); return endDateTimes.stream().filter(item -> !startDateTimes.contains(item)).collect(Collectors.toList()); } diff --git a/hutool-core/src/test/java/cn/hutool/core/date/IssueIB8OFSTest.java b/hutool-core/src/test/java/cn/hutool/core/date/IssueIB8OFSTest.java new file mode 100644 index 0000000000..1d6921523b --- /dev/null +++ b/hutool-core/src/test/java/cn/hutool/core/date/IssueIB8OFSTest.java @@ -0,0 +1,25 @@ +package cn.hutool.core.date; + +import cn.hutool.core.lang.Console; +import org.junit.jupiter.api.Assertions; +import org.junit.jupiter.api.Test; + +import java.util.List; + +public class IssueIB8OFSTest { + @Test + void rangeTest() { + DateRange startRange = DateUtil.range( + DateUtil.parse("2017-01-01"), + DateUtil.parse("2017-01-31"), DateField.DAY_OF_YEAR); + DateRange endRange = DateUtil.range( + DateUtil.parse("2017-01-31"), + DateUtil.parse("2017-02-02"), DateField.DAY_OF_YEAR); + + List dateTimes = DateUtil.rangeContains(startRange, endRange); + Assertions.assertEquals(1, dateTimes.size()); + + List dateNotTimes = DateUtil.rangeNotContains(startRange, endRange); + Assertions.assertEquals(2, dateNotTimes.size()); + } +} From b1fafb682fe30d42e45827f8797484e62700da47 Mon Sep 17 00:00:00 2001 From: "Zhenheng.Xie" Date: Wed, 4 Dec 2024 10:54:24 +0800 Subject: [PATCH 05/30] =?UTF-8?q?=E4=BC=98=E5=8C=96ExcelWriter=E4=B8=AD?= =?UTF-8?q?=E4=BD=BF=E7=94=A8=E6=AF=94=E8=BE=83=E5=99=A8writer=E7=9A=84?= =?UTF-8?q?=E6=96=B9=E6=B3=95=EF=BC=8C=E5=8F=AA=E5=AF=B9=E7=AC=AC=E4=B8=80?= =?UTF-8?q?=E6=9D=A1=E6=95=B0=E6=8D=AE=E8=BF=9B=E8=A1=8C=E6=8E=92=E5=BA=8F?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../java/cn/hutool/poi/excel/ExcelWriter.java | 17 +++-- .../cn/hutool/poi/excel/ExcelWriteTest.java | 72 +++++++++++++++++++ 2 files changed, 85 insertions(+), 4 deletions(-) diff --git a/hutool-poi/src/main/java/cn/hutool/poi/excel/ExcelWriter.java b/hutool-poi/src/main/java/cn/hutool/poi/excel/ExcelWriter.java index e101516b85..ee8fe7c8a9 100755 --- a/hutool-poi/src/main/java/cn/hutool/poi/excel/ExcelWriter.java +++ b/hutool-poi/src/main/java/cn/hutool/poi/excel/ExcelWriter.java @@ -865,11 +865,20 @@ public ExcelWriter write(Iterable data, Comparator comparator) { boolean isFirstRow = true; Map map; for (Object obj : data) { - if (obj instanceof Map) { - map = new TreeMap<>(comparator); - map.putAll((Map) obj); + // 只第一行使用比较器排序 + if (isFirstRow) { + if (obj instanceof Map) { + map = new TreeMap<>(comparator); + map.putAll((Map) obj); + } else { + map = BeanUtil.beanToMap(obj, new TreeMap<>(comparator), false, false); + } } else { - map = BeanUtil.beanToMap(obj, new TreeMap<>(comparator), false, false); + if (obj instanceof Map) { + map = (Map) obj; + } else { + map = BeanUtil.beanToMap(obj, new HashMap<>(), false, false); + } } writeRow(map, isFirstRow); if (isFirstRow) { diff --git a/hutool-poi/src/test/java/cn/hutool/poi/excel/ExcelWriteTest.java b/hutool-poi/src/test/java/cn/hutool/poi/excel/ExcelWriteTest.java index c0a03fee93..29ae68dd11 100755 --- a/hutool-poi/src/test/java/cn/hutool/poi/excel/ExcelWriteTest.java +++ b/hutool-poi/src/test/java/cn/hutool/poi/excel/ExcelWriteTest.java @@ -2,6 +2,7 @@ import cn.hutool.core.collection.CollUtil; import cn.hutool.core.collection.ListUtil; +import cn.hutool.core.comparator.IndexedComparator; import cn.hutool.core.date.DateUtil; import cn.hutool.core.io.FileUtil; import cn.hutool.core.lang.Console; @@ -904,4 +905,75 @@ public void autoSizeColumnTest() { } } + @Test + @Disabled + public void writeWithComparatorTest() { + // 生成测试数据, 10w行50列 + List> dataList = new ArrayList<>(); + for (int i = 1; i <= 100000; i++) { + Map map = new HashMap<>(); + map.put("test11", "test11_" + i); + map.put("test12", "test12_" + i); + map.put("test13", "test13_" + i); + map.put("test14", "test14_" + i); + map.put("test15", "test15_" + i); + map.put("test16", "test16_" + i); + map.put("test17", "test17_" + i); + map.put("test18", "test18_" + i); + map.put("test19", "test19_" + i); + map.put("test1", "test1_" + i); + map.put("test2", "test2_" + i); + map.put("test3", "test3_" + i); + map.put("test4", "test4_" + i); + map.put("test5", "test5_" + i); + map.put("test6", "test6_" + i); + map.put("test7", "test7_" + i); + map.put("test8", "test8_" + i); + map.put("test9", "test9_" + i); + map.put("test10", "test10_" + i); + map.put("test20", "test20_" + i); + map.put("test21", "test21_" + i); + map.put("test22", "test22_" + i); + map.put("test23", "test23_" + i); + map.put("test24", "test24_" + i); + map.put("test25", "test25_" + i); + map.put("test26", "test26_" + i); + map.put("test27", "test27_" + i); + map.put("test28", "test28_" + i); + map.put("test29", "test29_" + i); + map.put("test30", "test30_" + i); + map.put("test41", "test41_" + i); + map.put("test42", "test42_" + i); + map.put("test43", "test43_" + i); + map.put("test44", "test44_" + i); + map.put("test45", "test45_" + i); + map.put("test46", "test46_" + i); + map.put("test47", "test47_" + i); + map.put("test48", "test48_" + i); + map.put("test49", "test49_" + i); + map.put("test50", "test50_" + i); + map.put("test31", "test31_" + i); + map.put("test32", "test32_" + i); + map.put("test33", "test33_" + i); + map.put("test34", "test34_" + i); + map.put("test35", "test35_" + i); + map.put("test36", "test36_" + i); + map.put("test37", "test37_" + i); + map.put("test38", "test38_" + i); + map.put("test39", "test39_" + i); + map.put("test40", "test40_" + i); + dataList.add(map); + } + // 使用比较器写出 + try (BigExcelWriter excelWriter = ExcelUtil.getBigWriter("d:/writeWithComparatorTest.xlsx")) { + excelWriter.write(dataList, new IndexedComparator<>( + "test1", "test2", "test3", "test4", "test5", "test6", "test7", "test8", "test9", "test10", + "test11", "test12", "test13", "test14", "test15", "test16", "test17", "test18", "test19", "test20", + "test21", "test22", "test23", "test24", "test25", "test26", "test27", "test28", "test29", "test30", + "test31", "test32", "test33", "test34", "test35", "test36", "test37", "test38", "test39", "test40", + "test41", "test42", "test43", "test44", "test45", "test46", "test47", "test48", "test49", "test50" + )); + } + } + } From 7da0856314971e4b9556b805cd2117829472a9d0 Mon Sep 17 00:00:00 2001 From: Looly Date: Wed, 4 Dec 2024 12:12:59 +0800 Subject: [PATCH 06/30] =?UTF-8?q?=E4=BC=98=E5=8C=96ExcelWriter=E4=B8=AD?= =?UTF-8?q?=E4=BD=BF=E7=94=A8=E6=AF=94=E8=BE=83=E5=99=A8writer=E7=9A=84?= =?UTF-8?q?=E6=96=B9=E6=B3=95=EF=BC=8C=E5=8F=AA=E5=AF=B9=E7=AC=AC=E4=B8=80?= =?UTF-8?q?=E6=9D=A1=E6=95=B0=E6=8D=AE=E8=BF=9B=E8=A1=8C=E6=8E=92=E5=BA=8F?= =?UTF-8?q?=EF=BC=88pr#3807@Github=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- CHANGELOG.md | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 4f8f829de8..8d71bbe2f2 100755 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,9 +2,11 @@ # 🚀Changelog ------------------------------------------------------------------------------------------------------------- -# 5.8.35(2024-12-03) +# 5.8.35(2024-12-04) ### 🐣新特性 +* 【poi 】 优化ExcelWriter中使用比较器writer的方法,只对第一条数据进行排序(pr#3807@Github) + ### 🐞Bug修复 * 【crypto 】 修复JWTSignerUtil.createSigner中algorithmId未转换问题(issue#3806@Github) * 【core 】 修复DateUtil.rangeContains未重置问题(issue#IB8OFS@gitee) From 0c5444e442b3c8eb5c3f1977de440e5545de7cd7 Mon Sep 17 00:00:00 2001 From: Looly Date: Wed, 4 Dec 2024 12:20:55 +0800 Subject: [PATCH 07/30] =?UTF-8?q?=E4=BC=98=E5=8C=96Ftp.download=EF=BC=8C?= =?UTF-8?q?=E8=BF=94=E5=9B=9Efalse=E6=8A=9B=E5=87=BA=E5=BC=82=E5=B8=B8?= =?UTF-8?q?=EF=BC=88issue#3805@Github=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- CHANGELOG.md | 1 + hutool-extra/src/main/java/cn/hutool/extra/ftp/Ftp.java | 8 +++++++- 2 files changed, 8 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 8d71bbe2f2..fe0f37050a 100755 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -6,6 +6,7 @@ ### 🐣新特性 * 【poi 】 优化ExcelWriter中使用比较器writer的方法,只对第一条数据进行排序(pr#3807@Github) +* 【extra 】 优化Ftp.download,返回false抛出异常(issue#3805@Github) ### 🐞Bug修复 * 【crypto 】 修复JWTSignerUtil.createSigner中algorithmId未转换问题(issue#3806@Github) diff --git a/hutool-extra/src/main/java/cn/hutool/extra/ftp/Ftp.java b/hutool-extra/src/main/java/cn/hutool/extra/ftp/Ftp.java index 9bdc9fac2b..96fbd275ed 100755 --- a/hutool-extra/src/main/java/cn/hutool/extra/ftp/Ftp.java +++ b/hutool-extra/src/main/java/cn/hutool/extra/ftp/Ftp.java @@ -708,9 +708,11 @@ public void download(String path, String fileName, OutputStream out, Charset fil if (null != fileNameCharset) { fileName = new String(fileName.getBytes(fileNameCharset), StandardCharsets.ISO_8859_1); } + + boolean isSuccess; try { client.setFileType(FTPClient.BINARY_FILE_TYPE); - client.retrieveFile(fileName, out); + isSuccess = client.retrieveFile(fileName, out); } catch (IOException e) { throw new IORuntimeException(e); } finally { @@ -718,6 +720,10 @@ public void download(String path, String fileName, OutputStream out, Charset fil cd(pwd); } } + + if(false == isSuccess){ + throw new FtpException("retrieveFile return false"); + } } /** From ae1a18cd20d4a87ed19f7f0f9d9bb951ae0f0668 Mon Sep 17 00:00:00 2001 From: Looly Date: Wed, 4 Dec 2024 18:18:12 +0800 Subject: [PATCH 08/30] add test --- .../java/cn/hutool/core/date/DateBetweenTest.java | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-) diff --git a/hutool-core/src/test/java/cn/hutool/core/date/DateBetweenTest.java b/hutool-core/src/test/java/cn/hutool/core/date/DateBetweenTest.java index afcdda170d..86e723b2b0 100644 --- a/hutool-core/src/test/java/cn/hutool/core/date/DateBetweenTest.java +++ b/hutool-core/src/test/java/cn/hutool/core/date/DateBetweenTest.java @@ -1,12 +1,13 @@ package cn.hutool.core.date; import cn.hutool.core.date.BetweenFormatter.Level; -import static org.junit.jupiter.api.Assertions.*; import org.junit.jupiter.api.Test; import java.time.temporal.ChronoUnit; import java.util.Date; +import static org.junit.jupiter.api.Assertions.assertEquals; + public class DateBetweenTest { @Test @@ -36,6 +37,14 @@ public void betweenYearTest2() { assertEquals(18, betweenYear); } + @Test + public void betweenYearTest3() { + Date start = DateUtil.parse("20170301"); + Date end = DateUtil.parse("2024-02-29 14:56:18"); + long betweenYear = new DateBetween(start, end).betweenYear(false); + assertEquals(6, betweenYear); + } + @Test public void betweenMonthTest() { Date start = DateUtil.parse("2017-02-01 12:23:46"); From b8f681fef150c5d299df15b28dc1f531d8b91dc5 Mon Sep 17 00:00:00 2001 From: Looly Date: Thu, 5 Dec 2024 10:39:13 +0800 Subject: [PATCH 09/30] =?UTF-8?q?=E4=BC=98=E5=8C=96MAC=E5=9C=B0=E5=9D=80?= =?UTF-8?q?=E6=AD=A3=E5=88=99=EF=BC=88issue#IB95X4@Gitee=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- CHANGELOG.md | 3 ++- .../main/java/cn/hutool/core/lang/RegexPool.java | 3 ++- .../cn/hutool/core/util/IssueIB95X4Test.java | 16 ++++++++++++++++ 3 files changed, 20 insertions(+), 2 deletions(-) create mode 100644 hutool-core/src/test/java/cn/hutool/core/util/IssueIB95X4Test.java diff --git a/CHANGELOG.md b/CHANGELOG.md index fe0f37050a..f9e98ddfdb 100755 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,11 +2,12 @@ # 🚀Changelog ------------------------------------------------------------------------------------------------------------- -# 5.8.35(2024-12-04) +# 5.8.35(2024-12-05) ### 🐣新特性 * 【poi 】 优化ExcelWriter中使用比较器writer的方法,只对第一条数据进行排序(pr#3807@Github) * 【extra 】 优化Ftp.download,返回false抛出异常(issue#3805@Github) +* 【core 】 优化MAC地址正则(issue#IB95X4@Gitee) ### 🐞Bug修复 * 【crypto 】 修复JWTSignerUtil.createSigner中algorithmId未转换问题(issue#3806@Github) diff --git a/hutool-core/src/main/java/cn/hutool/core/lang/RegexPool.java b/hutool-core/src/main/java/cn/hutool/core/lang/RegexPool.java index 96d5b44579..664be9a469 100755 --- a/hutool-core/src/main/java/cn/hutool/core/lang/RegexPool.java +++ b/hutool-core/src/main/java/cn/hutool/core/lang/RegexPool.java @@ -132,7 +132,8 @@ public interface RegexPool { /** * MAC地址正则 */ - String MAC_ADDRESS = "((?:[a-fA-F0-9]{1,2}[:-]){5}[a-fA-F0-9]{1,2})|0x(\\d{12}).+ETHER"; + //String MAC_ADDRESS = "((?:[a-fA-F0-9]{1,2}[:-]){5}[a-fA-F0-9]{1,2})|0x(\\d{12}).+ETHER"; + String MAC_ADDRESS = "((?:[a-fA-F0-9]{1,2}[:-]){5}[a-fA-F0-9]{1,2})|((?:[a-fA-F0-9]{1,4}[.]){2}[a-fA-F0-9]{1,4})|[a-fA-F0-9]{12}|0x(\\d{12}).+ETHER"; /** * 16进制字符串 */ diff --git a/hutool-core/src/test/java/cn/hutool/core/util/IssueIB95X4Test.java b/hutool-core/src/test/java/cn/hutool/core/util/IssueIB95X4Test.java new file mode 100644 index 0000000000..49b2812290 --- /dev/null +++ b/hutool-core/src/test/java/cn/hutool/core/util/IssueIB95X4Test.java @@ -0,0 +1,16 @@ +package cn.hutool.core.util; + +import cn.hutool.core.lang.PatternPool; +import org.junit.jupiter.api.Assertions; +import org.junit.jupiter.api.Test; + +public class IssueIB95X4Test { + + @Test + void isMacTest() { + Assertions.assertTrue(ReUtil.isMatch(PatternPool.MAC_ADDRESS, "ab1c.2d3e.f468")); + Assertions.assertTrue(ReUtil.isMatch(PatternPool.MAC_ADDRESS, "ab:1c:2d:3e:f4:68")); + Assertions.assertTrue(ReUtil.isMatch(PatternPool.MAC_ADDRESS, "ab-1c-2d-3e-f4-68")); + Assertions.assertTrue(ReUtil.isMatch(PatternPool.MAC_ADDRESS, "ab1c2d3ef468")); + } +} From 75d10d7b147ce06094ed115c65ccefdccc246d31 Mon Sep 17 00:00:00 2001 From: Looly Date: Thu, 5 Dec 2024 16:54:05 +0800 Subject: [PATCH 10/30] add test --- .../java/cn/hutool/core/util/Issue3809Test.java | 16 ++++++++++++++++ 1 file changed, 16 insertions(+) create mode 100644 hutool-core/src/test/java/cn/hutool/core/util/Issue3809Test.java diff --git a/hutool-core/src/test/java/cn/hutool/core/util/Issue3809Test.java b/hutool-core/src/test/java/cn/hutool/core/util/Issue3809Test.java new file mode 100644 index 0000000000..ac667387b7 --- /dev/null +++ b/hutool-core/src/test/java/cn/hutool/core/util/Issue3809Test.java @@ -0,0 +1,16 @@ +package cn.hutool.core.util; + +import org.junit.jupiter.api.Assertions; +import org.junit.jupiter.api.Test; + +public class Issue3809Test { + @Test + void roundStrTest() { + Assertions.assertEquals("9999999999999999.99", NumberUtil.roundStr("9999999999999999.99", 2)); //输出结果不符合方法声明返回值规则 + Assertions.assertEquals("11111111111111119.00", NumberUtil.roundStr("11111111111111119.00", 2)); + Assertions.assertEquals("7999999999999999.99", NumberUtil.roundStr("7999999999999999.99", 2)); //输出结果不符合方法声明返回值规则 + Assertions.assertEquals("699999999991999.92", NumberUtil.roundStr("699999999991999.92", 2)); //输出结果不符合方法声明返回值规则 + Assertions.assertEquals("10.92", NumberUtil.roundStr("10.92", 2)); + Assertions.assertEquals("10.99", NumberUtil.roundStr("10.99", 2)); + } +} From 5622f5e7a7a8905b514e335f6a56161a7bf17182 Mon Sep 17 00:00:00 2001 From: TomShiDi <1341109792@qq.com> Date: Sun, 8 Dec 2024 15:41:43 +0800 Subject: [PATCH 11/30] =?UTF-8?q?feature:=20json=E7=9A=84getByPath?= =?UTF-8?q?=E6=96=B9=E6=B3=95=E6=96=B0=E5=A2=9E=E6=9B=B4=E4=B8=BA=E9=80=9A?= =?UTF-8?q?=E7=94=A8=E7=9A=84=E6=8C=87=E5=AE=9A=E5=87=BA=E5=8F=82=E7=B1=BB?= =?UTF-8?q?=E5=9E=8B=E9=87=8D=E8=BD=BD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../src/main/java/cn/hutool/json/JSON.java | 26 +++++++++++++++++++ .../main/java/cn/hutool/json/JSONArray.java | 9 ++++++- .../main/java/cn/hutool/json/JSONObject.java | 13 +++++++--- .../java/cn/hutool/json/JSONPathTest.java | 23 ++++++++++++++++ 4 files changed, 67 insertions(+), 4 deletions(-) diff --git a/hutool-json/src/main/java/cn/hutool/json/JSON.java b/hutool-json/src/main/java/cn/hutool/json/JSON.java index 4932f1e8a4..9a5972cc99 100755 --- a/hutool-json/src/main/java/cn/hutool/json/JSON.java +++ b/hutool-json/src/main/java/cn/hutool/json/JSON.java @@ -97,6 +97,32 @@ public interface JSON extends Cloneable, Serializable, IJSONTypeConverter { */ T getByPath(String expression, Class resultType); + /** + * 通过表达式获取JSON中嵌套的对象
+ *
    + *
  1. .表达式,可以获取Bean对象中的属性(字段)值或者Map中key对应的值
  2. + *
  3. []表达式,可以获取集合等对象中对应index的值
  4. + *
+ *

+ * 表达式栗子: + * + *

+	 * persion
+	 * persion.name
+	 * persons[3]
+	 * person.friends[5].name
+	 * 
+ *

+ * 获取表达式对应值后转换为对应类型的值 + * + * @param expression 表达式 + * @param targetType 返回值类型 + * @return 对象 + * @see BeanPath#get(Object) + * @since 5.8.34 + */ + T getByPath(String expression, TypeReference targetType); + /** * 格式化打印JSON,缩进为4个空格 * diff --git a/hutool-json/src/main/java/cn/hutool/json/JSONArray.java b/hutool-json/src/main/java/cn/hutool/json/JSONArray.java index e7371f14fc..636da5da72 100755 --- a/hutool-json/src/main/java/cn/hutool/json/JSONArray.java +++ b/hutool-json/src/main/java/cn/hutool/json/JSONArray.java @@ -3,6 +3,7 @@ import cn.hutool.core.bean.BeanPath; import cn.hutool.core.collection.CollUtil; import cn.hutool.core.lang.Filter; +import cn.hutool.core.lang.TypeReference; import cn.hutool.core.lang.Validator; import cn.hutool.core.lang.mutable.Mutable; import cn.hutool.core.lang.mutable.MutableObj; @@ -13,6 +14,7 @@ import java.io.StringWriter; import java.io.Writer; +import java.lang.reflect.Type; import java.util.ArrayList; import java.util.Collection; import java.util.Iterator; @@ -195,7 +197,7 @@ public JSONArray setDateFormat(String format) { */ public String join(String separator) throws JSONException { return StrJoiner.of(separator) - .append(this, InternalJSONUtil::valueToString).toString(); + .append(this, InternalJSONUtil::valueToString).toString(); } @Override @@ -218,6 +220,11 @@ public T getByPath(String expression, Class resultType) { return JSONConverter.jsonConvert(resultType, getByPath(expression), getConfig()); } + @Override + public T getByPath(String expression, TypeReference targetType) { + return JSONConverter.jsonConvert(targetType, getByPath(expression), getConfig()); + } + @Override public void putByPath(String expression, Object value) { BeanPath.create(expression).set(this, value); diff --git a/hutool-json/src/main/java/cn/hutool/json/JSONObject.java b/hutool-json/src/main/java/cn/hutool/json/JSONObject.java index 327be1be06..d09a6b067d 100755 --- a/hutool-json/src/main/java/cn/hutool/json/JSONObject.java +++ b/hutool-json/src/main/java/cn/hutool/json/JSONObject.java @@ -3,6 +3,7 @@ import cn.hutool.core.bean.BeanPath; import cn.hutool.core.collection.CollectionUtil; import cn.hutool.core.lang.Filter; +import cn.hutool.core.lang.TypeReference; import cn.hutool.core.lang.mutable.MutablePair; import cn.hutool.core.map.CaseInsensitiveMap; import cn.hutool.core.map.MapUtil; @@ -14,6 +15,7 @@ import java.io.StringWriter; import java.io.Writer; +import java.lang.reflect.Type; import java.math.BigDecimal; import java.math.BigInteger; import java.util.Collection; @@ -161,8 +163,8 @@ public JSONObject(Object source, boolean ignoreNullValue) { @Deprecated public JSONObject(Object source, boolean ignoreNullValue, boolean isOrder) { this(source, JSONConfig.create()// - .setIgnoreCase((source instanceof CaseInsensitiveMap))// - .setIgnoreNullValue(ignoreNullValue) + .setIgnoreCase((source instanceof CaseInsensitiveMap))// + .setIgnoreNullValue(ignoreNullValue) ); } @@ -320,6 +322,11 @@ public T getByPath(String expression, Class resultType) { return JSONConverter.jsonConvert(resultType, getByPath(expression), getConfig()); } + @Override + public T getByPath(String expression, TypeReference targetType) { + return JSONConverter.jsonConvert(targetType, getByPath(expression), getConfig()); + } + @Override public void putByPath(String expression, Object value) { BeanPath.create(expression).set(this, value); @@ -561,7 +568,7 @@ public Writer write(Writer writer, int indentFactor, int indent) throws JSONExce */ public Writer write(Writer writer, int indentFactor, int indent, Filter> filter) throws JSONException { final JSONWriter jsonWriter = JSONWriter.of(writer, indentFactor, indent, config) - .beginObj(); + .beginObj(); this.forEach((key, value) -> jsonWriter.writeField(new MutablePair<>(key, value), filter)); jsonWriter.end(); // 此处不关闭Writer,考虑writer后续还需要填内容 diff --git a/hutool-json/src/test/java/cn/hutool/json/JSONPathTest.java b/hutool-json/src/test/java/cn/hutool/json/JSONPathTest.java index 472def8519..437f012cb5 100644 --- a/hutool-json/src/test/java/cn/hutool/json/JSONPathTest.java +++ b/hutool-json/src/test/java/cn/hutool/json/JSONPathTest.java @@ -1,8 +1,12 @@ package cn.hutool.json; import static org.junit.jupiter.api.Assertions.*; + +import cn.hutool.core.lang.TypeReference; import org.junit.jupiter.api.Test; +import java.util.List; + /** * JSON路径单元测试 * @@ -27,4 +31,23 @@ public void getByPathTest2(){ Long accountId = JSONUtil.getByPath(json, "$.accountId", 0L); assertEquals(111L, accountId.longValue()); } + + @Test + public void getByPathTest3(){ + String str = "[{'accountId':1},{'accountId':2},{'accountId':3}]"; + JSON json = JSONUtil.parse(str); + // 返回指定泛型的对象 List + List accountIds = json.getByPath("$.accountId", new TypeReference>() { + }); + assertNotNull(accountIds); + assertArrayEquals(new Long[]{1L, 2L, 3L}, accountIds.toArray()); + + str = "{\"accountInfos\": [{\"accountId\":1},{\"accountId\":2},{\"accountId\":3}]}"; + json = JSONUtil.parse(str); + // 返回指定泛型的对象 List + accountIds = json.getByPath("$.accountInfos.accountId", new TypeReference>() { + }); + assertNotNull(accountIds); + assertArrayEquals(new Long[]{1L, 2L, 3L}, accountIds.toArray()); + } } From 8fd770fe4d5c29f80a09a8e04b4487056c677f7e Mon Sep 17 00:00:00 2001 From: Looly Date: Sun, 8 Dec 2024 16:12:34 +0800 Subject: [PATCH 12/30] =?UTF-8?q?JSON=E7=9A=84getByPath=E6=96=B9=E6=B3=95?= =?UTF-8?q?=E6=96=B0=E5=A2=9E=E6=9B=B4=E4=B8=BA=E9=80=9A=E7=94=A8=E7=9A=84?= =?UTF-8?q?=E6=8C=87=E5=AE=9A=E5=87=BA=E5=8F=82=E7=B1=BB=E5=9E=8B=E9=87=8D?= =?UTF-8?q?=E8=BD=BD=EF=BC=88pr#3814@Github=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- CHANGELOG.md | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index f9e98ddfdb..056710fe38 100755 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,16 +2,17 @@ # 🚀Changelog ------------------------------------------------------------------------------------------------------------- -# 5.8.35(2024-12-05) +# 5.8.35(2024-12-08) ### 🐣新特性 * 【poi 】 优化ExcelWriter中使用比较器writer的方法,只对第一条数据进行排序(pr#3807@Github) * 【extra 】 优化Ftp.download,返回false抛出异常(issue#3805@Github) * 【core 】 优化MAC地址正则(issue#IB95X4@Gitee) +* 【json 】 JSON的getByPath方法新增更为通用的指定出参类型重载(pr#3814@Github) ### 🐞Bug修复 * 【crypto 】 修复JWTSignerUtil.createSigner中algorithmId未转换问题(issue#3806@Github) -* 【core 】 修复DateUtil.rangeContains未重置问题(issue#IB8OFS@gitee) +* 【core 】 修复DateUtil.rangeContains未重置问题(issue#IB8OFS@Gitee) ------------------------------------------------------------------------------------------------------------- # 5.8.34(2024-11-25) From b6b8c28db8272ed31951e27a9e083240cf3a3fa6 Mon Sep 17 00:00:00 2001 From: Looly Date: Mon, 9 Dec 2024 20:47:12 +0800 Subject: [PATCH 13/30] add test --- .../java/cn/hutool/json/IssueIB9MH0Test.java | 38 +++++++++++++++++++ 1 file changed, 38 insertions(+) create mode 100644 hutool-json/src/test/java/cn/hutool/json/IssueIB9MH0Test.java diff --git a/hutool-json/src/test/java/cn/hutool/json/IssueIB9MH0Test.java b/hutool-json/src/test/java/cn/hutool/json/IssueIB9MH0Test.java new file mode 100644 index 0000000000..cfc431da71 --- /dev/null +++ b/hutool-json/src/test/java/cn/hutool/json/IssueIB9MH0Test.java @@ -0,0 +1,38 @@ +package cn.hutool.json; + +import cn.hutool.json.serialize.GlobalSerializeMapping; +import cn.hutool.json.serialize.JSONObjectSerializer; +import org.junit.jupiter.api.Assertions; +import org.junit.jupiter.api.Test; + +public class IssueIB9MH0Test { + + @Test + void parseTest() { + GlobalSerializeMapping.put(TabTypeEnum.class, (JSONObjectSerializer) (json, bean) -> json.set("code", bean.getCode()) + .set("title", bean.getTitle())); + final JSON parse = JSONUtil.parse(TabTypeEnum._01); + Assertions.assertEquals("{\"code\":\"tab_people_home\",\"title\":\"首页\"}", parse.toString()); + } + + public enum TabTypeEnum { + _01("tab_people_home","首页"), + _02("tab_people_hospital","医院"); + + private String code; + private String title; + + TabTypeEnum(String code, String title) { + this.code = code; + this.title = title; + } + + public String getCode() { + return code; + } + + public String getTitle() { + return title; + } + } +} From 7d7d4406fc5174db34b184e87133545ee00c344f Mon Sep 17 00:00:00 2001 From: Looly Date: Mon, 9 Dec 2024 20:54:21 +0800 Subject: [PATCH 14/30] fix bug --- hutool-extra/src/main/java/cn/hutool/extra/ssh/Sftp.java | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/hutool-extra/src/main/java/cn/hutool/extra/ssh/Sftp.java b/hutool-extra/src/main/java/cn/hutool/extra/ssh/Sftp.java index 865f216d44..4125090982 100755 --- a/hutool-extra/src/main/java/cn/hutool/extra/ssh/Sftp.java +++ b/hutool-extra/src/main/java/cn/hutool/extra/ssh/Sftp.java @@ -169,7 +169,7 @@ public void init(String sshHost, int sshPort, String sshUser, String sshPass, Ch */ public void init() { // issue#IB69U8 如果用户传入Session对象,则不能使用配置初始化,而是尝试重新连接 - if(StrUtil.isEmpty(this.ftpConfig.getHost()) && null != this.session){ + if(null != this.session){ try { this.session.connect((int) this.ftpConfig.getConnectionTimeout()); } catch (JSchException e) { From 51bc90bd0debda20011fb2e5c6f64db5b1703644 Mon Sep 17 00:00:00 2001 From: Looly Date: Thu, 12 Dec 2024 16:08:43 +0800 Subject: [PATCH 15/30] update api --- README-EN.md | 2 +- README.md | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/README-EN.md b/README-EN.md index d2404c4d95..1b8914dd3a 100755 --- a/README-EN.md +++ b/README-EN.md @@ -119,7 +119,7 @@ Each module can be introduced individually, or all modules can be introduced by [📘Chinese back-up documentation](https://plus.hutool.cn/) -[📙API](https://apidoc.gitee.com/dromara/hutool/) +[📙API](https://plus.hutool.cn/apidocs/) [🎬Video](https://www.bilibili.com/video/BV1bQ4y1M7d9?p=2) diff --git a/README.md b/README.md index 6190fc529a..713155f023 100755 --- a/README.md +++ b/README.md @@ -110,7 +110,7 @@ Hutool = Hu + tool,是原公司项目底层代码剥离后的开源库,“Hu [📘中文备用文档](https://plus.hutool.cn/) -[📙参考API](https://apidoc.gitee.com/dromara/hutool/) +[📙参考API](https://plus.hutool.cn/apidocs/) [🎬视频介绍](https://www.bilibili.com/video/BV1bQ4y1M7d9?p=2) From a62f7f3765996d020bc4d633c3889dbfc0354d13 Mon Sep 17 00:00:00 2001 From: LuoJing <1126184155@qq.com> Date: Sat, 14 Dec 2024 22:25:35 +0800 Subject: [PATCH 16/30] =?UTF-8?q?add=20=E6=B7=BB=E5=8A=A0=20EnumUtil#getBy?= =?UTF-8?q?(Class,=20Func1,=20Object)=E6=96=B9=E6=B3=95=EF=BC=8C=E6=9C=80?= =?UTF-8?q?=E7=BB=88=E7=9A=84=E6=9D=A1=E4=BB=B6=E8=BF=87=E6=BB=A4=E7=BB=9F?= =?UTF-8?q?=E4=B8=80=E4=BD=BF=E7=94=A8=20EnumUtil#getBy(Class,=20Predicate?= =?UTF-8?q?,=20Enum)=20=E6=96=B9=E6=B3=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../java/cn/hutool/core/util/EnumUtil.java | 80 +++++++++++++++---- 1 file changed, 64 insertions(+), 16 deletions(-) diff --git a/hutool-core/src/main/java/cn/hutool/core/util/EnumUtil.java b/hutool-core/src/main/java/cn/hutool/core/util/EnumUtil.java index 3036cd762c..23b5386892 100644 --- a/hutool-core/src/main/java/cn/hutool/core/util/EnumUtil.java +++ b/hutool-core/src/main/java/cn/hutool/core/util/EnumUtil.java @@ -60,11 +60,11 @@ public static String toString(Enum e) { * @since 5.1.6 */ public static > E getEnumAt(Class enumClass, int index) { - if(null == enumClass){ + if (null == enumClass) { return null; } final E[] enumConstants = enumClass.getEnumConstants(); - if(index < 0){ + if (index < 0) { index = enumConstants.length + index; } @@ -129,7 +129,7 @@ public static > E fromStringQuietly(Class enumClass, String */ @SuppressWarnings("unchecked") public static > E likeValueOf(Class enumClass, Object value) { - if(null == enumClass || null == value){ + if (null == enumClass || null == value) { return null; } if (value instanceof CharSequence) { @@ -161,7 +161,7 @@ public static > E likeValueOf(Class enumClass, Object value * @return name列表 */ public static List getNames(Class> clazz) { - if(null == clazz){ + if (null == clazz) { return null; } final Enum[] enums = clazz.getEnumConstants(); @@ -183,7 +183,7 @@ public static List getNames(Class> clazz) { * @return 字段值列表 */ public static List getFieldValues(Class> clazz, String fieldName) { - if(null == clazz || StrUtil.isBlank(fieldName)){ + if (null == clazz || StrUtil.isBlank(fieldName)) { return null; } final Enum[] enums = clazz.getEnumConstants(); @@ -210,7 +210,7 @@ public static List getFieldValues(Class> clazz, String * @since 4.1.20 */ public static List getFieldNames(Class> clazz) { - if(null == clazz){ + if (null == clazz) { return null; } final List names = new ArrayList<>(); @@ -238,11 +238,62 @@ public static List getFieldNames(Class> clazz) { * @since 5.8.0 */ public static > E getBy(Class enumClass, Predicate predicate) { - if(null == enumClass || null == predicate){ + return getBy(enumClass, predicate, null); + } + + /** + * 通过 某字段对应值 获取 枚举,获取不到时为 {@code defaultEnum} + * + * @param enumClass 枚举类 + * @param predicate 条件 + * @param defaultEnum 获取不到时的默认枚举值 + * @param 枚举类型 + * @return 对应枚举 ,获取不到时为 {@code defaultEnum} + */ + public static > E getBy(Class enumClass, Predicate predicate, E defaultEnum) { + if (null == enumClass || null == predicate) { return null; } return Arrays.stream(enumClass.getEnumConstants()) - .filter(predicate).findFirst().orElse(null); + .filter(predicate).findFirst().orElse(defaultEnum); + } + + /** + * 通过 某字段对应值 获取 枚举,获取不到时为 {@code null} + *

+ * {@link LambdaUtil#getRealClass(Func1)}} 是相对耗时的 + * 如果枚举值比较多,那么{@link EnumUtil#getBy(Func1, Object)} 方法 + * 大部分时间都是被{@link LambdaUtil#getRealClass(Func1)}}所消耗的 + *
+ * 如果可以在编码过程中可以提供对应的枚举类 该方法与枚举的{@code Enum.values()}方法是差不多的。 + * + * @param enumClass 枚举类, 为{@code null}返回{@code null} + * @param condition 条件字段,为{@code null}返回{@code null} + * @param value 条件字段值 + * @param 枚举类型 + * @param 字段类型 + * @return 对应枚举 ,获取不到时为 {@code null} + */ + public static , C> E getBy(Class enumClass, Func1 condition, C value) { + if (null == condition) { + return null; + } + return getBy(enumClass, constant -> ObjUtil.equals(condition.callWithRuntimeException(constant), value)); + } + + /** + * 通过 某字段对应值 获取 枚举,获取不到时为 {@code defaultEnum} + * + * @param enumClass 枚举类, 为{@code null}返回{@code null} + * @param condition 条件字段,为{@code null}返回{@code null} + * @param value 条件字段值 + * @param defaultEnum 获取不到时的默认枚举值 + * @param 枚举类型 + * @param 字段类型 + * @return 对应枚举 ,获取不到时为 {@code defaultEnum} + */ + public static , C> E getBy(Class enumClass, Func1 condition, C value, E defaultEnum) { + return ObjectUtil.defaultIfNull(getBy(enumClass, condition, value), defaultEnum); } /** @@ -259,10 +310,7 @@ public static , C> E getBy(Func1 condition, C value) { return null; } final Class implClass = LambdaUtil.getRealClass(condition); - return Arrays.stream(implClass.getEnumConstants()) - .filter(constant -> ObjUtil.equals(condition.callWithRuntimeException(constant), value)) - .findAny() - .orElse(null); + return getBy(implClass, condition, value); } /** @@ -293,7 +341,7 @@ public static , C> E getBy(Func1 condition, C value, E d * @since 5.8.0 */ public static , F, C> F getFieldBy(Func1 field, Function condition, C value) { - if(null == field || null == condition){ + if (null == field || null == condition) { return null; } final Class implClass = LambdaUtil.getRealClass(field); @@ -316,7 +364,7 @@ public static , F, C> F getFieldBy(Func1 field, Function * @since 4.0.2 */ public static > LinkedHashMap getEnumMap(final Class enumClass) { - if(null == enumClass){ + if (null == enumClass) { return null; } final LinkedHashMap map = new LinkedHashMap<>(); @@ -335,7 +383,7 @@ public static > LinkedHashMap getEnumMap(final Clas * @return 枚举名对应指定字段值的Map */ public static Map getNameFieldMap(Class> clazz, String fieldName) { - if(null == clazz || StrUtil.isBlank(fieldName)){ + if (null == clazz || StrUtil.isBlank(fieldName)) { return null; } final Enum[] enums = clazz.getEnumConstants(); @@ -359,7 +407,7 @@ public static Map getNameFieldMap(Class> clazz */ public static > boolean contains(final Class enumClass, String val) { final LinkedHashMap enumMap = getEnumMap(enumClass); - if(CollUtil.isEmpty(enumMap)){ + if (CollUtil.isEmpty(enumMap)) { return false; } return enumMap.containsKey(val); From 8a8a5f716147acdb8965a2fa51acabfdb8c76a5a Mon Sep 17 00:00:00 2001 From: Looly Date: Sun, 15 Dec 2024 22:23:41 +0800 Subject: [PATCH 17/30] =?UTF-8?q?DateUtil.parseUTC=E6=96=B9=E6=B3=95?= =?UTF-8?q?=E6=A0=87=E8=AE=B0=E5=BA=9F=E5=BC=83=EF=BC=8C=E6=94=B9=E5=90=8D?= =?UTF-8?q?=E4=B8=BAparseISO8601=EF=BC=88issue#IBB6I5@Gitee=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- CHANGELOG.md | 3 +- .../java/cn/hutool/core/date/DateUtil.java | 83 ++++++++++++------- .../cn/hutool/core/date/DateUtilTest.java | 22 ++--- .../cn/hutool/core/date/IssueIB9NPUTest.java | 12 +++ .../cn/hutool/core/date/IssueIBB6I5Test.java | 25 ++++++ 5 files changed, 102 insertions(+), 43 deletions(-) create mode 100644 hutool-core/src/test/java/cn/hutool/core/date/IssueIB9NPUTest.java create mode 100644 hutool-core/src/test/java/cn/hutool/core/date/IssueIBB6I5Test.java diff --git a/CHANGELOG.md b/CHANGELOG.md index 056710fe38..dd28968950 100755 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,13 +2,14 @@ # 🚀Changelog ------------------------------------------------------------------------------------------------------------- -# 5.8.35(2024-12-08) +# 5.8.35(2024-12-15) ### 🐣新特性 * 【poi 】 优化ExcelWriter中使用比较器writer的方法,只对第一条数据进行排序(pr#3807@Github) * 【extra 】 优化Ftp.download,返回false抛出异常(issue#3805@Github) * 【core 】 优化MAC地址正则(issue#IB95X4@Gitee) * 【json 】 JSON的getByPath方法新增更为通用的指定出参类型重载(pr#3814@Github) +* 【core 】 DateUtil.parseUTC方法标记废弃,改名为parseISO8601(issue#IBB6I5@Gitee) ### 🐞Bug修复 * 【crypto 】 修复JWTSignerUtil.createSigner中algorithmId未转换问题(issue#3806@Github) diff --git a/hutool-core/src/main/java/cn/hutool/core/date/DateUtil.java b/hutool-core/src/main/java/cn/hutool/core/date/DateUtil.java index ab92c85190..1dee902f28 100755 --- a/hutool-core/src/main/java/cn/hutool/core/date/DateUtil.java +++ b/hutool-core/src/main/java/cn/hutool/core/date/DateUtil.java @@ -844,16 +844,37 @@ public static DateTime parseTimeToday(CharSequence timeString) { * @param utcString UTC时间 * @return 日期对象 * @since 4.1.14 + * @deprecated 方法歧义,带T的日期并不一定是UTC时间,请使用 {@link #parseISO8601(String)} */ + @Deprecated public static DateTime parseUTC(String utcString) { - if (utcString == null) { + return parseISO8601(utcString); + } + + /** + * 解析ISO8601时间,格式:
+ *

    + *
  1. yyyy-MM-dd'T'HH:mm:ss'Z'
  2. + *
  3. yyyy-MM-dd'T'HH:mm:ss.SSS'Z'
  4. + *
  5. yyyy-MM-dd'T'HH:mm:ssZ
  6. + *
  7. yyyy-MM-dd'T'HH:mm:ss.SSSZ
  8. + *
  9. yyyy-MM-dd'T'HH:mm:ss+0800
  10. + *
  11. yyyy-MM-dd'T'HH:mm:ss+08:00
  12. + *
+ * + * @param iso8601String ISO8601时间 + * @return 日期对象 + * @since 5.8.34 + */ + public static DateTime parseISO8601(String iso8601String) { + if (iso8601String == null) { return null; } - final int length = utcString.length(); - if (StrUtil.contains(utcString, 'Z')) { + final int length = iso8601String.length(); + if (StrUtil.contains(iso8601String, 'Z')) { if (length == DatePattern.UTC_PATTERN.length() - 4) { // 格式类似:2018-09-13T05:34:31Z,-4表示减去4个单引号的长度 - return parse(utcString, DatePattern.UTC_FORMAT); + return parse(iso8601String, DatePattern.UTC_FORMAT); } final int patternLength = DatePattern.UTC_MS_PATTERN.length(); @@ -861,61 +882,61 @@ public static DateTime parseUTC(String utcString) { // -4 ~ -6范围表示匹配毫秒1~3位的情况 if (length <= patternLength && length >= patternLength - 6) { // issue#I7H34N,支持最多6位毫秒 - return parse(utcString, DatePattern.UTC_MS_FORMAT); + return parse(iso8601String, DatePattern.UTC_MS_FORMAT); } - } else if (StrUtil.contains(utcString, '+')) { + } else if (StrUtil.contains(iso8601String, '+')) { // 去除类似2019-06-01T19:45:43 +08:00加号前的空格 - utcString = utcString.replace(" +", "+"); - final String zoneOffset = StrUtil.subAfter(utcString, '+', true); + iso8601String = iso8601String.replace(" +", "+"); + final String zoneOffset = StrUtil.subAfter(iso8601String, '+', true); if (StrUtil.isBlank(zoneOffset)) { - throw new DateException("Invalid format: [{}]", utcString); + throw new DateException("Invalid format: [{}]", iso8601String); } if (false == StrUtil.contains(zoneOffset, ':')) { // +0800转换为+08:00 - final String pre = StrUtil.subBefore(utcString, '+', true); - utcString = pre + "+" + zoneOffset.substring(0, 2) + ":" + "00"; + final String pre = StrUtil.subBefore(iso8601String, '+', true); + iso8601String = pre + "+" + zoneOffset.substring(0, 2) + ":" + "00"; } - if (StrUtil.contains(utcString, CharUtil.DOT)) { + if (StrUtil.contains(iso8601String, CharUtil.DOT)) { // 带毫秒,格式类似:2018-09-13T05:34:31.999+08:00 - utcString = normalizeMillSeconds(utcString, ".", "+"); - return parse(utcString, DatePattern.UTC_MS_WITH_XXX_OFFSET_FORMAT); + iso8601String = normalizeMillSeconds(iso8601String, ".", "+"); + return parse(iso8601String, DatePattern.UTC_MS_WITH_XXX_OFFSET_FORMAT); } else { // 格式类似:2018-09-13T05:34:31+08:00 - return parse(utcString, DatePattern.UTC_WITH_XXX_OFFSET_FORMAT); + return parse(iso8601String, DatePattern.UTC_WITH_XXX_OFFSET_FORMAT); } - } else if(ReUtil.contains("-\\d{2}:?00", utcString)){ + } else if(ReUtil.contains("-\\d{2}:?00", iso8601String)){ // Issue#2612,类似 2022-09-14T23:59:00-08:00 或者 2022-09-14T23:59:00-0800 // 去除类似2019-06-01T19:45:43 -08:00加号前的空格 - utcString = utcString.replace(" -", "-"); - if(':' != utcString.charAt(utcString.length() - 3)){ - utcString = utcString.substring(0, utcString.length() - 2) + ":00"; + iso8601String = iso8601String.replace(" -", "-"); + if(':' != iso8601String.charAt(iso8601String.length() - 3)){ + iso8601String = iso8601String.substring(0, iso8601String.length() - 2) + ":00"; } - if (StrUtil.contains(utcString, CharUtil.DOT)) { + if (StrUtil.contains(iso8601String, CharUtil.DOT)) { // 带毫秒,格式类似:2018-09-13T05:34:31.999-08:00 - utcString = normalizeMillSeconds(utcString, ".", "-"); - return new DateTime(utcString, DatePattern.UTC_MS_WITH_XXX_OFFSET_FORMAT); + iso8601String = normalizeMillSeconds(iso8601String, ".", "-"); + return new DateTime(iso8601String, DatePattern.UTC_MS_WITH_XXX_OFFSET_FORMAT); } else { // 格式类似:2018-09-13T05:34:31-08:00 - return new DateTime(utcString, DatePattern.UTC_WITH_XXX_OFFSET_FORMAT); + return new DateTime(iso8601String, DatePattern.UTC_WITH_XXX_OFFSET_FORMAT); } } else { if (length == DatePattern.UTC_SIMPLE_PATTERN.length() - 2) { // 格式类似:2018-09-13T05:34:31 - return parse(utcString, DatePattern.UTC_SIMPLE_FORMAT); + return parse(iso8601String, DatePattern.UTC_SIMPLE_FORMAT); } else if (length == DatePattern.UTC_SIMPLE_PATTERN.length() - 5) { // 格式类似:2018-09-13T05:34 - return parse(utcString + ":00", DatePattern.UTC_SIMPLE_FORMAT); - } else if (StrUtil.contains(utcString, CharUtil.DOT)) { + return parse(iso8601String + ":00", DatePattern.UTC_SIMPLE_FORMAT); + } else if (StrUtil.contains(iso8601String, CharUtil.DOT)) { // 可能为: 2021-03-17T06:31:33.99 - utcString = normalizeMillSeconds(utcString, ".", null); - return parse(utcString, DatePattern.UTC_SIMPLE_MS_FORMAT); + iso8601String = normalizeMillSeconds(iso8601String, ".", null); + return parse(iso8601String, DatePattern.UTC_SIMPLE_MS_FORMAT); } } // 没有更多匹配的时间格式 - throw new DateException("No format fit for date String [{}] !", utcString); + throw new DateException("No format fit for date String [{}] !", iso8601String); } /** @@ -1025,8 +1046,8 @@ public static DateTime parse(CharSequence dateCharSequence) { // Wed Aug 01 00:00:00 CST 2012 return parseRFC2822(dateStr); } else if (StrUtil.contains(dateStr, 'T')) { - // UTC时间 - return parseUTC(dateStr); + // ISO8601时间 + return parseISO8601(dateStr); } //标准日期格式(包括单个数字的日期时间) diff --git a/hutool-core/src/test/java/cn/hutool/core/date/DateUtilTest.java b/hutool-core/src/test/java/cn/hutool/core/date/DateUtilTest.java index 3a535a7c9e..d8cd911989 100755 --- a/hutool-core/src/test/java/cn/hutool/core/date/DateUtilTest.java +++ b/hutool-core/src/test/java/cn/hutool/core/date/DateUtilTest.java @@ -605,9 +605,9 @@ public void parseToDateTimeTest5() { } @Test - public void parseUTCTest() { + public void parseISO8601Test() { String dateStr1 = "2018-09-13T05:34:31Z"; - DateTime dt = DateUtil.parseUTC(dateStr1); + DateTime dt = DateUtil.parseISO8601(dateStr1); // parse方法支持UTC格式测试 final DateTime dt2 = DateUtil.parse(dateStr1); @@ -622,12 +622,12 @@ public void parseUTCTest() { assertEquals("2018-09-13 13:34:31", dateStr); dateStr1 = "2018-09-13T13:34:32+0800"; - dt = DateUtil.parseUTC(dateStr1); + dt = DateUtil.parseISO8601(dateStr1); dateStr = dt.toString(TimeZone.getTimeZone("GMT+8:00")); assertEquals("2018-09-13 13:34:32", dateStr); dateStr1 = "2018-09-13T13:34:33+08:00"; - dt = DateUtil.parseUTC(dateStr1); + dt = DateUtil.parseISO8601(dateStr1); dateStr = dt.toString(TimeZone.getTimeZone("GMT+8:00")); assertEquals("2018-09-13 13:34:33", dateStr); @@ -644,14 +644,14 @@ public void parseUTCTest() { assertEquals("2018-09-13 13:34:35", dateStr); dateStr1 = "2018-09-13T13:34:36.999+0800"; - dt = DateUtil.parseUTC(dateStr1); + dt = DateUtil.parseISO8601(dateStr1); final SimpleDateFormat simpleDateFormat = new SimpleDateFormat(DatePattern.NORM_DATETIME_MS_PATTERN); simpleDateFormat.setTimeZone(TimeZone.getTimeZone("GMT+8:00")); dateStr = dt.toString(simpleDateFormat); assertEquals("2018-09-13 13:34:36.999", dateStr); dateStr1 = "2018-09-13T13:34:37.999+08:00"; - dt = DateUtil.parseUTC(dateStr1); + dt = DateUtil.parseISO8601(dateStr1); dateStr = dt.toString(simpleDateFormat); assertEquals("2018-09-13 13:34:37.999", dateStr); @@ -676,19 +676,19 @@ public void parseUTCTest() { } @Test - public void parseUTCTest2() { + public void parseUTCTest() { // issue1503@Github // 检查不同毫秒长度都可以正常匹配 String utcTime = "2021-03-30T12:56:51.3Z"; - DateTime parse = DateUtil.parseUTC(utcTime); + DateTime parse = DateUtil.parseISO8601(utcTime); assertEquals("2021-03-30 12:56:51", parse.toString()); utcTime = "2021-03-30T12:56:51.34Z"; - parse = DateUtil.parseUTC(utcTime); + parse = DateUtil.parseISO8601(utcTime); assertEquals("2021-03-30 12:56:51", parse.toString()); utcTime = "2021-03-30T12:56:51.345Z"; - parse = DateUtil.parseUTC(utcTime); + parse = DateUtil.parseISO8601(utcTime); assertEquals("2021-03-30 12:56:51", parse.toString()); } @@ -994,7 +994,7 @@ public void parseSingleNumberTest() { @SuppressWarnings("ConstantConditions") @Test - public void parseISO8601Test() { + public void parseWithMilsTest() { final String dt = "2020-06-03 12:32:12,333"; final DateTime parse = DateUtil.parse(dt); assertEquals("2020-06-03 12:32:12", parse.toString()); diff --git a/hutool-core/src/test/java/cn/hutool/core/date/IssueIB9NPUTest.java b/hutool-core/src/test/java/cn/hutool/core/date/IssueIB9NPUTest.java new file mode 100644 index 0000000000..447f5b1aab --- /dev/null +++ b/hutool-core/src/test/java/cn/hutool/core/date/IssueIB9NPUTest.java @@ -0,0 +1,12 @@ +package cn.hutool.core.date; + +import org.junit.jupiter.api.Test; + +import java.text.SimpleDateFormat; + +public class IssueIB9NPUTest { + @Test + void parseTest() { + DateUtil.parse("202409032400", new SimpleDateFormat("yyyyMMddHHmm")); + } +} diff --git a/hutool-core/src/test/java/cn/hutool/core/date/IssueIBB6I5Test.java b/hutool-core/src/test/java/cn/hutool/core/date/IssueIBB6I5Test.java new file mode 100644 index 0000000000..718f37a9fb --- /dev/null +++ b/hutool-core/src/test/java/cn/hutool/core/date/IssueIBB6I5Test.java @@ -0,0 +1,25 @@ +package cn.hutool.core.date; + +import org.junit.jupiter.api.Assertions; +import org.junit.jupiter.api.Test; + +import java.time.ZoneId; +import java.util.TimeZone; + +public class IssueIBB6I5Test { + @Test + void parseISO8601Test() { + DateTime date = DateUtil.parseISO8601("2024-12-13T08:02:27Z"); + TimeZone timeZone = TimeZone.getTimeZone(ZoneId.of("Asia/Shanghai")); + date.setTimeZone(timeZone); + Assertions.assertEquals("2024-12-13 16:02:27", date.toString()); + } + + @Test + void parseISO8601Test2() { + DateTime date = DateUtil.parseISO8601("2024-12-13T08:02:27"); + TimeZone timeZone = TimeZone.getTimeZone(ZoneId.of("Asia/Shanghai")); + date.setTimeZone(timeZone); + Assertions.assertEquals("2024-12-13 08:02:27", date.toString()); + } +} From 4e2c460ab601e42087b457ce07958e4d6252418c Mon Sep 17 00:00:00 2001 From: Looly Date: Sun, 15 Dec 2024 22:51:28 +0800 Subject: [PATCH 18/30] =?UTF-8?q?=E6=B7=BB=E5=8A=A0EnumUtil#getBy(Class,?= =?UTF-8?q?=20Func1,=20Object)=E6=96=B9=E6=B3=95?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- CHANGELOG.md | 1 + hutool-core/src/main/java/cn/hutool/core/util/EnumUtil.java | 4 ++-- 2 files changed, 3 insertions(+), 2 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index dd28968950..e7d4efc7a4 100755 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -10,6 +10,7 @@ * 【core 】 优化MAC地址正则(issue#IB95X4@Gitee) * 【json 】 JSON的getByPath方法新增更为通用的指定出参类型重载(pr#3814@Github) * 【core 】 DateUtil.parseUTC方法标记废弃,改名为parseISO8601(issue#IBB6I5@Gitee) +* 【core 】 添加EnumUtil#getBy(Class, Func1, Object)方法(pr#1283@Gitee) ### 🐞Bug修复 * 【crypto 】 修复JWTSignerUtil.createSigner中algorithmId未转换问题(issue#3806@Github) diff --git a/hutool-core/src/main/java/cn/hutool/core/util/EnumUtil.java b/hutool-core/src/main/java/cn/hutool/core/util/EnumUtil.java index 23b5386892..2ab529a268 100644 --- a/hutool-core/src/main/java/cn/hutool/core/util/EnumUtil.java +++ b/hutool-core/src/main/java/cn/hutool/core/util/EnumUtil.java @@ -260,11 +260,11 @@ public static > E getBy(Class enumClass, Predicate + *

* {@link LambdaUtil#getRealClass(Func1)}} 是相对耗时的 * 如果枚举值比较多,那么{@link EnumUtil#getBy(Func1, Object)} 方法 * 大部分时间都是被{@link LambdaUtil#getRealClass(Func1)}}所消耗的 - *
+ *
* 如果可以在编码过程中可以提供对应的枚举类 该方法与枚举的{@code Enum.values()}方法是差不多的。 * * @param enumClass 枚举类, 为{@code null}返回{@code null} From 9c8dadf600928d2ea23908b33a854215bdb519b3 Mon Sep 17 00:00:00 2001 From: Looly Date: Thu, 19 Dec 2024 21:29:34 +0800 Subject: [PATCH 19/30] add gitcode --- CHANGELOG.md | 3 ++- bin/push_dev.sh | 8 ++++++-- bin/push_master.sh | 8 ++++++-- bin/sync.sh | 1 + hutool-db/src/main/java/cn/hutool/db/Entity.java | 12 ++++++++++++ 5 files changed, 27 insertions(+), 5 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index e7d4efc7a4..f86eb77fab 100755 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,7 +2,7 @@ # 🚀Changelog ------------------------------------------------------------------------------------------------------------- -# 5.8.35(2024-12-15) +# 5.8.35(2024-12-19) ### 🐣新特性 * 【poi 】 优化ExcelWriter中使用比较器writer的方法,只对第一条数据进行排序(pr#3807@Github) @@ -11,6 +11,7 @@ * 【json 】 JSON的getByPath方法新增更为通用的指定出参类型重载(pr#3814@Github) * 【core 】 DateUtil.parseUTC方法标记废弃,改名为parseISO8601(issue#IBB6I5@Gitee) * 【core 】 添加EnumUtil#getBy(Class, Func1, Object)方法(pr#1283@Gitee) +* 【db 】 添加Entity.addCondition方法(issue#IBCDL2@Gitee) ### 🐞Bug修复 * 【crypto 】 修复JWTSignerUtil.createSigner中algorithmId未转换问题(issue#3806@Github) diff --git a/bin/push_dev.sh b/bin/push_dev.sh index 2e7f969360..5bca1c384c 100755 --- a/bin/push_dev.sh +++ b/bin/push_dev.sh @@ -3,7 +3,11 @@ echo -e "\033[32mCheckout to v5-dev\033[0m" git checkout v5-dev -echo -e "\033[32mPush to origin v5-dev\033[0m" +echo -e "\033[32mPush to Github(origin) v5-dev\033[0m" git push origin v5-dev -echo -e "\033[32mPush to osc v5-dev\033[0m" + +echo -e "\033[32mPush to Gitee v5-dev\033[0m" git push osc v5-dev + +echo -e "\033[32mPush to Gitcode v5-dev\033[0m" +git push gitcode v5-dev diff --git a/bin/push_master.sh b/bin/push_master.sh index 729541c981..683910d49b 100755 --- a/bin/push_master.sh +++ b/bin/push_master.sh @@ -6,7 +6,11 @@ git checkout v5-master echo -e "\033[32mMerge v5-dev branch\033[0m" git merge v5-dev -m 'Prepare release' -echo -e "\033[32mPush to origin v5-master\033[0m" +echo -e "\033[32mPush to Github(origin) v5-master\033[0m" git push origin v5-master -echo -e "\033[32mPush to osc v5-master\033[0m" + +echo -e "\033[32mPush to Gitee v5-master\033[0m" git push osc v5-master + +echo -e "\033[32mPush to Gitcode v5-master\033[0m" +git push gitcode v5-master diff --git a/bin/sync.sh b/bin/sync.sh index 804660f3b8..393c032470 100644 --- a/bin/sync.sh +++ b/bin/sync.sh @@ -3,3 +3,4 @@ git checkout v5-dev git pull osc v5-dev git pull origin v5-dev +git pull gitcode v5-dev diff --git a/hutool-db/src/main/java/cn/hutool/db/Entity.java b/hutool-db/src/main/java/cn/hutool/db/Entity.java index cd807c3599..a66ad8060d 100755 --- a/hutool-db/src/main/java/cn/hutool/db/Entity.java +++ b/hutool-db/src/main/java/cn/hutool/db/Entity.java @@ -8,6 +8,7 @@ import cn.hutool.core.util.CharsetUtil; import cn.hutool.core.util.ReflectUtil; import cn.hutool.core.util.StrUtil; +import cn.hutool.db.sql.Condition; import cn.hutool.db.sql.SqlUtil; import java.nio.charset.Charset; @@ -266,6 +267,17 @@ public Entity removeNew(final String... keys) { } // -------------------------------------------------------------------- Put and Set start + /** + * 添加条件 + * + * @param condition 条件 + * @return this + * @since 5.8.34 + */ + public Entity addCondition(final Condition condition) { + return set(condition.getField(), condition); + } + @Override public Entity set(String field, Object value) { return (Entity) super.set(field, value); From 7467d03fe27fc67f4e1ddd4ac7b1f285f7a8f069 Mon Sep 17 00:00:00 2001 From: Looly Date: Sat, 21 Dec 2024 00:46:42 +0800 Subject: [PATCH 20/30] =?UTF-8?q?=E4=BF=AE=E5=A4=8DStampedCache=E7=B1=BBge?= =?UTF-8?q?t=E6=96=B9=E6=B3=95=E5=B9=B6=E5=8F=91=E9=97=AE=E9=A2=98?= =?UTF-8?q?=EF=BC=88issue#IBCIQG@Gitee=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- CHANGELOG.md | 3 ++- .../cn/hutool/cache/impl/StampedCache.java | 27 ++++++++++++++++--- 2 files changed, 25 insertions(+), 5 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index f86eb77fab..bc9f5fa5e3 100755 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,7 +2,7 @@ # 🚀Changelog ------------------------------------------------------------------------------------------------------------- -# 5.8.35(2024-12-19) +# 5.8.35(2024-12-21) ### 🐣新特性 * 【poi 】 优化ExcelWriter中使用比较器writer的方法,只对第一条数据进行排序(pr#3807@Github) @@ -16,6 +16,7 @@ ### 🐞Bug修复 * 【crypto 】 修复JWTSignerUtil.createSigner中algorithmId未转换问题(issue#3806@Github) * 【core 】 修复DateUtil.rangeContains未重置问题(issue#IB8OFS@Gitee) +* 【cache 】 修复StampedCache类get方法并发问题(issue#IBCIQG@Gitee) ------------------------------------------------------------------------------------------------------------- # 5.8.34(2024-11-25) diff --git a/hutool-cache/src/main/java/cn/hutool/cache/impl/StampedCache.java b/hutool-cache/src/main/java/cn/hutool/cache/impl/StampedCache.java index 2e90c9c4c5..b9971c3151 100755 --- a/hutool-cache/src/main/java/cn/hutool/cache/impl/StampedCache.java +++ b/hutool-cache/src/main/java/cn/hutool/cache/impl/StampedCache.java @@ -88,7 +88,12 @@ public void clear() { } /** - * 获取值 + * 获取值,使用乐观锁,但是此方法可能导致读取脏数据,但对于缓存业务可容忍。情况如下: + *

+	 *     1. 读取时无写入,不冲突,直接获取值
+	 *     2. 读取时无写入,但是乐观读时触发了并发异常,此时获取同步锁,获取新值
+	 *     4. 读取时有写入,此时获取同步锁,获取新值
+	 * 
* * @param key 键 * @param isUpdateLastAccess 是否更新最后修改时间 @@ -97,10 +102,24 @@ public void clear() { */ private V get(K key, boolean isUpdateLastAccess, boolean isUpdateCount) { // 尝试读取缓存,使用乐观读锁 + CacheObj co = null; long stamp = lock.tryOptimisticRead(); - CacheObj co = getWithoutLock(key); - if (false == lock.validate(stamp)) { - // 有写线程修改了此对象,悲观读 + boolean isReadError = true; + if(lock.validate(stamp)){ + try{ + // 乐观读,可能读取脏数据,在缓存中可容忍,分两种情况 + // 1. 读取时无线程写入 + // 2. 读取时有线程写入,导致数据不一致,此时读取未更新的缓存值 + co = getWithoutLock(key); + isReadError = false; + } catch (final Exception ignore){ + // ignore + } + } + + if(isReadError){ + // 转换为悲观读 + // 原因可能为无锁读时触发并发异常,或者锁被占(正在写) stamp = lock.readLock(); try { co = getWithoutLock(key); From c45232e235a625d8d947bf1c7d66208f3d521c3e Mon Sep 17 00:00:00 2001 From: Looly Date: Sat, 21 Dec 2024 11:29:25 +0800 Subject: [PATCH 21/30] =?UTF-8?q?=E4=BF=AE=E5=A4=8DFIFOCache=E7=B1=BB?= =?UTF-8?q?=E4=BD=BF=E7=94=A8StampedCache=E5=AF=BC=E8=87=B4=E5=B9=B6?= =?UTF-8?q?=E5=8F=91=E8=AF=BB=E7=9A=84=E5=B9=B6=E5=8F=91=E9=97=AE=E9=A2=98?= =?UTF-8?q?=EF=BC=88issue#IBCIQG@Gitee=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- CHANGELOG.md | 1 + hutool-cache/src/main/java/cn/hutool/cache/impl/FIFOCache.java | 2 +- 2 files changed, 2 insertions(+), 1 deletion(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index bc9f5fa5e3..f480027906 100755 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -17,6 +17,7 @@ * 【crypto 】 修复JWTSignerUtil.createSigner中algorithmId未转换问题(issue#3806@Github) * 【core 】 修复DateUtil.rangeContains未重置问题(issue#IB8OFS@Gitee) * 【cache 】 修复StampedCache类get方法并发问题(issue#IBCIQG@Gitee) +* 【cache 】 修复FIFOCache类使用StampedCache导致并发读的并发问题(issue#IBCIQG@Gitee) ------------------------------------------------------------------------------------------------------------- # 5.8.34(2024-11-25) diff --git a/hutool-cache/src/main/java/cn/hutool/cache/impl/FIFOCache.java b/hutool-cache/src/main/java/cn/hutool/cache/impl/FIFOCache.java index 071ac50676..68de47ef8f 100755 --- a/hutool-cache/src/main/java/cn/hutool/cache/impl/FIFOCache.java +++ b/hutool-cache/src/main/java/cn/hutool/cache/impl/FIFOCache.java @@ -16,7 +16,7 @@ * @param 值类型 * @author Looly */ -public class FIFOCache extends StampedCache { +public class FIFOCache extends ReentrantCache { private static final long serialVersionUID = 1L; /** From fe74f26f6f037fc42fa04570a9a24079f3efde35 Mon Sep 17 00:00:00 2001 From: Looly Date: Sat, 21 Dec 2024 13:09:03 +0800 Subject: [PATCH 22/30] =?UTF-8?q?=E6=B7=BB=E5=8A=A0StopReadException?= =?UTF-8?q?=EF=BC=8C=E5=AE=9A=E4=B9=89sax=E8=AF=BB=E5=8F=96=E6=97=B6?= =?UTF-8?q?=E7=94=A8=E6=88=B7=E5=8F=AF=E6=89=8B=E5=8A=A8=E7=BB=88=E6=AD=A2?= =?UTF-8?q?=EF=BC=88issue#3820@Github=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- CHANGELOG.md | 1 + .../poi/excel/sax/Excel03SaxReader.java | 2 ++ .../cn/hutool/poi/excel/sax/ExcelSaxUtil.java | 8 +++-- .../poi/excel/sax/StopReadException.java | 33 +++++++++++++++++++ .../cn/hutool/poi/excel/ExcelSaxReadTest.java | 19 +++++++++++ 5 files changed, 60 insertions(+), 3 deletions(-) create mode 100644 hutool-poi/src/main/java/cn/hutool/poi/excel/sax/StopReadException.java diff --git a/CHANGELOG.md b/CHANGELOG.md index f480027906..bccaa41f95 100755 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -12,6 +12,7 @@ * 【core 】 DateUtil.parseUTC方法标记废弃,改名为parseISO8601(issue#IBB6I5@Gitee) * 【core 】 添加EnumUtil#getBy(Class, Func1, Object)方法(pr#1283@Gitee) * 【db 】 添加Entity.addCondition方法(issue#IBCDL2@Gitee) +* 【poi 】 添加StopReadException,定义sax读取时用户可手动终止(issue#3820@Github) ### 🐞Bug修复 * 【crypto 】 修复JWTSignerUtil.createSigner中algorithmId未转换问题(issue#3806@Github) diff --git a/hutool-poi/src/main/java/cn/hutool/poi/excel/sax/Excel03SaxReader.java b/hutool-poi/src/main/java/cn/hutool/poi/excel/sax/Excel03SaxReader.java index a24882c9df..72c10ee7ee 100644 --- a/hutool-poi/src/main/java/cn/hutool/poi/excel/sax/Excel03SaxReader.java +++ b/hutool-poi/src/main/java/cn/hutool/poi/excel/sax/Excel03SaxReader.java @@ -147,6 +147,8 @@ public Excel03SaxReader read(POIFSFileSystem fs, String idOrRidOrSheetName) thro factory.processWorkbookEvents(request, fs); } catch (IOException e) { throw new POIException(e); + } catch (final StopReadException e) { + // issue#3820 跳过,用户抛出此异常,表示强制结束读取 } finally { IoUtil.close(fs); } diff --git a/hutool-poi/src/main/java/cn/hutool/poi/excel/sax/ExcelSaxUtil.java b/hutool-poi/src/main/java/cn/hutool/poi/excel/sax/ExcelSaxUtil.java index 66e5b176b4..526e29daed 100644 --- a/hutool-poi/src/main/java/cn/hutool/poi/excel/sax/ExcelSaxUtil.java +++ b/hutool-poi/src/main/java/cn/hutool/poi/excel/sax/ExcelSaxUtil.java @@ -47,8 +47,8 @@ public class ExcelSaxUtil { */ public static ExcelSaxReader createSaxReader(boolean isXlsx, RowHandler rowHandler) { return isXlsx - ? new Excel07SaxReader(rowHandler) - : new Excel03SaxReader(rowHandler); + ? new Excel07SaxReader(rowHandler) + : new Excel03SaxReader(rowHandler); } /** @@ -184,6 +184,8 @@ public static void readFrom(InputStream xmlDocStream, ContentHandler handler) th throw new IORuntimeException(e); } catch (SAXException e) { throw new POIException(e); + } catch (final StopReadException e) { + // issue#3820 跳过,用户抛出此异常,表示强制结束读取 } } @@ -268,7 +270,7 @@ private static Number getNumberValue(String value, String numFmtString) { // issue#IB0EJ9 可能精度丢失,对含有小数的value判断并转为BigDecimal final double number = Double.parseDouble(value); - if(StrUtil.contains(value, CharUtil.DOT) && !value.equals(Double.toString(number))){ + if (StrUtil.contains(value, CharUtil.DOT) && !value.equals(Double.toString(number))) { // 精度丢失 return NumberUtil.toBigDecimal(value); } diff --git a/hutool-poi/src/main/java/cn/hutool/poi/excel/sax/StopReadException.java b/hutool-poi/src/main/java/cn/hutool/poi/excel/sax/StopReadException.java new file mode 100644 index 0000000000..22d56c4b9c --- /dev/null +++ b/hutool-poi/src/main/java/cn/hutool/poi/excel/sax/StopReadException.java @@ -0,0 +1,33 @@ +package cn.hutool.poi.excel.sax; + +import cn.hutool.poi.exceptions.POIException; + +/** + * 读取结束异常,用于标记读取结束
+ * Sax方式读取时,如果用户在RowHandler中抛出此异常,表示读取结束,此时不再读取其他数据 + * + * @author Looly + * @since 5.8.35 + */ +public class StopReadException extends POIException { + private static final long serialVersionUID = 1L; + + /** + * 构造 + * + */ + public StopReadException() { + this("Stop read by user."); + } + + /** + * 构造 + * + * @param message 消息 + */ + public StopReadException(final String message) { + super(message); + // 去除堆栈 + setStackTrace(new StackTraceElement[0]); + } +} diff --git a/hutool-poi/src/test/java/cn/hutool/poi/excel/ExcelSaxReadTest.java b/hutool-poi/src/test/java/cn/hutool/poi/excel/ExcelSaxReadTest.java index b54379de2e..2f52c1a0eb 100644 --- a/hutool-poi/src/test/java/cn/hutool/poi/excel/ExcelSaxReadTest.java +++ b/hutool-poi/src/test/java/cn/hutool/poi/excel/ExcelSaxReadTest.java @@ -8,6 +8,7 @@ import cn.hutool.core.util.StrUtil; import cn.hutool.poi.excel.cell.FormulaCellValue; import cn.hutool.poi.excel.sax.Excel03SaxReader; +import cn.hutool.poi.excel.sax.StopReadException; import cn.hutool.poi.excel.sax.handler.RowHandler; import cn.hutool.poi.exceptions.POIException; import org.apache.poi.ss.usermodel.CellStyle; @@ -33,6 +34,24 @@ public void excel07Test() { ExcelUtil.readBySax("aaa.xlsx", 0, createRowHandler()); } + @Test + void readEndByExceptionTest(){ + ExcelUtil.readBySax("aaa.xlsx", 0, (sheetIndex, rowIndex, rowList) -> { + if (rowIndex == 1) { + throw new StopReadException(); + } + }); + } + + @Test + void readEndByException03Test(){ + ExcelUtil.readBySax("aaa.xls", 0, (sheetIndex, rowIndex, rowList) -> { + if (rowIndex == 1) { + throw new StopReadException(); + } + }); + } + @Test public void excel07ByNameTest() { // 工具化快速读取 From 416f0f3fa7bf2bfe8948088dd560d8be172d2851 Mon Sep 17 00:00:00 2001 From: Looly Date: Wed, 25 Dec 2024 12:53:24 +0800 Subject: [PATCH 23/30] =?UTF-8?q?=E5=BA=9F=E5=BC=83StampedCache=EF=BC=8C?= =?UTF-8?q?=E5=8F=AF=E8=83=BD=E9=80=A0=E6=88=90Map=E5=BE=AA=E7=8E=AF?= =?UTF-8?q?=E8=B0=83=E7=94=A8=E5=AF=BC=E8=87=B4=E6=AD=BB=E9=94=81=EF=BC=88?= =?UTF-8?q?issue#IBDGBZ@Gitee=EF=BC=89?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- CHANGELOG.md | 3 ++- hutool-cache/src/main/java/cn/hutool/cache/impl/LFUCache.java | 2 +- .../src/main/java/cn/hutool/cache/impl/StampedCache.java | 2 ++ .../src/main/java/cn/hutool/cache/impl/TimedCache.java | 2 +- 4 files changed, 6 insertions(+), 3 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index bccaa41f95..e384f82ffe 100755 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,7 +2,7 @@ # 🚀Changelog ------------------------------------------------------------------------------------------------------------- -# 5.8.35(2024-12-21) +# 5.8.35(2024-12-25) ### 🐣新特性 * 【poi 】 优化ExcelWriter中使用比较器writer的方法,只对第一条数据进行排序(pr#3807@Github) @@ -19,6 +19,7 @@ * 【core 】 修复DateUtil.rangeContains未重置问题(issue#IB8OFS@Gitee) * 【cache 】 修复StampedCache类get方法并发问题(issue#IBCIQG@Gitee) * 【cache 】 修复FIFOCache类使用StampedCache导致并发读的并发问题(issue#IBCIQG@Gitee) +* 【cache 】 废弃StampedCache,可能造成Map循环调用导致死锁(issue#IBDGBZ@Gitee) ------------------------------------------------------------------------------------------------------------- # 5.8.34(2024-11-25) diff --git a/hutool-cache/src/main/java/cn/hutool/cache/impl/LFUCache.java b/hutool-cache/src/main/java/cn/hutool/cache/impl/LFUCache.java index b3bcdffc99..6ac8e6299f 100755 --- a/hutool-cache/src/main/java/cn/hutool/cache/impl/LFUCache.java +++ b/hutool-cache/src/main/java/cn/hutool/cache/impl/LFUCache.java @@ -15,7 +15,7 @@ * @param 键类型 * @param 值类型 */ -public class LFUCache extends StampedCache { +public class LFUCache extends ReentrantCache { private static final long serialVersionUID = 1L; /** diff --git a/hutool-cache/src/main/java/cn/hutool/cache/impl/StampedCache.java b/hutool-cache/src/main/java/cn/hutool/cache/impl/StampedCache.java index b9971c3151..a3ca63a309 100755 --- a/hutool-cache/src/main/java/cn/hutool/cache/impl/StampedCache.java +++ b/hutool-cache/src/main/java/cn/hutool/cache/impl/StampedCache.java @@ -12,7 +12,9 @@ * @param 值类型 * @author looly * @since 5.7.15 + * @deprecated Map使用StampedLock可能造成数据不一致甚至Map循环调用,此缓存废弃 */ +@Deprecated public abstract class StampedCache extends AbstractCache { private static final long serialVersionUID = 1L; diff --git a/hutool-cache/src/main/java/cn/hutool/cache/impl/TimedCache.java b/hutool-cache/src/main/java/cn/hutool/cache/impl/TimedCache.java index dfccd942ed..3733a899c0 100755 --- a/hutool-cache/src/main/java/cn/hutool/cache/impl/TimedCache.java +++ b/hutool-cache/src/main/java/cn/hutool/cache/impl/TimedCache.java @@ -17,7 +17,7 @@ * @param 键类型 * @param 值类型 */ -public class TimedCache extends StampedCache { +public class TimedCache extends ReentrantCache { private static final long serialVersionUID = 1L; /** 正在执行的定时任务 */ From 987bd783cf13c93104d10ff0355a43c4baaf6ef5 Mon Sep 17 00:00:00 2001 From: miko <1059665047@qq.com> Date: Wed, 25 Dec 2024 16:20:06 +0800 Subject: [PATCH 24/30] =?UTF-8?q?GifCaptcha.setRepeat=E8=AE=BE=E7=BD=AE?= =?UTF-8?q?=E6=97=A0=E6=95=88=E5=80=BC=EF=BC=8C=E5=BA=94=E8=AF=A5=E4=BF=9D?= =?UTF-8?q?=E6=8C=81=E4=B8=BA=200?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../src/main/java/cn/hutool/captcha/GifCaptcha.java | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-) diff --git a/hutool-captcha/src/main/java/cn/hutool/captcha/GifCaptcha.java b/hutool-captcha/src/main/java/cn/hutool/captcha/GifCaptcha.java index 7da77496c4..d32c195d3d 100755 --- a/hutool-captcha/src/main/java/cn/hutool/captcha/GifCaptcha.java +++ b/hutool-captcha/src/main/java/cn/hutool/captcha/GifCaptcha.java @@ -113,9 +113,7 @@ public GifCaptcha setQuality(int quality) { * @return this */ public GifCaptcha setRepeat(int repeat) { - if (repeat >= 0) { - this.repeat = repeat; - } + this.repeat = Math.max(repeat, 0); return this; } From 980d1e79e55c1cafc0c1ea9a482442579b76eb4a Mon Sep 17 00:00:00 2001 From: miko <1059665047@qq.com> Date: Wed, 25 Dec 2024 16:20:42 +0800 Subject: [PATCH 25/30] =?UTF-8?q?GifCaptcha=E9=83=A8=E5=88=86=E6=B5=8B?= =?UTF-8?q?=E8=AF=95=E7=94=A8=E4=BE=8B?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../cn/hutool/captcha/GifCaptchaUtilTest.java | 115 ++++++++++++++++++ 1 file changed, 115 insertions(+) create mode 100644 hutool-captcha/src/test/java/cn/hutool/captcha/GifCaptchaUtilTest.java diff --git a/hutool-captcha/src/test/java/cn/hutool/captcha/GifCaptchaUtilTest.java b/hutool-captcha/src/test/java/cn/hutool/captcha/GifCaptchaUtilTest.java new file mode 100644 index 0000000000..e02f5f539b --- /dev/null +++ b/hutool-captcha/src/test/java/cn/hutool/captcha/GifCaptchaUtilTest.java @@ -0,0 +1,115 @@ +package cn.hutool.captcha; + +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +import java.awt.*; +import java.io.ByteArrayOutputStream; +import java.lang.reflect.Field; +import java.lang.reflect.Method; + +import static org.junit.jupiter.api.Assertions.*; + +public class GifCaptchaUtilTest { + + private GifCaptcha captcha; + + @BeforeEach + public void setUp() { + // 初始化 GifCaptcha 类的实例 + captcha = new GifCaptcha(200, 100, 4, 10); // width, height, codeCount, interfereCount + } + + // 使用反射调用私有方法 + private Object invokePrivateMethod(String methodName, Class[] parameterTypes, Object[] parameters) throws Exception { + Method method = GifCaptcha.class.getDeclaredMethod(methodName, parameterTypes); + method.setAccessible(true); // 允许访问私有方法 + return method.invoke(captcha, parameters); + } + + // 测试 setQuality() 方法 + @Test + public void testSetQuality() throws Exception { + captcha.setQuality(20); + // 通过反射获取 quality 字段的值并进行断言 + assertEquals(20, getPrivateField("quality"), "Quality 应该设置为 20"); + + captcha.setQuality(0); // 设置无效值,应该被设置为 1 + assertEquals(1, getPrivateField("quality"), "Quality 应该设置为 1,如果小于 1"); + } + + // 测试 setRepeat() 方法 + @Test + public void testSetRepeat() throws Exception { + captcha.setRepeat(5); + // 通过反射获取 repeat 字段的值并进行断言 + assertEquals(5, getPrivateField("repeat"), "Repeat 应该设置为 5"); + + captcha.setRepeat(-1); // 设置无效值,应该保持为 0 + assertEquals(0, getPrivateField("repeat"), "Repeat 应该设置为 0,如果设置了负值"); + } + + // 测试 setColorRange() 方法 + @Test + public void testSetColorRange() throws Exception { + captcha.setMinColor(100).setMaxColor(200); + // 通过反射获取 minColor 和 maxColor 字段的值并进行断言 + assertEquals(100, getPrivateField("minColor"), "Min color 应该设置为 100"); + assertEquals(200, getPrivateField("maxColor"), "Max color 应该设置为 200"); + } + + // 测试生成验证码图像的方法 createCode() + @Test + public void testCreateCode() throws Exception { + captcha.createCode(); + byte[] imageBytes = captcha.getImageBytes(); + + // 检查生成的图片字节是否不为 null 或空 + assertNotNull(imageBytes, "生成的图片字节不应该为 null"); + assertTrue(imageBytes.length > 0, "生成的图片字节不应该为空"); + + // 可选:你也可以通过解码图片字节,检查它是否是有效的 GIF 格式 + ByteArrayOutputStream out = new ByteArrayOutputStream(); + out.write(imageBytes); + + // 解码图片检查它是否为有效的 GIF(假设你有库可以解码 GIF) + // ImageIO.read(new ByteArrayInputStream(imageBytes)); // 可以取消注释来检查它是否是有效的 GIF + } + + // 测试 graphicsImage() 方法 + @Test + public void testGraphicsImage() throws Exception { + char[] chars = new char[]{'A', 'B', 'C', 'D'}; + Color[] colors = new Color[]{ + Color.RED, Color.GREEN, Color.BLUE, Color.YELLOW + }; + + // 使用反射调用 private 方法 graphicsImage + Object result = invokePrivateMethod("graphicsImage", new Class[]{char[].class, Color[].class, char[].class, int.class}, new Object[]{chars, colors, chars, 0}); + + assertNotNull(result, "生成的图片不应该为 null"); + assertTrue(result instanceof java.awt.image.BufferedImage, "返回的结果应该是 BufferedImage 类型"); + } + + // 测试 getRandomColor() 方法 + @Test + public void testRandomColor() throws Exception { + // 使用反射调用 private 方法 getRandomColor + Object result = invokePrivateMethod("getRandomColor", new Class[]{int.class, int.class}, new Object[]{0, 255}); + + assertNotNull(result, "生成的颜色不应该为 null"); + assertTrue(result instanceof Color, "返回的结果应该是 Color 类型"); + + Color color = (Color) result; + assertTrue(color.getRed() >= 0 && color.getRed() <= 255, "颜色的红色分量应该在 0 到 255 之间"); + assertTrue(color.getGreen() >= 0 && color.getGreen() <= 255, "颜色的绿色分量应该在 0 到 255 之间"); + assertTrue(color.getBlue() >= 0 && color.getBlue() <= 255, "颜色的蓝色分量应该在 0 到 255 之间"); + } + + // 辅助方法:通过反射获取私有字段的值 + private Object getPrivateField(String fieldName) throws NoSuchFieldException, IllegalAccessException { + Field field = GifCaptcha.class.getDeclaredField(fieldName); + field.setAccessible(true); // 允许访问私有字段 + return field.get(captcha); + } +} From 79edb438311554a0593d80660927d1171ea613e3 Mon Sep 17 00:00:00 2001 From: miko <1059665047@qq.com> Date: Wed, 25 Dec 2024 16:47:34 +0800 Subject: [PATCH 26/30] =?UTF-8?q?ShearCaptcha=E9=83=A8=E5=88=86=E6=B5=8B?= =?UTF-8?q?=E8=AF=95=E7=94=A8=E4=BE=8B?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .../cn/hutool/captcha/ShearCaptchaTest.java | 148 ++++++++++++++++++ 1 file changed, 148 insertions(+) create mode 100644 hutool-captcha/src/test/java/cn/hutool/captcha/ShearCaptchaTest.java diff --git a/hutool-captcha/src/test/java/cn/hutool/captcha/ShearCaptchaTest.java b/hutool-captcha/src/test/java/cn/hutool/captcha/ShearCaptchaTest.java new file mode 100644 index 0000000000..b68cf1e966 --- /dev/null +++ b/hutool-captcha/src/test/java/cn/hutool/captcha/ShearCaptchaTest.java @@ -0,0 +1,148 @@ +package cn.hutool.captcha; +import cn.hutool.captcha.ShearCaptcha; +import cn.hutool.captcha.generator.RandomGenerator; +import cn.hutool.core.img.GraphicsUtil; +import cn.hutool.core.img.ImgUtil; +import cn.hutool.core.util.RandomUtil; +import org.junit.jupiter.api.BeforeEach; +import org.junit.jupiter.api.Test; + +import java.awt.*; +import java.awt.image.BufferedImage; +import java.lang.reflect.Method; + +import static org.junit.jupiter.api.Assertions.*; + +public class ShearCaptchaTest { + + private ShearCaptcha captcha; + + @BeforeEach + public void setUp() { + // 初始化 ShearCaptcha 实例 + captcha = new ShearCaptcha(200, 100); + } + + // 测试构造函数和基本功能 + @Test + public void testConstructor() { + assertNotNull(captcha, "Captcha 实例应该被成功创建"); + } + + // 测试生成验证码图片的功能 + @Test + public void testCreateImage() { + String code = "ABCD"; + Image image = captcha.createImage(code); + assertNotNull(image, "验证码图片不应该为 null"); + assertTrue(image instanceof BufferedImage, "生成的图片应该是 BufferedImage 类型"); + + // 可选:进一步测试图像的内容 + BufferedImage bufferedImage = (BufferedImage) image; + assertEquals(200, bufferedImage.getWidth(), "图像宽度应该为 200"); + assertEquals(100, bufferedImage.getHeight(), "图像高度应该为 100"); + } + + // 测试绘制字符串的方法 + @Test + public void testDrawString() throws Exception { + String code = "ABCD"; + Method drawStringMethod = ShearCaptcha.class.getDeclaredMethod("drawString", Graphics2D.class, String.class); + drawStringMethod.setAccessible(true); + + Graphics2D g2d = (Graphics2D) new BufferedImage(200, 100, BufferedImage.TYPE_INT_ARGB).getGraphics(); + drawStringMethod.invoke(captcha, g2d, code); + + assertNotNull(g2d, "Graphics2D 对象不应该为 null"); + assertTrue(g2d.getRenderingHints().containsKey(RenderingHints.KEY_ANTIALIASING), "应该启用抗锯齿"); + } + + // 测试 shear() 方法 + @Test + public void testShear() throws Exception { + // 使用反射测试 shear 方法 + Method shearMethod = ShearCaptcha.class.getDeclaredMethod("shear", Graphics.class, int.class, int.class, Color.class); + shearMethod.setAccessible(true); + + Graphics g = new BufferedImage(200, 100, BufferedImage.TYPE_INT_ARGB).getGraphics(); + shearMethod.invoke(captcha, g, 200, 100, Color.WHITE); + + // 假设没有明显的错误输出,认为测试通过 + assertNotNull(g, "Graphics 对象不应该为 null"); + } + + // 测试 shearX() 方法 + @Test + public void testShearX() throws Exception { + // 使用反射测试 shearX 方法 + Method shearXMethod = ShearCaptcha.class.getDeclaredMethod("shearX", Graphics.class, int.class, int.class, Color.class); + shearXMethod.setAccessible(true); + + Graphics g = new BufferedImage(200, 100, BufferedImage.TYPE_INT_ARGB).getGraphics(); + shearXMethod.invoke(captcha, g, 200, 100, Color.RED); + + // 假设没有明显的错误输出,认为测试通过 + assertNotNull(g, "Graphics 对象不应该为 null"); + } + + // 测试 shearY() 方法 + @Test + public void testShearY() throws Exception { + // 使用反射测试 shearY 方法 + Method shearYMethod = ShearCaptcha.class.getDeclaredMethod("shearY", Graphics.class, int.class, int.class, Color.class); + shearYMethod.setAccessible(true); + + Graphics g = new BufferedImage(200, 100, BufferedImage.TYPE_INT_ARGB).getGraphics(); + shearYMethod.invoke(captcha, g, 200, 100, Color.BLUE); + + // 假设没有明显的错误输出,认为测试通过 + assertNotNull(g, "Graphics 对象不应该为 null"); + } + + // 测试 drawInterfere() 方法 + @Test + public void testDrawInterfere() throws Exception { + // 使用反射测试 drawInterfere 方法 + Method drawInterfereMethod = ShearCaptcha.class.getDeclaredMethod("drawInterfere", Graphics.class, int.class, int.class, int.class, int.class, int.class, Color.class); + drawInterfereMethod.setAccessible(true); + + Graphics g = new BufferedImage(200, 100, BufferedImage.TYPE_INT_ARGB).getGraphics(); + drawInterfereMethod.invoke(captcha, g, 0, 0, 200, 100, 4, Color.GREEN); + + // 假设没有明显的错误输出,认为测试通过 + assertNotNull(g, "Graphics 对象不应该为 null"); + } + + // 测试验证码生成时的干扰线 + @Test + public void testDrawInterfereLines() { + // 设置干扰线数量 + captcha = new ShearCaptcha(200, 100, 4); + Image image = captcha.createImage("ABCD"); + + // 检查图像内容,判断干扰线是否正确绘制 + assertNotNull(image, "生成的验证码图片不应该为空"); + } + + // 测试验证码的尺寸 + @Test + public void testCaptchaSize() { + captcha = new ShearCaptcha(300, 150); + + String code = "XYZ"; + Image image = captcha.createImage(code); + + BufferedImage bufferedImage = (BufferedImage) image; + assertEquals(300, bufferedImage.getWidth(), "图像宽度应该为 300"); + assertEquals(150, bufferedImage.getHeight(), "图像高度应该为 150"); + } + + // 测试生成随机验证码字符 + @Test + public void testRandomGenerator() { + RandomGenerator randomGenerator = new RandomGenerator(4); + String code = randomGenerator.generate(); + assertNotNull(code, "生成的验证码字符不应该为 null"); + assertEquals(4, code.length(), "验证码字符长度应该为 4"); + } +} From 30e062e2c646cbe2a99655dc4a93e9629083f01c Mon Sep 17 00:00:00 2001 From: Looly Date: Wed, 25 Dec 2024 17:35:32 +0800 Subject: [PATCH 27/30] add test --- .../test/java/cn/hutool/captcha/GifCaptchaUtilTest.java | 5 +++-- .../src/test/java/cn/hutool/captcha/ShearCaptchaTest.java | 7 ++----- 2 files changed, 5 insertions(+), 7 deletions(-) diff --git a/hutool-captcha/src/test/java/cn/hutool/captcha/GifCaptchaUtilTest.java b/hutool-captcha/src/test/java/cn/hutool/captcha/GifCaptchaUtilTest.java index e02f5f539b..2125aa64a3 100644 --- a/hutool-captcha/src/test/java/cn/hutool/captcha/GifCaptchaUtilTest.java +++ b/hutool-captcha/src/test/java/cn/hutool/captcha/GifCaptchaUtilTest.java @@ -4,6 +4,7 @@ import org.junit.jupiter.api.Test; import java.awt.*; +import java.awt.image.BufferedImage; import java.io.ByteArrayOutputStream; import java.lang.reflect.Field; import java.lang.reflect.Method; @@ -88,7 +89,7 @@ public void testGraphicsImage() throws Exception { Object result = invokePrivateMethod("graphicsImage", new Class[]{char[].class, Color[].class, char[].class, int.class}, new Object[]{chars, colors, chars, 0}); assertNotNull(result, "生成的图片不应该为 null"); - assertTrue(result instanceof java.awt.image.BufferedImage, "返回的结果应该是 BufferedImage 类型"); + assertInstanceOf(BufferedImage.class, result, "返回的结果应该是 BufferedImage 类型"); } // 测试 getRandomColor() 方法 @@ -98,7 +99,7 @@ public void testRandomColor() throws Exception { Object result = invokePrivateMethod("getRandomColor", new Class[]{int.class, int.class}, new Object[]{0, 255}); assertNotNull(result, "生成的颜色不应该为 null"); - assertTrue(result instanceof Color, "返回的结果应该是 Color 类型"); + assertInstanceOf(Color.class, result, "返回的结果应该是 Color 类型"); Color color = (Color) result; assertTrue(color.getRed() >= 0 && color.getRed() <= 255, "颜色的红色分量应该在 0 到 255 之间"); diff --git a/hutool-captcha/src/test/java/cn/hutool/captcha/ShearCaptchaTest.java b/hutool-captcha/src/test/java/cn/hutool/captcha/ShearCaptchaTest.java index b68cf1e966..b75b46eb15 100644 --- a/hutool-captcha/src/test/java/cn/hutool/captcha/ShearCaptchaTest.java +++ b/hutool-captcha/src/test/java/cn/hutool/captcha/ShearCaptchaTest.java @@ -1,9 +1,6 @@ package cn.hutool.captcha; -import cn.hutool.captcha.ShearCaptcha; + import cn.hutool.captcha.generator.RandomGenerator; -import cn.hutool.core.img.GraphicsUtil; -import cn.hutool.core.img.ImgUtil; -import cn.hutool.core.util.RandomUtil; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.Test; @@ -35,7 +32,7 @@ public void testCreateImage() { String code = "ABCD"; Image image = captcha.createImage(code); assertNotNull(image, "验证码图片不应该为 null"); - assertTrue(image instanceof BufferedImage, "生成的图片应该是 BufferedImage 类型"); + assertInstanceOf(BufferedImage.class, image, "生成的图片应该是 BufferedImage 类型"); // 可选:进一步测试图像的内容 BufferedImage bufferedImage = (BufferedImage) image; From 8db00aad247b8d898f811a158157a5179f2acad3 Mon Sep 17 00:00:00 2001 From: VampireAchao Date: Wed, 25 Dec 2024 17:46:38 +0800 Subject: [PATCH 28/30] add gitcode --- README.md | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-) diff --git a/README.md b/README.md index 713155f023..9034505b0c 100755 --- a/README.md +++ b/README.md @@ -36,6 +36,9 @@ github star + + gitcode star +


@@ -191,15 +194,16 @@ Hutool的源码分为两个分支,功能如下: - [Gitee issue](https://gitee.com/dromara/hutool/issues) - [Github issue](https://github.com/dromara/hutool/issues) +- [Gitcode issue](https://gitcode.com/dromara/hutool/issues) ### 🧬贡献代码的步骤 -1. 在Gitee或者Github上fork项目到自己的repo +1. 在Gitee或者Github/Gitcode上fork项目到自己的repo 2. 把fork过去的项目也就是你的项目clone到你的本地 3. 修改代码(记得一定要修改v5-dev分支) 4. commit后push到自己的库(v5-dev分支) -5. 登录Gitee或Github在你首页可以看到一个 pull request 按钮,点击它,填写一些说明信息,然后提交即可。 +5. 登录Gitee或Github/Gitcode在你首页可以看到一个 pull request 按钮,点击它,填写一些说明信息,然后提交即可。 6. 等待维护者合并 ### 📐PR遵照的原则 From 7298016046895dcc2b033473047dfdc06f82bc9f Mon Sep 17 00:00:00 2001 From: Looly Date: Wed, 25 Dec 2024 18:07:11 +0800 Subject: [PATCH 29/30] add gitcode --- README-EN.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/README-EN.md b/README-EN.md index 1b8914dd3a..80a055aef1 100755 --- a/README-EN.md +++ b/README-EN.md @@ -36,6 +36,9 @@ github star + + gitcode star +


@@ -199,6 +202,7 @@ When submitting feedback, please indicate which JDK version, Hutool version, and - [Gitee issue](https://gitee.com/dromara/hutool/issues) - [Github issue](https://github.com/dromara/hutool/issues) +- [Gitcode issue](https://gitcode.com/dromara/hutool/issues) ### 🧬Principles of PR(pull request) From 6a9ee9aebb77aa3ff0ab4b5915ae25c0d5ece7ee Mon Sep 17 00:00:00 2001 From: Looly Date: Wed, 25 Dec 2024 18:23:05 +0800 Subject: [PATCH 30/30] =?UTF-8?q?=F0=9F=90=8CRelease=205.8.35?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- hutool-all/pom.xml | 2 +- hutool-aop/pom.xml | 2 +- hutool-bloomFilter/pom.xml | 2 +- hutool-bom/pom.xml | 2 +- hutool-cache/pom.xml | 2 +- hutool-captcha/pom.xml | 2 +- hutool-core/pom.xml | 2 +- hutool-cron/pom.xml | 2 +- hutool-crypto/pom.xml | 2 +- hutool-db/pom.xml | 2 +- hutool-dfa/pom.xml | 2 +- hutool-extra/pom.xml | 2 +- hutool-http/pom.xml | 2 +- hutool-json/pom.xml | 2 +- hutool-jwt/pom.xml | 2 +- hutool-log/pom.xml | 2 +- hutool-poi/pom.xml | 2 +- hutool-script/pom.xml | 2 +- hutool-setting/pom.xml | 2 +- hutool-socket/pom.xml | 2 +- hutool-system/pom.xml | 2 +- pom.xml | 2 +- 22 files changed, 22 insertions(+), 22 deletions(-) diff --git a/hutool-all/pom.xml b/hutool-all/pom.xml index 81a654d69c..95a1e8296b 100755 --- a/hutool-all/pom.xml +++ b/hutool-all/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-all diff --git a/hutool-aop/pom.xml b/hutool-aop/pom.xml index 6d6e53098c..3b96ca4cdb 100755 --- a/hutool-aop/pom.xml +++ b/hutool-aop/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-aop diff --git a/hutool-bloomFilter/pom.xml b/hutool-bloomFilter/pom.xml index b7e9ea2fdc..ff6d81e10c 100755 --- a/hutool-bloomFilter/pom.xml +++ b/hutool-bloomFilter/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-bloomFilter diff --git a/hutool-bom/pom.xml b/hutool-bom/pom.xml index f108ab20ab..1b8b92bd4b 100755 --- a/hutool-bom/pom.xml +++ b/hutool-bom/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-bom diff --git a/hutool-cache/pom.xml b/hutool-cache/pom.xml index d17e8eae86..6e302bf304 100755 --- a/hutool-cache/pom.xml +++ b/hutool-cache/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-cache diff --git a/hutool-captcha/pom.xml b/hutool-captcha/pom.xml index 11cca40cfc..6ab907469c 100755 --- a/hutool-captcha/pom.xml +++ b/hutool-captcha/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-captcha diff --git a/hutool-core/pom.xml b/hutool-core/pom.xml index b4cc9eb0da..bc1ab47d9f 100755 --- a/hutool-core/pom.xml +++ b/hutool-core/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-core diff --git a/hutool-cron/pom.xml b/hutool-cron/pom.xml index 2ce06aaa5a..78263c9826 100755 --- a/hutool-cron/pom.xml +++ b/hutool-cron/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-cron diff --git a/hutool-crypto/pom.xml b/hutool-crypto/pom.xml index 72ecdb5a3c..557797fb6a 100755 --- a/hutool-crypto/pom.xml +++ b/hutool-crypto/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-crypto diff --git a/hutool-db/pom.xml b/hutool-db/pom.xml index 6fe8568223..ee443457a5 100755 --- a/hutool-db/pom.xml +++ b/hutool-db/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-db diff --git a/hutool-dfa/pom.xml b/hutool-dfa/pom.xml index 4a0c152f4c..5927c802fb 100755 --- a/hutool-dfa/pom.xml +++ b/hutool-dfa/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-dfa diff --git a/hutool-extra/pom.xml b/hutool-extra/pom.xml index 25994e3cd1..564ebc22d8 100755 --- a/hutool-extra/pom.xml +++ b/hutool-extra/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-extra diff --git a/hutool-http/pom.xml b/hutool-http/pom.xml index e713b68a7f..1662ffb7f1 100755 --- a/hutool-http/pom.xml +++ b/hutool-http/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-http diff --git a/hutool-json/pom.xml b/hutool-json/pom.xml index 9690297662..281a1fc5f0 100755 --- a/hutool-json/pom.xml +++ b/hutool-json/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-json diff --git a/hutool-jwt/pom.xml b/hutool-jwt/pom.xml index 3a6bf7b614..2f1fc0078d 100755 --- a/hutool-jwt/pom.xml +++ b/hutool-jwt/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-jwt diff --git a/hutool-log/pom.xml b/hutool-log/pom.xml index de97402c34..f42c075b54 100755 --- a/hutool-log/pom.xml +++ b/hutool-log/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-log diff --git a/hutool-poi/pom.xml b/hutool-poi/pom.xml index 8e9132d726..3166aafcb4 100755 --- a/hutool-poi/pom.xml +++ b/hutool-poi/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-poi diff --git a/hutool-script/pom.xml b/hutool-script/pom.xml index 5d7fa1a84f..e7147b9fca 100755 --- a/hutool-script/pom.xml +++ b/hutool-script/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-script diff --git a/hutool-setting/pom.xml b/hutool-setting/pom.xml index b1b6dfefd7..8529bb9999 100755 --- a/hutool-setting/pom.xml +++ b/hutool-setting/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-setting diff --git a/hutool-socket/pom.xml b/hutool-socket/pom.xml index b92702fcd5..18a5e972eb 100755 --- a/hutool-socket/pom.xml +++ b/hutool-socket/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-socket diff --git a/hutool-system/pom.xml b/hutool-system/pom.xml index 4d34d06b8c..09b69acbce 100755 --- a/hutool-system/pom.xml +++ b/hutool-system/pom.xml @@ -9,7 +9,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool-system diff --git a/pom.xml b/pom.xml index 3ed5095f12..582dc12b46 100755 --- a/pom.xml +++ b/pom.xml @@ -8,7 +8,7 @@ cn.hutool hutool-parent - 5.8.35-SNAPSHOT + 5.8.35 hutool Hutool是一个小而全的Java工具类库,通过静态方法封装,降低相关API的学习成本,提高工作效率,使Java拥有函数式语言般的优雅,让Java语言也可以“甜甜的”。 https://github.com/dromara/hutool