作者 shenhailong

统一认证 - user-center

... ... @@ -58,6 +58,9 @@ spring:
#password=1q2w3e4r
#spring datasource mysql,注意编码配置,缺少数据库编码配置容易引起中文入库乱码
url: jdbc:mysql://118.31.66.166:3306/station?useUnicode=true&characterEncoding=utf8
# url: jdbc:mysql://localhost:3306/station?useUnicode=true&characterEncoding=utf8
# username: root
# password: Long455900
username: 110
password: QAHqCJf2kFYCLirM
driver-class-name: com.mysql.cj.jdbc.Driver
... ... @@ -105,6 +108,7 @@ eureka:
service-url:
# defaultZone: http://127.0.0.1:12345/eureka/
defaultZone: http://192.168.1.53:12345/eureka/
# defaultZone: http://127.0.0.1:8004/eureka/
registry-fetch-interval-seconds: 30
... ...
... ... @@ -213,6 +213,13 @@
<!-- </dependency>-->
<dependency>
<groupId>net.sf.json-lib</groupId>
<artifactId>json-lib</artifactId>
<version>2.4</version>
<classifier>jdk15</classifier>
</dependency>
<dependency>
<groupId>de.codecentric</groupId>
<artifactId>spring-boot-admin-starter-client</artifactId>
<version>2.1.6</version>
... ... @@ -242,6 +249,35 @@
<version>0.0.9</version>
</dependency>
<!-- https://mvnrepository.com/artifact/org.apache.httpcomponents/httpclient -->
<dependency>
<groupId>org.apache.httpcomponents</groupId>
<artifactId>httpclient</artifactId>
<version>4.5.13</version>
</dependency>
<!-- https://mvnrepository.com/artifact/com.google.code.gson/gson -->
<dependency>
<groupId>com.google.code.gson</groupId>
<artifactId>gson</artifactId>
<version>2.8.6</version>
</dependency>
<!-- sm4jar-->
<!-- https://mvnrepository.com/artifact/org.bouncycastle/bcprov-jdk16 -->
<!-- <dependency>-->
<!-- <groupId>org.bouncycastle</groupId>-->
<!-- <artifactId>bcprov-jdk16</artifactId>-->
<!-- <version>1.46</version>-->
<!-- </dependency>-->
<dependency>
<groupId>commons-httpclient</groupId>
<artifactId>commons-httpclient</artifactId>
<version>3.1</version>
</dependency>
</dependencies>
<dependencyManagement>
... ...
... ... @@ -4,38 +4,45 @@ import com.alibaba.fastjson.JSON;
import com.google.code.kaptcha.impl.DefaultKaptcha;
import com.google.gson.Gson;
import com.thoughtworks.xstream.core.util.Base64Encoder;
import com.tianbo.warehouse.bean.AuthSuccessResponse;
import com.tianbo.warehouse.controller.response.ResultJson;
import com.tianbo.warehouse.controller.response.ResultMessage;
import com.tianbo.warehouse.dao.KakoUserMapper;
import com.tianbo.warehouse.model.KakoUser;
import com.tianbo.warehouse.model.ROLE;
import com.tianbo.warehouse.model.resource.UserDate;
import com.tianbo.warehouse.security.filter.JwtTokenUtil;
import com.tianbo.warehouse.service.PermissionService;
import com.tianbo.warehouse.service.RoleService;
import com.tianbo.warehouse.service.kakoImp.KakoUserService;
import com.tianbo.warehouse.util.JsonUtil;
import com.tianbo.warehouse.util.KIAM.HttpClientUtil;
import com.tianbo.warehouse.util.RedisUtils;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.util.StringUtils;
import org.springframework.web.bind.annotation.*;
import javax.imageio.ImageIO;
import javax.servlet.http.Cookie;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.awt.image.BufferedImage;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import java.util.UUID;
import java.util.*;
@Slf4j
@RestController()
@RequestMapping("/anonymous")
public class AnonymousController {
@Value("${jwt.max-alive}")
protected Integer jwtMaxAlive;
@Autowired
RoleService roleService;
... ... @@ -43,8 +50,32 @@ public class AnonymousController {
RedisUtils redisUtils;
@Autowired
KakoUserMapper kakoUserMapperl;
@Autowired
private DefaultKaptcha captchaProducer;
@Autowired
private PermissionService permissionService;
@Autowired
private KakoUserMapper kakoUserMapper;
@Autowired
private KakoUserService kakoUserService;
/**
* 验证服务票据响应属性名
*/
private static final String SERVICE_RESPONESE = "serviceResponse";
private static final String AUTHENTICATION_SUCCESS = "authenticationSuccess";
private static final String LOGIN_NAME = "LOGIN_NAME";
private static final String ATTRIBUTES = "attributes";
private static final String USER_ID = "USER_ID";
/**
* 配置匿名者可以访问的路由,并更新到redis,匿名者默认可以访问的role_name =ROLE_anonymous
* 此方法会将所有符合权限组名=ROLE_anonymous的权限更新到redis中,供gateway调用判断权限
... ... @@ -86,4 +117,150 @@ public class AnonymousController {
return new ResultJson("200","verify get ok",map,verifyToken);
}
/**
* 验证票据
* @param ticket
* @return
* @throws Exception
*/
@RequestMapping (value = "/ssoLogin")
@ResponseBody
public AuthSuccessResponse ssoLogin(String ticket) throws Exception {
try {
log.info("票据接受:{}", ticket);
if (!StringUtils.isEmpty(ticket)){
log.info("开始验证票据");
String result = HttpClientUtil.httpGet("http://10.5.14.103:27080/sso/p3/serviceValidate?format=json&service="+"http://10.50.7.70:9909/%23/ssologin"+"&ticket="+ticket, "UTF-8");
log.info("验证票据返回值:{}", result);
Map<String, Object> userInfo = resolveUserInfo(result);
if (userInfo != null){
log.info("userInfo:{}", userInfo);
// KakoUser user = kakoUserMapper.findLonginName(userInfo.get("loginName").toString(), userInfo.get("userId").toString());
KakoUser user = kakoUserService.loadByUsername(userInfo.get("loginName").toString());
log.info("查询用户信息:{}", user);
//返回前端登陆成功后的用户信息
KakoUser loginedUser = new KakoUser();
loginedUser.setLoginName(user.getUsername());
loginedUser.setId(user.getId());
loginedUser.setName(user.getName());
loginedUser.setRoles(user.getRoles());
//设置用户的TOKEN的有效时间,时间配置在配置文件中设置
String jwtToken = JwtTokenUtil.generateToken(loginedUser.getUsername(), jwtMaxAlive);
log.info("设置用户token:{}", jwtToken);
loginedUser.setToken(jwtToken);
//这里将登录成功的[user]对象数据写入redis缓存,KEY为token value为user的JSON对象
String json = JSON.toJSONString(user);
boolean set = redisUtils.set(jwtToken, json, 3600 * 24 * 7);
log.info("用户信息存入redis:{}", set);
Map<String,Object> menuMap = permissionService.getUserMenusKako(user.getId());
//返回用户信息和用户可访问的目录列表
return new AuthSuccessResponse(loginedUser,menuMap);
}
return null;
}else {
return null;
}
}catch (Exception e){
e.printStackTrace();
return null;
}
}
public Map<String, Object> resolveUserInfo(String result){
//认证成功,解析用户信息
Gson gson = new Gson();
Map resultMap = gson.fromJson(result, Map.class);
Object serviceResponse = resultMap.get(SERVICE_RESPONESE);
if(serviceResponse != null && serviceResponse instanceof Map){
Object authenticationSuccess = ((Map) serviceResponse).get(AUTHENTICATION_SUCCESS);
if(authenticationSuccess != null && authenticationSuccess instanceof Map){
Map<String, Object> userInfo = new HashMap<>();
userInfo.put("attributes", ((Map) authenticationSuccess).get(ATTRIBUTES));
Object attributes = ((Map) authenticationSuccess).get("attributes");
userInfo.put("loginName", ((Map) attributes).get(LOGIN_NAME));
userInfo.put("userId", ((Map) attributes).get(USER_ID));
return userInfo;
}
}
return null;
}
/**
* 资源同步
* @param map
* @return
* @throws Exception
*/
@PostMapping(value = "/userSynchronization")
@ResponseBody
public ResultMessage userSynchronization(@RequestBody Map<String, Object> map) throws Exception {
if ("user".equals(map.get("resType").toString())){
JsonUtil jsonUtil = new JsonUtil();
List<UserDate> list = jsonUtil.mapToList(map, UserDate.class, "data");
// 判断该用户是否存在
int i = 0;
for (UserDate userDate: list){
log.info("用户信息:{}", userDate);
if (kakoUserMapperl.findLonginName(userDate.getLOGIN_NAME(), "") != null){
KakoUser kakoUser = new KakoUser();
kakoUser.setLoginName(userDate.getLOGIN_NAME());
kakoUser.setPassword(userDate.getPWD());
kakoUser.setUserSyncId(userDate.getUSER_ID());
kakoUser.setMobile(userDate.getMOBILE());
kakoUser.setEmail(userDate.getEMAIL());
kakoUser.setDelFlag("0");
kakoUser.setName(userDate.getUSER_NAME());
kakoUser.setCompanyId("1");
kakoUser.setOfficeId("5e95a0f081c64fce9f85d59e18cfdc5f");
kakoUser.setUpdateBy("tyrz");
kakoUser.setLoginFlag("1");
kakoUser.setUpdateDate(new Date());
log.info("通过账号为条件更新");
i = kakoUserMapperl.updateSyncUserLoginName(kakoUser);
}else {
if (kakoUserMapperl.findLonginName("", userDate.getUSER_ID()) != null){
KakoUser kakoUser = new KakoUser();
kakoUser.setLoginName(userDate.getLOGIN_NAME());
kakoUser.setPassword(userDate.getPWD());
kakoUser.setUserSyncId(userDate.getUSER_ID());
kakoUser.setMobile(userDate.getMOBILE());
kakoUser.setEmail(userDate.getEMAIL());
kakoUser.setDelFlag("0");
kakoUser.setName(userDate.getUSER_NAME());
kakoUser.setCompanyId("1");
kakoUser.setOfficeId("5e95a0f081c64fce9f85d59e18cfdc5f");
kakoUser.setUpdateBy("tyrz");
kakoUser.setLoginFlag("1");
kakoUser.setUpdateDate(new Date());
log.info("账号不存在用过统一认证id更新");
i = kakoUserMapperl.updateSyncUserId(kakoUser);
}else {
KakoUser kakoUser = new KakoUser();
kakoUser.setId(UUID.randomUUID().toString());
kakoUser.setLoginName(userDate.getLOGIN_NAME());
kakoUser.setPassword(userDate.getPWD());
kakoUser.setUserSyncId(userDate.getUSER_ID());
kakoUser.setMobile(userDate.getMOBILE());
kakoUser.setEmail(userDate.getEMAIL());
kakoUser.setName(userDate.getUSER_NAME());
kakoUser.setCompanyId("1");
kakoUser.setOfficeId("5e95a0f081c64fce9f85d59e18cfdc5f");
kakoUser.setLoginFlag("1");
kakoUser.setCreateBy("tyrz");
kakoUser.setUpdateBy("tyrz");
kakoUser.setCreateDate(new Date());
kakoUser.setUpdateDate(new Date());
log.info("账号统一认证id都不在 新增");
i = kakoUserMapperl.insertSelective(kakoUser);
}
}
}
return i > 0 ? new ResultMessage("200","资源同步成功"):new ResultMessage("202", "资源同步失败");
}
return new ResultMessage("201","不是用户信息");
}
}
... ...
... ... @@ -2,49 +2,36 @@ package com.tianbo.warehouse.controller.kako;
import com.alibaba.fastjson.JSON;
import com.github.pagehelper.PageInfo;
import com.google.code.kaptcha.Constants;
import com.google.code.kaptcha.impl.DefaultKaptcha;
import com.google.code.kaptcha.util.Config;
import com.tianbo.warehouse.annotation.LogAnnotation;
import com.tianbo.warehouse.annotation.RequestRequire;
import com.tianbo.warehouse.annotation.UserPasswordMd5;
import com.tianbo.warehouse.annotation.cache.annotation.RedisCacheDelTarget;
import com.tianbo.warehouse.controller.response.ResultJson;
import com.tianbo.warehouse.dao.KakoUserMapper;
import com.tianbo.warehouse.controller.response.ResultMessage;
import com.tianbo.warehouse.model.KakoUser;
import com.tianbo.warehouse.model.KakoUserRole;
import com.tianbo.warehouse.model.USERS;
import com.tianbo.warehouse.model.UserRole;
import com.tianbo.warehouse.security.CustomUserDetailService;
import com.tianbo.warehouse.service.UserService;
import com.tianbo.warehouse.service.kakoImp.KakoUserService;
import com.tianbo.warehouse.service.validated.InsertUser;
import com.tianbo.warehouse.service.validated.UpdateUser;
import com.tianbo.warehouse.util.KIAM.HttpClientUtil;
import com.tianbo.warehouse.util.RedisUtils;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import net.sf.json.JSONObject;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.security.core.context.SecurityContextHolder;
import org.springframework.security.core.userdetails.UserDetails;
import org.springframework.validation.BindingResult;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.*;
import javax.annotation.Resource;
import javax.imageio.ImageIO;
import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;
import java.awt.image.BufferedImage;
import java.io.IOException;
import java.util.List;
import java.util.Map;
import java.util.Properties;
@RestController
@Slf4j
... ... @@ -175,5 +162,4 @@ public class UserController {
}
return new ResultJson("500","缓存更新失败");
}
}
... ...
package com.tianbo.warehouse.controller.response;
import lombok.Data;
import java.io.Serializable;
/**
* @author shenhailong
* <p> 返回统一认证接口
* 2020/12/22/16:41
*/
@Data
public class ResultMessage implements Serializable {
private static final long serialVersionUID = 1L;
private String resultCode;
private String resultMessage;
public ResultMessage(String resultCode, String resultMessage) {
this.resultCode = resultCode;
this.resultMessage = resultMessage;
}
}
... ...
package com.tianbo.warehouse.dao;
import com.tianbo.warehouse.model.KakoUser;
import org.apache.ibatis.annotations.Param;
import java.util.List;
... ... @@ -23,5 +24,12 @@ public interface KakoUserMapper {
int lockUser(KakoUser record);
KakoUser findLonginName(@Param(value = "loginName") String loginName,
@Param(value = "userSyncId") String userSyncId);
int updateSyncUserLoginName(KakoUser kakoUser);
int updateSyncUserId(KakoUser kakoUser);
}
\ No newline at end of file
... ...
... ... @@ -5,6 +5,7 @@ import com.alibaba.fastjson.serializer.SerializerFeature;
import com.tianbo.warehouse.service.validated.InsertUser;
import com.tianbo.warehouse.service.validated.UpdateUser;
import com.tianbo.warehouse.validate.CheckUserExist;
import lombok.Data;
import org.hibernate.validator.constraints.Length;
import org.springframework.security.core.GrantedAuthority;
import org.springframework.security.core.authority.SimpleGrantedAuthority;
... ... @@ -17,6 +18,7 @@ import java.util.Collection;
import java.util.Date;
import java.util.List;
@Data
public class KakoUser implements UserDetails {
private String id;
... ... @@ -33,6 +35,8 @@ public class KakoUser implements UserDetails {
@Length(min = 6, max = 22, message = "密码 长度必须在 {min} - {max} 之间",groups=InsertUser.class)
private String password;
private String oldPassword;
private String no;
private String name;
... ... @@ -67,6 +71,8 @@ public class KakoUser implements UserDetails {
private String token;
private String userSyncId;
@JSONField(serialzeFeatures= {SerializerFeature.WriteMapNullValue,SerializerFeature.WriteNullStringAsEmpty})
private List<ROLE> roles;
... ...
package com.tianbo.warehouse.model.resource;
import lombok.Data;
/**
* @author shenhailong
* <p> 用户修改密码推送统一认证 接受 返回实体类
* 2020/12/25/13:23
*/
@Data
public class ResultPwd {
private String result;
private String resultMsg;
}
... ...
package com.tianbo.warehouse.model.resource;
import lombok.Data;
/**
* @author shenhailong
* <p>
* 2020/12/22/15:10
*/
@Data
public class UserDate {
private String USER_ID;
private String USER_NAME;
private String USER_NO;
private String MOBILE;
private String IDCARD_NO;
private String COUNTRY;
private String SEX;
private String NATIONALITY;
private String OFFICE_PHONE;
private String OFFICE_ADDRESS;
private String EMAIL;
private String JOB_LEVEL;
private String JOB_TITLE;
private String JOB_TYPE;
private String JOB_STATUS;
private String JOB_POSITION;
private String SECRET_LEVEL;
private String USER_POST;
private String USER_JOB_ID;
private String ORG_ID;
private String USER_TITLE;
private String LOGIN_NAME;
private String SHOW_ORDER;
private String REMARK;
private String NAIL_ID;
private String PK_PSNDOC;
private String PWD;
private String PWD_ENCRYPT;
private String UPDATE_TIME;
}
... ...
package com.tianbo.warehouse.model.resource;
import lombok.Data;
import java.io.Serializable;
import java.util.List;
/**
* @author shenhailong
* <p>
* 2020/12/22/15:08
*/
@Data
public class UserSync{
private String action;
private String resType;
private String syncTime;
private List data;
}
... ...
... ... @@ -5,12 +5,15 @@ import com.tianbo.warehouse.model.KakoUser;
import com.tianbo.warehouse.model.USERS;
import com.tianbo.warehouse.security.CustomUserDetailService;
import com.tianbo.warehouse.service.UserService;
import com.tianbo.warehouse.util.KIAM.SM3EncryptUtil;
import com.tianbo.warehouse.util.RedisUtils;
import org.apache.shiro.codec.CodecException;
import org.apache.shiro.crypto.hash.Hash;
import org.apache.shiro.crypto.hash.SimpleHash;
import org.apache.shiro.util.ByteSource;
import org.bouncycastle.jcajce.provider.digest.SM3;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.security.authentication.AuthenticationProvider;
import org.springframework.security.authentication.BadCredentialsException;
import org.springframework.security.authentication.DisabledException;
... ... @@ -43,6 +46,9 @@ public class MyLoginAuthenticationProvider extends CodecSupport implements Authe
@Autowired
private RedisUtils redisUtils;
// @Value("${http.serverStatus}")
// private String serverStatus;
@Override
public Authentication authenticate(Authentication authentication) throws AuthenticationException {
// 获取前端表单中输入后返回的用户名、密码
... ... @@ -51,7 +57,6 @@ public class MyLoginAuthenticationProvider extends CodecSupport implements Authe
UserDetails userInfo = userDetailsService.loadUserByUsername(userName);
//验证登录密码是否符合规则,如位数包含的字符等
boolean isValid = PasswordSaltUtils.isValidPassword(password, userInfo.getPassword(), "");
// 验证密码
... ... @@ -64,11 +69,12 @@ public class MyLoginAuthenticationProvider extends CodecSupport implements Authe
}
//取盐规则
byte[] salt = PasswordSaltUtils.getSalt16(userInfo.getPassword());
// byte[] salt = PasswordSaltUtils.getSalt16(userInfo.getPassword());
//真实密码
String realPass = PasswordSaltUtils.getPassword16(userInfo.getPassword());
// String realPass = PasswordSaltUtils.getPassword16(userInfo.getPassword());
//用户登录密码与盐运算
Object tokenHashedCredentials = this.hashProvidedCredentials(password,salt,1024);
// Object tokenHashedCredentials = this.hashProvidedCredentials(password,salt,1024);
try{
String loginUserLock = redisUtils.get(userName+"-lock");
... ... @@ -77,7 +83,9 @@ public class MyLoginAuthenticationProvider extends CodecSupport implements Authe
loginUserLockNO = Integer.valueOf(loginUserLock);
}
//判断密码是否正确
if(!equals(realPass,tokenHashedCredentials.toString())){
// if(!equals(realPass,tokenHashedCredentials.toString())){
// sm3加密
if(!equals(SM3EncryptUtil.passwordSm3(password),userInfo.getPassword())){
redisUtils.set(userName+"-lock", String.valueOf(++loginUserLockNO),120);
//两分钟内错误登录次数超过5次锁定账户
... ... @@ -92,8 +100,6 @@ public class MyLoginAuthenticationProvider extends CodecSupport implements Authe
}catch (Exception e){
throw new BadCredentialsException("验证失败!");
}
// 前后端分离情况下 处理逻辑...
// 更新登录令牌 - 之后访问系统其它接口直接通过token认证用户权限...
return new UsernamePasswordAuthenticationToken(userInfo, password, userInfo.getAuthorities());
... ...
... ... @@ -3,21 +3,22 @@ package com.tianbo.warehouse.service.kakoImp;
import com.github.pagehelper.Page;
import com.github.pagehelper.PageHelper;
import com.github.pagehelper.PageInfo;
import com.google.gson.Gson;
import com.tianbo.warehouse.dao.KakoUserMapper;
import com.tianbo.warehouse.dao.ROLEMapper;
import com.tianbo.warehouse.dao.UserRoleMapper;
import com.tianbo.warehouse.model.*;
import com.tianbo.warehouse.security.handel.kakologin.Digests;
import com.tianbo.warehouse.security.handel.kakologin.Encodes;
import com.tianbo.warehouse.model.resource.ResultPwd;
import com.tianbo.warehouse.service.PermissionService;
import com.tianbo.warehouse.util.KIAM.HttpClientUtil;
import com.tianbo.warehouse.util.KIAM.SM3EncryptUtil;
import com.tianbo.warehouse.util.KIAM.SM4EncryptUtil;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import javax.annotation.Resource;
import java.util.Date;
import java.util.List;
import java.util.UUID;
import java.util.*;
@Service
public class KakoUserServiceImpl implements KakoUserService{
... ... @@ -79,11 +80,28 @@ public class KakoUserServiceImpl implements KakoUserService{
public int updateByPrimaryKeySelective(KakoUser record){
int i = 0;
if(record.getPassword()!=null && !record.getPassword().isEmpty()){
String entryPassWord = entryptPassword(record.getPassword());
record.setPassword(entryPassWord);
}
if (record!=null){
i = kakoUserMapper.updateByPrimaryKeySelective(record);
// String entryPassWord = entryptPassword(record.getPassword());
// 更改运用sm3加密
try {
// 通知统一认证接口 新密码 旧密码 运用sm4加密推送
Map<String, Object> map = new HashMap<>();
SM4EncryptUtil sm4EncryptUtil = new SM4EncryptUtil();
String OLD_PWD = sm4EncryptUtil.pwd(record.getOldPassword());
map.put("OLD_PWD", OLD_PWD);
String NEW_PWD = sm4EncryptUtil.pwd(record.getPassword());
map.put("NEW_PWD", NEW_PWD);
String result = HttpClientUtil.httpPost("http://10.5.14.103:28080/urm/service/V3/res/user/updatePwd?userId="+record.getUserSyncId(), map);
Gson gson = new Gson();
ResultPwd resultPwd = gson.fromJson(result, ResultPwd.class);
if ("true".equals(resultPwd.getResult())){
record.setPassword(SM3EncryptUtil.passwordSm3(record.getPassword()));
i = kakoUserMapper.updateByPrimaryKeySelective(record);
}
}catch (Exception e){
e.printStackTrace();
}
}
return i;
... ... @@ -100,8 +118,13 @@ public class KakoUserServiceImpl implements KakoUserService{
return 0;
}
if(record.getPassword()!=null && !record.getPassword().isEmpty()){
String entryPassWord = entryptPassword(record.getPassword());
record.setPassword(entryPassWord);
// String entryPassWord = entryptPassword(record.getPassword());
// 更改用户密码加密方式 sm3加密 跟base64
try {
record.setPassword(SM3EncryptUtil.passwordSm3(record.getPassword()));
}catch (Exception e){
e.printStackTrace();
}
}
record.setCreateDate(new Date());
record.setUpdateDate(new Date());
... ... @@ -113,12 +136,12 @@ public class KakoUserServiceImpl implements KakoUserService{
/**
* 生成安全的密码,生成随机的16位salt并经过1024次 sha-1 hash
*/
public static String entryptPassword(String plainPassword) {
String plain = Encodes.unescapeHtml(plainPassword);
byte[] salt = Digests.generateSalt(SALT_SIZE);
byte[] hashPassword = Digests.sha1(plain.getBytes(), salt, HASH_INTERATIONS);
return Encodes.encodeHex(salt)+Encodes.encodeHex(hashPassword);
}
// public static String entryptPassword(String plainPassword) {
// String plain = Encodes.unescapeHtml(plainPassword);
// byte[] salt = Digests.generateSalt(SALT_SIZE);
// byte[] hashPassword = Digests.sha1(plain.getBytes(), salt, HASH_INTERATIONS);
// return Encodes.encodeHex(salt)+Encodes.encodeHex(hashPassword);
// }
/**
* 检查是否存在用户
... ...
package com.tianbo.warehouse.util;
import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import java.util.List;
import java.util.Map;
/**
* @author shenhailong
* <p>
* 2020/12/16/16:12
*/
public class JsonUtil<T> {
public static JSONObject mapToJson(Map<String, Object> map) {
String data = JSON.toJSONString(map);
return JSON.parseObject(data);
}
/**
* map中取key对应的value
* @param map
* @param key
* @return
*/
public String mapToString(Map<String, Object> map, String key) {
JSONObject jsonObject = mapToJson(map);
return jsonObject.getString(key);
}
/**
* map中取类对象
* @param map
* @param clazz
* @param key
* @param <T>
* @return
*/
public static <T> T mapToObject(Map<String, Object> map, Class<T> clazz, String key) {
T t = null;
JSONObject jsonObject = mapToJson(map);
JSONObject object = jsonObject.getJSONObject(key);
t = object.toJavaObject(clazz);
return t;
}
/**
* map中取list
* @param map
* @param clazz
* @param key
* @return
*/
public List<T> mapToList(Map<String, Object> map, Class<T> clazz, String key) {
List<T> t = null;
JSONObject jsonObject = mapToJson(map);
JSONArray array = jsonObject.getJSONArray(key);
t = array.toJavaList(clazz);
return t;
}
}
... ...
package com.tianbo.warehouse.util.KIAM;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.HttpException;
import org.apache.commons.httpclient.HttpStatus;
import org.apache.commons.httpclient.NameValuePair;
import org.apache.commons.httpclient.methods.GetMethod;
import org.apache.commons.httpclient.methods.PostMethod;
import org.apache.commons.httpclient.params.HttpMethodParams;
import java.io.IOException;
import java.util.Iterator;
import java.util.Map;
@Slf4j
public class HttpClientUtil {
public static String httpReader(String url, String code) {
System.out.println("GetPage:" + url);
HttpClient client = new HttpClient();
GetMethod method = new GetMethod(url);
String result = null;
try {
client.executeMethod(method);
int status = method.getStatusCode();
if (status == HttpStatus.SC_OK) {
result = method.getResponseBodyAsString();
} else {
System.out.println("Method failed: " + method.getStatusLine());
}
} catch (HttpException e) {
// �����������쳣��������Э�鲻�Ի��߷��ص�����������
System.out.println("Please check your provided http address!");
e.printStackTrace();
} catch (IOException e) {
// ���������쳣
System.out.println("���������쳣��");
e.printStackTrace();
} finally {
// �ͷ�����
if (method != null) {
method.releaseConnection();
}
method = null;
client = null;
}
return result;
}
public static String httpGet(String url, String code) {
log.info("GetPage:{}"+ url);
String content = null;
HttpClient httpClient = new HttpClient();
//����header
httpClient.getParams().setParameter(HttpMethodParams.USER_AGENT, "Mozilla/5.0 (X11; U; Linux i686; zh-CN; rv:1.9.1.2) Gecko/20090803 Fedora/3.5.2-2.fc11 Firefox/3.5.2");
GetMethod method = new GetMethod(url);
try {
int statusCode = httpClient.executeMethod(method);
System.out.println("httpClientUtils::statusCode=" + statusCode);
System.out.println(method.getStatusLine());
content = new String(method.getResponseBody(), code);
} catch (Exception e) {
System.out.println("time out");
e.printStackTrace();
} finally {
if (method != null) method.releaseConnection();
method = null;
httpClient = null;
}
return content;
}
public static String httpPost(String url, Map paramMap, String code) {
System.out.println("GetPage:" + url);
String content = null;
if (url == null || url.trim().length() == 0 || paramMap == null
|| paramMap.isEmpty()) {
return null;
}
HttpClient httpClient = new HttpClient();
//����header
httpClient.getParams().setParameter(HttpMethodParams.USER_AGENT, "Mozilla/5.0 (X11; U; Linux i686; zh-CN; rv:1.9.1.2) Gecko/20090803 Fedora/3.5.2-2.fc11 Firefox/3.5.2");//
//��������
//httpClient.getHostConfiguration().setProxy("128.128.176.74", 808);
PostMethod method = new PostMethod(url);
Iterator it = paramMap.keySet().iterator();
while (it.hasNext()) {
String key = it.next() + "";
Object o = paramMap.get(key);
if (o != null && o instanceof String) {
method.addParameter(new NameValuePair(key, o.toString()));
}
if (o != null && o instanceof String[]) {
String[] s = (String[]) o;
if (s != null) {
for (int i = 0; i < s.length; i++) {
method.addParameter(new NameValuePair(key, s[i]));
}
}
}
}
try {
int statusCode = httpClient.executeMethod(method);
System.out.println("httpClientUtils::statusCode=" + statusCode);
System.out.println(method.getStatusLine());
content = new String(method.getResponseBody(), code);
} catch (Exception e) {
System.out.println("time out");
e.printStackTrace();
} finally {
if (method != null) {
method.releaseConnection();
}
method = null;
httpClient = null;
}
return content;
}
public static String httpPost(String url, Map paramMap) {
//���룺UTF-8
return HttpClientUtil.httpPost(url, paramMap, "UTF-8");
}
}
... ...
package com.tianbo.warehouse.util.KIAM;
import org.bouncycastle.crypto.digests.SM3Digest;
import org.bouncycastle.jce.provider.BouncyCastleProvider;
import java.io.UnsupportedEncodingException;
import java.security.Security;
import java.util.Base64;
/**
* sm3生成密码摘要
* 需要依赖 Bouncy Castle轻量级密码术包 1.60
*/
public class SM3EncryptUtil {
private static byte[] SECRET_KEY = {101, 87, 99, 10, 34, 45, 77, 76, 98, 13, 12, 18, 73, 84, 91, 93};
public static byte[] hash(byte[] srcData) {
SM3Digest digest = new SM3Digest();
digest.update(srcData, 0, srcData.length);
byte[] hash = new byte[digest.getDigestSize()];
digest.doFinal(hash, 0);
return hash;
}
public static String bytetoString(byte[] digest) {
String str = "";
String tempStr = "";
for (int i = 0; i < digest.length; i++) {
tempStr = (Integer.toHexString(digest[i] & 0xff));
if (tempStr.length() == 1) {
str = str + "0" + tempStr;
} else {
str = str + tempStr;
}
}
return str.toLowerCase();
}
// public static void main(String[] args) {
// Security.addProvider(new BouncyCastleProvider());
// try {
// String pwdDigest = passwordSm3("vmvnv1v2VV.");
// System.out.println(pwdDigest);
// } catch (Exception e) {
// e.printStackTrace();
// }
// }
/**
* 密码SM3加密
* @param password
* @return
*/
public static String passwordSm3(String password){
Security.addProvider(new BouncyCastleProvider());
try {
byte[] pwdBytes = password.getBytes("UTF-8");
byte[] pwdDigest = hash(pwdBytes);
return bytetoString(pwdDigest);
} catch (Exception e) {
e.printStackTrace();
return null;
}
}
}
... ...
package com.tianbo.warehouse.util.KIAM;
import com.tianbo.warehouse.model.resource.ResultPwd;
import org.bouncycastle.jce.provider.BouncyCastleProvider;
import javax.crypto.BadPaddingException;
import javax.crypto.Cipher;
import javax.crypto.IllegalBlockSizeException;
import javax.crypto.NoSuchPaddingException;
import javax.crypto.spec.SecretKeySpec;
import java.security.*;
import java.util.Base64;
/**
* sm4加密工具
* 需要依赖 Bouncy Castle轻量级密码术包 1.60
*/
public class SM4EncryptUtil {
/**
* 密钥, 禁止修改
*/
private static byte[] SECRET_KEY = {101, 87, 99, 10, 34, 45, 77, 76, 98, 13, 12, 18, 73, 84, 91, 93};
/**
* 解密方法
*/
public static byte[] decryptSM4( byte[] cipherText)
throws IllegalBlockSizeException, BadPaddingException, InvalidKeyException,
NoSuchAlgorithmException, NoSuchProviderException, NoSuchPaddingException {
return decryptSM4(SECRET_KEY, cipherText);
}
public static byte[] decryptSM4(byte[] key, byte[] cipherText)
throws IllegalBlockSizeException, BadPaddingException, InvalidKeyException,
NoSuchAlgorithmException, NoSuchProviderException, NoSuchPaddingException {
Cipher cipher = generateEcbCipher("SM4/ECB/PKCS5Padding", Cipher.DECRYPT_MODE, key);
return cipher.doFinal(cipherText);
}
/**
* 解密方法
*/
public static byte[] encryptSM4( byte[] cipherText)
throws IllegalBlockSizeException, BadPaddingException, InvalidKeyException,
NoSuchAlgorithmException, NoSuchProviderException, NoSuchPaddingException {
return encryptSM4(SECRET_KEY, cipherText);
}
public static byte[] encryptSM4(byte[] key, byte[] data)
throws InvalidKeyException, NoSuchAlgorithmException, NoSuchProviderException,
NoSuchPaddingException, IllegalBlockSizeException, BadPaddingException {
Cipher cipher = generateEcbCipher("SM4/ECB/PKCS5Padding", Cipher.ENCRYPT_MODE, key);
return cipher.doFinal(data);
}
private static Cipher generateEcbCipher(String algorithmName, int mode, byte[] key)
throws NoSuchAlgorithmException, NoSuchProviderException, NoSuchPaddingException,
InvalidKeyException {
Cipher cipher = Cipher.getInstance(algorithmName, "BC");
Key sm4Key = new SecretKeySpec(key, "SM4");
cipher.init(mode, sm4Key);
return cipher;
}
public static void main(String[] args) {
Security.addProvider(new BouncyCastleProvider());
try {
ResultPwd resultPwd = new ResultPwd();
resultPwd.setResult("123456");
// String pwd = "vmvnv1v2VV.";
SM4EncryptUtil sm4EncryptUtil = new SM4EncryptUtil();
String pwd = sm4EncryptUtil.pwd("123456");
String encryptPwd = new String(Base64.getEncoder().encode(encryptSM4(pwd.getBytes("UTF-8"))));
System.out.println("加密密码: " +encryptPwd);
String originPwd = new String(decryptSM4(Base64.getDecoder().decode(encryptPwd)));
System.out.println("解密密码: "+ originPwd);
} catch (Exception e) {
e.printStackTrace();
}
}
public String pwd(String pwd){
try {
String encryptPwd = new String(Base64.getEncoder().encode(encryptSM4(pwd.getBytes("UTF-8"))));
return encryptPwd;
} catch (Exception e) {
e.printStackTrace();
return "";
}
}
}
... ...
package com.tianbo.warehouse.util.KIAM;
import org.apache.http.HttpStatus;
import org.apache.http.client.ClientProtocolException;
import org.apache.http.client.config.RequestConfig;
import org.apache.http.client.methods.CloseableHttpResponse;
import org.apache.http.client.methods.HttpGet;
import org.apache.http.client.methods.HttpPut;
import org.apache.http.entity.StringEntity;
import org.apache.http.impl.client.CloseableHttpClient;
import org.apache.http.impl.client.HttpClients;
import org.apache.http.util.EntityUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import com.google.gson.Gson;
import java.io.IOException;
import java.net.URI;
import java.net.URISyntaxException;
import java.util.Calendar;
import java.util.HashMap;
import java.util.Map;
import org.apache.commons.lang3.RandomStringUtils;
import org.apache.commons.lang3.StringUtils;
/**
* @author shenhailong
* <p>
* 2020/12/14/16:24
*/
public class SignatureDemo {
private static final Logger logger = LoggerFactory.getLogger(SignatureDemo.class);
// 接口服务地址

static String restSever = "http://10.5.14.103:28087/upm/service/V1/auth/userApp";
//应用标识

static String appKey = "8744334580944896";
// 身份系统签发给应用对接的密钥

static String appPwd = "c6dddfab2b59d87f98c703d924f3718bb4350f17";
public static void doMain() {
// 时间戳

Long ts = Calendar.getInstance().getTime().getTime();
// 随机数

String once = RandomStringUtils.randomAlphanumeric(32);
// 接口header中的公共参数

String commonParamUrl = String.format("appKey=%s" + "&" + "ts=%s" + "&" + "once=%s", appKey, ts, once);
// 创建HttpClient对象

CloseableHttpClient httpclient = HttpClients.createDefault();
/**
* GET查询接口演示代码
*/
String getQueryParam = "startTime=2019-06-21T08:00:00.000Z";
String getFullUrl = restSever + "?" + getQueryParam;
HttpGet httpGet = new HttpGet(getFullUrl);
// get请求查询参数,用在URL上的,这里若是通过ID查询的,接口中ID是作为路径存在的,所以需要将ID组合成

String getAllParamUrl = commonParamUrl + "&" + getQueryParam;
// 对参数签名,并放入请求header中的signData参数中

try {
// 签名数据

String signData = TokenUtils.getSignature(appPwd, getAllParamUrl);
//添加header参数 appCode、timestamp、 signatureNonce、signature

httpGet.addHeader("appKey", appKey);
httpGet.addHeader("ts", ts.toString());
httpGet.addHeader("once", once);
System.out.println("once:" + once);
httpGet.addHeader("signData", signData);
System.out.println("headers:" + httpGet.getAllHeaders());
String urlStr = httpGet.getURI().toString();
// 公共参数URL

System.out.println("commonParamter:" + urlStr);
if (StringUtils.endsWith(urlStr, "/")) {
urlStr = StringUtils.removeEnd(urlStr, "/");
}
httpGet.setURI(new URI(urlStr));
RequestConfig requestConfig = RequestConfig.custom().setConnectTimeout(3000).setConnectionRequestTimeout(3000).setSocketTimeout(3000).build();
httpGet.setConfig(requestConfig);
System.out.println("urlStr in request:" + httpGet.getURI().toString());
// 执行请求

CloseableHttpResponse response = httpclient.execute(httpGet);
// 取响应的结果

int statusCode = response.getStatusLine().getStatusCode();
// 打印响应结果

if (statusCode == HttpStatus.SC_OK) {
String resp = EntityUtils.toString(response.getEntity(), "utf-8");
System.out.println("status:" + statusCode);
System.out.println("result:" + resp);
}
} catch (URISyntaxException e) {
logger.error("签名失败:", e);
} catch (ClientProtocolException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
/**
 * PUT修改接口的演示代码,POST与PUT类似
 */
String ID = "aa03a5c692cf480b87887e0ff8cfe566";
// 这里若是通过ID查询的,接口中ID是作为路径存在的,所以需要将ID组合成

String putQueryParam = "ID=" + ID;
String putFullUrl = restSever + "/" + ID;
// 访问用户接口

HttpPut httpPut = new HttpPut(putFullUrl);
// 模拟POST/PUT的body中数据,需转为JSON进行签名。GET则没有这部分内容。

Map<String, Object> dataMap = new HashMap<String, Object>();
dataMap.put("USER_NAME", "张三");
String bodyParam = new Gson().toJson(dataMap);
String postAllParamUrl = commonParamUrl + "&" + putQueryParam + "&bodyData=" + bodyParam;
StringEntity bodyData = new StringEntity(bodyParam.toString(), "UTF-8");
httpPut.setEntity(bodyData);
// 对参数签名,并放入请求header中的signData参数中

try {
// 签名数据

String signData = TokenUtils.getSignature(appPwd, postAllParamUrl);
// 添加header参数 appCode、timestamp、 signatureNonce、signature

httpPut.addHeader("appKey", appKey);
httpPut.addHeader("ts", ts.toString());
httpPut.addHeader("once", once);
System.out.println("once:" + once);
httpPut.addHeader("signData", signData);
System.out.println("headers:" + httpPut.getAllHeaders());
String urlStr = httpPut.getURI().toString();
// 公共参数URL

System.out.println("commonParamter:" + urlStr);
if (StringUtils.endsWith(urlStr, "/")) {
urlStr = StringUtils.removeEnd(urlStr, "/");
}
httpPut.setURI(new URI(urlStr));
RequestConfig requestConfig = RequestConfig.custom().setConnectTimeout(3000).setConnectionRequestTimeout(3000).setSocketTimeout(3000).build();
httpPut.setConfig(requestConfig);
System.out.println("urlStr in request:" + httpPut.getURI().toString());
// 执行请求

CloseableHttpResponse response = httpclient.execute(httpPut);
// 取响应的结果

int statusCode = response.getStatusLine().getStatusCode();
// 打印响应结果

if (statusCode == HttpStatus.SC_OK) {
String resp = EntityUtils.toString(response.getEntity(), "utf-8");
System.out.println("status:" + statusCode);
System.out.println("result:" + resp);
}
} catch (URISyntaxException e) {
logger.error("签名失败:", e);
} catch (ClientProtocolException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
}
... ...
package com.tianbo.warehouse.util.KIAM;
import java.io.UnsupportedEncodingException;
import java.net.URLDecoder;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.util.Arrays;
import org.apache.commons.lang3.ArrayUtils;
import org.apache.commons.lang3.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
/**
* @author shenhailong
* <p>
* 2020/12/14/16:44
*/
public class TokenUtils {
private static final Logger logger = LoggerFactory.getLogger(TokenUtils.class);
private static String[] hexDigits = { "0", "1", "2", "3", "4", "5", "6", "7", "8", "9", "a", "b", "c", "d", "e","f" };
public static String getSignature(String appPwd, String paramUrl) {
if (StringUtils.isNotBlank(paramUrl)) {
try {
paramUrl = URLDecoder.decode(paramUrl, "UTF-8");
} catch (UnsupportedEncodingException e) {
logger.error("生成signData失败:", e);
throw new RuntimeException("生成signData失败:", e);
}
}
String[] paraArray = new String[] {};
if (StringUtils.isNotBlank(paramUrl)) {
String[] queryArray = paramUrl.split("&");
paraArray = (String[]) ArrayUtils.addAll(queryArray, paraArray);
} Arrays.sort(paraArray);
StringBuffer buffer = new StringBuffer();
buffer.append(appPwd);
buffer.append(":");
for (int i = 0; i < paraArray.length; i++) {
buffer.append(paraArray[i]);
buffer.append("&");
}
buffer.deleteCharAt(buffer.length() - 1);
buffer.append(":");
buffer.append(appPwd);
MessageDigest md = null;
try {
md = MessageDigest.getInstance("SM3");
md.update(buffer.toString().getBytes("UTF-8"));
} catch (NoSuchAlgorithmException e) {
logger.error("生成signData失败:", e);
throw new RuntimeException("生成signData失败.", e);
} catch (UnsupportedEncodingException e) {
logger.error("生成signData失败:", e);
throw new RuntimeException("生成signData失败.", e);
} String encode = byteArrayToHexString(md.digest());
return encode;
}
private static String byteArrayToHexString(byte[] byteArray) {
StringBuffer sb = new StringBuffer();
for (byte byt : byteArray) {
sb.append(byteToHexString(byt));
} return sb.toString();
}
private static String byteToHexString(byte byt) {
int n = byt;
if (n < 0) {
n = 256 + n;
}
return hexDigits[n / 16] + hexDigits[n % 16];
}
}
... ...
... ... @@ -23,11 +23,12 @@
<result column="update_date" property="updateDate" jdbcType="TIMESTAMP" />
<result column="remarks" property="remarks" jdbcType="VARCHAR" />
<result column="del_flag" property="delFlag" jdbcType="CHAR" />
<result column="user_sync_id" property="userSyncId" jdbcType="VARCHAR" />
</resultMap>
<sql id="Base_Column_List" >
id, company_id, office_id, login_name, password, no, name, email, phone, mobile,
user_type, photo, login_ip, login_date, login_flag, create_by, create_date, update_by,
update_date, remarks, del_flag
update_date, remarks, del_flag, user_sync_id
</sql>
<select id="selectByPrimaryKey" resultMap="BaseResultMap" parameterType="java.lang.String" >
select
... ... @@ -144,6 +145,9 @@
<if test="delFlag != null" >
del_flag,
</if>
<if test="userSyncId != null" >
user_sync_id,
</if>
</trim>
<trim prefix="values (" suffix=")" suffixOverrides="," >
<if test="id != null" >
... ... @@ -308,4 +312,146 @@
login_flag = #{loginFlag,jdbcType=VARCHAR}
where login_name = #{loginName,jdbcType=VARCHAR}
</update>
<select id="findLonginName" parameterType="java.lang.String" resultMap="BaseResultMap">
select
<include refid="Base_Column_List"/>
from
sys_user
where
1=1
<if test="loginName != null and loginName != ''">
and login_name = #{loginName,jdbcType=VARCHAR}
</if>
<if test="userSyncId != null and userSyncId != ''">
and user_sync_id = #{userSyncId,jdbcType=VARCHAR}
</if>
</select>
<update id="updateSyncUserLoginName" parameterType="com.tianbo.warehouse.model.KakoUser" >
update sys_user
<set >
<if test="companyId != null" >
company_id = #{companyId,jdbcType=VARCHAR},
</if>
<if test="officeId != null" >
office_id = #{officeId,jdbcType=VARCHAR},
</if>
<if test="password != null" >
password = #{password,jdbcType=VARCHAR},
</if>
<if test="no != null" >
no = #{no,jdbcType=VARCHAR},
</if>
<if test="name != null" >
name = #{name,jdbcType=VARCHAR},
</if>
<if test="email != null" >
email = #{email,jdbcType=VARCHAR},
</if>
<if test="phone != null" >
phone = #{phone,jdbcType=VARCHAR},
</if>
<if test="mobile != null" >
mobile = #{mobile,jdbcType=VARCHAR},
</if>
<if test="userType != null" >
user_type = #{userType,jdbcType=CHAR},
</if>
<if test="photo != null" >
photo = #{photo,jdbcType=VARCHAR},
</if>
<if test="loginIp != null" >
login_ip = #{loginIp,jdbcType=VARCHAR},
</if>
<if test="loginDate != null" >
login_date = #{loginDate,jdbcType=TIMESTAMP},
</if>
<if test="loginFlag != null" >
login_flag = #{loginFlag,jdbcType=VARCHAR},
</if>
<if test="createBy != null" >
create_by = #{createBy,jdbcType=VARCHAR},
</if>
<if test="createDate != null" >
create_date = #{createDate,jdbcType=TIMESTAMP},
</if>
<if test="updateBy != null" >
update_by = #{updateBy,jdbcType=VARCHAR},
</if>
<if test="updateDate != null" >
update_date = #{updateDate,jdbcType=TIMESTAMP},
</if>
<if test="remarks != null" >
remarks = #{remarks,jdbcType=VARCHAR},
</if>
<if test="delFlag != null" >
del_flag = #{delFlag,jdbcType=CHAR},
</if>
<if test="userSyncId != null" >
user_sync_id = #{userSyncId,jdbcType=VARCHAR}
</if>
</set>
where login_name = #{loginName,jdbcType=VARCHAR}
</update>
<update id="updateSyncUserId" parameterType="com.tianbo.warehouse.model.KakoUser" >
update sys_user
<set >
<if test="companyId != null" >
company_id = #{companyId,jdbcType=VARCHAR},
</if>
<if test="officeId != null" >
office_id = #{officeId,jdbcType=VARCHAR},
</if>
<if test="password != null" >
password = #{password,jdbcType=VARCHAR},
</if>
<if test="no != null" >
no = #{no,jdbcType=VARCHAR},
</if>
<if test="name != null" >
name = #{name,jdbcType=VARCHAR},
</if>
<if test="email != null" >
email = #{email,jdbcType=VARCHAR},
</if>
<if test="phone != null" >
phone = #{phone,jdbcType=VARCHAR},
</if>
<if test="mobile != null" >
mobile = #{mobile,jdbcType=VARCHAR},
</if>
<if test="userType != null" >
user_type = #{userType,jdbcType=CHAR},
</if>
<if test="photo != null" >
photo = #{photo,jdbcType=VARCHAR},
</if>
<if test="loginIp != null" >
login_ip = #{loginIp,jdbcType=VARCHAR},
</if>
<if test="loginDate != null" >
login_date = #{loginDate,jdbcType=TIMESTAMP},
</if>
<if test="loginFlag != null" >
login_flag = #{loginFlag,jdbcType=VARCHAR},
</if>
<if test="createBy != null" >
create_by = #{createBy,jdbcType=VARCHAR},
</if>
<if test="createDate != null" >
create_date = #{createDate,jdbcType=TIMESTAMP},
</if>
<if test="updateBy != null" >
update_by = #{updateBy,jdbcType=VARCHAR},
</if>
<if test="updateDate != null" >
update_date = #{updateDate,jdbcType=TIMESTAMP},
</if>
<if test="delFlag != null" >
del_flag = #{delFlag,jdbcType=CHAR}
</if>
</set>
where user_sync_id = #{userSyncId,jdbcType=VARCHAR}
</update>
</mapper>
\ No newline at end of file
... ...