diff --git a/pigx-common/pigx-common-core/src/main/java/com/pig4cloud/pigx/common/core/constant/CacheConstants.java b/pigx-common/pigx-common-core/src/main/java/com/pig4cloud/pigx/common/core/constant/CacheConstants.java index 871f2ddf8..ccd614e77 100644 --- a/pigx-common/pigx-common-core/src/main/java/com/pig4cloud/pigx/common/core/constant/CacheConstants.java +++ b/pigx-common/pigx-common-core/src/main/java/com/pig4cloud/pigx/common/core/constant/CacheConstants.java @@ -85,4 +85,9 @@ public interface CacheConstants { */ String TENANT_DETAILS = GLOBALLY + "tenant_details"; + /** + * 客户端配置缓存 + */ + String CLIENT_FLAG = "client_config_flag"; + } diff --git a/pigx-common/pigx-common-core/src/main/java/com/pig4cloud/pigx/common/core/constant/CommonConstants.java b/pigx-common/pigx-common-core/src/main/java/com/pig4cloud/pigx/common/core/constant/CommonConstants.java index 909d31dc7..a20223926 100644 --- a/pigx-common/pigx-common-core/src/main/java/com/pig4cloud/pigx/common/core/constant/CommonConstants.java +++ b/pigx-common/pigx-common-core/src/main/java/com/pig4cloud/pigx/common/core/constant/CommonConstants.java @@ -100,4 +100,14 @@ public interface CommonConstants { */ String IMAGE_CODE_TYPE = "blockPuzzle"; + /** + * 验证码开关 + */ + String CAPTCHA_FLAG = "captcha_flag"; + + /** + * 密码传输是否加密 + */ + String ENC_FLAG = "enc_flag"; + } diff --git a/pigx-common/pigx-common-core/src/main/java/com/pig4cloud/pigx/common/core/constant/enums/CaptchaFlagTypeEnum.java b/pigx-common/pigx-common-core/src/main/java/com/pig4cloud/pigx/common/core/constant/enums/CaptchaFlagTypeEnum.java new file mode 100644 index 000000000..525f1ccdb --- /dev/null +++ b/pigx-common/pigx-common-core/src/main/java/com/pig4cloud/pigx/common/core/constant/enums/CaptchaFlagTypeEnum.java @@ -0,0 +1,36 @@ +package com.pig4cloud.pigx.common.core.constant.enums; + +import lombok.AllArgsConstructor; +import lombok.Getter; + +/** + * @author lengleng + * @date 2020-11-18 + *

+ * 验证码状态 + */ +@Getter +@AllArgsConstructor +public enum CaptchaFlagTypeEnum { + + /** + * 开启验证码 + */ + ON("1", "开启验证码"), + + /** + * 关闭验证码 + */ + OFF("0", "关闭验证码"); + + /** + * 类型 + */ + private String type; + + /** + * 描述 + */ + private String description; + +} diff --git a/pigx-common/pigx-common-core/src/main/java/com/pig4cloud/pigx/common/core/constant/enums/EncFlagTypeEnum.java b/pigx-common/pigx-common-core/src/main/java/com/pig4cloud/pigx/common/core/constant/enums/EncFlagTypeEnum.java new file mode 100644 index 000000000..497029e90 --- /dev/null +++ b/pigx-common/pigx-common-core/src/main/java/com/pig4cloud/pigx/common/core/constant/enums/EncFlagTypeEnum.java @@ -0,0 +1,36 @@ +package com.pig4cloud.pigx.common.core.constant.enums; + +import lombok.AllArgsConstructor; +import lombok.Getter; + +/** + * @author lengleng + * @date 2020-11-18 + *

+ * 密码是否加密传输 + */ +@Getter +@AllArgsConstructor +public enum EncFlagTypeEnum { + + /** + * 是 + */ + YES("1", "是"), + + /** + * 否 + */ + NO("0", "否"); + + /** + * 类型 + */ + private String type; + + /** + * 描述 + */ + private String description; + +} diff --git a/pigx-common/pigx-common-security/src/main/java/com/pig4cloud/pigx/common/security/component/PigxLocalResourceServerTokenServices.java b/pigx-common/pigx-common-security/src/main/java/com/pig4cloud/pigx/common/security/component/PigxLocalResourceServerTokenServices.java index fd6e6a599..0f85d2fdb 100644 --- a/pigx-common/pigx-common-security/src/main/java/com/pig4cloud/pigx/common/security/component/PigxLocalResourceServerTokenServices.java +++ b/pigx-common/pigx-common-security/src/main/java/com/pig4cloud/pigx/common/security/component/PigxLocalResourceServerTokenServices.java @@ -33,8 +33,11 @@ public class PigxLocalResourceServerTokenServices implements ResourceServerToken public OAuth2Authentication loadAuthentication(String accessToken) throws AuthenticationException, InvalidTokenException { OAuth2Authentication oAuth2Authentication = tokenStore.readAuthentication(accessToken); - OAuth2Request oAuth2Request = oAuth2Authentication.getOAuth2Request(); + if (oAuth2Authentication == null) { + return null; + } + OAuth2Request oAuth2Request = oAuth2Authentication.getOAuth2Request(); if (!(oAuth2Authentication.getPrincipal() instanceof PigxUser)) { return oAuth2Authentication; } diff --git a/pigx-gateway/src/main/java/com/pig4cloud/pigx/gateway/filter/PasswordDecoderFilter.java b/pigx-gateway/src/main/java/com/pig4cloud/pigx/gateway/filter/PasswordDecoderFilter.java index f3a298785..efbe6b8ab 100644 --- a/pigx-gateway/src/main/java/com/pig4cloud/pigx/gateway/filter/PasswordDecoderFilter.java +++ b/pigx-gateway/src/main/java/com/pig4cloud/pigx/gateway/filter/PasswordDecoderFilter.java @@ -24,15 +24,23 @@ import cn.hutool.crypto.Mode; import cn.hutool.crypto.Padding; import cn.hutool.crypto.symmetric.AES; import cn.hutool.http.HttpUtil; +import cn.hutool.json.JSONObject; +import cn.hutool.json.JSONUtil; +import com.pig4cloud.pigx.common.core.constant.CacheConstants; +import com.pig4cloud.pigx.common.core.constant.CommonConstants; import com.pig4cloud.pigx.common.core.constant.SecurityConstants; +import com.pig4cloud.pigx.common.core.constant.enums.EncFlagTypeEnum; +import com.pig4cloud.pigx.common.core.util.WebUtils; import com.pig4cloud.pigx.gateway.config.GatewayConfigProperties; +import lombok.RequiredArgsConstructor; import lombok.extern.slf4j.Slf4j; -import org.springframework.beans.factory.annotation.Autowired; import org.springframework.cloud.gateway.filter.GatewayFilter; import org.springframework.cloud.gateway.filter.factory.AbstractGatewayFilterFactory; import org.springframework.cloud.gateway.filter.factory.rewrite.CachedBodyOutputMessage; import org.springframework.cloud.gateway.support.BodyInserterContext; import org.springframework.core.io.buffer.DataBuffer; +import org.springframework.data.redis.core.RedisTemplate; +import org.springframework.data.redis.serializer.StringRedisSerializer; import org.springframework.http.HttpHeaders; import org.springframework.http.MediaType; import org.springframework.http.codec.HttpMessageReader; @@ -62,6 +70,8 @@ import java.util.function.Function; */ @Slf4j @Component +@RequiredArgsConstructor +@SuppressWarnings("all") public class PasswordDecoderFilter extends AbstractGatewayFilterFactory { private final List> messageReaders = HandlerStrategies.withDefaults().messageReaders(); @@ -70,24 +80,31 @@ public class PasswordDecoderFilter extends AbstractGatewayFilterFactory { private static final String KEY_ALGORITHM = "AES"; - @Autowired - private GatewayConfigProperties gatewayConfig; + private final RedisTemplate redisTemplate; + + private final GatewayConfigProperties gatewayConfig; @Override public GatewayFilter apply(Object config) { return (exchange, chain) -> { ServerHttpRequest request = exchange.getRequest(); - // 不是登录请求,直接向下执行 + // 1. 不是登录请求,直接向下执行 if (!StrUtil.containsAnyIgnoreCase(request.getURI().getPath(), SecurityConstants.OAUTH_TOKEN_URL)) { return chain.filter(exchange); } - // 刷新token,直接向下执行 + // 2. 刷新token类型,直接向下执行 String grantType = request.getQueryParams().getFirst("grant_type"); if (StrUtil.equals(SecurityConstants.REFRESH_TOKEN, grantType)) { return chain.filter(exchange); } + // 3. 判断客户端是否需要解密,明文传输直接向下执行 + if (!isEncClient(request)) { + return chain.filter(exchange); + } + + // 4. 前端加密密文解密逻辑 Class inClass = String.class; Class outClass = String.class; ServerRequest serverRequest = ServerRequest.create(exchange, messageReaders); @@ -109,6 +126,34 @@ public class PasswordDecoderFilter extends AbstractGatewayFilterFactory { }; } + /** + * 根据请求的clientId 查询客户端配置是否是加密传输 + * @param request 请求上下文 + * @return true 加密传输 、 false 原文传输 + */ + private boolean isEncClient(ServerHttpRequest request) { + String header = request.getHeaders().getFirst(HttpHeaders.AUTHORIZATION); + String clientId = WebUtils.extractClientId(header).orElse(null); + // 获取租户拼接区分租户的key + String tenantId = request.getHeaders().getFirst(CommonConstants.TENANT_ID); + String key = String.format("%s:%s:%s", StrUtil.isBlank(tenantId) ? CommonConstants.TENANT_ID_1 : tenantId, + CacheConstants.CLIENT_FLAG, clientId); + + redisTemplate.setKeySerializer(new StringRedisSerializer()); + Object val = redisTemplate.opsForValue().get(key); + + // 当配置不存在时,默认需要解密 + if (val == null) { + return true; + } + + JSONObject information = JSONUtil.parseObj(val.toString()); + if (StrUtil.equals(EncFlagTypeEnum.NO.getType(), information.getStr(CommonConstants.ENC_FLAG))) { + return false; + } + return true; + } + /** * 原文解密 * @return diff --git a/pigx-gateway/src/main/java/com/pig4cloud/pigx/gateway/filter/ValidateCodeGatewayFilter.java b/pigx-gateway/src/main/java/com/pig4cloud/pigx/gateway/filter/ValidateCodeGatewayFilter.java index 8936f1a45..697508f51 100644 --- a/pigx-gateway/src/main/java/com/pig4cloud/pigx/gateway/filter/ValidateCodeGatewayFilter.java +++ b/pigx-gateway/src/main/java/com/pig4cloud/pigx/gateway/filter/ValidateCodeGatewayFilter.java @@ -18,6 +18,8 @@ package com.pig4cloud.pigx.gateway.filter; import cn.hutool.core.util.StrUtil; +import cn.hutool.json.JSONObject; +import cn.hutool.json.JSONUtil; import com.anji.captcha.model.vo.CaptchaVO; import com.anji.captcha.service.CaptchaService; import com.fasterxml.jackson.core.JsonProcessingException; @@ -25,12 +27,11 @@ import com.fasterxml.jackson.databind.ObjectMapper; import com.pig4cloud.pigx.common.core.constant.CacheConstants; import com.pig4cloud.pigx.common.core.constant.CommonConstants; import com.pig4cloud.pigx.common.core.constant.SecurityConstants; -import com.pig4cloud.pigx.common.core.constant.enums.LoginTypeEnum; +import com.pig4cloud.pigx.common.core.constant.enums.CaptchaFlagTypeEnum; import com.pig4cloud.pigx.common.core.exception.ValidateCodeException; import com.pig4cloud.pigx.common.core.util.R; import com.pig4cloud.pigx.common.core.util.SpringContextHolder; import com.pig4cloud.pigx.common.core.util.WebUtils; -import com.pig4cloud.pigx.gateway.config.GatewayConfigProperties; import lombok.AllArgsConstructor; import lombok.SneakyThrows; import lombok.extern.slf4j.Slf4j; @@ -53,22 +54,21 @@ import reactor.core.publisher.Mono; @Slf4j @Component @AllArgsConstructor +@SuppressWarnings("all") public class ValidateCodeGatewayFilter extends AbstractGatewayFilterFactory { private final ObjectMapper objectMapper; private final RedisTemplate redisTemplate; - private final GatewayConfigProperties gatewayConfig; - @Override public GatewayFilter apply(Object config) { return (exchange, chain) -> { ServerHttpRequest request = exchange.getRequest(); - // 不是登录请求,直接向下执行 + // 不是账号密码登录、短信登录,直接向下执行 if (!StrUtil.containsAnyIgnoreCase(request.getURI().getPath(), SecurityConstants.OAUTH_TOKEN_URL, - SecurityConstants.SMS_TOKEN_URL, SecurityConstants.SOCIAL_TOKEN_URL)) { + SecurityConstants.SMS_TOKEN_URL)) { return chain.filter(exchange); } @@ -78,25 +78,12 @@ public class ValidateCodeGatewayFilter extends AbstractGatewayFilterFactory { return chain.filter(exchange); } - // 终端设置不校验, 直接向下执行 + // 判断客户端是否跳过检验 + if (!isCheckCaptchaClient(request)) { + return chain.filter(exchange); + } + try { - String header = request.getHeaders().getFirst(HttpHeaders.AUTHORIZATION); - String clientId = WebUtils.extractClientId(header).orElse(null); - if (StrUtil.isNotBlank(clientId) && gatewayConfig.getIgnoreClients().contains(clientId)) { - return chain.filter(exchange); - } - - // 如果是社交登录,判断是否包含SMS - if (StrUtil.containsAnyIgnoreCase(request.getURI().getPath(), SecurityConstants.SOCIAL_TOKEN_URL)) { - String mobile = request.getQueryParams().getFirst("mobile"); - if (StrUtil.containsAny(mobile, LoginTypeEnum.SMS.getType())) { - throw new ValidateCodeException("验证码不合法"); - } - else { - return chain.filter(exchange); - } - } - // 校验验证码 checkCode(request); } @@ -117,6 +104,34 @@ public class ValidateCodeGatewayFilter extends AbstractGatewayFilterFactory { }; } + /** + * 是否需要校验客户端,根据client 查询客户端配置 + * @param request 请求 + * @return true 需要校验, false 不需要校验 + */ + private boolean isCheckCaptchaClient(ServerHttpRequest request) { + String header = request.getHeaders().getFirst(HttpHeaders.AUTHORIZATION); + String clientId = WebUtils.extractClientId(header).orElse(null); + // 获取租户拼接区分租户的key + String tenantId = request.getHeaders().getFirst(CommonConstants.TENANT_ID); + String key = String.format("%s:%s:%s", StrUtil.isBlank(tenantId) ? CommonConstants.TENANT_ID_1 : tenantId, + CacheConstants.CLIENT_FLAG, clientId); + + redisTemplate.setKeySerializer(new StringRedisSerializer()); + Object val = redisTemplate.opsForValue().get(key); + + // 当配置不存在时,默认需要校验 + if (val == null) { + return true; + } + + JSONObject information = JSONUtil.parseObj(val.toString()); + if (StrUtil.equals(CaptchaFlagTypeEnum.OFF.getType(), information.getStr(CommonConstants.CAPTCHA_FLAG))) { + return false; + } + return true; + } + /** * 检查code * @param request @@ -139,7 +154,6 @@ public class ValidateCodeGatewayFilter extends AbstractGatewayFilterFactory { if (!captchaService.verification(vo).isSuccess()) { throw new ValidateCodeException("验证码不能为空"); } - return; } diff --git a/pigx-upms/pigx-upms-api/src/main/java/com/pig4cloud/pigx/admin/api/dto/SysOauthClientDetailsDTO.java b/pigx-upms/pigx-upms-api/src/main/java/com/pig4cloud/pigx/admin/api/dto/SysOauthClientDetailsDTO.java new file mode 100644 index 000000000..dcc3e5a4d --- /dev/null +++ b/pigx-upms/pigx-upms-api/src/main/java/com/pig4cloud/pigx/admin/api/dto/SysOauthClientDetailsDTO.java @@ -0,0 +1,25 @@ +package com.pig4cloud.pigx.admin.api.dto; + +import com.pig4cloud.pigx.admin.api.entity.SysOauthClientDetails; +import lombok.Data; + +/** + * @author lengleng + * @date 2020/11/18 + *

+ * 终端管理传输对象 + */ +@Data +public class SysOauthClientDetailsDTO extends SysOauthClientDetails { + + /** + * 验证码开关 + */ + private String captchaFlag; + + /** + * 前端密码传输是否加密 + */ + private String encFlag; + +} diff --git a/pigx-upms/pigx-upms-api/src/main/java/com/pig4cloud/pigx/admin/api/entity/SysOauthClientDetails.java b/pigx-upms/pigx-upms-api/src/main/java/com/pig4cloud/pigx/admin/api/entity/SysOauthClientDetails.java index 42acda534..9011f377b 100644 --- a/pigx-upms/pigx-upms-api/src/main/java/com/pig4cloud/pigx/admin/api/entity/SysOauthClientDetails.java +++ b/pigx-upms/pigx-upms-api/src/main/java/com/pig4cloud/pigx/admin/api/entity/SysOauthClientDetails.java @@ -125,4 +125,9 @@ public class SysOauthClientDetails extends Model { @ApiModelProperty(value = "删除标记,1:已删除,0:正常") private String delFlag; + /** + * 租户编号 + */ + private Integer tenantId; + } diff --git a/pigx-upms/pigx-upms-biz/src/main/java/com/pig4cloud/pigx/admin/config/ClientDetailsInitRunner.java b/pigx-upms/pigx-upms-biz/src/main/java/com/pig4cloud/pigx/admin/config/ClientDetailsInitRunner.java new file mode 100644 index 000000000..127d9b6c0 --- /dev/null +++ b/pigx-upms/pigx-upms-biz/src/main/java/com/pig4cloud/pigx/admin/config/ClientDetailsInitRunner.java @@ -0,0 +1,76 @@ +package com.pig4cloud.pigx.admin.config; + +import cn.hutool.core.util.StrUtil; +import com.pig4cloud.pigx.admin.api.entity.SysOauthClientDetails; +import com.pig4cloud.pigx.admin.service.SysOauthClientDetailsService; +import com.pig4cloud.pigx.admin.service.SysTenantService; +import com.pig4cloud.pigx.common.core.constant.CacheConstants; +import com.pig4cloud.pigx.common.data.tenant.TenantBroker; +import lombok.RequiredArgsConstructor; +import lombok.extern.slf4j.Slf4j; +import org.springframework.boot.web.context.WebServerInitializedEvent; +import org.springframework.context.ApplicationEvent; +import org.springframework.context.event.EventListener; +import org.springframework.core.annotation.Order; +import org.springframework.data.redis.core.RedisTemplate; +import org.springframework.scheduling.annotation.Async; +import org.springframework.stereotype.Service; + +import java.util.ArrayList; +import java.util.List; + +/** + * @author lengleng + * @date 2020/11/18 + *

+ * oauth 客户端认证参数初始化 + */ +@Slf4j +@Service +@RequiredArgsConstructor +@SuppressWarnings("all") +public class ClientDetailsInitRunner { + + private final SysOauthClientDetailsService clientDetailsService; + + private final SysTenantService tenantService; + + private final RedisTemplate redisTemplate; + + @Async + @Order + @EventListener({ WebServerInitializedEvent.class, ClientDetailsInitEvent.class }) + public void initClientDetails() { + log.debug("初始化客户端信息开始 "); + List clientDetailsList = new ArrayList<>(); + + // 查询全部租户的客户端定义信息 + tenantService.list().forEach(tenant -> clientDetailsList + .addAll(TenantBroker.applyAs(tenant.getId(), tenantId -> clientDetailsService.list()))); + + for (SysOauthClientDetails client : clientDetailsList) { + if (StrUtil.isBlank(client.getAdditionalInformation())) { + continue; + } + // 拼接key 1:client_config_flag:clinetId + String key = String.format("%s:%s:%s", client.getTenantId(), CacheConstants.CLIENT_FLAG, + client.getClientId()); + // hashkey clientId + redisTemplate.opsForValue().set(key, client.getAdditionalInformation()); + } + + log.debug("初始化客户端信息结束 "); + } + + /** + * 客户端刷新事件 + */ + public static class ClientDetailsInitEvent extends ApplicationEvent { + + public ClientDetailsInitEvent(Object source) { + super(source); + } + + } + +} diff --git a/pigx-upms/pigx-upms-biz/src/main/java/com/pig4cloud/pigx/admin/controller/SysClientController.java b/pigx-upms/pigx-upms-biz/src/main/java/com/pig4cloud/pigx/admin/controller/SysClientController.java index c31f1fc8b..5ec64fdd4 100644 --- a/pigx-upms/pigx-upms-biz/src/main/java/com/pig4cloud/pigx/admin/controller/SysClientController.java +++ b/pigx-upms/pigx-upms-biz/src/main/java/com/pig4cloud/pigx/admin/controller/SysClientController.java @@ -21,6 +21,7 @@ package com.pig4cloud.pigx.admin.controller; import com.baomidou.mybatisplus.core.toolkit.Wrappers; import com.baomidou.mybatisplus.extension.plugins.pagination.Page; +import com.pig4cloud.pigx.admin.api.dto.SysOauthClientDetailsDTO; import com.pig4cloud.pigx.admin.api.entity.SysOauthClientDetails; import com.pig4cloud.pigx.admin.service.SysOauthClientDetailsService; import com.pig4cloud.pigx.common.core.util.R; @@ -67,19 +68,19 @@ public class SysClientController { */ @GetMapping("/page") public R getOauthClientDetailsPage(Page page, SysOauthClientDetails sysOauthClientDetails) { - return R.ok(clientDetailsService.page(page, Wrappers.query(sysOauthClientDetails))); + return R.ok(clientDetailsService.queryPage(page, sysOauthClientDetails)); } /** * 添加 - * @param sysOauthClientDetails 实体 + * @param clientDetailsDTO 实体 * @return success/false */ @SysLog("添加终端") @PostMapping @PreAuthorize("@pms.hasPermission('sys_client_add')") - public R add(@Valid @RequestBody SysOauthClientDetails sysOauthClientDetails) { - return R.ok(clientDetailsService.save(sysOauthClientDetails)); + public R add(@Valid @RequestBody SysOauthClientDetailsDTO clientDetailsDTO) { + return R.ok(clientDetailsService.saveClient(clientDetailsDTO)); } /** @@ -96,14 +97,14 @@ public class SysClientController { /** * 编辑 - * @param sysOauthClientDetails 实体 + * @param clientDetailsDTO 实体 * @return success/false */ @SysLog("编辑终端") @PutMapping @PreAuthorize("@pms.hasPermission('sys_client_edit')") - public R update(@Valid @RequestBody SysOauthClientDetails sysOauthClientDetails) { - return R.ok(clientDetailsService.updateClientById(sysOauthClientDetails)); + public R update(@Valid @RequestBody SysOauthClientDetailsDTO clientDetailsDTO) { + return R.ok(clientDetailsService.updateClientById(clientDetailsDTO)); } } diff --git a/pigx-upms/pigx-upms-biz/src/main/java/com/pig4cloud/pigx/admin/service/SysOauthClientDetailsService.java b/pigx-upms/pigx-upms-biz/src/main/java/com/pig4cloud/pigx/admin/service/SysOauthClientDetailsService.java index cbf4a0a92..d56fa4962 100644 --- a/pigx-upms/pigx-upms-biz/src/main/java/com/pig4cloud/pigx/admin/service/SysOauthClientDetailsService.java +++ b/pigx-upms/pigx-upms-biz/src/main/java/com/pig4cloud/pigx/admin/service/SysOauthClientDetailsService.java @@ -19,7 +19,9 @@ package com.pig4cloud.pigx.admin.service; +import com.baomidou.mybatisplus.extension.plugins.pagination.Page; import com.baomidou.mybatisplus.extension.service.IService; +import com.pig4cloud.pigx.admin.api.dto.SysOauthClientDetailsDTO; import com.pig4cloud.pigx.admin.api.entity.SysOauthClientDetails; /** @@ -41,9 +43,24 @@ public interface SysOauthClientDetailsService extends IService @@ -38,9 +51,12 @@ import org.springframework.stereotype.Service; * @since 2018-05-15 */ @Service +@RequiredArgsConstructor public class SysOauthClientDetailsServiceImpl extends ServiceImpl implements SysOauthClientDetailsService { + private final RedisTemplate redisTemplate; + /** * 通过ID删除客户端 * @param clientId @@ -49,22 +65,90 @@ public class SysOauthClientDetailsServiceImpl extends ServiceImpllambdaQuery().eq(SysOauthClientDetails::getClientId, clientId)); + // 更新库 + baseMapper + .delete(Wrappers.lambdaQuery().eq(SysOauthClientDetails::getClientId, clientId)); + // 更新Redis + SpringContextHolder.publishEvent(new ClientDetailsInitRunner.ClientDetailsInitEvent(clientId)); + return Boolean.TRUE; } /** * 根据客户端信息 - * @param clientDetails + * @param clientDetailsDTO * @return */ @Override - @CacheEvict(value = CacheConstants.CLIENT_DETAILS_KEY, key = "#clientDetails.clientId") - public Boolean updateClientById(SysOauthClientDetails clientDetails) { - if (StrUtil.isBlank(clientDetails.getAdditionalInformation())) { - clientDetails.setAdditionalInformation(null); - } - return this.updateById(clientDetails); + @CacheEvict(value = CacheConstants.CLIENT_DETAILS_KEY, key = "#clientDetailsDTO.clientId") + public Boolean updateClientById(SysOauthClientDetailsDTO clientDetailsDTO) { + // copy dto 对象 + SysOauthClientDetails clientDetails = new SysOauthClientDetails(); + BeanUtils.copyProperties(clientDetailsDTO, clientDetails); + + // 获取扩展信息,插入开关相关 + String information = clientDetailsDTO.getAdditionalInformation(); + JSONObject informationObj = JSONUtil.parseObj(information) + .set(CommonConstants.CAPTCHA_FLAG, clientDetailsDTO.getCaptchaFlag()) + .set(CommonConstants.ENC_FLAG, clientDetailsDTO.getEncFlag()); + clientDetails.setAdditionalInformation(informationObj.toString()); + + // 更新数据库 + baseMapper.updateById(clientDetails); + // 更新Redis + SpringContextHolder.publishEvent(new ClientDetailsInitRunner.ClientDetailsInitEvent(clientDetails)); + return Boolean.TRUE; + } + + /** + * 添加客户端 + * @param clientDetailsDTO + * @return + */ + @Override + @Transactional(rollbackFor = Exception.class) + public Boolean saveClient(SysOauthClientDetailsDTO clientDetailsDTO) { + // copy dto 对象 + SysOauthClientDetails clientDetails = new SysOauthClientDetails(); + BeanUtils.copyProperties(clientDetailsDTO, clientDetails); + + // 获取扩展信息,插入开关相关 + String information = clientDetailsDTO.getAdditionalInformation(); + JSONUtil.parseObj(information).set(CommonConstants.CAPTCHA_FLAG, clientDetailsDTO.getCaptchaFlag()) + .set(CommonConstants.ENC_FLAG, clientDetailsDTO.getEncFlag()); + + // 插入数据 + this.baseMapper.insert(clientDetails); + // 更新Redis + SpringContextHolder.publishEvent(new ClientDetailsInitRunner.ClientDetailsInitEvent(clientDetails)); + return Boolean.TRUE; + } + + /** + * 分页查询客户端信息 + * @param page + * @param query + * @return + */ + @Override + public Page queryPage(Page page, SysOauthClientDetails query) { + Page selectPage = baseMapper.selectPage(page, Wrappers.query(query)); + + // 处理扩展字段组装dto + List collect = selectPage.getRecords().stream().map(details -> { + String information = details.getAdditionalInformation(); + String captchaFlag = JSONUtil.parseObj(information).getStr(CommonConstants.CAPTCHA_FLAG); + String encFlag = JSONUtil.parseObj(information).getStr(CommonConstants.ENC_FLAG); + SysOauthClientDetailsDTO dto = new SysOauthClientDetailsDTO(); + BeanUtils.copyProperties(details, dto); + dto.setCaptchaFlag(captchaFlag); + dto.setEncFlag(encFlag); + return dto; + }).collect(Collectors.toList()); + + // 构建dto page 对象 + Page dtoPage = new Page<>(page.getCurrent(), page.getSize(), selectPage.getTotal()); + dtoPage.setRecords(collect); + return dtoPage; } } diff --git a/pigx-visual/pigx-codegen/src/main/java/com/pig4cloud/pigx/codegen/service/impl/GeneratorServiceImpl.java b/pigx-visual/pigx-codegen/src/main/java/com/pig4cloud/pigx/codegen/service/impl/GeneratorServiceImpl.java index 95867c348..d39399e2f 100755 --- a/pigx-visual/pigx-codegen/src/main/java/com/pig4cloud/pigx/codegen/service/impl/GeneratorServiceImpl.java +++ b/pigx-visual/pigx-codegen/src/main/java/com/pig4cloud/pigx/codegen/service/impl/GeneratorServiceImpl.java @@ -22,7 +22,6 @@ import cn.hutool.core.io.IoUtil; import cn.hutool.core.map.MapUtil; import cn.hutool.core.util.StrUtil; import com.baomidou.dynamic.datasource.annotation.DS; -import com.baomidou.dynamic.datasource.toolkit.DynamicDataSourceContextHolder; import com.baomidou.mybatisplus.core.metadata.IPage; import com.baomidou.mybatisplus.core.toolkit.Wrappers; import com.baomidou.mybatisplus.extension.plugins.pagination.Page; @@ -75,8 +74,6 @@ public class GeneratorServiceImpl implements GeneratorService { List formConfList = genFormConfMapper.selectList(Wrappers.lambdaQuery() .eq(GenFormConf::getTableName, genConfig.getTableName()).orderByDesc(GenFormConf::getCreateTime)); - DynamicDataSourceContextHolder.push(genConfig.getDsName()); - String tableNames = genConfig.getTableName(); for (String tableName : StrUtil.split(tableNames, StrUtil.DASHED)) { // 查询表信息