MrShi
13 小时以前 9eeb62c02a7b3c7b95c20678b6a9c74e7f12f943
server/services/src/main/java/com/doumee/service/system/impl/SystemDictDataServiceImpl.java
@@ -1,9 +1,13 @@
package com.doumee.service.system.impl;
import com.alibaba.fastjson.JSONObject;
import com.alibaba.fastjson.TypeReference;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.doumee.core.constants.ResponseStatus;
import com.doumee.core.exception.BusinessException;
import com.doumee.core.douyin.DouyinClient;
import com.doumee.dao.business.web.request.LocaltionDTO;
import com.doumee.dao.business.web.response.DouyinConfigDTO;
import com.doumee.dao.business.web.response.MiniProgrammeDTO;
import com.doumee.dao.system.SystemDictMapper;
import com.doumee.dao.system.model.SystemDict;
@@ -19,6 +23,7 @@
import com.doumee.service.system.SystemDictDataService;
import com.baomidou.mybatisplus.core.conditions.Wrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import lombok.extern.slf4j.Slf4j;
import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
@@ -26,6 +31,7 @@
import org.springframework.util.CollectionUtils;
import java.io.IOException;
import java.math.BigDecimal;
import java.util.*;
import java.util.stream.Collectors;
@@ -37,12 +43,16 @@
 * @date 2022/03/15 09:54
 */
@Service
@Slf4j
public class SystemDictDataServiceImpl implements SystemDictDataService {
    @Autowired
    private SystemDictDataMapper systemDictDataMapper;
    @Autowired
    private SystemDictMapper systemDictMapper;
    /** 抖音 HTTP 客户端:用于改完应用配置后清空 client_token 缓存 */
    @Autowired
    private DouyinClient douyinClient;
    @Override
    public String create(SystemDictData systemDictData) {
@@ -139,6 +149,15 @@
    @Override
    public void updateMiniProgrammeDTO(MiniProgrammeDTO miniProgrammeDTO) {
        try {
            if(miniProgrammeDTO.getParkLatLngList()!=null){
                try {
                    TypeReference typeReference =  new TypeReference<List<LocaltionDTO>>(){};
                    List<LocaltionDTO> response = JSONObject.parseObject(miniProgrammeDTO.getParkLatLngList(), typeReference.getType());
                }catch (Exception e){
                    e.printStackTrace();
                    throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(),"运营区域参数解析有误!");
                }
            }
            String jasonStr = MiniProgrammeDTO.toUnderlineJSONString(miniProgrammeDTO);
            JSONObject parse = (JSONObject) JSONObject.parse(jasonStr);
            parse.entrySet().forEach(s->{
@@ -154,4 +173,69 @@
            throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(),"字典值解析有误");
        }
    }
    @Override
    public DouyinConfigDTO getDouyinConfigDTO() {
        try {
            // 复用 MiniProgrammeDTO 的驼峰⇄下划线工具:对象属性 → {client_key,client_secret,account_id,poi_id}
            String jasonStr = MiniProgrammeDTO.toUnderlineJSONString(new DouyinConfigDTO());
            JSONObject parse = (JSONObject) JSONObject.parse(jasonStr);
            List<String> collect = parse.entrySet().stream().map(s -> s.getKey().toUpperCase()).collect(Collectors.toList());
            QueryWrapper<SystemDictData> wrapper = new QueryWrapper<>();
            wrapper.lambda()
                    .in(SystemDictData::getLabel,collect);
            List<SystemDictData> systemDictData = systemDictDataMapper.selectList(wrapper);
            if (CollectionUtils.isEmpty(systemDictData)){
                throw new BusinessException(ResponseStatus.DATA_EXISTS.getCode(),"字典不存在");
            }
            systemDictData.forEach(s->{
                parse.put(s.getLabel().toLowerCase(),s.getCode());
            });
            String s = parse.toJSONString();
            return MiniProgrammeDTO.toSnakeObject(s, DouyinConfigDTO.class);
        } catch (BusinessException e) {
            throw e;
        } catch (Exception e) {
            throw new BusinessException(ResponseStatus.SERVER_ERROR.getCode(),"字典值解析有误");
        }
    }
    @Transactional(rollbackFor = {Exception.class,BusinessException.class})
    @Override
    public void updateDouyinAppConfigDTO(DouyinConfigDTO douyinConfigDTO) {
        try {
            String jasonStr = MiniProgrammeDTO.toUnderlineJSONString(douyinConfigDTO);
            JSONObject parse = (JSONObject) JSONObject.parse(jasonStr);
            // 仅更新抖音应用三项(client_key/client_secret/account_id),poi_id 由独立接口维护
            parse.entrySet().forEach(s->{
                UpdateWrapper<SystemDictData> wrapper = new UpdateWrapper<>();
                wrapper.lambda()
                        .eq(SystemDictData::getLabel,s.getKey().toUpperCase())
                        .set(SystemDictData::getCode,s.getValue());
                systemDictDataMapper.update(null,wrapper);
            });
        } catch (JsonProcessingException e) {
            throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(),"字典值解析有误");
        }
        // client_key/client_secret 改了之后,缓存的旧 access-token 已失效,清掉后下次调用才用新配置换取新 token。
        // 清缓存属于副作用,失败不回滚配置(配置已正确入库,token 下次过期自愈)。
        try {
            douyinClient.clearAccessToken();
        } catch (Exception e) {
            log.warn("更新抖音应用配置后清空 access-token 失败", e);
        }
    }
    @Transactional(rollbackFor = {Exception.class,BusinessException.class})
    @Override
    public void updateDouyinPoiIdDTO(String poiId) {
        if (StringUtils.isBlank(poiId)){
            throw new BusinessException(ResponseStatus.BAD_REQUEST.getCode(),"门店ID不能为空");
        }
        UpdateWrapper<SystemDictData> wrapper = new UpdateWrapper<>();
        wrapper.lambda()
                .eq(SystemDictData::getLabel, Constants.DOUYIN_POI_ID)
                .set(SystemDictData::getCode,poiId);
        systemDictDataMapper.update(null,wrapper);
    }
}