完善工具类

This commit is contained in:
卢春梦 2024-03-09 15:45:00 +08:00
parent 54af570642
commit 55b092665b
3 changed files with 738 additions and 12 deletions

View File

@ -21,16 +21,51 @@ package org.springblade.core.tool.utils;
* @author L.cm * @author L.cm
*/ */
public interface CharPool { public interface CharPool {
// @formatter:off
char UPPER_A = 'A'; char UPPER_A = 'A';
char LOWER_A = 'a'; char LOWER_A = 'a';
char UPPER_Z = 'Z'; char UPPER_Z = 'Z';
char LOWER_Z = 'z'; char LOWER_Z = 'z';
char DOT = '.'; char DOT = '.';
char AT = '@'; char AT = '@';
char LEFT_BRACE = '{'; char LEFT_BRACE = '{';
char RIGHT_BRACE = '}'; char RIGHT_BRACE = '}';
char LEFT_BRACKET = '('; char LEFT_BRACKET = '(';
char RIGHT_BRACKET = ')'; char RIGHT_BRACKET = ')';
char DASH = '-';
char PERCENT = '%';
char PIPE = '|';
char PLUS = '+';
char QUESTION_MARK = '?';
char EXCLAMATION_MARK = '!';
char EQUALS = '=';
char AMPERSAND = '&';
char ASTERISK = '*';
char STAR = ASTERISK;
char BACK_SLASH = '\\';
char COLON = ':';
char COMMA = ',';
char DOLLAR = '$';
char SLASH = '/';
char HASH = '#';
char HAT = '^';
char LEFT_CHEV = '<';
char NEWLINE = '\n';
char N = 'n';
char Y = 'y';
char QUOTE = '\"';
char RETURN = '\r';
char TAB = '\t';
char RIGHT_CHEV = '>';
char SEMICOLON = ';';
char SINGLE_QUOTE = '\'';
char BACKTICK = '`';
char SPACE = ' ';
char TILDA = '~';
char LEFT_SQ_BRACKET = '[';
char RIGHT_SQ_BRACKET = ']';
char UNDERSCORE = '_';
char ONE = '1';
char ZERO = '0';
// @formatter:on
} }

View File

