Преглед на файлове

Merge branch 'master' of http://gogs.efunbox.cn:3000/Rankin/rankin

xuchaolang преди 6 години
родител
ревизия
a91873c70b
променени са 20 файла, в които са добавени 202 реда и са изтрити 31 реда
  1. 9 3
      rankin-api-web/src/main/java/cn/rankin/apiweb/controller/LoginController.java
  2. 2 0
      rankin-api-web/src/main/java/cn/rankin/apiweb/entity/GlobalHeader.java
  3. 9 1
      rankin-api-web/src/main/java/cn/rankin/apiweb/service/user/UserClient.java
  4. 51 7
      rankin-api-web/src/main/java/cn/rankin/apiweb/service/user/UserService.java
  5. 19 3
      rankin-cms-web/src/main/java/cn/rankin/cmsweb/controller/user/UserTagController.java
  6. 36 3
      rankin-common-utils/src/main/java/cn/rankin/common/utils/util/HttpUtil.java
  7. 2 0
      rankin-data-api/src/main/java/cn/rankin/data/api/app/dto/DeviceLoginDTO.java
  8. 2 0
      rankin-data-api/src/main/java/cn/rankin/data/api/app/dto/LoginInfoDTO.java
  9. 3 2
      rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/DeviceUserVo.java
  10. 3 0
      rankin-data-api/src/main/java/cn/rankin/data/api/user/dto/TerminalDeviceDTO.java
  11. 3 0
      rankin-data-api/src/main/java/cn/rankin/data/api/user/entity/TerminalDevice.java
  12. 3 0
      rankin-data-api/src/main/java/cn/rankin/data/api/user/entity/TerminalDeviceBindLog.java
  13. 3 0
      rankin-data-api/src/main/java/cn/rankin/data/api/user/entity/TerminalUser.java
  14. 2 0
      rankin-data-api/src/main/java/cn/rankin/data/api/user/vo/TerminalDeviceVo.java
  15. 2 0
      rankin-data-api/src/main/java/cn/rankin/data/api/user/vo/TerminalUserVo.java
  16. 7 1
      rankin-user-service/src/main/java/cn/rankin/userservice/controller/TerminalDeviceController.java
  17. 1 0
      rankin-user-service/src/main/java/cn/rankin/userservice/controller/TerminalUserController.java
  18. 6 1
      rankin-user-service/src/main/java/cn/rankin/userservice/repository/TerminalDeviceRepository.java
  19. 2 1
      rankin-user-service/src/main/java/cn/rankin/userservice/service/TerminalDeviceBindLogService.java
  20. 37 9
      rankin-user-service/src/main/java/cn/rankin/userservice/service/TerminalDeviceService.java

+ 9 - 3
rankin-api-web/src/main/java/cn/rankin/apiweb/controller/LoginController.java

@@ -8,6 +8,7 @@ import cn.rankin.common.utils.util.HttpUtil;
 import cn.rankin.data.api.app.dto.DeviceLoginDTO;
 import cn.rankin.data.api.app.dto.LoginInfoDTO;
 import cn.rankin.data.api.app.vo.UserInfoVo;
+import lombok.extern.slf4j.Slf4j;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.web.bind.annotation.RequestBody;
 import org.springframework.web.bind.annotation.RequestMapping;
@@ -16,7 +17,7 @@ import org.springframework.web.bind.annotation.RestController;
 
 import javax.servlet.http.HttpServletRequest;
 import javax.validation.Valid;
