package com.liquidnet.service.adam.service.impl.admin;

import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.liquidnet.common.cache.redis.util.RedisUtil;
import com.liquidnet.commons.lang.util.BsonUtil;
import com.liquidnet.commons.lang.util.IDGenerator;
import com.liquidnet.commons.lang.util.JsonUtils;
import com.liquidnet.service.adam.constant.AdamRedisConst;
import com.liquidnet.service.adam.dto.AdamMemberPriceParam;
import com.liquidnet.service.adam.dto.vo.AdamMemberPriceVo;
import com.liquidnet.service.adam.entity.AdamMemberPrice;
import com.liquidnet.service.adam.mapper.AdamMemberPriceMapper;
import com.liquidnet.service.adam.service.admin.IAdamMemberPriceAdminService;
import com.mongodb.client.model.FindOneAndUpdateOptions;
import com.mongodb.client.model.ReturnDocument;
import lombok.extern.slf4j.Slf4j;
import org.bson.Document;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.mongodb.core.MongoTemplate;
import org.springframework.data.mongodb.core.query.Criteria;
import org.springframework.data.mongodb.core.query.Query;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.CollectionUtils;

import java.time.LocalDateTime;
import java.util.List;

@Slf4j
@Service
public class AdamMemberPriceAdminServiceImpl extends ServiceImpl<AdamMemberPriceMapper, AdamMemberPrice> implements IAdamMemberPriceAdminService {
    @Autowired
    AdamMemberPriceMapper adamMemberPriceMapper;
    @Autowired
    MongoTemplate mongoTemplate;
    @Autowired
    RedisUtil redisUtil;

    @Override
    @Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
    public AdamMemberPriceVo add(AdamMemberPrice info) {
        List<AdamMemberPrice> existList = adamMemberPriceMapper.selectList(
                Wrappers.lambdaQuery(AdamMemberPrice.class).eq(AdamMemberPrice::getMemberId, info.getMemberId()));
        info.setMemberPriceId(CollectionUtils.isEmpty(existList) ? "101" : IDGenerator.nextSnowId().toString());
        info.setCreatedAt(LocalDateTime.now());

        adamMemberPriceMapper.insert(info);

        AdamMemberPriceVo vo = AdamMemberPriceVo.getNew().copy(info);

        mongoTemplate.insert(vo, AdamMemberPriceVo.class.getSimpleName());

        return vo;
    }

    @Override
    @Transactional(propagation = Propagation.REQUIRED, rollbackFor = Exception.class)
    public AdamMemberPriceVo edit(AdamMemberPriceParam param) {
        AdamMemberPrice updateInfo = new AdamMemberPrice();
        updateInfo.setState(param.getState());
        updateInfo.setName(param.getName());
        updateInfo.setPrice(param.getPrice());
        updateInfo.setPriceFixed(param.getPriceFixed());
        updateInfo.setDays(param.getDays());
        updateInfo.setDetail(param.getDetail());
        updateInfo.setUpdatedAt(LocalDateTime.now());

        String memberPriceId = param.getMemberPriceId();

        adamMemberPriceMapper.update(
                updateInfo, Wrappers.lambdaQuery(AdamMemberPrice.class).eq(AdamMemberPrice::getMemberPriceId, memberPriceId));

        Document doc = mongoTemplate.getCollection(AdamMemberPriceVo.class.getSimpleName()).findOneAndUpdate(
                Query.query(Criteria.where("memberPriceId").is(memberPriceId)).getQueryObject(),
                new Document("$set", Document.parse(JsonUtils.toJson(updateInfo))),
                new FindOneAndUpdateOptions().returnDocument(ReturnDocument.AFTER)
        );
        redisUtil.del(AdamRedisConst.INFO_MEMBER_PRICE.concat(memberPriceId));

        return BsonUtil.toBean(doc, AdamMemberPriceVo.class);
    }
}
