/*
 *      Copyright (c) 2018-2028, Chill Zhuang All rights reserved.
 *
 *  Redistribution and use in source and binary forms, with or without
 *  modification, are permitted provided that the following conditions are met:
 *
 *  Redistributions of source code must retain the above copyright notice,
 *  this list of conditions and the following disclaimer.
 *  Redistributions in binary form must reproduce the above copyright
 *  notice, this list of conditions and the following disclaimer in the
 *  documentation and/or other materials provided with the distribution.
 *  Neither the name of the dreamlu.net developer nor the names of its
 *  contributors may be used to endorse or promote products derived from
 *  this software without specific prior written permission.
 *  Author: Chill 庄骞 (smallchill@163.com)
 */
package org.springblade.modules.martial.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import lombok.RequiredArgsConstructor;
import org.springblade.core.tool.utils.DateUtil;
import org.springblade.modules.martial.mapper.MartialCompetitionMapper;
import org.springblade.modules.martial.mapper.MartialCompetitionRulesAttachmentMapper;
import org.springblade.modules.martial.mapper.MartialCompetitionRulesChapterMapper;
import org.springblade.modules.martial.mapper.MartialCompetitionRulesContentMapper;
import org.springblade.modules.martial.pojo.entity.MartialCompetition;
import org.springblade.modules.martial.pojo.entity.MartialCompetitionRulesAttachment;
import org.springblade.modules.martial.pojo.entity.MartialCompetitionRulesChapter;
import org.springblade.modules.martial.pojo.entity.MartialCompetitionRulesContent;
import org.springblade.modules.martial.pojo.vo.MartialCompetitionRulesVO;
import org.springblade.modules.martial.service.IMartialCompetitionRulesService;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;

/**
 * 赛事规程服务实现类
 *
 * @author BladeX
 */
@Service
@RequiredArgsConstructor
public class MartialCompetitionRulesServiceImpl implements IMartialCompetitionRulesService {

	private final MartialCompetitionMapper competitionMapper;
	private final MartialCompetitionRulesAttachmentMapper attachmentMapper;
	private final MartialCompetitionRulesChapterMapper chapterMapper;
	private final MartialCompetitionRulesContentMapper contentMapper;

	@Override
	public MartialCompetitionRulesVO getRulesByCompetitionId(Long competitionId) {
		MartialCompetitionRulesVO vo = new MartialCompetitionRulesVO();
		vo.setCompetitionId(competitionId);

		// 获取赛事信息
		MartialCompetition competition = competitionMapper.selectById(competitionId);
		if (competition != null) {
			vo.setCompetitionName(competition.getCompetitionName());
		}

		// 获取附件列表
		List<MartialCompetitionRulesAttachment> attachments = getAttachmentList(competitionId);
		List<MartialCompetitionRulesVO.AttachmentVO> attachmentVOList = attachments.stream()
			.map(this::convertToAttachmentVO)
			.collect(Collectors.toList());
		vo.setAttachments(attachmentVOList);

		// 获取章节列表
		List<MartialCompetitionRulesChapter> chapters = getChapterList(competitionId);
		List<MartialCompetitionRulesVO.ChapterVO> chapterVOList = new ArrayList<>();
		for (MartialCompetitionRulesChapter chapter : chapters) {
			MartialCompetitionRulesVO.ChapterVO chapterVO = convertToChapterVO(chapter);
			// 获取章节内容
			List<MartialCompetitionRulesContent> contents = getContentList(chapter.getId());
			List<String> contentList = contents.stream()
				.map(MartialCompetitionRulesContent::getContent)
				.collect(Collectors.toList());
			chapterVO.setContents(contentList);
			chapterVO.setItems(contentList); // 别名
			chapterVOList.add(chapterVO);
		}
		vo.setChapters(chapterVOList);

		return vo;
	}

	@Override
	public List<MartialCompetitionRulesAttachment> getAttachmentList(Long competitionId) {
		LambdaQueryWrapper<MartialCompetitionRulesAttachment> wrapper = new LambdaQueryWrapper<>();
		wrapper.eq(MartialCompetitionRulesAttachment::getCompetitionId, competitionId)
			.eq(MartialCompetitionRulesAttachment::getStatus, 1)
			.orderByAsc(MartialCompetitionRulesAttachment::getOrderNum);
		return attachmentMapper.selectList(wrapper);
	}

	@Override
	public boolean saveAttachment(MartialCompetitionRulesAttachment attachment) {
		if (attachment.getId() == null) {
			return attachmentMapper.insert(attachment) > 0;
		} else {
			return attachmentMapper.updateById(attachment) > 0;
		}
	}