-
+@Slf4j
 @RestController
 @RequestMapping(value = "/token")
 public class LoginController {
@@ -29,13 +30,18 @@ public class LoginController {
         String ip = HttpUtil.getClientIp(request);
         loginInfoDTO.setIp(ip);
         loginInfoDTO.setTerminal(request.getHeader("terminal"));
+        loginInfoDTO.setMerchant(request.getHeader("merchant"));
+
+        log.info("login request header : ip={},terminal={},merchant={}",ip , request.getHeader("terminal"), request.getHeader("merchant"));
         return userService.login(loginInfoDTO);
     }
 
     @RequestMapping(method = RequestMethod.PUT)
-    public APIResult<UserInfoVo> refresh(@RequestBody DeviceLoginDTO deviceLoginDTO) {
+    public APIResult<UserInfoVo> refresh(HttpServletRequest request, @RequestBody DeviceLoginDTO deviceLoginDTO) {
         String deviceCode = deviceLoginDTO.getDeviceCode();
-        return userService.refresh(deviceCode, Boolean.TRUE);
+        String merchant = request.getHeader("merchant");
+        log.info("refresh request header : deviceCode={}, merchant={}", deviceCode, merchant);
+        return userService.refresh(deviceCode, merchant, Boolean.TRUE);
     }
 
     @RequestMapping(method = RequestMethod.DELETE)

+ 2 - 0
rankin-api-web/src/main/java/cn/rankin/apiweb/entity/GlobalHeader.java

@@ -11,6 +11,8 @@ public class GlobalHeader implements Serializable {
 
     private String uid;
 
+    private String merchant;
+
     private String eid;
 
     private String sign;

+ 9 - 1
rankin-api-web/src/main/java/cn/rankin/apiweb/service/user/UserClient.java

@@ -33,7 +33,7 @@ public interface UserClient {
     APIResult<TerminalDeviceVo> findDeviceByUid(@PathVariable("userId") String uid);
 
     @RequestMapping(value = "/device/deviceCode/{deviceCode}", method = RequestMethod.GET)
-    APIResult<TerminalDeviceVo> findByDeviceCode(@PathVariable("deviceCode") String deviceCode);
+    APIResult<List<TerminalDeviceVo>> findByDeviceCode(@PathVariable("deviceCode") String deviceCode);
 
     @RequestMapping(value = "/white/user/{userId}", method = RequestMethod.GET)
     APIResult<WhiteUserVo> findWhiteUserById(@PathVariable("userId") String userId);
@@ -44,6 +44,9 @@ public interface UserClient {
     @RequestMapping(value = "/userTag/code/{code}", method = RequestMethod.GET)
     List<UserTag> findUserTagByCodeUid(@PathVariable("code") String code, @RequestParam("uid") String uid);
 
+    @RequestMapping(value = "/device/updatebind", method = RequestMethod.PUT)
+    APIResult<TerminalDeviceVo> updateDeviceBind(TerminalDeviceDTO deviceDTO);
+
 
     @Component
     class UserServiceHystrix implements UserClient {
@@ -93,5 +96,10 @@ public interface UserClient {
             return null;
         }
 
+        @Override
+        public APIResult<TerminalDeviceVo> updateDeviceBind(TerminalDeviceDTO deviceDTO) {
+            return APIResult.error(ApiWebCode.SERVER_ERROR);
+        }
+
     }
 }

+ 51 - 7
rankin-api-web/src/main/java/cn/rankin/apiweb/service/user/UserService.java

@@ -18,11 +18,13 @@ import cn.rankin.data.api.user.vo.TerminalDeviceVo;
 import cn.rankin.data.api.user.vo.TerminalUserVo;
 import com.alibaba.fastjson.JSON;
 import lombok.extern.slf4j.Slf4j;
+import org.apache.commons.lang3.StringUtils;
 import org.apache.commons.lang3.time.DateUtils;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.beans.factory.annotation.Value;
 import org.springframework.data.domain.Sort;
 import org.springframework.stereotype.Service;
+import org.springframework.util.CollectionUtils;
 
 import java.util.Date;
 import java.util.List;
@@ -52,6 +54,7 @@ public class UserService {
 
     public APIResult<UserInfoVo> login(LoginInfoDTO loginInfoDTO) {
         String deviceCode = loginInfoDTO.getDeviceCode();
+        String merchant = loginInfoDTO.getMerchant();
         String eid = loginInfoDTO.getEid();
         String loginPassword = loginInfoDTO.getPassword();
         log.info("user login start, user={}", JSON.toJSONString(loginInfoDTO));
@@ -63,12 +66,20 @@ public class UserService {
             return APIResult.error(ApiWebCode.LOGIN_ERROR);
         }
 
+
+
         String storePassword = userVo.getPassword();
         if (!SecurityManager.validate(loginPassword, storePassword)) {
             log.error("密码校验错误, loginPassword={}, storePassword={}", loginPassword, storePassword);
             return APIResult.error(ApiWebCode.PASSWORD_ERROR);
         }
 
+
+/*        if(StringUtils.isNotBlank(merchant) && !merchant.equals(userVo.getMerchantSimple())){
+            log.error("渠道校验错误, requestMerchant={}, userMerchant={}", merchant, userVo.getMerchantSimple());
+            return APIResult.error(ApiWebCode.LOGIN_ERROR);
+        }*/
+
         String userId = userVo.getId();
         String ip = loginInfoDTO.getIp();
         String terminal = loginInfoDTO.getTerminal();
@@ -90,7 +101,7 @@ public class UserService {
             }
         }
 
-        TerminalDeviceVo deviceVo = this.bind(userId, deviceCode, ip, terminal);
+        TerminalDeviceVo deviceVo = this.bind(userId, deviceCode, merchant, ip, terminal);
         if (deviceVo == null) {
             return APIResult.error(ApiWebCode.DEVICE_BOUND_ERROR);
         }
@@ -118,16 +129,17 @@ public class UserService {
         return APIResult.ok();
     }
 
-    public TerminalDeviceVo bind(String userId, String deviceCode, String ip, String terminal) {
+    public TerminalDeviceVo bind(String userId, String deviceCode, String merchant, String ip, String terminal) {
         TerminalDeviceDTO deviceDTO = new TerminalDeviceDTO();
         deviceDTO.setUserId(userId);
         deviceDTO.setDeviceCode(deviceCode);
+        deviceDTO.setMerchant(merchant);
         deviceDTO.setIp(ip);
         deviceDTO.setTerminal(terminal);
         APIResult<TerminalDeviceVo> apiResult = userClient.deviceBind(deviceDTO);
         if (!apiResult.getSuccess()) {
             log.error("bind user api error");
-            return null;
+            throw new RuntimeException(apiResult.getMessage());
         }
         return apiResult.getData();
     }
@@ -168,19 +180,40 @@ public class UserService {
         return toDeviceUserVo(userVo, deviceVo);
     }
 
-    public APIResult<UserInfoVo> refresh(String deviceCode, Boolean force) {
-        APIResult<TerminalDeviceVo> deviceAPIResult = userClient.findByDeviceCode(deviceCode);
+    public APIResult<UserInfoVo> refresh(String deviceCode, String merchant, Boolean force) {
+
+        APIResult<List<TerminalDeviceVo>> deviceAPIResult = userClient.findByDeviceCode(deviceCode);
         if (!deviceAPIResult.getSuccess()) {
             log.error("load device api error, {}", deviceAPIResult.getMessage());
             return APIResult.error(ApiWebCode.NOT_FOUND);
         }
 
-        TerminalDeviceVo deviceVo = deviceAPIResult.getData();
-        if (deviceVo == null) {
+        List<TerminalDeviceVo> deviceVoList = deviceAPIResult.getData();
+        if (CollectionUtils.isEmpty(deviceVoList)) {
             log.error("device code not bind any eid! deviceCode={}", deviceCode);
             return APIResult.error(ApiWebCode.NOT_EXISTS);
         }
 
+        TerminalDeviceVo deviceVo = null;
+
+        for (TerminalDeviceVo dv : deviceVoList) {
+            //判断当前鉴权账号
+            if(StringUtils.isBlank(dv.getMerchant())){
+                //如果设备渠道code为空,则设置为当前渠道code
+                dv.setMerchant(merchant);
+                //更新数据库
+                updateDeviceBind(dv);
+                deviceVo = dv;
+            }else if(StringUtils.isNotBlank(merchant) && merchant.equals(dv.getMerchant())) {
+                deviceVo = dv;
+            }
+        }
+
+        if(null == deviceVo){
+            log.error("by device code not find this merchant! deviceCode={},merchant={}", deviceCode, merchant);
+            return APIResult.error(ApiWebCode.INVALID_TOKEN);
+        }
+
         String uid = deviceVo.getUserId();
 
         DeviceUserVo deviceUserVo;
@@ -209,6 +242,17 @@ public class UserService {
         return APIResult.ok(userInfoVo);
     }
 
+    private void updateDeviceBind(TerminalDeviceVo terminalDeviceVo) {
+        TerminalDeviceDTO deviceDTO = new TerminalDeviceDTO();
+        deviceDTO.setId(terminalDeviceVo.getId());
+        deviceDTO.setMerchant(terminalDeviceVo.getMerchant());
+        APIResult<TerminalDeviceVo> apiResult = userClient.updateDeviceBind(deviceDTO);
+        if (!apiResult.getSuccess()) {
+            log.error("update bind user api error");
+            throw new RuntimeException("update bind user api error");
+        }
+    }
+
     // cache user and device info
     public void save(DeviceUserVo deviceUserVo) {
         String key = getUserFormatKey(deviceUserVo.getUid());

+ 19 - 3
rankin-cms-web/src/main/java/cn/rankin/cmsweb/controller/user/UserTagController.java

@@ -137,11 +137,27 @@ public class UserTagController {
         dto.setProductList(productIdList);
 
         UserTag userTag = userTagService.update(dto);
-        if (userTag != null) {
+        if (userTag == null) {
             log.error("{copyTag}  update UserTag is error, id={}", dto.getId());
-            return APIResult.ok(userTag);
+            return APIResult.error(APICode.OPERATE_ERROR);
         }else{
-            return APIResult.error(APICode.NOT_EXISTS);
+            List<UserTagProductRelation> relationList = userTagProductRelationServiceInterface.findByUserTagId(userTag.getId());
+            if( !CollectionUtils.isEmpty(relationList)){
+                //开始组装产品数据
+                List<MerchantProduct> merchantProductList = new ArrayList<>();
+                relationList.forEach(relation -> {
+                    String pid = relation.getPid();
+                    MerchantProduct merchantProduct = merchantProductService.findMerchantProductByPid(pid);
+                    if(null != merchantProduct){
+                        merchantProductList.add(merchantProduct);
+                    }else{
+                        log.error("not found MerchantProduct by pid, pid={}", pid);
+                    }
+                });
+
+                userTag.setProductList(merchantProductList);
+            }
+            return APIResult.ok(userTag);
         }
     }
 }

+ 36 - 3
rankin-common-utils/src/main/java/cn/rankin/common/utils/util/HttpUtil.java

@@ -106,11 +106,44 @@ public class HttpUtil {
     }
 
     public static String getClientIp(HttpServletRequest request) {
-        String ip = request.getHeader("x-forwarded-for");
-        if (StringUtils.isEmpty(ip)) {
-            return null;
+        // 获取请求主机IP地址,如果通过代理进来,则透过防火墙获取真实IP地址
+        String ip = request.getHeader("X-Forwarded-For");
+        if (logger.isInfoEnabled()) {
+            logger.info("getIpAddress(HttpServletRequest) - X-Forwarded-For - String ip=" + ip);
         }
 
+        if (StringUtils.isEmpty(ip) || "unknown".equalsIgnoreCase(ip)) {
+            ip = request.getHeader("Proxy-Client-IP");
+            if (logger.isInfoEnabled()) {
+                logger.info("getIpAddress(HttpServletRequest) - Proxy-Client-IP - String ip=" + ip);
+            }
+        }
+        if (StringUtils.isEmpty(ip) || "unknown".equalsIgnoreCase(ip)) {
+            ip = request.getHeader("WL-Proxy-Client-IP");
+            if (logger.isInfoEnabled()) {
+                logger.info("getIpAddress(HttpServletRequest) - WL-Proxy-Client-IP - String ip=" + ip);
+            }
+        }
+        if (StringUtils.isEmpty(ip) || "unknown".equalsIgnoreCase(ip)) {
+            ip = request.getHeader("HTTP_CLIENT_IP");
+            if (logger.isInfoEnabled()) {
+                logger.info("getIpAddress(HttpServletRequest) - HTTP_CLIENT_IP - String ip=" + ip);
+            }
+        }
+        if (StringUtils.isEmpty(ip) || "unknown".equalsIgnoreCase(ip)) {
+            ip = request.getHeader("HTTP_X_FORWARDED_FOR");
+            if (logger.isInfoEnabled()) {
+                logger.info("getIpAddress(HttpServletRequest) - HTTP_X_FORWARDED_FOR - String ip=" + ip);
+            }
+        }
+        if (StringUtils.isEmpty(ip) || "unknown".equalsIgnoreCase(ip)) {
+            ip = request.getRemoteAddr();
+            if (logger.isInfoEnabled()) {
+                logger.info("getIpAddress(HttpServletRequest) - getRemoteAddr - String ip=" + ip);
+            }
+        }
+
+
         return ip.split(",")[0];
     }
 

+ 2 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/app/dto/DeviceLoginDTO.java

@@ -10,4 +10,6 @@ import java.io.Serializable;
 public class DeviceLoginDTO implements Serializable{
 
     private String deviceCode;
+
+    private String merchant;
 }

+ 2 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/app/dto/LoginInfoDTO.java

@@ -13,6 +13,8 @@ public class LoginInfoDTO implements Serializable {
     @NotNull
     private String deviceCode;
 
+    private String merchant;
+
     @NotNull
     private String eid;
 

+ 3 - 2
rankin-data-api/src/main/java/cn/rankin/data/api/app/vo/DeviceUserVo.java

@@ -1,7 +1,5 @@
 package cn.rankin.data.api.app.vo;
 
-import cn.rankin.common.utils.enums.GenderEnum;
-import cn.rankin.common.utils.util.SecurityUtil;
 import lombok.Data;
 import lombok.ToString;
 import java.io.Serializable;
@@ -17,6 +15,9 @@ public class DeviceUserVo implements Serializable {
     //设备信息
     private String deviceCode;
 
+    //渠道信息 simple
+    private String merchant;
+
     //用户信息
     private String eid;
 

+ 3 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/user/dto/TerminalDeviceDTO.java

@@ -16,6 +16,9 @@ public class TerminalDeviceDTO {
     private String deviceCode;
 
     @NotNull
+    private String merchant;
+
+    @NotNull
     private String userId;
 
     private String brand;

+ 3 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/user/entity/TerminalDevice.java

@@ -32,6 +32,9 @@ public class TerminalDevice implements Serializable {
 	@Column(name = "device_code")
 	private String deviceCode;
 
+	@Column(name = "merchant")
+	private String merchant;
+
 	@Column(name="user_id")
 	private String userId;
 

+ 3 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/user/entity/TerminalDeviceBindLog.java

@@ -24,6 +24,9 @@ public class TerminalDeviceBindLog implements Serializable {
     @Column(name = "device_code")
     private String deviceCode;
 
+    @Column(name = "merchant")
+    private String merchant;
+
     @Column(name="user_id")
     private String userId;
 

+ 3 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/user/entity/TerminalUser.java

@@ -54,6 +54,9 @@ public class TerminalUser implements Serializable {
     private String merchantName;
 
     @Transient
+    private String merchantSimple;
+
+    @Transient
     private String merchantContactName;
 
     @Transient

+ 2 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/user/vo/TerminalDeviceVo.java

@@ -22,6 +22,8 @@ public class TerminalDeviceVo implements Serializable {
 
     private String deviceCode;
 
+    private String merchant;
+
     private BaseStatusEnum status;
 
     private Date gmtCreated;

+ 2 - 0
rankin-data-api/src/main/java/cn/rankin/data/api/user/vo/TerminalUserVo.java

@@ -33,6 +33,8 @@ public class TerminalUserVo implements Serializable {
 
     private String merchantName;
 
+    private String merchantSimple;
+
     private String merchantContactName;
 
     private String merchantContactMobile;

+ 7 - 1
rankin-user-service/src/main/java/cn/rankin/userservice/controller/TerminalDeviceController.java

@@ -9,6 +9,7 @@ import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.web.bind.annotation.*;
 
 import javax.validation.Valid;
+import java.util.List;
 
 @RestController
 @RequestMapping(value = "/device")
@@ -22,6 +23,11 @@ public class TerminalDeviceController {
         return terminalDeviceService.bind(terminalDeviceDTO);
     }
 
+    @RequestMapping(value = "/updatebind", method = RequestMethod.PUT)
+    public APIResult<TerminalDevice> updatebind(@Valid @RequestBody TerminalDeviceDTO terminalDeviceDTO) {
+        return terminalDeviceService.updatebind(terminalDeviceDTO);
+    }
+
     @RequestMapping(value = "/unbind", method = RequestMethod.DELETE)
     public APIResult<Boolean> unbind(@RequestParam("userId") String userId) {
         return terminalDeviceService.unbind(userId);
@@ -38,7 +44,7 @@ public class TerminalDeviceController {
     }
 
     @RequestMapping(value = "/deviceCode/{deviceCode}", method = RequestMethod.GET)
-    public APIResult<TerminalDevice> findByDeviceCode(@PathVariable("deviceCode") String deviceCode) {
+    public APIResult<List<TerminalDevice>> findByDeviceCode(@PathVariable("deviceCode") String deviceCode) {
         return terminalDeviceService.findByDeviceCode(deviceCode);
     }
 }

+ 1 - 0
rankin-user-service/src/main/java/cn/rankin/userservice/controller/TerminalUserController.java

@@ -285,6 +285,7 @@ public class TerminalUserController {
 
         Merchant merchant = merchantService.findOne(campus.getMerchantId());
         if (merchant != null) {
+            terminalUser.setMerchantSimple(merchant.getSimple());
             terminalUser.setMerchantName(merchant.getName());
             terminalUser.setMerchantContactMobile(merchant.getMobile());
             terminalUser.setMerchantContactName(merchant.getContactName());

+ 6 - 1
rankin-user-service/src/main/java/cn/rankin/userservice/repository/TerminalDeviceRepository.java

@@ -5,11 +5,13 @@ import cn.rankin.data.api.user.entity.TerminalDevice;
 import org.springframework.data.jpa.repository.Modifying;
 import org.springframework.stereotype.Repository;
 
+import java.util.List;
+
 
 @Repository
 public interface TerminalDeviceRepository extends BasicJpaRepository<TerminalDevice, String> {
 
-    TerminalDevice findByDeviceCode(String code);
+    List<TerminalDevice> findByDeviceCode(String code);
 
     TerminalDevice findByUserId(String userId);
 
@@ -18,4 +20,7 @@ public interface TerminalDeviceRepository extends BasicJpaRepository<TerminalDev
     @Modifying
     Integer deleteByUserId(String userId);
 
+    @Modifying
+    Integer deleteByDeviceCodeAndMerchant(String code, String merchant);
+
 }

+ 2 - 1
rankin-user-service/src/main/java/cn/rankin/userservice/service/TerminalDeviceBindLogService.java

@@ -14,9 +14,10 @@ public class TerminalDeviceBindLogService {
     private TerminalDeviceBindLogRepository terminalDeviceBindLogRepository;
 
     @Transactional
-    public TerminalDeviceBindLog insert(String deviceCode, String userId, String brand, String ip, String modelNo, String terminal) {
+    public TerminalDeviceBindLog insert(String deviceCode, String merchant, String userId, String brand, String ip, String modelNo, String terminal) {
         TerminalDeviceBindLog deviceBindLog = new TerminalDeviceBindLog();
         deviceBindLog.setDeviceCode(deviceCode);
+        deviceBindLog.setMerchant(merchant);
         deviceBindLog.setUserId(userId);
         deviceBindLog.setBrand(brand);
         deviceBindLog.setIp(ip);

+ 37 - 9
rankin-user-service/src/main/java/cn/rankin/userservice/service/TerminalDeviceService.java

@@ -5,10 +5,12 @@ import cn.rankin.data.api.user.dto.TerminalDeviceDTO;
 import cn.rankin.data.api.user.entity.TerminalDevice;
 import cn.rankin.userservice.code.UserServiceAPICode;
 import cn.rankin.userservice.repository.TerminalDeviceRepository;
+import org.apache.commons.lang.StringUtils;
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.stereotype.Service;
 
 import javax.transaction.Transactional;
+import java.util.List;
 
 @Service
 public class TerminalDeviceService {
@@ -22,35 +24,45 @@ public class TerminalDeviceService {
     @Transactional
     public APIResult<TerminalDevice> bind(TerminalDeviceDTO terminalDeviceDTO) {
         String deviceCode = terminalDeviceDTO.getDeviceCode();
+        String merchant = terminalDeviceDTO.getMerchant();
         String userId = terminalDeviceDTO.getUserId();
         String brand = terminalDeviceDTO.getBrand();
         String ip = terminalDeviceDTO.getIp();
         String modelNo = terminalDeviceDTO.getModelNo();
         String terminal = terminalDeviceDTO.getTerminal();
 
-        TerminalDevice terminalDevice = terminalDeviceRepository.findByDeviceCodeOrUserId(deviceCode, userId);
+        TerminalDevice terminalDevice = terminalDeviceRepository.findByUserId(userId);
         if (terminalDevice != null) {
-            if (userId.equals(terminalDevice.getUserId())) {
+            if(!deviceCode.equals(terminalDevice.getDeviceCode())){
+                //存在设备号不一致,账号被其他设备使用中
                 return APIResult.error(UserServiceAPICode.USER_IS_BOUND);
-            }else {
-                return APIResult.error(UserServiceAPICode.DEVICE_IS_BOUND);
+            }else{
+                //根据设备号,merchant,删除设备绑定记录,后面会重新添加绑定关系
+                deleteTerminalDeviceByDeviceCodeMerchant(deviceCode, merchant);
+                terminalDeviceBindLogService.insert(deviceCode, merchant, userId, brand, ip, modelNo, terminal+"_del");
             }
         }
 
         terminalDevice = new TerminalDevice();
         terminalDevice.setUserId(userId);
         terminalDevice.setDeviceCode(deviceCode);
+        terminalDevice.setMerchant(merchant);
         terminalDevice.setBrand(brand);
         terminalDevice.setModelNo(modelNo);
         terminalDevice.setIp(ip);
         terminalDevice.setTerminal(terminal);
 
         TerminalDevice deviceBind = terminalDeviceRepository.save(terminalDevice);
-        terminalDeviceBindLogService.insert(deviceCode, userId, brand, ip, modelNo, terminal);
+        terminalDeviceBindLogService.insert(deviceCode, merchant, userId, brand, ip, modelNo, terminal);
 
         return APIResult.ok(deviceBind);
     }
 
+    private void deleteTerminalDeviceByDeviceCodeMerchant(String deviceCode, String merchant) {
+        terminalDeviceRepository.deleteByDeviceCodeAndMerchant(deviceCode, merchant);
+        terminalDeviceRepository.deleteByDeviceCodeAndMerchant(deviceCode, null);
+    }
+
     @Transactional
     public APIResult<Boolean> unbind(String userId) {
         TerminalDevice terminalDevice = terminalDeviceRepository.findByUserId(userId);
@@ -73,11 +85,27 @@ public class TerminalDeviceService {
         return terminalDeviceRepository.findByUserId(userId);
     }
 
-    public APIResult<TerminalDevice> findByDeviceCode(String deviceCode) {
-        TerminalDevice terminalDevice = terminalDeviceRepository.findByDeviceCode(deviceCode);
-        if (terminalDevice == null) {
+    public APIResult<List<TerminalDevice>> findByDeviceCode(String deviceCode) {
+        List<TerminalDevice> terminalDeviceList = terminalDeviceRepository.findByDeviceCode(deviceCode);
+        /*if (terminalDevice == null) {
             return APIResult.error(UserServiceAPICode.NOT_EXISTS);
+        }*/
+        return APIResult.ok(terminalDeviceList);
+    }
+
+    public APIResult<TerminalDevice> updatebind(TerminalDeviceDTO terminalDeviceDTO) {
+        if(StringUtils.isBlank(terminalDeviceDTO.getId())){
+            return APIResult.error(UserServiceAPICode.PARAMETER_ERROR);
         }
-        return APIResult.ok(terminalDevice);
+
+        TerminalDevice terminalDevice = terminalDeviceRepository.getOne(terminalDeviceDTO.getId());
+        if(null == terminalDevice){
+            return APIResult.error(UserServiceAPICode.PARAMETER_ERROR);
+        }
+        terminalDevice.setMerchant(terminalDeviceDTO.getMerchant());
+
+        TerminalDevice device = terminalDeviceRepository.update(terminalDevice);
+
+        return APIResult.ok(device);
     }
 }