@ -0,0 +1,295 @@
/**
* Copyright (c) 2018-2028, DreamLu 卢春梦 (qq596392912@gmail.com).
* <p>
* Licensed under the GNU LESSER GENERAL PUBLIC LICENSE 3.0;
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
* <p>
* http://www.gnu.org/licenses/lgpl.html
* <p>
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.springblade.core.tool.utils;
import org.springframework.lang.Nullable;
import org.springframework.util.StringUtils;
import java.util.Arrays;
/**
* 脱敏工具类
*
* @author Katrel同事
* @author L.cm
*/
public class DesensitizationUtil {
/**
* [中文姓名] 只显示第一个汉字其他隐藏为2个星号<例子**>
*
* @param fullName 全名
* @return 脱敏后的字符串
*/
@Nullable
public static String chineseName(@Nullable final String fullName) {
return sensitive(fullName, 1, 0);
}
/**
* [身份证号] 显示最后四位其他隐藏共计18位或者15位<例子*************5762>
*
* @param id 身份证号
* @return 脱敏后的字符串
*/
@Nullable
public static String idCardNum(@Nullable final String id) {
return sensitive(id, 0, 4);
}
/**
* [固定电话] 后四位其他隐藏<例子****1234>
*
* @param num 固定电话号
* @return 脱敏后的字符串
*/
@Nullable
public static String phoneNo(@Nullable final String num) {
return sensitive(num, 0, 4);
}
/**
* [手机号码] 前三位后四位其他隐藏<例子:138****1234>
*
* @param num 手机号
* @return 脱敏后的字符串
*/
@Nullable
public static String mobileNo(@Nullable final String num) {
return sensitive(num, 3, 4);
}
/**
* [地址] 只显示到地区不显示详细地址我们要对个人信息增强保护<例子北京市海淀区****>
*
* @param address 地区
* @param sensitiveSize 敏感信息长度
* @return 脱敏后的字符串
*/
@Nullable
public static String address(@Nullable final String address, final int sensitiveSize) {
return sensitive(address, 0, sensitiveSize);
}
/**
* [电子邮箱] 邮箱前缀仅显示第一个字母前缀其他隐藏用星号代替@及后面的地址显示<例子:g**@163.com>
*
* @param email 邮箱
* @return 脱敏后的字符串
*/
@Nullable
public static String email(@Nullable final String email) {
if (email == null) {
return null;
}
if (!StringUtils.hasText(email)) {
return StringPool.EMPTY;
}
final int index = email.indexOf(CharPool.AT);
if (index <= 1) {
return email;
} else {
return sensitive(email, 1, email.length() - index);
}
}
/**
* [银行卡号] 前六位后四位其他用星号隐藏每位1个星号<例子:622260***********1234>
*
* @param cardNum 银行卡号
* @return 脱敏后的字符串
*/
@Nullable
public static String bankCard(@Nullable final String cardNum) {
return sensitive(cardNum, 6, 4);
}
/**
* [公司开户银行联号] 公司开户银行联行号,显示前两位其他用星号隐藏每位1个星号<例子:12********>
*
* @param code 银行联行号
* @return 脱敏后的字符串
*/
@Nullable
public static String cnApsCode(@Nullable final String code) {
return sensitive(code, 2, 0);
}
/**
* 右边脱敏
*
* @param sensitiveStr 待脱敏的字符串
* @return 脱敏后的字符串
*/
@Nullable
public static String right(@Nullable final String sensitiveStr) {
if (sensitiveStr == null) {
return null;
}
if (!StringUtils.hasText(sensitiveStr)) {
return StringPool.EMPTY;
}
int length = sensitiveStr.length();
return sensitive(sensitiveStr, length / 2, 0);
}
/**
* 左边脱敏
*
* @param sensitiveStr 待脱敏的字符串
* @return 脱敏后的字符串
*/
@Nullable
public static String left(@Nullable final String sensitiveStr) {
if (sensitiveStr == null) {
return null;
}
if (!StringUtils.hasText(sensitiveStr)) {
return StringPool.EMPTY;
}
int length = sensitiveStr.length();
return sensitive(sensitiveStr, 0, length / 2);
}
/**
* 中间脱敏保留两端
*
* @param sensitiveStr 待脱敏的字符串
* @return 脱敏后的字符串
*/
@Nullable
public static String middle(@Nullable final String sensitiveStr) {
if (sensitiveStr == null) {
return null;
}
if (!StringUtils.hasText(sensitiveStr)) {
return StringPool.EMPTY;
}
int length = sensitiveStr.length();
if (length < 3) {
return StringUtil.leftPad(StringPool.EMPTY, length, CharPool.STAR);
} else if (length < 6) {
// 小于6个字符脱敏中间
char[] chars = new char[length];
int last = length - 1;
Arrays.fill(chars, 1, last, CharPool.STAR);
chars[0] = sensitiveStr.charAt(0);
chars[last] = sensitiveStr.charAt(last);
return new String(chars);
} else {
// 大于6个字符
int fromLastLen = length / 3;
return sensitive(sensitiveStr, fromLastLen, fromLastLen);
}
}
/**
* 全部脱敏
*
* @param sensitiveStr 待脱敏的字符串
* @return 脱敏后的字符串
*/
@Nullable
public static String all(@Nullable final String sensitiveStr) {
return sensitive(sensitiveStr, 0, 0);
}
/**
* 文本脱敏
*
* @param str 字符串
* @param fromIndex 开始的索引
* @param lastSize 尾部长度
* @return 脱敏后的字符串
*/
@Nullable
public static String sensitive(@Nullable String str, int fromIndex, int lastSize) {
return sensitive(str, fromIndex, lastSize, CharPool.STAR);
}
/**
* 文本脱敏
*
* @param str 字符串
* @param fromIndex 开始的索引
* @param lastSize 尾部长度
* @param padSize 填充的长度
* @return 脱敏后的字符串
*/
@Nullable
public static String sensitive(@Nullable String str, int fromIndex, int lastSize, int padSize) {
return sensitive(str, fromIndex, lastSize, CharPool.STAR, padSize);
}
/**
* 文本脱敏
*
* @param str 字符串
* @param fromIndex 开始的索引
* @param lastSize 尾部长度
* @param padChar 填充的字符
* @return 脱敏后的字符串
*/
@Nullable
public static String sensitive(@Nullable String str, int fromIndex, int lastSize, char padChar) {
return sensitive(str, fromIndex, lastSize, padChar, -1);
}
/**
* 文本脱敏
*
* @param str 字符串
* @param fromIndex 开始的索引
* @param lastSize 尾部长度
* @param padChar 填充的字符
* @param padSize 填充的长度
* @return 脱敏后的字符串
*/
@Nullable
public static String sensitive(@Nullable String str, int fromIndex, int lastSize, char padChar, int padSize) {
if (str == null) {
return null;
}
if (!StringUtils.hasText(str)) {
return StringPool.EMPTY;
}
int length = str.length();
// 全部脱敏
if (fromIndex == 0 && lastSize == 0) {
int padSiz = padSize > 0 ? padSize : length;
return StringUtil.repeat(CharPool.STAR, padSiz);
}
int toIndex = length - lastSize;
int padSiz = padSize > 0 ? padSize : toIndex - fromIndex;
// 头部脱敏
if (fromIndex == 0) {
String tail = str.substring(toIndex);
return StringUtil.repeat(padChar, padSiz).concat(tail);
}
// 尾部脱敏
if (toIndex == length) {
String head = str.substring(0, fromIndex);
return head.concat(StringUtil.repeat(padChar, padSiz));
}
// 中部
String head = str.substring(0, fromIndex);
String tail = str.substring(toIndex);
return head + StringUtil.repeat(padChar, padSiz) + tail;
}
}