	@Override
	public boolean removeAttachment(Long id) {
		return attachmentMapper.deleteById(id) > 0;
	}

	@Override
	public List<MartialCompetitionRulesChapter> getChapterList(Long competitionId) {
		LambdaQueryWrapper<MartialCompetitionRulesChapter> wrapper = new LambdaQueryWrapper<>();
		wrapper.eq(MartialCompetitionRulesChapter::getCompetitionId, competitionId)
			.eq(MartialCompetitionRulesChapter::getStatus, 1)
			.orderByAsc(MartialCompetitionRulesChapter::getOrderNum);
		return chapterMapper.selectList(wrapper);
	}

	@Override
	public boolean saveChapter(MartialCompetitionRulesChapter chapter) {
		if (chapter.getId() == null) {
			return chapterMapper.insert(chapter) > 0;
		} else {
			return chapterMapper.updateById(chapter) > 0;
		}
	}

	@Override
	@Transactional(rollbackFor = Exception.class)
	public boolean removeChapter(Long id) {
		// 删除章节下的所有内容
		LambdaQueryWrapper<MartialCompetitionRulesContent> wrapper = new LambdaQueryWrapper<>();
		wrapper.eq(MartialCompetitionRulesContent::getChapterId, id);
		contentMapper.delete(wrapper);
		// 删除章节
		return chapterMapper.deleteById(id) > 0;
	}

	@Override
	public List<MartialCompetitionRulesContent> getContentList(Long chapterId) {
		LambdaQueryWrapper<MartialCompetitionRulesContent> wrapper = new LambdaQueryWrapper<>();
		wrapper.eq(MartialCompetitionRulesContent::getChapterId, chapterId)
			.eq(MartialCompetitionRulesContent::getStatus, 1)
			.orderByAsc(MartialCompetitionRulesContent::getOrderNum);
		return contentMapper.selectList(wrapper);
	}

	@Override
	public boolean saveContent(MartialCompetitionRulesContent content) {
		if (content.getId() == null) {
			return contentMapper.insert(content) > 0;
		} else {
			return contentMapper.updateById(content) > 0;
		}
	}

	@Override
	public boolean removeContent(Long id) {
		return contentMapper.deleteById(id) > 0;
	}

	@Override
	@Transactional(rollbackFor = Exception.class)
	public boolean batchSaveContents(Long chapterId, List<String> contents) {
		// 先删除原有内容
		LambdaQueryWrapper<MartialCompetitionRulesContent> wrapper = new LambdaQueryWrapper<>();
		wrapper.eq(MartialCompetitionRulesContent::getChapterId, chapterId);
		contentMapper.delete(wrapper);

		// 批量插入新内容
		for (int i = 0; i < contents.size(); i++) {
			MartialCompetitionRulesContent content = new MartialCompetitionRulesContent();
			content.setChapterId(chapterId);
			content.setContent(contents.get(i));
			content.setOrderNum(i + 1);
			content.setStatus(1);
			contentMapper.insert(content);
		}
		return true;
	}

	/**
	 * 转换为附件VO
	 */
	private MartialCompetitionRulesVO.AttachmentVO convertToAttachmentVO(MartialCompetitionRulesAttachment attachment) {
		MartialCompetitionRulesVO.AttachmentVO vo = new MartialCompetitionRulesVO.AttachmentVO();
		vo.setId(attachment.getId());
		vo.setName(attachment.getFileName());
		vo.setFileName(attachment.getFileName());
		vo.setUrl(attachment.getFileUrl());
		vo.setFileUrl(attachment.getFileUrl());
		vo.setSize(attachment.getFileSize());
		vo.setFileSize(attachment.getFileSize());
		vo.setFileType(attachment.getFileType());
		vo.setUploadTime(DateUtil.format(attachment.getCreateTime(), DateUtil.PATTERN_DATETIME));
		return vo;
	}

	/**
	 * 转换为章节VO
	 */
	private MartialCompetitionRulesVO.ChapterVO convertToChapterVO(MartialCompetitionRulesChapter chapter) {
		MartialCompetitionRulesVO.ChapterVO vo = new MartialCompetitionRulesVO.ChapterVO();
		vo.setId(chapter.getId());
		vo.setChapterNumber(chapter.getChapterNumber());
		vo.setNumber(chapter.getChapterNumber());
		vo.setTitle(chapter.getTitle());
		vo.setName(chapter.getTitle());
		vo.setOrder(chapter.getOrderNum());
		return vo;
	}

}
