package com.ruoyi.web.work.service.impl;

import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.ruoyi.common.config.RuoYiConfig;
import com.ruoyi.common.constant.CacheConstants;
import com.ruoyi.common.constant.Constants;
import com.ruoyi.common.core.domain.AjaxResult;
import com.ruoyi.common.core.redis.RedisCache;
import com.ruoyi.common.utils.DateUtils;
import com.ruoyi.common.utils.StringUtils;
import com.ruoyi.web.work.api.util.AppUtil;
import com.ruoyi.web.work.domain.Contract;
import com.ruoyi.web.work.domain.ContractDetail;
import com.ruoyi.web.work.domain.Platform;
import com.ruoyi.web.work.domain.User;
import com.ruoyi.web.work.domain.dto.ContractDto;
import com.ruoyi.web.work.mapper.ContractMapper;
import com.ruoyi.web.work.service.IContractDetailService;
import com.ruoyi.web.work.service.IContractService;
import com.ruoyi.web.work.service.IUserService;
import com.spire.doc.Document;
import com.spire.doc.FileFormat;
import com.spire.doc.documents.TextSelection;
import com.spire.doc.fields.DocPicture;
import com.spire.doc.fields.TextRange;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import javax.servlet.http.HttpServletResponse;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.io.OutputStream;
import java.rmi.ServerException;
import java.util.List;

/**
 * @author lsw
 * @date 2024-04-22
 */
@Service
public class ContractServiceImpl extends ServiceImpl<ContractMapper, Contract> implements IContractService {
    @Autowired
    private ContractMapper contractMapper;

    @Autowired
    private IContractDetailService detailService;

    @Autowired
    IUserService userService;

    @Autowired
    private RedisCache redisCache;

    @Override
    public List<Contract> selectList(Contract contract) {
        return contractMapper.selectList(contract);
    }

    @Override
    public Contract selectContract() {
        return contractMapper.selectContract();
    }

    @Transactional
    @Override
    public AjaxResult add(ContractDto dto) throws ServerException {
        Contract contract = getById(dto.getContractId());
        if (contract == null) {
            return AjaxResult.error("合同信息不存在");
        }
        ContractDetail detail = detailService.selectByUserId(AppUtil.getUser().getId());
        if (detail != null) {
            return AjaxResult.error("你已签署合同");
        }
        detail = new ContractDetail();
        detail.setUserId(AppUtil.getUser().getId());
        detail.setContractId(contract.getId());
        detail.setUrl(dto.getUrl());
        detail.setState(1);
        if (!detailService.save(detail)) {
            throw new ServerException("签署合同失败,请联系平台");
        }
        User user = userService.getById(AppUtil.getUser().getId());
        user.setIsContract(1);
        if (!userService.updateById(user)) {
            throw new ServerException("签署合同失败,请联系平台");
        }
        return AjaxResult.success();
    }

    @Override
    public void look(HttpServletResponse response, Long userId) throws IOException {
        Platform platform = redisCache.getCacheObject(CacheConstants.APP_PLATFORM);
        User user = userService.getById(userId);
        if (user == null) {
            throw new ServerException("用户信息不存在");
        }
        ContractDetail detail = detailService.selectByUserId(userId);
        if (detail == null) {
            throw new ServerException("你还未签约");
        }
        Contract contract = getById(detail.getContractId());
        if (contract == null) {
            throw new ServerException("合同不存在");
        }
        String contractPath = RuoYiConfig.getProfile() + StringUtils.substringAfter(RuoYiConfig.getProfile() + contract.getUrl(), Constants.RESOURCE_PREFIX);
        String imgPath = RuoYiConfig.getProfile() + StringUtils.substringAfter(RuoYiConfig.getProfile() + detail.getUrl(), Constants.RESOURCE_PREFIX);
        // 加载文档
        Document doc = new Document();
        doc.loadFromFile(contractPath);
        // 创建一个 DocPicture 对象，并加载要插入的图片
        DocPicture picture = new DocPicture(doc);
        picture.loadImage(imgPath);

        // 调整图片大小和旋转角度
        picture.setWidth(80); // 设置图片宽度
        picture.setHeight(30); // 设置图片高度

        // 查找并替换占位符
        doc.replace("${serviceCompany}", platform.getServiceCompany(), true, true);
        doc.replace("${director}", platform.getDirector(), true, true);
        doc.replace("${address}", platform.getAddress(), true, true);
        doc.replace("${name}", user.getName(), true, true);
        doc.replace("${idCard}", user.getIdCard(), true, true);
        if (user.getPhone() != null) {
            doc.replace("${phone}", user.getPhone(), true, true);
        }
        doc.replace("${address2}", user.getAddress(), true, true);
        doc.replace("${date}", DateUtils.getDate(), true, true);
        // 查找并替换占位符
        TextSelection[] selections = doc.findAllString("${jiaSign}", true, true);
        for (TextSelection selection : selections) {
            // 获取占位符的文本范围
            TextRange range = selection.getAsOneRange();
            // 在占位符位置插入图片
            range.getOwnerParagraph().getChildObjects().insert(range.getOwnerParagraph().getChildObjects().indexOf(range) + 1, picture);
            // 移除占位符
            range.getOwnerParagraph().getChildObjects().remove(range);
        }
        // 创建一个内存流
        ByteArrayOutputStream outputStream = new ByteArrayOutputStream();
        // 将文档保存到流中
        doc.saveToStream(outputStream, FileFormat.Docx_2013);
        // 获取流中的字节数组
        byte[] byteArray = outputStream.toByteArray();
        // 设置响应头
        response.setContentType("application/vnd.openxmlformats-officedocument.wordprocessingml.document");
        response.setHeader("Content-Disposition", "attachment; filename=output.docx");
        // 将流中的内容写入响应输出流
        OutputStream outStream = response.getOutputStream();
        outStream.write(byteArray);
        // 关闭输出流
        outStream.close();
    }
}