View File

@ -19,6 +19,7 @@ import org.springblade.core.tool.support.StrFormatter;
import org.springblade.core.tool.support.StrSpliter; import org.springblade.core.tool.support.StrSpliter;
import org.springframework.lang.Nullable; import org.springframework.lang.Nullable;
import org.springframework.util.Assert; import org.springframework.util.Assert;
import org.springframework.util.StringUtils;
import org.springframework.web.util.HtmlUtils; import org.springframework.web.util.HtmlUtils;
import java.io.StringReader; import java.io.StringReader;
@ -36,6 +37,10 @@ import java.util.stream.Stream;
public class StringUtil extends org.springframework.util.StringUtils { public class StringUtil extends org.springframework.util.StringUtils {
public static final int INDEX_NOT_FOUND = -1; public static final int INDEX_NOT_FOUND = -1;
/**
* <p>The maximum size to which the padding constant(s) can expand.</p>
*/
private static final int PAD_LIMIT = 8192;
/** /**
* Check whether the given {@code CharSequence} contains actual <em>text</em>. * Check whether the given {@code CharSequence} contains actual <em>text</em>.
@ -1473,5 +1478,396 @@ public class StringUtil extends org.springframework.util.StringUtils {
} }
/**
* 参考自 commons lang 微调
*
* <p>Returns padding using the specified delimiter repeated
* to a given length.</p>
*
* <pre>
* StringUtils.repeat('e', 0) = ""
* StringUtils.repeat('e', 3) = "eee"
* StringUtils.repeat('e', -2) = ""
* </pre>
*
* <p>Note: this method does not support padding with
* <a href="http://www.unicode.org/glossary/#supplementary_character">Unicode Supplementary Characters</a>
* as they require a pair of {@code char}s to be represented.
* </p>
*
* @param ch character to repeat
* @param repeat number of times to repeat char, negative treated as zero
* @return String with repeated character
*/
public static String repeat(final char ch, final int repeat) {
if (repeat <= 0) {
return StringPool.EMPTY;
}
final char[] buf = new char[repeat];
Arrays.fill(buf, ch);
return new String(buf);
}
/**
* 参考自 commons lang 微调
*
* <p>Gets the leftmost {@code len} characters of a String.</p>
*
* <p>If {@code len} characters are not available, or the
* String is {@code null}, the String will be returned without
* an exception. An empty String is returned if len is negative.</p>
*
* <pre>
* StringUtils.left(null, *) = null
* StringUtils.left(*, -ve) = ""
* StringUtils.left("", *) = ""
* StringUtils.left("abc", 0) = ""
* StringUtils.left("abc", 2) = "ab"
* StringUtils.left("abc", 4) = "abc"
* </pre>
*
* @param str the CharSequence to get the leftmost characters from, may be null
* @param len the length of the required String
* @return the leftmost characters, {@code null} if null String input
*/
@Nullable
public static String left(@Nullable final String str, final int len) {
if (str == null) {
return null;
}
if (len < 0) {
return StringPool.EMPTY;
}
if (str.length() <= len) {
return str;
}
return str.substring(0, len);
}
/**
* 参考自 commons lang 微调
*
* <p>Gets the rightmost {@code len} characters of a String.</p>
*
* <p>If {@code len} characters are not available, or the String
* is {@code null}, the String will be returned without an
* an exception. An empty String is returned if len is negative.</p>
*
* <pre>
* StringUtils.right(null, *) = null
* StringUtils.right(*, -ve) = ""
* StringUtils.right("", *) = ""
* StringUtils.right("abc", 0) = ""
* StringUtils.right("abc", 2) = "bc"
* StringUtils.right("abc", 4) = "abc"
* </pre>
*
* @param str the String to get the rightmost characters from, may be null
* @param len the length of the required String
* @return the rightmost characters, {@code null} if null String input
*/
@Nullable
public static String right(@Nullable final String str, final int len) {
if (str == null) {
return null;
}
if (len < 0) {
return StringPool.EMPTY;
}
int length = str.length();
if (length <= len) {
return str;
}
return str.substring(length - len);
}
/**
* 参考自 commons lang 微调
*
* <p>Right pad a String with spaces (' ').</p>
*
* <p>The String is padded to the size of {@code size}.</p>
*
* <pre>
* StringUtils.rightPad(null, *) = null
* StringUtils.rightPad("", 3) = " "
* StringUtils.rightPad("bat", 3) = "bat"
* StringUtils.rightPad("bat", 5) = "bat "
* StringUtils.rightPad("bat", 1) = "bat"
* StringUtils.rightPad("bat", -1) = "bat"
* </pre>
*
* @param str the String to pad out, may be null
* @param size the size to pad to
* @return right padded String or original String if no padding is necessary,
* {@code null} if null String input
*/
@Nullable
public static String rightPad(@Nullable final String str, final int size) {
return rightPad(str, size, CharPool.SPACE);
}
/**
* 参考自 commons lang 微调
*
* <p>Right pad a String with a specified character.</p>
*
* <p>The String is padded to the size of {@code size}.</p>
*
* <pre>
* StringUtils.rightPad(null, *, *) = null
* StringUtils.rightPad("", 3, 'z') = "zzz"
* StringUtils.rightPad("bat", 3, 'z') = "bat"
* StringUtils.rightPad("bat", 5, 'z') = "batzz"
* StringUtils.rightPad("bat", 1, 'z') = "bat"
* StringUtils.rightPad("bat", -1, 'z') = "bat"
* </pre>
*
* @param str the String to pad out, may be null
* @param size the size to pad to
* @param padChar the character to pad with
* @return right padded String or original String if no padding is necessary,
* {@code null} if null String input
*/
@Nullable
public static String rightPad(@Nullable final String str, final int size, final char padChar) {
if (str == null) {
return null;
}
final int pads = size - str.length();
if (pads <= 0) {
// returns original String when possible
return str;
}
if (pads > PAD_LIMIT) {
return rightPad(str, size, String.valueOf(padChar));
}
return str.concat(repeat(padChar, pads));
}
/**
* 参考自 commons lang 微调
*
* <p>Right pad a String with a specified String.</p>
*
* <p>The String is padded to the size of {@code size}.</p>
*
* <pre>
* StringUtils.rightPad(null, *, *) = null
* StringUtils.rightPad("", 3, "z") = "zzz"
* StringUtils.rightPad("bat", 3, "yz") = "bat"
* StringUtils.rightPad("bat", 5, "yz") = "batyz"
* StringUtils.rightPad("bat", 8, "yz") = "batyzyzy"
* StringUtils.rightPad("bat", 1, "yz") = "bat"
* StringUtils.rightPad("bat", -1, "yz") = "bat"
* StringUtils.rightPad("bat", 5, null) = "bat "
* StringUtils.rightPad("bat", 5, "") = "bat "
* </pre>
*
* @param str the String to pad out, may be null
* @param size the size to pad to
* @param padStr the String to pad with, null or empty treated as single space
* @return right padded String or original String if no padding is necessary,
* {@code null} if null String input
*/
@Nullable
public static String rightPad(@Nullable final String str, final int size, String padStr) {
if (str == null) {
return null;
}
if (!StringUtils.hasLength(padStr)) {
padStr = StringPool.SPACE;
}
final int padLen = padStr.length();
final int strLen = str.length();
final int pads = size - strLen;
if (pads <= 0) {
// returns original String when possible
return str;
}
if (padLen == 1 && pads <= PAD_LIMIT) {
return rightPad(str, size, padStr.charAt(0));
}
if (pads == padLen) {
return str.concat(padStr);
} else if (pads < padLen) {
return str.concat(padStr.substring(0, pads));
} else {
final char[] padding = new char[pads];
final char[] padChars = padStr.toCharArray();
for (int i = 0; i < pads; i++) {
padding[i] = padChars[i % padLen];
}
return str.concat(new String(padding));
}
}
/**
* 参考自 commons lang 微调
*
* <p>Left pad a String with spaces (' ').</p>
*
* <p>The String is padded to the size of {@code size}.</p>
*
* <pre>
* StringUtils.leftPad(null, *) = null
* StringUtils.leftPad("", 3) = " "
* StringUtils.leftPad("bat", 3) = "bat"
* StringUtils.leftPad("bat", 5) = " bat"
* StringUtils.leftPad("bat", 1) = "bat"
* StringUtils.leftPad("bat", -1) = "bat"
* </pre>
*
* @param str the String to pad out, may be null
* @param size the size to pad to
* @return left padded String or original String if no padding is necessary,
* {@code null} if null String input
*/
@Nullable
public static String leftPad(@Nullable final String str, final int size) {
return leftPad(str, size, CharPool.SPACE);
}
/**
* 参考自 commons lang 微调
*
* <p>Left pad a String with a specified character.</p>
*
* <p>Pad to a size of {@code size}.</p>
*
* <pre>
* StringUtils.leftPad(null, *, *) = null
* StringUtils.leftPad("", 3, 'z') = "zzz"
* StringUtils.leftPad("bat", 3, 'z') = "bat"
* StringUtils.leftPad("bat", 5, 'z') = "zzbat"
* StringUtils.leftPad("bat", 1, 'z') = "bat"
* StringUtils.leftPad("bat", -1, 'z') = "bat"
* </pre>
*
* @param str the String to pad out, may be null
* @param size the size to pad to
* @param padChar the character to pad with
* @return left padded String or original String if no padding is necessary,
* {@code null} if null String input
* @since 2.0
*/
@Nullable
public static String leftPad(@Nullable final String str, final int size, final char padChar) {
if (str == null) {
return null;
}
final int pads = size - str.length();
if (pads <= 0) {
// returns original String when possible
return str;
}
if (pads > PAD_LIMIT) {
return leftPad(str, size, String.valueOf(padChar));
}
return repeat(padChar, pads).concat(str);
}
/**
* 参考自 commons lang 微调
*
* <p>Left pad a String with a specified String.</p>
*
* <p>Pad to a size of {@code size}.</p>
*
* <pre>
* StringUtils.leftPad(null, *, *) = null
* StringUtils.leftPad("", 3, "z") = "zzz"
* StringUtils.leftPad("bat", 3, "yz") = "bat"
* StringUtils.leftPad("bat", 5, "yz") = "yzbat"
* StringUtils.leftPad("bat", 8, "yz") = "yzyzybat"
* StringUtils.leftPad("bat", 1, "yz") = "bat"
* StringUtils.leftPad("bat", -1, "yz") = "bat"
* StringUtils.leftPad("bat", 5, null) = " bat"
* StringUtils.leftPad("bat", 5, "") = " bat"
* </pre>
*
* @param str the String to pad out, may be null
* @param size the size to pad to
* @param padStr the String to pad with, null or empty treated as single space
* @return left padded String or original String if no padding is necessary,
* {@code null} if null String input
*/
@Nullable
public static String leftPad(@Nullable final String str, final int size, String padStr) {
if (str == null) {
return null;
}
if (!StringUtils.hasLength(padStr)) {
padStr = StringPool.SPACE;
}
final int padLen = padStr.length();
final int strLen = str.length();
final int pads = size - strLen;
if (pads <= 0) {
// returns original String when possible
return str;
}
if (padLen == 1 && pads <= PAD_LIMIT) {
return leftPad(str, size, padStr.charAt(0));
}
if (pads == padLen) {
return padStr.concat(str);
} else if (pads < padLen) {
return padStr.substring(0, pads).concat(str);
} else {
final char[] padding = new char[pads];
final char[] padChars = padStr.toCharArray();
for (int i = 0; i < pads; i++) {
padding[i] = padChars[i % padLen];
}
return new String(padding).concat(str);
}
}
/**
* 参考自 commons lang 微调
*
* <p>Gets {@code len} characters from the middle of a String.</p>
*
* <p>If {@code len} characters are not available, the remainder
* of the String will be returned without an exception. If the
* String is {@code null}, {@code null} will be returned.
* An empty String is returned if len is negative or exceeds the
* length of {@code str}.</p>
*
* <pre>
* StringUtils.mid(null, *, *) = null
* StringUtils.mid(*, *, -ve) = ""
* StringUtils.mid("", 0, *) = ""
* StringUtils.mid("abc", 0, 2) = "ab"
* StringUtils.mid("abc", 0, 4) = "abc"
* StringUtils.mid("abc", 2, 4) = "c"
* StringUtils.mid("abc", 4, 2) = ""
* StringUtils.mid("abc", -2, 2) = "ab"
* </pre>
*
* @param str the String to get the characters from, may be null
* @param pos the position to start from, negative treated as zero
* @param len the length of the required String
* @return the middle characters, {@code null} if null String input
*/
@Nullable
public static String mid(@Nullable final String str, int pos, final int len) {
if (str == null) {
return null;
}
int length = str.length();
if (len < 0 || pos > length) {
return StringPool.EMPTY;
}
if (pos < 0) {
pos = 0;
}
if (length <= pos + len) {
return str.substring(pos);
}
return str.substring(pos, pos + len);
}
} }