From 552750da152668c0dbe6964312bdd75c232fcad3 Mon Sep 17 00:00:00 2001 From: Looly Date: Mon, 9 Nov 2020 03:45:21 +0800 Subject: [PATCH] fix Ipv4Util bug --- CHANGELOG.md | 3 + .../core/convert/impl/ClassConverter.java | 37 ++++-- .../java/cn/hutool/core/net/Ipv4Util.java | 114 ++++++++---------- .../java/cn/hutool/core/util/ClassUtil.java | 5 +- .../java/cn/hutool/core/util/StrUtil.java | 48 ++++---- .../cn/hutool/core/convert/ConvertTest.java | 6 + .../java/cn/hutool/core/net/Ipv4UtilTest.java | 45 +++++++ 7 files changed, 156 insertions(+), 102 deletions(-) create mode 100644 hutool-core/src/test/java/cn/hutool/core/net/Ipv4UtilTest.java diff --git a/CHANGELOG.md b/CHANGELOG.md index 4b039fdfe..4913eb5a7 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -14,6 +14,9 @@ ### Bug修复 * 【core 】 修复DateUtil.current使用System.nanoTime的问题(issue#1198@Github) * 【core 】 修复Excel03SaxReader判断日期出错问题(issue#I23M9H@Gitee) +* 【core 】 修复ClassUtil.getTypeArgument方法在判断泛型时导致的问题(issue#1207@Github) +* 【core 】 修复Ipv4Util分隔符问题(issue#I24A9I@Gitee) +* 【core 】 修复Ipv4Util.longToIp的问题 ------------------------------------------------------------------------------------------------------------- diff --git a/hutool-core/src/main/java/cn/hutool/core/convert/impl/ClassConverter.java b/hutool-core/src/main/java/cn/hutool/core/convert/impl/ClassConverter.java index d2e1ec647..573d9501d 100644 --- a/hutool-core/src/main/java/cn/hutool/core/convert/impl/ClassConverter.java +++ b/hutool-core/src/main/java/cn/hutool/core/convert/impl/ClassConverter.java @@ -1,26 +1,39 @@ package cn.hutool.core.convert.impl; import cn.hutool.core.convert.AbstractConverter; -import cn.hutool.core.util.ClassUtil; +import cn.hutool.core.util.ClassLoaderUtil; /** * 类转换器
- * 将类名转换为类 - * @author Looly + * 将类名转换为类,默认初始化这个类(执行static块) * + * @author Looly */ -public class ClassConverter extends AbstractConverter>{ +public class ClassConverter extends AbstractConverter> { private static final long serialVersionUID = 1L; - + + private final boolean isInitialized; + + /** + * 构造 + */ + public ClassConverter() { + this(true); + } + + /** + * 构造 + * + * @param isInitialized 是否初始化类(调用static模块内容和初始化static属性) + * @since 5.5.0 + */ + public ClassConverter(boolean isInitialized) { + this.isInitialized = isInitialized; + } + @Override protected Class convertInternal(Object value) { - String valueStr = convertToStr(value); - try { - return ClassUtil.getClassLoader().loadClass(valueStr); - } catch (Exception e) { - // Ignore Exception - } - return null; + return ClassLoaderUtil.loadClass(convertToStr(value), isInitialized); } } diff --git a/hutool-core/src/main/java/cn/hutool/core/net/Ipv4Util.java b/hutool-core/src/main/java/cn/hutool/core/net/Ipv4Util.java index b5ec8e720..56121c8e8 100644 --- a/hutool-core/src/main/java/cn/hutool/core/net/Ipv4Util.java +++ b/hutool-core/src/main/java/cn/hutool/core/net/Ipv4Util.java @@ -1,11 +1,15 @@ package cn.hutool.core.net; +import cn.hutool.core.collection.ListUtil; import cn.hutool.core.convert.Convert; +import cn.hutool.core.lang.Assert; import cn.hutool.core.lang.Validator; +import cn.hutool.core.util.CharUtil; import cn.hutool.core.util.StrUtil; import java.util.ArrayList; import java.util.List; +import java.util.Objects; /** * IPV4地址工具类 @@ -24,7 +28,7 @@ public class Ipv4Util { /** * IP与掩码的分割符 */ - public static final String IP_MASK_SPLIT_MARK = "/"; + public static final String IP_MASK_SPLIT_MARK = StrUtil.SLASH; /** * 最大掩码位 @@ -51,15 +55,15 @@ public class Ipv4Util { */ public static List list(String ipRange, boolean isAll) { if (ipRange.contains(IP_SPLIT_MARK)) { - String[] range = ipRange.split(IP_SPLIT_MARK); + // X.X.X.X-X.X.X.X + final String[] range = StrUtil.split(ipRange, IP_SPLIT_MARK); return list(range[0], range[1]); } else if (ipRange.contains(IP_MASK_SPLIT_MARK)) { - String[] param = ipRange.split(IP_MASK_SPLIT_MARK); + // X.X.X.X/X + final String[] param = StrUtil.split(ipRange, IP_MASK_SPLIT_MARK); return list(param[0], Integer.parseInt(param[1]), isAll); } else { - List ips = new ArrayList<>(); - ips.add(ipRange); - return ips; + return ListUtil.toList(ipRange); } } @@ -72,26 +76,27 @@ public class Ipv4Util { * @return 区间地址 */ public static List list(String ip, int maskBit, boolean isAll) { - List list = new ArrayList<>(); if (maskBit == IP_MASK_MAX) { - if (Boolean.TRUE.equals(isAll)) { + final List list = new ArrayList<>(); + if (isAll) { list.add(ip); } - } else { - String startIp = getBeginIpStr(ip, maskBit); - String endIp = getEndIpStr(ip, maskBit); - String subStart = startIp.split("\\.")[0] + "." + startIp.split("\\.")[1] + "." + startIp.split("\\.")[2] + "."; - String subEnd = endIp.split("\\.")[0] + "." + endIp.split("\\.")[1] + "." + endIp.split("\\.")[2] + "."; - if (Boolean.TRUE.equals(isAll)) { - startIp = subStart + (Integer.parseInt(startIp.split("\\.")[3])); - endIp = subEnd + (Integer.parseInt(endIp.split("\\.")[3])); - } else { - startIp = subStart + (Integer.parseInt(startIp.split("\\.")[3]) + 1); - endIp = subEnd + (Integer.parseInt(endIp.split("\\.")[3]) - 1); - } - list = list(startIp, endIp); + return list; } - return list; + + String startIp = getBeginIpStr(ip, maskBit); + String endIp = getEndIpStr(ip, maskBit); + if (isAll) { + return list(startIp, endIp); + } + + int lastDotIndex = startIp.lastIndexOf(CharUtil.DOT) + 1; + startIp = StrUtil.subPre(startIp, lastDotIndex) + + (Integer.parseInt(Objects.requireNonNull(StrUtil.subSuf(startIp, lastDotIndex))) + 1); + lastDotIndex = endIp.lastIndexOf(CharUtil.DOT) + 1; + endIp = StrUtil.subPre(endIp, lastDotIndex) + + (Integer.parseInt(Objects.requireNonNull(StrUtil.subSuf(endIp, lastDotIndex))) - 1); + return list(startIp, endIp); } /** @@ -102,8 +107,8 @@ public class Ipv4Util { * @return 区间地址 */ public static List list(String ipFrom, String ipTo) { - final int[] ipf = Convert.convert(int[].class, StrUtil.splitToArray(ipFrom, '.')); - final int[] ipt = Convert.convert(int[].class, StrUtil.splitToArray(ipTo, '.')); + final int[] ipf = Convert.convert(int[].class, StrUtil.splitToArray(ipFrom, CharUtil.DOT)); + final int[] ipt = Convert.convert(int[].class, StrUtil.splitToArray(ipTo, CharUtil.DOT)); final List ips = new ArrayList<>(); for (int a = ipf[0]; a <= ipt[0]; a++) { @@ -130,14 +135,14 @@ public class Ipv4Util { public static String longToIpv4(long longIP) { final StringBuilder sb = StrUtil.builder(); // 直接右移24位 - sb.append((longIP >>> 24)); - sb.append("."); + sb.append(longIP >> 24 & 0xFF); + sb.append(CharUtil.DOT); // 将高8位置0,然后右移16位 - sb.append(((longIP & 0x00FFFFFF) >>> 16)); - sb.append("."); - sb.append(((longIP & 0x0000FFFF) >>> 8)); - sb.append("."); - sb.append((longIP & 0x000000FF)); + sb.append(longIP >> 16 & 0xFF); + sb.append(CharUtil.DOT); + sb.append(longIP >> 8 & 0xFF); + sb.append(CharUtil.DOT); + sb.append(longIP & 0xFF); return sb.toString(); } @@ -148,20 +153,9 @@ public class Ipv4Util { * @return long值 */ public static long ipv4ToLong(String strIP) { - if (Validator.isIpv4(strIP)) { - long[] ip = new long[4]; - // 先找到IP地址字符串中.的位置 - int position1 = strIP.indexOf("."); - int position2 = strIP.indexOf(".", position1 + 1); - int position3 = strIP.indexOf(".", position2 + 1); - // 将每个.之间的字符串转换成整型 - ip[0] = Long.parseLong(strIP.substring(0, position1)); - ip[1] = Long.parseLong(strIP.substring(position1 + 1, position2)); - ip[2] = Long.parseLong(strIP.substring(position2 + 1, position3)); - ip[3] = Long.parseLong(strIP.substring(position3 + 1)); - return (ip[0] << 24) + (ip[1] << 16) + (ip[2] << 8) + ip[3]; - } - return 0; + Validator.validateIpv4(strIP, "Invalid IPv4 address!"); + final long[] ip = Convert.convert(long[].class, StrUtil.split(strIP, CharUtil.DOT)); + return (ip[0] << 24) + (ip[1] << 16) + (ip[2] << 8) + ip[3]; } /** @@ -208,8 +202,8 @@ public class Ipv4Util { String str; int inetmask = 0; int count; - for (String s : StrUtil.split(mask, ',')) { - sbf = toBin(Integer.parseInt(s)); + for (String part : StrUtil.split(mask, CharUtil.DOT)) { + sbf = toBin(Integer.parseInt(part)); str = sbf.reverse().toString(); count = 0; for (int i = 0; i < str.length(); i++) { @@ -233,15 +227,12 @@ public class Ipv4Util { */ public static int countByMaskBit(int maskBit, boolean isAll) { //如果是可用地址的情况,掩码位小于等于0或大于等于32,则可用地址为0 - boolean isZero = !isAll && (maskBit <= 0 || maskBit >= 32); - if (isZero) { + if ((false == isAll) && (maskBit <= 0 || maskBit >= 32)) { return 0; } - if (isAll) { - return (int) Math.pow(2, 32 - maskBit); - } else { - return (int) Math.pow(2, 32 - maskBit) - 2; - } + + final int count = (int) Math.pow(2, 32 - maskBit); + return isAll ? count : count - 2; } /** @@ -264,14 +255,13 @@ public class Ipv4Util { public static String getMaskByIpRange(String fromIp, String toIp) { long toIpLong = ipv4ToLong(toIp); long fromIpLong = ipv4ToLong(fromIp); - if (fromIpLong > toIpLong) { - throw new IllegalArgumentException("to IP must be greater than from IP!"); - } - String[] fromIpSplit = StrUtil.splitToArray(fromIp, '.'); - String[] toIpSplit = StrUtil.splitToArray(toIp, '.'); + Assert.isTrue(fromIpLong < toIpLong, "to IP must be greater than from IP!"); + + String[] fromIpSplit = StrUtil.splitToArray(fromIp, CharUtil.DOT); + String[] toIpSplit = StrUtil.splitToArray(toIp, CharUtil.DOT); StringBuilder mask = new StringBuilder(); for (int i = 0; i < toIpSplit.length; i++) { - mask.append(255 - Integer.parseInt(toIpSplit[i]) + Integer.parseInt(fromIpSplit[i])).append("."); + mask.append(255 - Integer.parseInt(toIpSplit[i]) + Integer.parseInt(fromIpSplit[i])).append(CharUtil.DOT); } return mask.substring(0, mask.length() - 1); } @@ -290,8 +280,8 @@ public class Ipv4Util { throw new IllegalArgumentException("to IP must be greater than from IP!"); } int count = 1; - int[] fromIpSplit = StrUtil.split(fromIp, '.').stream().mapToInt(Integer::parseInt).toArray(); - int[] toIpSplit = StrUtil.split(toIp, '.').stream().mapToInt(Integer::parseInt).toArray(); + int[] fromIpSplit = StrUtil.split(fromIp, CharUtil.DOT).stream().mapToInt(Integer::parseInt).toArray(); + int[] toIpSplit = StrUtil.split(toIp, CharUtil.DOT).stream().mapToInt(Integer::parseInt).toArray(); for (int i = fromIpSplit.length - 1; i >= 0; i--) { count += (toIpSplit[i] - fromIpSplit[i]) * Math.pow(256, fromIpSplit.length - i - 1); } diff --git a/hutool-core/src/main/java/cn/hutool/core/util/ClassUtil.java b/hutool-core/src/main/java/cn/hutool/core/util/ClassUtil.java index 4b3fa4717..d2eb6eca3 100644 --- a/hutool-core/src/main/java/cn/hutool/core/util/ClassUtil.java +++ b/hutool-core/src/main/java/cn/hutool/core/util/ClassUtil.java @@ -950,10 +950,7 @@ public class ClassUtil { */ public static Class getTypeArgument(Class clazz, int index) { final Type argumentType = TypeUtil.getTypeArgument(clazz, index); - if (argumentType instanceof Class) { - return (Class) argumentType; - } - return null; + return TypeUtil.getClass(argumentType); } /** diff --git a/hutool-core/src/main/java/cn/hutool/core/util/StrUtil.java b/hutool-core/src/main/java/cn/hutool/core/util/StrUtil.java index e7bfad1c8..891a41ca6 100644 --- a/hutool-core/src/main/java/cn/hutool/core/util/StrUtil.java +++ b/hutool-core/src/main/java/cn/hutool/core/util/StrUtil.java @@ -1972,45 +1972,45 @@ public class StrUtil { * abcdefgh 2 -3 =》 cde
* * @param str String - * @param fromIndex 开始的index(包括) - * @param toIndex 结束的index(不包括) + * @param fromIndexInclude 开始的index(包括) + * @param toIndexExclude 结束的index(不包括) * @return 字串 */ - public static String sub(CharSequence str, int fromIndex, int toIndex) { + public static String sub(CharSequence str, int fromIndexInclude, int toIndexExclude) { if (isEmpty(str)) { return str(str); } int len = str.length(); - if (fromIndex < 0) { - fromIndex = len + fromIndex; - if (fromIndex < 0) { - fromIndex = 0; + if (fromIndexInclude < 0) { + fromIndexInclude = len + fromIndexInclude; + if (fromIndexInclude < 0) { + fromIndexInclude = 0; } - } else if (fromIndex > len) { - fromIndex = len; + } else if (fromIndexInclude > len) { + fromIndexInclude = len; } - if (toIndex < 0) { - toIndex = len + toIndex; - if (toIndex < 0) { - toIndex = len; + if (toIndexExclude < 0) { + toIndexExclude = len + toIndexExclude; + if (toIndexExclude < 0) { + toIndexExclude = len; } - } else if (toIndex > len) { - toIndex = len; + } else if (toIndexExclude > len) { + toIndexExclude = len; } - if (toIndex < fromIndex) { - int tmp = fromIndex; - fromIndex = toIndex; - toIndex = tmp; + if (toIndexExclude < fromIndexInclude) { + int tmp = fromIndexInclude; + fromIndexInclude = toIndexExclude; + toIndexExclude = tmp; } - if (fromIndex == toIndex) { + if (fromIndexInclude == toIndexExclude) { return EMPTY; } - return str.toString().substring(fromIndex, toIndex); + return str.toString().substring(fromIndexInclude, toIndexExclude); } /** @@ -2095,11 +2095,11 @@ public class StrUtil { * 切割指定位置之前部分的字符串 * * @param string 字符串 - * @param toIndex 切割到的位置(不包括) + * @param toIndexExclude 切割到的位置(不包括) * @return 切割后的剩余的前半部分字符串 */ - public static String subPre(CharSequence string, int toIndex) { - return sub(string, 0, toIndex); + public static String subPre(CharSequence string, int toIndexExclude) { + return sub(string, 0, toIndexExclude); } /** diff --git a/hutool-core/src/test/java/cn/hutool/core/convert/ConvertTest.java b/hutool-core/src/test/java/cn/hutool/core/convert/ConvertTest.java index 43d5bd5f6..c55dcf783 100644 --- a/hutool-core/src/test/java/cn/hutool/core/convert/ConvertTest.java +++ b/hutool-core/src/test/java/cn/hutool/core/convert/ConvertTest.java @@ -238,6 +238,12 @@ public class ConvertTest { Assert.assertEquals("[1, 2]", atomicLongArray.toString()); } + @Test + public void toClassTest(){ + final Class convert = Convert.convert(Class.class, "cn.hutool.core.convert.ConvertTest.Product"); + Assert.assertEquals(Product.class, convert); + } + @Data @AllArgsConstructor public static class Product implements Serializable { diff --git a/hutool-core/src/test/java/cn/hutool/core/net/Ipv4UtilTest.java b/hutool-core/src/test/java/cn/hutool/core/net/Ipv4UtilTest.java new file mode 100644 index 000000000..7f4a7574b --- /dev/null +++ b/hutool-core/src/test/java/cn/hutool/core/net/Ipv4UtilTest.java @@ -0,0 +1,45 @@ +package cn.hutool.core.net; + +import cn.hutool.core.lang.Console; +import org.junit.Assert; +import org.junit.Test; + +import java.util.List; + +public class Ipv4UtilTest { + + @Test + public void getMaskBitByMaskTest(){ + final int maskBitByMask = Ipv4Util.getMaskBitByMask("255.255.255.0"); + Assert.assertEquals(24, maskBitByMask); + } + + @Test + public void getMaskByMaskBitTest(){ + final String mask = Ipv4Util.getMaskByMaskBit(24); + Assert.assertEquals("255.255.255.0", mask); + } + + @Test + public void longToIpTest() { + String ip = "192.168.1.255"; + final long ipLong = Ipv4Util.ipv4ToLong(ip); + String ipv4 = Ipv4Util.longToIpv4(ipLong); + Assert.assertEquals(ip, ipv4); + } + + @Test + public void getEndIpStrTest(){ + String ip = "192.168.1.1"; + final int maskBitByMask = Ipv4Util.getMaskBitByMask("255.255.255.0"); + final String endIpStr = Ipv4Util.getEndIpStr(ip, maskBitByMask); + Console.log(endIpStr); + } + + @Test + public void listTest(){ + int maskBit = Ipv4Util.getMaskBitByMask("255.255.255.0"); + final List list = Ipv4Util.list("192.168.100.2", maskBit, false); + Assert.assertEquals(254, list.size()); + } +}