json转换
This commit is contained in:
parent
cd5e7096bb
commit
5d4ea5327d
|
|
@ -0,0 +1,242 @@
|
|||
package com.bonus.canteen.core.config;
|
||||
|
||||
import cn.hutool.core.util.ArrayUtil;
|
||||
import com.fasterxml.jackson.annotation.JsonIgnore;
|
||||
import com.fasterxml.jackson.annotation.JsonIgnoreProperties;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import com.google.common.collect.Lists;
|
||||
import com.google.common.collect.Maps;
|
||||
import org.apache.commons.lang3.StringUtils;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
import org.springframework.data.redis.core.StringRedisTemplate;
|
||||
import org.springframework.data.redis.core.script.DefaultRedisScript;
|
||||
|
||||
import java.time.Instant;
|
||||
import java.util.Map;
|
||||
import java.util.Optional;
|
||||
import java.util.UUID;
|
||||
|
||||
@JsonIgnoreProperties(
|
||||
ignoreUnknown = true
|
||||
)
|
||||
public class AccessToken {
|
||||
private static final Logger log = LoggerFactory.getLogger(AccessToken.class);
|
||||
@JsonIgnore
|
||||
protected static ObjectMapper objectMapper;
|
||||
@JsonIgnore
|
||||
protected static SecureProperties secureProperties;
|
||||
@JsonIgnore
|
||||
protected static StringRedisTemplate redisTemplate;
|
||||
@JsonIgnore
|
||||
protected static AuthenticationPredicate authenticationPredicate;
|
||||
private String id;
|
||||
private Long subjectId;
|
||||
private String subjectName;
|
||||
private Map<String, String> subjectData = Maps.newHashMap();
|
||||
private String scope;
|
||||
private boolean identified;
|
||||
private long createTime;
|
||||
private long lastTime;
|
||||
|
||||
public static Optional<AccessToken> recovery(String clientToken) {
|
||||
StringRedisTemplate var10000 = redisTemplate;
|
||||
String var10001 = secureProperties.getServer().getStoreKey();
|
||||
clientToken = (String)var10000.boundValueOps(var10001 + ":" + clientToken).get();
|
||||
if (StringUtils.isBlank(clientToken)) {
|
||||
return Optional.empty();
|
||||
} else {
|
||||
try {
|
||||
AccessToken existToken = (AccessToken)objectMapper.readValue(clientToken, AccessToken.class);
|
||||
return authenticationPredicate.authenticated(existToken) ? Optional.of(existToken) : Optional.empty();
|
||||
} catch (Exception var2) {
|
||||
log.error("Deserialize exist token error", var2);
|
||||
return Optional.empty();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
public static AccessToken create(long subjectId) {
|
||||
AccessToken accessToken = create();
|
||||
accessToken.setSubjectId(subjectId);
|
||||
return accessToken;
|
||||
}
|
||||
|
||||
public static AccessToken create(long subjectId, String subjectName) {
|
||||
AccessToken accessToken = create(subjectId);
|
||||
accessToken.setSubjectName(subjectName);
|
||||
return accessToken;
|
||||
}
|
||||
|
||||
public static AccessToken create() {
|
||||
AccessToken accessToken = new AccessToken();
|
||||
accessToken.setId(UUID.randomUUID().toString());
|
||||
accessToken.setCreateTime(Instant.now().getEpochSecond());
|
||||
accessToken.setLastTime(Instant.now().getEpochSecond());
|
||||
return accessToken;
|
||||
}
|
||||
|
||||
public AccessToken touch() {
|
||||
this.identified = this.isAuthenticated();
|
||||
this.lastTime = Instant.now().getEpochSecond();
|
||||
return this.store();
|
||||
}
|
||||
|
||||
@JsonIgnore
|
||||
public boolean isAuthenticated() {
|
||||
return this.identified && !this.isExpired();
|
||||
}
|
||||
|
||||
@JsonIgnore
|
||||
private boolean isExpired() {
|
||||
return this.lastTime + secureProperties.getExpireAfter() < Instant.now().getEpochSecond();
|
||||
}
|
||||
|
||||
public AccessToken withData(Map<String, String> data) {
|
||||
this.subjectData = data;
|
||||
return this;
|
||||
}
|
||||
|
||||
public AccessToken setData(String name, String value) {
|
||||
this.subjectData.put(name, value);
|
||||
return this;
|
||||
}
|
||||
|
||||
public AccessToken removeData(String... keys) {
|
||||
if (ArrayUtil.isEmpty(keys)) {
|
||||
return this;
|
||||
} else {
|
||||
String[] var2 = keys;
|
||||
int var3 = keys.length;
|
||||
|
||||
for(int var4 = 0; var4 < var3; ++var4) {
|
||||
String key = var2[var4];
|
||||
this.subjectData.remove(key);
|
||||
}
|
||||
|
||||
return this;
|
||||
}
|
||||
}
|
||||
|
||||
public AccessToken revokeAuthenticate() {
|
||||
this.identified = false;
|
||||
return this.store();
|
||||
}
|
||||
|
||||
public AccessToken authenticate() {
|
||||
if (this.subjectId == null) {
|
||||
throw new RuntimeException("required subjectId is not provide");
|
||||
} else {
|
||||
this.identified = true;
|
||||
return this;
|
||||
}
|
||||
}
|
||||
|
||||
public AccessToken store() {
|
||||
try {
|
||||
StringRedisTemplate var10000 = redisTemplate;
|
||||
DefaultRedisScript var10001 = new DefaultRedisScript("redis.call('SET',KEYS[1],ARGV[1],'EX',ARGV[3]);redis.call('SET',KEYS[2],ARGV[2],'EX',ARGV[3]);");
|
||||
String[] var10002 = new String[2];
|
||||
String var10005 = secureProperties.getServer().getStoreKey();
|
||||
var10002[0] = var10005 + ":" + this.getId();
|
||||
var10005 = secureProperties.getServer().getSubjectRefTokenKey();
|
||||
var10002[1] = var10005 + ":" + this.getSubjectId() + ":" + this.getId() + ":" + this.getCreateTime();
|
||||
var10000.execute(var10001, Lists.newArrayList(var10002), new Object[]{objectMapper.writeValueAsString(this), this.getId(), String.valueOf(secureProperties.getServer().getTtl())});
|
||||
} catch (Exception var2) {
|
||||
log.error("Token store error", var2);
|
||||
}
|
||||
|
||||
return this;
|
||||
}
|
||||
|
||||
public AccessToken bind() {
|
||||
WebContext.get().setAccessToken(this);
|
||||
return this;
|
||||
}
|
||||
|
||||
public void write() {
|
||||
WebContext.get().getResponse().ifPresent((response) -> {
|
||||
response.setHeader(secureProperties.getTokenSymbol(), this.getId());
|
||||
});
|
||||
}
|
||||
|
||||
public void clear() {
|
||||
try {
|
||||
StringRedisTemplate var10000 = redisTemplate;
|
||||
DefaultRedisScript var10001 = new DefaultRedisScript("redis.call('DEL',KEYS[1],KEYS[2]);");
|
||||
String[] var10002 = new String[2];
|
||||
String var10005 = secureProperties.getServer().getStoreKey();
|
||||
var10002[0] = var10005 + ":" + this.getId();
|
||||
var10005 = secureProperties.getServer().getSubjectRefTokenKey();
|
||||
var10002[1] = var10005 + ":" + this.getSubjectId() + ":" + this.getId() + ":" + this.getCreateTime();
|
||||
var10000.execute(var10001, Lists.newArrayList(var10002), new Object[0]);
|
||||
} catch (Exception var2) {
|
||||
log.error("Token clear error", var2);
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public String getId() {
|
||||
return this.id;
|
||||
}
|
||||
|
||||
public Long getSubjectId() {
|
||||
return this.subjectId;
|
||||
}
|
||||
|
||||
public String getSubjectName() {
|
||||
return this.subjectName;
|
||||
}
|
||||
|
||||
public Map<String, String> getSubjectData() {
|
||||
return this.subjectData;
|
||||
}
|
||||
|
||||
public String getScope() {
|
||||
return this.scope;
|
||||
}
|
||||
|
||||
public boolean isIdentified() {
|
||||
return this.identified;
|
||||
}
|
||||
|
||||
public long getCreateTime() {
|
||||
return this.createTime;
|
||||
}
|
||||
|
||||
public long getLastTime() {
|
||||
return this.lastTime;
|
||||
}
|
||||
|
||||
public void setId(final String id) {
|
||||
this.id = id;
|
||||
}
|
||||
|
||||
public void setSubjectId(final Long subjectId) {
|
||||
this.subjectId = subjectId;
|
||||
}
|
||||
|
||||
public void setSubjectName(final String subjectName) {
|
||||
this.subjectName = subjectName;
|
||||
}
|
||||
|
||||
public void setSubjectData(final Map<String, String> subjectData) {
|
||||
this.subjectData = subjectData;
|
||||
}
|
||||
|
||||
public void setScope(final String scope) {
|
||||
this.scope = scope;
|
||||
}
|
||||
|
||||
public void setIdentified(final boolean identified) {
|
||||
this.identified = identified;
|
||||
}
|
||||
|
||||
public void setCreateTime(final long createTime) {
|
||||
this.createTime = createTime;
|
||||
}
|
||||
|
||||
public void setLastTime(final long lastTime) {
|
||||
this.lastTime = lastTime;
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
package com.bonus.canteen.core.config;
|
||||
|
||||
public interface AuthenticationPredicate {
|
||||
boolean authenticated(AccessToken accessToken);
|
||||
}
|
||||
|
|
@ -0,0 +1,154 @@
|
|||
package com.bonus.canteen.core.config;//package com.bonus.canteen.core.config;
|
||||
//
|
||||
//import cn.hutool.core.map.MapUtil;
|
||||
//import com.bonus.canteen.core.customer.service.AuthorizingService;
|
||||
//import com.bonus.canteen.core.secure.PmsCache;
|
||||
//import com.fasterxml.jackson.core.JsonProcessingException;
|
||||
//import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
//import com.google.common.collect.Maps;
|
||||
//import com.google.common.collect.Sets;
|
||||
//import org.apache.commons.collections4.CollectionUtils;
|
||||
//import org.apache.commons.collections4.ListUtils;
|
||||
//import org.apache.commons.lang3.BooleanUtils;
|
||||
//import org.slf4j.Logger;
|
||||
//import org.slf4j.LoggerFactory;
|
||||
//import org.springframework.data.redis.core.BoundHashOperations;
|
||||
//import org.springframework.data.redis.core.StringRedisTemplate;
|
||||
//import java.time.Instant;
|
||||
//import java.util.*;
|
||||
//import java.util.function.Function;
|
||||
//import java.util.stream.Collectors;
|
||||
//import java.util.stream.Stream;
|
||||
//
|
||||
//public class SecureManager {
|
||||
// private static final Logger log = LoggerFactory.getLogger(SecureManager.class);
|
||||
// private static SecureProperties secureProperties;
|
||||
// private static StringRedisTemplate redisTemplate;
|
||||
// private static AuthorizingService authorizingService;
|
||||
// private static ObjectMapper objectMapper;
|
||||
//
|
||||
// private SecureManager() {
|
||||
// }
|
||||
//
|
||||
// public static void setSecureProperties(SecureProperties secureProperties) {
|
||||
// if (SecureManager.secureProperties == null) {
|
||||
// SecureManager.secureProperties = secureProperties;
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// public static void setRedisTemplate(StringRedisTemplate redisTemplate) {
|
||||
// if (SecureManager.redisTemplate == null) {
|
||||
// SecureManager.redisTemplate = redisTemplate;
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// public static void setAuthorizingService(AuthorizingService authorizingService) {
|
||||
// if (SecureManager.authorizingService == null) {
|
||||
// SecureManager.authorizingService = authorizingService;
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// public static void setObjectMapper(ObjectMapper objectMapper) {
|
||||
// if (SecureManager.objectMapper == null) {
|
||||
// SecureManager.objectMapper = objectMapper;
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// private static String getPmsKey(long subjectId) {
|
||||
// return "permissions:subject_id:" + subjectId;
|
||||
// }
|
||||
//
|
||||
// private static String getRoleKey(long subjectId) {
|
||||
// return "roles:subject_id:" + subjectId;
|
||||
// }
|
||||
//
|
||||
// public static void clearAllRoleAndPermission() {
|
||||
// redisTemplate.delete(secureProperties.getPermissionKey());
|
||||
// }
|
||||
//
|
||||
// public static void clearRoleAndPermission(long subjectId) {
|
||||
// redisTemplate.boundHashOps(secureProperties.getPermissionKey()).delete(new Object[]{getRoleKey(subjectId), getPmsKey(subjectId)});
|
||||
// }
|
||||
//
|
||||
// public static void clearRole(long subjectId) {
|
||||
// redisTemplate.boundHashOps(secureProperties.getPermissionKey()).delete(new Object[]{getRoleKey(subjectId)});
|
||||
// }
|
||||
//
|
||||
// public static void clearPermission(long subjectId) {
|
||||
// redisTemplate.boundHashOps(secureProperties.getPermissionKey()).delete(new Object[]{getPmsKey(subjectId)});
|
||||
// }
|
||||
//
|
||||
// public static boolean isLogin() {
|
||||
// return (Boolean)WebContext.get().getAccessToken().map(AccessToken::isAuthenticated).orElse(false);
|
||||
// }
|
||||
//
|
||||
// public static Optional<Long> getSubjectId() {
|
||||
// return WebContext.get().getAccessToken().map(AccessToken::getSubjectId);
|
||||
// }
|
||||
//
|
||||
// public static Optional<String> getSubjectName() {
|
||||
// return WebContext.get().getAccessToken().map(AccessToken::getSubjectName);
|
||||
// }
|
||||
//
|
||||
// public static Map<String, String> getSubjectData() {
|
||||
// return (Map)WebContext.get().getAccessToken().map(AccessToken::getSubjectData).orElse(Maps.newHashMap());
|
||||
// }
|
||||
//
|
||||
// public static Map<String, String> attachData(Map<String, String> data) {
|
||||
// try {
|
||||
// if (MapUtil.isEmpty(data)) {
|
||||
// return Maps.newHashMapWithExpectedSize(0);
|
||||
// } else {
|
||||
// AccessToken accessToken = (AccessToken)WebContext.get().getAccessToken().orElse(AccessToken.create());
|
||||
// Objects.requireNonNull(accessToken);
|
||||
// data.forEach(accessToken::setData);
|
||||
// accessToken.bind().store();
|
||||
// return accessToken.getSubjectData();
|
||||
// }
|
||||
// } catch (Throwable var2) {
|
||||
// throw var2;
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// public static Map<String, String> attachData(String key, String value) {
|
||||
// try {
|
||||
// return attachData(Collections.singletonMap(key, value));
|
||||
// } catch (Throwable var3) {
|
||||
// throw var3;
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// public static void logout() {
|
||||
// WebContext.get().getAccessToken().ifPresent(AccessToken::clear);
|
||||
// }
|
||||
//
|
||||
// public static void revokeAuthenticate() {
|
||||
// WebContext.get().getAccessToken().ifPresent((accessToken) -> {
|
||||
// accessToken.revokeAuthenticate().store();
|
||||
// });
|
||||
// }
|
||||
//
|
||||
// public static void revokeAuthenticate(long subjectId, int reservedRecentNum) {
|
||||
// StringRedisTemplate var10000 = redisTemplate;
|
||||
// String var10001 = secureProperties.getServer().getSubjectRefTokenKey();
|
||||
// Set<String> keys = var10000.keys(var10001 + ":" + subjectId + ":*");
|
||||
// if (CollectionUtils.size(keys) > reservedRecentNum) {
|
||||
// assert keys != null;
|
||||
//
|
||||
// Map<Long, List<String>> createTimeAsc_keys = (Map)keys.stream().collect(Collectors.groupingBy((key) -> {
|
||||
// return Long.parseLong(key.split(":")[4]);
|
||||
// }, TreeMap::new, Collectors.toList()));
|
||||
// List<String> keysAsc = createTimeAsc_keys.values().stream().flatMap(Collection::stream).collect(Collectors.toList());
|
||||
// List<String> beDeleteRefKeys = keysAsc.subList(0, keysAsc.size() - reservedRecentNum);
|
||||
// List<String> beDeleteTokenKeys = beDeleteRefKeys.stream().map((dk) -> {
|
||||
// String var100001 = secureProperties.getServer().getStoreKey();
|
||||
// return var100001 + ":" + dk.split(":")[3];
|
||||
// }).collect(Collectors.toList());
|
||||
// redisTemplate.delete(ListUtils.sum(beDeleteRefKeys, beDeleteTokenKeys));
|
||||
// }
|
||||
// }
|
||||
//
|
||||
// public String toString() {
|
||||
// return "SecureManager()";
|
||||
// }
|
||||
//}
|
||||
|
|
@ -0,0 +1,367 @@
|
|||
package com.bonus.canteen.core.config;
|
||||
|
||||
import cn.hutool.core.codec.Base64Decoder;
|
||||
import com.google.common.collect.Sets;
|
||||
import org.springframework.boot.context.properties.ConfigurationProperties;
|
||||
import org.springframework.cloud.context.config.annotation.RefreshScope;
|
||||
import org.springframework.stereotype.Component;
|
||||
|
||||
import java.util.Set;
|
||||
|
||||
@RefreshScope
|
||||
@Component
|
||||
@ConfigurationProperties(
|
||||
prefix = "secure"
|
||||
)
|
||||
public class SecureProperties {
|
||||
public static final String PREFIX = "secure";
|
||||
private boolean enabled = true;
|
||||
private boolean prohibitUnannotatedHandler = false;
|
||||
private String tokenSymbol = "X-Token";
|
||||
private String permissionKey = "secure:pms";
|
||||
private long permissionTTL = 7200L;
|
||||
private long expireAfter = 7200L;
|
||||
private ServerStore server = new ServerStore();
|
||||
private Security security = new Security();
|
||||
private MdcLogParameter mdc = new MdcLogParameter();
|
||||
|
||||
public boolean isEnabled() {
|
||||
return this.enabled;
|
||||
}
|
||||
|
||||
public boolean isProhibitUnannotatedHandler() {
|
||||
return this.prohibitUnannotatedHandler;
|
||||
}
|
||||
|
||||
public String getTokenSymbol() {
|
||||
return this.tokenSymbol;
|
||||
}
|
||||
|
||||
public String getPermissionKey() {
|
||||
return this.permissionKey;
|
||||
}
|
||||
|
||||
public long getPermissionTTL() {
|
||||
return this.permissionTTL;
|
||||
}
|
||||
|
||||
public long getExpireAfter() {
|
||||
return this.expireAfter;
|
||||
}
|
||||
|
||||
public ServerStore getServer() {
|
||||
return this.server;
|
||||
}
|
||||
|
||||
public Security getSecurity() {
|
||||
return this.security;
|
||||
}
|
||||
|
||||
public MdcLogParameter getMdc() {
|
||||
return this.mdc;
|
||||
}
|
||||
|
||||
public void setEnabled(final boolean enabled) {
|
||||
this.enabled = enabled;
|
||||
}
|
||||
|
||||
public void setProhibitUnannotatedHandler(final boolean prohibitUnannotatedHandler) {
|
||||
this.prohibitUnannotatedHandler = prohibitUnannotatedHandler;
|
||||
}
|
||||
|
||||
public void setTokenSymbol(final String tokenSymbol) {
|
||||
this.tokenSymbol = tokenSymbol;
|
||||
}
|
||||
|
||||
public void setPermissionKey(final String permissionKey) {
|
||||
this.permissionKey = permissionKey;
|
||||
}
|
||||
|
||||
public void setPermissionTTL(final long permissionTTL) {
|
||||
this.permissionTTL = permissionTTL;
|
||||
}
|
||||
|
||||
public void setExpireAfter(final long expireAfter) {
|
||||
this.expireAfter = expireAfter;
|
||||
}
|
||||
|
||||
public void setServer(final ServerStore server) {
|
||||
this.server = server;
|
||||
}
|
||||
|
||||
public void setSecurity(final Security security) {
|
||||
this.security = security;
|
||||
}
|
||||
|
||||
public void setMdc(final MdcLogParameter mdc) {
|
||||
this.mdc = mdc;
|
||||
}
|
||||
|
||||
public static class ServerStore {
|
||||
private String storeKey = "secure:token";
|
||||
private String subjectRefTokenKey = "secure:subject-token";
|
||||
private long ttl = 14400L;
|
||||
|
||||
public String getStoreKey() {
|
||||
return this.storeKey;
|
||||
}
|
||||
|
||||
public String getSubjectRefTokenKey() {
|
||||
return this.subjectRefTokenKey;
|
||||
}
|
||||
|
||||
public long getTtl() {
|
||||
return this.ttl;
|
||||
}
|
||||
|
||||
public void setStoreKey(final String storeKey) {
|
||||
this.storeKey = storeKey;
|
||||
}
|
||||
|
||||
public void setSubjectRefTokenKey(final String subjectRefTokenKey) {
|
||||
this.subjectRefTokenKey = subjectRefTokenKey;
|
||||
}
|
||||
|
||||
public void setTtl(final long ttl) {
|
||||
this.ttl = ttl;
|
||||
}
|
||||
}
|
||||
|
||||
public static class Security {
|
||||
private String encryptUriPrefix = "/security";
|
||||
private String keyExchangePath = "/exchange/key";
|
||||
private String publicKeyExchangePath = "/exchange/public-key";
|
||||
private Set<String> ignoredUri = Sets.newHashSet();
|
||||
private String requestBodySignParamName = "body";
|
||||
private String clientKeySignParamName = "clientKey";
|
||||
private Set<String> addonSignHeaderPrefix = Sets.newHashSet(new String[]{"X-Security-Ext"});
|
||||
private Set<String> tokenHeaderNames = Sets.newHashSet(new String[]{"X-Security-Token", "X-Security-Tenant-Id", "X-Security-Sn"});
|
||||
private String tokenSignHeaderName = "X-Security-Token-Sign";
|
||||
private String serverKeySignParamName = "serverKey";
|
||||
private String serverSm4Key = "McaCOPft5/J3bUG4pdVjhg==";
|
||||
private byte[] serverSm4KeyBytes;
|
||||
private String serverSm2Key;
|
||||
private byte[] serverSm2KeyBytes;
|
||||
private String clientSm2Key;
|
||||
private byte[] clientSm2KeyBytes;
|
||||
private String timestampHeaderName;
|
||||
private String nonceHeaderName;
|
||||
private String signHeaderName;
|
||||
private String serverEncryptedClientKeyHeaderName;
|
||||
private long maxWindowSeconds;
|
||||
private String playKey;
|
||||
|
||||
public void setServerSm4Key(String serverSm4Key) {
|
||||
this.serverSm4Key = serverSm4Key;
|
||||
this.serverSm4KeyBytes = Base64Decoder.decode(serverSm4Key);
|
||||
}
|
||||
|
||||
public Security() {
|
||||
this.serverSm4KeyBytes = Base64Decoder.decode(this.serverSm4Key);
|
||||
this.serverSm2Key = "D55F4709BE51FCDC71D6385885A5CAEE70A09438F862BEB4E56F64A70C76EF5F";
|
||||
this.serverSm2KeyBytes = Base64Decoder.decode(this.serverSm2Key);
|
||||
this.clientSm2Key = "04768E8E44656FFD4BA58C0270002A28365A5F6B0F6D40E88B9221CDFAAA8E82C8CCEDBA5FC2D03F20B11492EBE90CC04782682AFE326363A503F086C04A14092C";
|
||||
this.clientSm2KeyBytes = Base64Decoder.decode(this.serverSm2Key);
|
||||
this.timestampHeaderName = "X-Security-Timestamp";
|
||||
this.nonceHeaderName = "X-Security-Nonce";
|
||||
this.signHeaderName = "X-Security-Sign";
|
||||
this.serverEncryptedClientKeyHeaderName = "X-Security-Server-Encrypted-Client-Key";
|
||||
this.maxWindowSeconds = 90L;
|
||||
this.playKey = "__play:";
|
||||
}
|
||||
|
||||
public String getEncryptUriPrefix() {
|
||||
return this.encryptUriPrefix;
|
||||
}
|
||||
|
||||
public String getKeyExchangePath() {
|
||||
return this.keyExchangePath;
|
||||
}
|
||||
|
||||
public String getPublicKeyExchangePath() {
|
||||
return this.publicKeyExchangePath;
|
||||
}
|
||||
|
||||
public Set<String> getIgnoredUri() {
|
||||
return this.ignoredUri;
|
||||
}
|
||||
|
||||
public String getRequestBodySignParamName() {
|
||||
return this.requestBodySignParamName;
|
||||
}
|
||||
|
||||
public String getClientKeySignParamName() {
|
||||
return this.clientKeySignParamName;
|
||||
}
|
||||
|
||||
public Set<String> getAddonSignHeaderPrefix() {
|
||||
return this.addonSignHeaderPrefix;
|
||||
}
|
||||
|
||||
public Set<String> getTokenHeaderNames() {
|
||||
return this.tokenHeaderNames;
|
||||
}
|
||||
|
||||
public String getTokenSignHeaderName() {
|
||||
return this.tokenSignHeaderName;
|
||||
}
|
||||
|
||||
public String getServerKeySignParamName() {
|
||||
return this.serverKeySignParamName;
|
||||
}
|
||||
|
||||
public String getServerSm4Key() {
|
||||
return this.serverSm4Key;
|
||||
}
|
||||
|
||||
public byte[] getServerSm4KeyBytes() {
|
||||
return this.serverSm4KeyBytes;
|
||||
}
|
||||
|
||||
public String getServerSm2Key() {
|
||||
return this.serverSm2Key;
|
||||
}
|
||||
|
||||
public byte[] getServerSm2KeyBytes() {
|
||||
return this.serverSm2KeyBytes;
|
||||
}
|
||||
|
||||
public String getClientSm2Key() {
|
||||
return this.clientSm2Key;
|
||||
}
|
||||
|
||||
public byte[] getClientSm2KeyBytes() {
|
||||
return this.clientSm2KeyBytes;
|
||||
}
|
||||
|
||||
public String getTimestampHeaderName() {
|
||||
return this.timestampHeaderName;
|
||||
}
|
||||
|
||||
public String getNonceHeaderName() {
|
||||
return this.nonceHeaderName;
|
||||
}
|
||||
|
||||
public String getSignHeaderName() {
|
||||
return this.signHeaderName;
|
||||
}
|
||||
|
||||
public String getServerEncryptedClientKeyHeaderName() {
|
||||
return this.serverEncryptedClientKeyHeaderName;
|
||||
}
|
||||
|
||||
public long getMaxWindowSeconds() {
|
||||
return this.maxWindowSeconds;
|
||||
}
|
||||
|
||||
public String getPlayKey() {
|
||||
return this.playKey;
|
||||
}
|
||||
|
||||
public void setEncryptUriPrefix(final String encryptUriPrefix) {
|
||||
this.encryptUriPrefix = encryptUriPrefix;
|
||||
}
|
||||
|
||||
public void setKeyExchangePath(final String keyExchangePath) {
|
||||
this.keyExchangePath = keyExchangePath;
|
||||
}
|
||||
|
||||
public void setPublicKeyExchangePath(final String publicKeyExchangePath) {
|
||||
this.publicKeyExchangePath = publicKeyExchangePath;
|
||||
}
|
||||
|
||||
public void setIgnoredUri(final Set<String> ignoredUri) {
|
||||
this.ignoredUri = ignoredUri;
|
||||
}
|
||||
|
||||
public void setRequestBodySignParamName(final String requestBodySignParamName) {
|
||||
this.requestBodySignParamName = requestBodySignParamName;
|
||||
}
|
||||
|
||||
public void setClientKeySignParamName(final String clientKeySignParamName) {
|
||||
this.clientKeySignParamName = clientKeySignParamName;
|
||||
}
|
||||
|
||||
public void setAddonSignHeaderPrefix(final Set<String> addonSignHeaderPrefix) {
|
||||
this.addonSignHeaderPrefix = addonSignHeaderPrefix;
|
||||
}
|
||||
|
||||
public void setTokenHeaderNames(final Set<String> tokenHeaderNames) {
|
||||
this.tokenHeaderNames = tokenHeaderNames;
|
||||
}
|
||||
|
||||
public void setTokenSignHeaderName(final String tokenSignHeaderName) {
|
||||
this.tokenSignHeaderName = tokenSignHeaderName;
|
||||
}
|
||||
|
||||
public void setServerKeySignParamName(final String serverKeySignParamName) {
|
||||
this.serverKeySignParamName = serverKeySignParamName;
|
||||
}
|
||||
|
||||
public void setServerSm4KeyBytes(final byte[] serverSm4KeyBytes) {
|
||||
this.serverSm4KeyBytes = serverSm4KeyBytes;
|
||||
}
|
||||
|
||||
public void setServerSm2Key(final String serverSm2Key) {
|
||||
this.serverSm2Key = serverSm2Key;
|
||||
}
|
||||
|
||||
public void setServerSm2KeyBytes(final byte[] serverSm2KeyBytes) {
|
||||
this.serverSm2KeyBytes = serverSm2KeyBytes;
|
||||
}
|
||||
|
||||
public void setClientSm2Key(final String clientSm2Key) {
|
||||
this.clientSm2Key = clientSm2Key;
|
||||
}
|
||||
|
||||
public void setClientSm2KeyBytes(final byte[] clientSm2KeyBytes) {
|
||||
this.clientSm2KeyBytes = clientSm2KeyBytes;
|
||||
}
|
||||
|
||||
public void setTimestampHeaderName(final String timestampHeaderName) {
|
||||
this.timestampHeaderName = timestampHeaderName;
|
||||
}
|
||||
|
||||
public void setNonceHeaderName(final String nonceHeaderName) {
|
||||
this.nonceHeaderName = nonceHeaderName;
|
||||
}
|
||||
|
||||
public void setSignHeaderName(final String signHeaderName) {
|
||||
this.signHeaderName = signHeaderName;
|
||||
}
|
||||
|
||||
public void setServerEncryptedClientKeyHeaderName(final String serverEncryptedClientKeyHeaderName) {
|
||||
this.serverEncryptedClientKeyHeaderName = serverEncryptedClientKeyHeaderName;
|
||||
}
|
||||
|
||||
public void setMaxWindowSeconds(final long maxWindowSeconds) {
|
||||
this.maxWindowSeconds = maxWindowSeconds;
|
||||
}
|
||||
|
||||
public void setPlayKey(final String playKey) {
|
||||
this.playKey = playKey;
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
public static class MdcLogParameter {
|
||||
private String subjectId = "x-id";
|
||||
private String subjectName = "x-name";
|
||||
|
||||
public String getSubjectId() {
|
||||
return this.subjectId;
|
||||
}
|
||||
|
||||
public String getSubjectName() {
|
||||
return this.subjectName;
|
||||
}
|
||||
|
||||
public void setSubjectId(final String subjectId) {
|
||||
this.subjectId = subjectId;
|
||||
}
|
||||
|
||||
public void setSubjectName(final String subjectName) {
|
||||
this.subjectName = subjectName;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,126 @@
|
|||
package com.bonus.canteen.core.config;
|
||||
|
||||
import cn.hutool.core.codec.Base64Decoder;
|
||||
import cn.hutool.core.codec.Base64Encoder;
|
||||
import cn.hutool.core.util.PrimitiveArrayUtil;
|
||||
import cn.hutool.core.util.RandomUtil;
|
||||
import cn.hutool.crypto.Mode;
|
||||
import cn.hutool.crypto.Padding;
|
||||
import cn.hutool.crypto.SmUtil;
|
||||
import cn.hutool.crypto.asymmetric.KeyType;
|
||||
import cn.hutool.crypto.symmetric.SM4;
|
||||
import com.bonus.canteen.core.common.utils.SpringContextHolder;
|
||||
import com.google.common.base.Joiner;
|
||||
import org.bouncycastle.jce.provider.BouncyCastleProvider;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import javax.crypto.KeyGenerator;
|
||||
import javax.crypto.SecretKey;
|
||||
import java.io.PrintStream;
|
||||
import java.nio.charset.StandardCharsets;
|
||||
import java.security.NoSuchAlgorithmException;
|
||||
import java.util.SortedMap;
|
||||
|
||||
public class SmUtils {
|
||||
private static final Logger log = LoggerFactory.getLogger(SmUtils.class);
|
||||
private static SecureProperties secureProperties = SpringContextHolder.getBean(SecureProperties.class);
|
||||
public static void setSecureProperties(SecureProperties secureProperties) {
|
||||
if (SmUtils.secureProperties == null) {
|
||||
SmUtils.secureProperties = secureProperties;
|
||||
}
|
||||
}
|
||||
|
||||
public static String signBySm3(SortedMap<String, String> data, String clientKey) {
|
||||
data.put(secureProperties.getSecurity().getClientKeySignParamName(), clientKey);
|
||||
String joinedParam = Joiner.on("&").useForNull("").withKeyValueSeparator("=").join(data);
|
||||
log.debug("Sign param:{}", joinedParam);
|
||||
return Base64Encoder.encode(SmUtil.sm3().digest(joinedParam));
|
||||
}
|
||||
|
||||
public static String signBySm3WithServerKey(SortedMap<String, String> data, String clientKey) {
|
||||
data.put(secureProperties.getSecurity().getServerKeySignParamName(), secureProperties.getSecurity().getServerSm4Key());
|
||||
return signBySm3(data, clientKey);
|
||||
}
|
||||
|
||||
public static String signAuthTokenBySm3(SortedMap<String, String> data, String clientKey) {
|
||||
return signBySm3WithServerKey(data, clientKey);
|
||||
}
|
||||
|
||||
public static String decryptBySm2(String data) {
|
||||
return SmUtil.sm2(secureProperties.getSecurity().getServerSm2Key(), secureProperties.getSecurity().getClientSm2Key()).decryptStr(data, KeyType.PrivateKey);
|
||||
}
|
||||
|
||||
public static String signBySm2(String data) {
|
||||
return Base64Encoder.encode(SmUtil.sm2(secureProperties.getSecurity().getServerSm2Key(), secureProperties.getSecurity().getClientSm2Key()).sign(data.getBytes(StandardCharsets.UTF_8)));
|
||||
}
|
||||
|
||||
public static String decryptBySm4(String data, byte[] key) {
|
||||
byte[] decodedData = Base64Decoder.decode(data);
|
||||
if (decodedData.length <= 16) {
|
||||
throw new IllegalArgumentException("Encrypted data byte length must greater than 16");
|
||||
} else {
|
||||
byte[] iv = PrimitiveArrayUtil.sub(decodedData, 0, 16);
|
||||
byte[] dataBytes = PrimitiveArrayUtil.sub(decodedData, 16, decodedData.length);
|
||||
return (new SM4(Mode.CBC, Padding.PKCS5Padding, key, iv)).decryptStr(dataBytes);
|
||||
}
|
||||
}
|
||||
|
||||
public static String decryptBySm4(String data, String key) {
|
||||
return decryptBySm4(data, Base64Decoder.decode(key));
|
||||
}
|
||||
|
||||
public static String decryptBySm4WithServerKey(String data) {
|
||||
return decryptBySm4(data, secureProperties.getSecurity().getServerSm4KeyBytes());
|
||||
}
|
||||
|
||||
public static String encryptBySm4(String data, byte[] key) {
|
||||
SM4 var10000 = new SM4(Mode.CBC, Padding.PKCS5Padding, key, RandomUtil.randomBytes(16));
|
||||
String var10001 = RandomUtil.randomString(16);
|
||||
return var10000.encryptBase64(var10001 + data);
|
||||
}
|
||||
|
||||
public static String encryptBySm4WithServerKey(String data) {
|
||||
return encryptBySm4(data, secureProperties.getSecurity().getServerSm4KeyBytes());
|
||||
}
|
||||
|
||||
public static void main(String[] args) throws NoSuchAlgorithmException {
|
||||
//sm2() 移到 SmUtilsTest.java
|
||||
sm4();
|
||||
sm4WithoutIV();
|
||||
}
|
||||
|
||||
private static void sm4() throws NoSuchAlgorithmException {
|
||||
System.out.println("================sm4==================");
|
||||
BouncyCastleProvider provider = new BouncyCastleProvider();
|
||||
KeyGenerator generator = KeyGenerator.getInstance("SM4", provider);
|
||||
SecretKey secretKey = generator.generateKey();
|
||||
byte[] encoded = secretKey.getEncoded();
|
||||
String key = Base64Encoder.encode(encoded);
|
||||
System.out.println("key: " + key);
|
||||
String data = "liolay";
|
||||
String encryptBySm4 = encryptBySm4(data, encoded);
|
||||
System.out.println("encrypt: " + encryptBySm4);
|
||||
PrintStream var10000 = System.out;
|
||||
String var10001 = decryptBySm4(encryptBySm4, encoded);
|
||||
var10000.println("decrypt: " + var10001);
|
||||
var10000 = System.out;
|
||||
var10001 = decryptBySm4(encryptBySm4, key);
|
||||
var10000.println("decrypt: " + var10001);
|
||||
}
|
||||
|
||||
private static void sm4WithoutIV() throws NoSuchAlgorithmException {
|
||||
System.out.println("================sm4WithoutIV==================");
|
||||
BouncyCastleProvider provider = new BouncyCastleProvider();
|
||||
KeyGenerator generator = KeyGenerator.getInstance("SM4", provider);
|
||||
SecretKey secretKey = generator.generateKey();
|
||||
byte[] key = secretKey.getEncoded();
|
||||
String keyEncode = Base64Encoder.encode(key);
|
||||
System.out.println("key: " + keyEncode);
|
||||
String plainData = "liolay";
|
||||
String encryptedData = encryptBySm4(plainData, key);
|
||||
System.out.println("encrypt: " + encryptedData);
|
||||
String decryptData = decryptBySm4(encryptedData, key);
|
||||
System.out.println("decrypt: " + decryptData);
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,102 @@
|
|||
package com.bonus.canteen.core.config;
|
||||
|
||||
import com.google.common.collect.Maps;
|
||||
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import java.util.Map;
|
||||
import java.util.Optional;
|
||||
|
||||
public class WebContext {
|
||||
private static final ThreadLocal<Context> THREAD_CONTEXT = new InheritableThreadLocal<Context>() {
|
||||
@Override
|
||||
protected Context initialValue() {
|
||||
return new Context();
|
||||
}
|
||||
};
|
||||
|
||||
private WebContext() {
|
||||
}
|
||||
|
||||
public static void reset() {
|
||||
THREAD_CONTEXT.remove();
|
||||
}
|
||||
|
||||
public static Context get() {
|
||||
return (Context)THREAD_CONTEXT.get();
|
||||
}
|
||||
|
||||
public static void set(Context context) {
|
||||
THREAD_CONTEXT.set(context);
|
||||
}
|
||||
|
||||
public static class Context {
|
||||
private HttpServletRequest request;
|
||||
private HttpServletResponse response;
|
||||
private AccessToken accessToken;
|
||||
private Map<String, Object> attributes = Maps.newHashMap();
|
||||
|
||||
public Context(HttpServletRequest request, HttpServletResponse response) {
|
||||
this.request = request;
|
||||
this.response = response;
|
||||
}
|
||||
|
||||
public void setAttribute(String key, Object data) {
|
||||
this.attributes.put(key, data);
|
||||
}
|
||||
|
||||
public Object getAttribute(String key) {
|
||||
return this.attributes.get(key);
|
||||
}
|
||||
|
||||
public void removeAttribute(String key) {
|
||||
this.attributes.remove(key);
|
||||
}
|
||||
|
||||
public void clearAttribute() {
|
||||
this.attributes.clear();
|
||||
}
|
||||
|
||||
public Optional<AccessToken> getAccessToken() {
|
||||
return Optional.ofNullable(this.accessToken);
|
||||
}
|
||||
|
||||
public Optional<HttpServletRequest> getRequest() {
|
||||
return Optional.ofNullable(this.request);
|
||||
}
|
||||
|
||||
public Optional<HttpServletResponse> getResponse() {
|
||||
return Optional.ofNullable(this.response);
|
||||
}
|
||||
|
||||
public Map<String, Object> getAttributes() {
|
||||
return this.attributes;
|
||||
}
|
||||
|
||||
public void setRequest(final HttpServletRequest request) {
|
||||
this.request = request;
|
||||
}
|
||||
|
||||
public void setResponse(final HttpServletResponse response) {
|
||||
this.response = response;
|
||||
}
|
||||
|
||||
public void setAccessToken(final AccessToken accessToken) {
|
||||
this.accessToken = accessToken;
|
||||
}
|
||||
|
||||
public void setAttributes(final Map<String, Object> attributes) {
|
||||
this.attributes = attributes;
|
||||
}
|
||||
|
||||
public Context() {
|
||||
}
|
||||
|
||||
public Context(final HttpServletRequest request, final HttpServletResponse response, final AccessToken accessToken, final Map<String, Object> attributes) {
|
||||
this.request = request;
|
||||
this.response = response;
|
||||
this.accessToken = accessToken;
|
||||
this.attributes = attributes;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,11 @@
|
|||
package com.bonus.canteen.core.config.json;
|
||||
|
||||
import com.fasterxml.jackson.datatype.jsr310.ser.InstantSerializer;
|
||||
|
||||
import java.time.format.DateTimeFormatter;
|
||||
|
||||
public class InstantsSerializer extends InstantSerializer {
|
||||
public InstantsSerializer(DateTimeFormatter defaultFormat) {
|
||||
super(InstantSerializer.INSTANCE, false, defaultFormat);
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,78 @@
|
|||
package com.bonus.canteen.core.config.json;
|
||||
|
||||
import com.bonus.canteen.core.config.WebContext;
|
||||
import com.fasterxml.jackson.core.JsonGenerator;
|
||||
import com.fasterxml.jackson.databind.Module;
|
||||
import com.fasterxml.jackson.databind.SerializerProvider;
|
||||
import com.fasterxml.jackson.databind.module.SimpleModule;
|
||||
import com.fasterxml.jackson.databind.ser.std.StdSerializer;
|
||||
import com.fasterxml.jackson.datatype.jsr310.PackageVersion;
|
||||
import com.fasterxml.jackson.datatype.jsr310.deser.LocalDateDeserializer;
|
||||
import com.fasterxml.jackson.datatype.jsr310.deser.LocalDateTimeDeserializer;
|
||||
import com.fasterxml.jackson.datatype.jsr310.deser.LocalTimeDeserializer;
|
||||
import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateSerializer;
|
||||
import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateTimeSerializer;
|
||||
import com.fasterxml.jackson.datatype.jsr310.ser.LocalTimeSerializer;
|
||||
import org.springframework.boot.autoconfigure.jackson.Jackson2ObjectMapperBuilderCustomizer;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.context.annotation.Configuration;
|
||||
|
||||
import javax.servlet.http.HttpServletRequest;
|
||||
import java.io.IOException;
|
||||
import java.time.*;
|
||||
import java.time.format.DateTimeFormatter;
|
||||
import java.util.Locale;
|
||||
import java.util.Objects;
|
||||
import java.util.Optional;
|
||||
import java.util.TimeZone;
|
||||
|
||||
//@AutoConfiguration(
|
||||
// before = {JacksonAutoConfiguration.class}
|
||||
//)
|
||||
@Configuration
|
||||
//@ConditionalOnClass({ObjectMapper.class})
|
||||
public class JacksonConfiguration {
|
||||
public static final StdSerializer<Long> LONG_STD_SERIALIZER;
|
||||
|
||||
@Bean
|
||||
Jackson2ObjectMapperBuilderCustomizer objectMapperBuilderCustomizer() {
|
||||
return (builder) -> {
|
||||
builder.serializerByType(Long.TYPE, LONG_STD_SERIALIZER);
|
||||
builder.serializerByType(Long.class, LONG_STD_SERIALIZER);
|
||||
builder.locale(Locale.CHINA);
|
||||
builder.timeZone(TimeZone.getTimeZone(ZoneId.systemDefault()));
|
||||
builder.simpleDateFormat("yyyy-MM-dd HH:mm:ss");
|
||||
builder.modules(new Module[]{new SimpleModule(PackageVersion.VERSION) {
|
||||
{
|
||||
this.addSerializer(LocalDateTime.class, new LocalDateTimeSerializer(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
|
||||
this.addSerializer(LocalDate.class, new LocalDateSerializer(DateTimeFormatter.ofPattern("yyyy-MM-dd")));
|
||||
this.addSerializer(LocalTime.class, new LocalTimeSerializer(DateTimeFormatter.ofPattern("HH:mm:ss")));
|
||||
this.addSerializer(Instant.class, new InstantsSerializer(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss.SSS")));
|
||||
this.addDeserializer(LocalDateTime.class, new LocalDateTimeDeserializer(DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss")));
|
||||
this.addDeserializer(LocalDate.class, new LocalDateDeserializer(DateTimeFormatter.ofPattern("yyyy-MM-dd")));
|
||||
this.addDeserializer(LocalTime.class, new LocalTimeDeserializer(DateTimeFormatter.ofPattern("HH:mm:ss")));
|
||||
}
|
||||
}});
|
||||
};
|
||||
}
|
||||
|
||||
static {
|
||||
LONG_STD_SERIALIZER = new StdSerializer<Long>(Long.TYPE) {
|
||||
@Override
|
||||
public void serialize(Long value, JsonGenerator jsonGenerator, SerializerProvider serializerProvider) throws IOException {
|
||||
if (value == null) {
|
||||
jsonGenerator.writeNull();
|
||||
} else {
|
||||
Optional<HttpServletRequest> requestOptional = WebContext.get().getRequest();
|
||||
if ((Boolean)requestOptional.map((request) -> {
|
||||
return Objects.isNull(request.getHeader("User-Agent")) || request.getHeader("User-Agent").contains("okhttp");
|
||||
}).orElse(false)) {
|
||||
jsonGenerator.writeNumber(value);
|
||||
} else {
|
||||
jsonGenerator.writeString(value.toString());
|
||||
}
|
||||
}
|
||||
}
|
||||
};
|
||||
}
|
||||
}
|
||||
|
|
@ -0,0 +1,57 @@
|
|||
package com.bonus.canteen.core.config.json;
|
||||
|
||||
import com.fasterxml.jackson.core.JsonProcessingException;
|
||||
import com.fasterxml.jackson.databind.JsonNode;
|
||||
import com.fasterxml.jackson.databind.ObjectMapper;
|
||||
import org.apache.ibatis.type.BaseTypeHandler;
|
||||
import org.apache.ibatis.type.JdbcType;
|
||||
import org.apache.ibatis.type.MappedTypes;
|
||||
import org.slf4j.Logger;
|
||||
import org.slf4j.LoggerFactory;
|
||||
|
||||
import java.sql.CallableStatement;
|
||||
import java.sql.PreparedStatement;
|
||||
import java.sql.ResultSet;
|
||||
import java.sql.SQLException;
|
||||
|
||||
@MappedTypes({JsonNode.class})
|
||||
public class JsonNodeTypeHandler extends BaseTypeHandler<JsonNode> {
|
||||
private static final Logger log = LoggerFactory.getLogger(JsonNodeTypeHandler.class);
|
||||
private final ObjectMapper objectMapper = new ObjectMapper();
|
||||
|
||||
@Override
|
||||
public void setNonNullParameter(PreparedStatement preparedStatement, int i, JsonNode jsonNode, JdbcType jdbcType) throws SQLException {
|
||||
preparedStatement.setString(i, jsonNode.toString());
|
||||
}
|
||||
|
||||
private JsonNode read(String json) {
|
||||
if (json != null && !json.isEmpty()) {
|
||||
try {
|
||||
return this.objectMapper.readTree(json);
|
||||
} catch (JsonProcessingException var3) {
|
||||
log.warn("JSON parse failed", var3);
|
||||
return null;
|
||||
}
|
||||
} else {
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public JsonNode getNullableResult(ResultSet rs, String columnName) throws SQLException {
|
||||
String json = rs.getString(columnName);
|
||||
return this.read(json);
|
||||
}
|
||||
|
||||
@Override
|
||||
public JsonNode getNullableResult(ResultSet rs, int columnIndex) throws SQLException {
|
||||
String json = rs.getString(columnIndex);
|
||||
return this.read(json);
|
||||
}
|
||||
|
||||
@Override
|
||||
public JsonNode getNullableResult(CallableStatement cs, int columnIndex) throws SQLException {
|
||||
String json = cs.getString(columnIndex);
|
||||
return this.read(json);
|
||||
}
|
||||
}
|
||||
Loading…
Reference in New Issue