package com.ssj.service.mapper;

import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.ssj.bean.conch.conch.dto.KmtExerciseQuestionProblemDto;
import com.ssj.bean.kmt.kmt.domain.*;
import com.ssj.bean.kmt.kmt.model.QuestionListKnowModel;
import com.ssj.bean.sys.homework.domain.HomeworkCount;
import com.ssj.bean.weixin.libmy.domain.TbLibJoin;
import com.ssj.bean.weixin.libmy.domain.TbLibManager;
import com.ssj.service.conch.parents.v2.dto.TrainRecommendQuestionDTO;
import com.ssj.service.kmt.dto.ExerciseBookDto;
import com.ssj.service.kmt.dto.ExerciseQuetionDto;
import com.ssj.service.kmt.dto.OriginalQuestionDTO;
import com.ssj.service.kmt.dto.exercise.ExerciseQuestionRollbacks;
import com.ssj.service.kmt.dto.exercise.ExerciseUnitBookcourseDto;
import com.ssj.service.kmt.dto.exercise.KmtExerciseBookLibDto;
import com.ssj.service.kmt.dto.exercise.KmtExerciseQuestionRollBackInfo;
import com.ssj.service.kmt.exercisesys.dto.*;
import com.ssj.service.kmt.exercisesys.request.*;
import com.ssj.service.kmt.request.UnitAndPeriodListRequest;
import com.ssj.service.sys.homework.vo.HomeworkExerciseBookDto;
import org.apache.ibatis.annotations.Mapper;
import org.apache.ibatis.annotations.Param;
import org.apache.ibatis.annotations.Select;
import org.apache.ibatis.annotations.Update;

import java.util.Date;
import java.util.List;
import java.util.Map;
import java.util.Set;

@Mapper
public interface KmtExerciseMapper {

    /**
     * in 查询题目列表
     * @param ids
     * @return
     */
    public List<KmtExerciseQuestion> findKmtExerciseQuestionsByIdIn(List<String> ids);

    /**
     * 删除上一次加工的知识点
     * @param questionIds
     * @return
     */
    public void deleteKmtExerciseQuestionKnowByQuestionIds(List<String> questionIds);

    /**
     * 题目列表提交审核
     * @param questionIds
     */
    public void updateKmtExerciseQuestion2Review(List<String> questionIds);

    /**
     * 根据错题id查询题目关联的知识点
     * @param questionId 题目id
     * @return 知识点id列表
     */
    List<String> findWrongQuestionKnowHowDetailIdList(@Param("questionId") String questionId);

    /**
     * 根据错题知识点id和需要排除的题目id查询推荐的题目
     * @param wrongQuestionKnowHowDetailIdList 错题知识点id
     * @param needExcludedQuestionIdSet 需要排除的题目id
     * @return 原题列表
     */
    List<KmtExerciseQuestion> findTempRecommendQuestion(@Param("wrongQuestionKnowHowDetailIdList") List<String> wrongQuestionKnowHowDetailIdList, @Param("needExcludedQuestionIdSet") Set<String> needExcludedQuestionIdSet);

    /**
     * 根据题目id查询整道题(顺序未排列，需要返回结果后程序排序)
     * @param parentQuestionIdList 题目id
     * @return 原题列表
     */
    List<OriginalQuestionDTO> findFullBigQuestionByParentId(@Param("parentQuestionIdList") List<String> parentQuestionIdList);

    /**
     * 查询待加工审核的题目
     * @param bookCourseId 课时
     * @param dealType 1加工，2审核
     * @param userId 加工员/审核员
     * @return
     */
    List<ExerciseQuetionDto> findQuestionByBookCourseIdAndUserId(@Param("bookCourseId") String bookCourseId,
                                                                 @Param("dealType") int dealType,
                                                                 @Param("userId") String userId,
                                                                 @Param("exerciseBookId") String exerciseBookId);

    /**
     * 查询课时下的所有题目
     * @param bookCourseId
     * @return
     */
    List<ExerciseQuetionDto> findQuestionByBookCourseId(@Param("bookCourseId") String bookCourseId);

    /**
     * 查询打回列表
     * @param questionIds
     * @param dealType
     * @return
     */
    List<KmtExerciseQuestionRollback> findKmtExerciseQuestionRollbacks(@Param("questionIds") List<String> questionIds,
                                                                       @Param("dealType") int dealType);

    /**
     * 查询题目的打回记录倒序（新用户）
     * @param questionId
     * @return
     */
    List<KmtExerciseQuestionRollBackInfo> findQuestionRollbackRecord(String questionId);



    /**
     * 查询题目的打回记录倒序（老用户）
     * @param questionId
     * @return
     */
    List<ExerciseQuestionRollbacks> findQuestionRollbackRecordOld(String questionId);
    /**
     * 统计错题数和总题数
     * @param vipId 学生id
     * @param subject 科目
     * @param beginDateTime 开始时间
     * @param endDateTime 结束时间
     */
    List<Map<String, Object>> countWrongAndTotal(@Param("vipId") String vipId, @Param("subject") String subject, @Param("beginDateTime") String beginDateTime, @Param("endDateTime") String endDateTime);

    /**
     * 统计知识点涉及次数
     * @param vipId 学生id
     * @param subject 科目
     * @param beginDateTimeStr 开始时间
     * @param endDateTimeStr 结束时间
     */
    List<Map<String, Object>> countKnowledgeTimes(@Param("vipId") String vipId, @Param("subject") String subject, @Param("beginDateTimeStr") String beginDateTimeStr, @Param("endDateTimeStr") String endDateTimeStr);

    /**
     * 统计知识点掌握情况
     * @param vipId 学生id
     * @param subject 科目
     * @param beginDateTimeStr 开始时间
     * @param endDateTimeStr 结束时间
     */
    List<Map<String, Object>> countKnowledgeMastery(@Param("vipId") String vipId, @Param("subject") String subject, @Param("beginDateTimeStr") String beginDateTimeStr, @Param("endDateTimeStr") String endDateTimeStr);

    /**
     * 查询月作业统计数据
     * @param vipId 学生id
     * @param homeworkMonth 月份，如："2019-06"
     */
    HomeworkCount findMonthHomeworkCount(@Param("vipId") String vipId, @Param("homeworkMonth") String homeworkMonth);

    /**
     * 查询题目的关联知识点（去重）
     * @param questionIds
     * @return
     */
    List<String> findHowDetailIdsByQuestionIds(@Param("questionIds") List<String> questionIds);

    /**
     * 查询相似题
     * @param questionIds
     * @return
     */
    List<KmtExerciseQuestionProblemDto> findSimilarQuestionByIds(@Param("list") List<String> questionIds);

    List<Map<String, Object>> countKnowledgeMasteryV2(@Param("vipId") String vipId, @Param("subject") String subject, @Param("beginDateTimeStr") String beginDateTimeStr, @Param("endDateTimeStr") String endDateTimeStr);

    /**
     * 查询未解析的课时
     * @param analysisUserId
     * @param maxCount
     * @return
     */
    List<KmtExerciseBookCourse> findUnAnalysisBookCourse(@Param("analysisUserId") String analysisUserId, @Param("maxCount") int maxCount);

    /**
     * 根据练习册id列表查询需要更新到es的数据
     * @param questionIdList 题目id列表
     */
    List<Map<String, Object>> findData2EsByQuestionList(@Param("questionIdList") List<String> questionIdList);

    /**
     * 全量更新es索引kmt_exercise_question_know中的数据
     * @param pageSize 每次查询数据量
     */
    List<Map<String, Object>> findAll2Es(@Param("pageSize") int pageSize);

    /**
     * 全量同步数据到es时，更新加载状态
     * @param kmtExerciseQuestionKnowIdList 需要更新的记录id列表
     */
    void updateLoadStatus(@Param("kmtExerciseQuestionKnowIdList") List<String> kmtExerciseQuestionKnowIdList);

    /**
     * 查询未加工练习册
     * @param handleUserId
     * @return
     */
    List<ExerciseBookDto> findUnHandleBooks(@Param("handleUserId") String handleUserId,
                                            @Param("bookName") String bookName);

    /**
     * 查询未分配加工人练习册
     * @return
     */
    List<ExerciseBookDto> findUndistributedHandlerBooks(@Param("subject") String subject,
                                                        @Param("semester") int semester,
                                                        @Param("versionType") int versionType,
                                                        @Param("grade") String grade);

    /**
     * 查询未审核练习册
     * @param auditingUserId
     * @return
     */
    List<ExerciseBookDto> findUnAuditingBooks(@Param("auditingUserId") String auditingUserId,
                                              @Param("bookName") String bookName);


    /**
     * 查询未分配审核练习册
     * @return
     */
    List<ExerciseBookDto> findUndistributedAuditerBooks(@Param("subject") String subject,
                                                        @Param("semester") int semester,
                                                        @Param("versionType") int versionType,
                                                        @Param("grade") String grade);

    /**
     * 查询所有联系册
     * @param subject
     * @param semester
     * @param versionType
     * @param grade
     * @return
     */
    List<ExerciseBookDto> findAllExerciseBooks(@Param("subject") String subject,
                                               @Param("semester") int semester,
                                               @Param("versionType") int versionType,
                                               @Param("grade") String grade,
                                               @Param("bookName") String bookName);

    /**
     * 查询待加工审核的单元课时
     * @param bookId
     * @param dealType
     * @return
     */
    List<ExerciseUnitBookcourseDto> findUnHandleExerciseBookCourse(@Param("bookId") String bookId,
                                                                   @Param("dealType") int dealType,
                                                                   @Param("userId") String userId);


    /**
     * 查询解析未加工未审核的单元课时  kmt_exercise_book_course, kmt_exercise_questions, kmt_exercise_book_unit
     * @param bookId
     * @param dealType
     * @return
     */
    List<ExerciseUnitBookcourseDto> findAnalysisUnHandleExerciseBookCourse(@Param("bookId") String bookId,
                                                                           @Param("dealType") int dealType);

    /**
     * 查询练习册下的所有课时
     * @param bookId
     * @return
     */
    List<ExerciseUnitBookcourseDto> findAllExerciseBookCourse(@Param("bookId") String bookId,
                                                              @Param("exerciseBookId") String exerciseBookId);

    /**
     * 查询练习册下的所有课时
     * @param exerciseBookId
     * @return
     */
    List<ExerciseUnitBookcourseDto> findAllExerciseBookCourseByExerciseBookId(@Param("exerciseBookId") String exerciseBookId);


    /**
     * 查询未加工/审核的题目数量
     * @param bookCourseId
     * @param ids
     * @param dealType
     * @return
     */
    Integer findUnHandleQuestionCount(@Param("bookCourseId") String bookCourseId,
                                      @Param("ids") List<String> ids,
                                      @Param("dealType") int dealType);

    /**
     * 查询未加工/审核的课时数量
     * @param bookCourseId
     * @param unitId
     * @param dealType
     * @return
     */
    Integer findUnHandleBookCourseCount(@Param("unitId") String unitId,
                                        @Param("bookCourseId") String bookCourseId,
                                        @Param("dealType") int dealType);

    /**
     * 查询未加工/审核的单元数量
     * @param bookId
     * @param unitId
     * @param dealType
     * @return
     */
    Integer findUnHandleUnitCount(@Param("bookId") String bookId,
                                  @Param("unitId") String unitId,
                                  @Param("dealType") int dealType);

    /**
     * 查询搜索的题目, kmt_exercise_questions, kmt_sys_user
     * @param questionId
     * @return
     */
    List<ExerciseQuetionDto> findKmtQuestionsById(@Param("questionId") String questionId,
                                                  @Param("userId") String userId,
                                                  @Param("dealType") int dealType,
                                                  Page page);

    /**
     * 按知识点分页查询题目 kmt_exercise_questions, kmt_sys_user, kmt_exercise_question_know
     * @param howDetailsId
     * @param howDetailsKdId
     * @param userId
     * @param dealType
     * @param page
     * @return
     */
    List<ExerciseQuetionDto> findKmtQuestionByDetailId(@Param("howDetailsId") String howDetailsId,
                                                       @Param("howDetailsKdId") String howDetailsKdId,
                                                       @Param("userId") String userId,
                                                       @Param("dealType") int dealType,
                                                       @Param("userIdList") List<String> userIdList,
                                                       Page page);

    /**
     * 按年级、科目、版本、上下册分页查询题目 kmt_exercise_questions, kmt_sys_user, kmt_exercise_question_know,zyb_know_how_details_sort
     * @param grade
     * @param courseName
     * @param semester
     * @param versionType
     * @param userId
     * @param dealType
     * @param page
     * @return
     */
    List<ExerciseQuetionDto> findKmtQuestionByGradeSubjectVersionSemester(@Param("grade") String grade,
                                                                          @Param("courseName") String courseName,
                                                                          @Param("semester") int semester,
                                                                          @Param("type") int versionType,
                                                                          @Param("userId") String userId,
                                                                          @Param("dealType") int dealType,
                                                                          @Param("userIdList") List<String> userIdList,
                                                                          Page page);

    /**
     * 查询所有kmt题目  kmt_exercise_questions, kmt_sys_user,
     * @param userId
     * @param dealType
     * @param page
     * @return
     */
    List<ExerciseQuetionDto> findAllKmtQuestions(@Param("userId") String userId,
                                                 @Param("dealType") int dealType,
                                                 @Param("userIdList") List<String> userIdList,
                                                 Page page);

    /**
     * 查询小题 kmt_exercise_questions, kmt_sys_user
     * @param parentIds
     * @return
     */
    List<ExerciseQuetionDto> findSmallQuestionByParentIds(@Param("parentIds") List<String> parentIds);

    /**
     * 查询大题 kmt_exercise_questions
     * @param id
     * @return
     */
    ExerciseQuetionDto findBigQuestionById(@Param("id") String id);

    /**
     * 查询题目的知识点列表 kmt_exercise_question_know, zyb_know_how_details_sort
     * @param questionIds
     * @return
     */
    List<QuestionListKnowModel> findQuestionKnowByQuestionIds(@Param("questionIds") List<String> questionIds);


    /**
     * 查询题目的知识点列表 kmt_quality_question_know, zyb_know_how_details_sort
     * @param questionIds
     * @return
     */
    List<QuestionListKnowModel> findKmtQuestionKnowByQuestionIds(@Param("questionIds") List<String> questionIds);


    /**
     * 查询父题目
     * @param questionId
     * @return
     */
    KmtExerciseQuestion findPrentQuestionByChildQuestionId(@Param("questionId") String questionId);



    /**
     * 根据给定知识点id列表和知识点版本，统计练习册题目数量
     * @param knowledgeIdList 知识点id列表
     * @param version 知识点版本
     * @return 题目数量
     */
    int countQuestionByKnowledgeAndVersion(@Param("knowledgeIdList") List<String> knowledgeIdList, @Param("version") int version);

    /**
     * 根据题目id查询整道大题所有题目
     * @param questionId 题目id（大题id或小题id均可）
     * @return 整道大题原题
     */
    List<OriginalQuestionDTO> findFullBigQuestion(@Param("questionId") String questionId);

    /**
     * 更新练习册为未加工 kmt_exercise_book
     * @param id
     */
    void updateKmtExerciseBookNotHandle(@Param("id") String id);

    /**
     * 更新练习册为未审核 kmt_exercise_book
     * @param id
     */
    void updateKmtExerciseBookNotAuditing(@Param("id") String id);

    /**
     * 更新练习册为解析未加工  kmt_exercise_book
     * @param id
     */
    void updateKmtExerciseBookAnalysisNotHandle(@Param("id") String id);

    /**
     * 更新练习册为解析未审核 kmt_exercise_book
     * @param id
     */
    void updateKmtExerciseBookAnalysisNotAuditing(@Param("id") String id);

    /**
     * 更新练习册课时为未加工 kmt_exercise_book_course
     * @param id
     */
    void updateKmtExerciseBookCourseNotHandle(@Param("id") String id);

    /**
     * 更新练习册课时为未审核 kmt_exercise_book_course
     * @param id
     */
    void updateKmtExerciseBookCourseNotAuditing(@Param("id") String id);

    /**
     * 查询解析未加工的练习册 kmt_exercise_book  kmt_exercise_questions
     * @param
     * @return
     */
    List<ExerciseBookDto> findUnAnalysisHandleBooks(@Param("analysisUserId") String analysisUserId,
                                                    @Param("bookName") String bookName);

    /**
     * 查询解析未审核的练习册 kmt_exercise_book  kmt_exercise_questions
     * @param
     * @return
     */
    List<ExerciseBookDto> findUnAnalysisAuditingBooks(@Param("analysisAuditerId") String analysisAuditerId,
                                                      @Param("bookName") String bookName);

    /**
     * 查询校对的练习册
     * @param userId
     * @param bookName
     * @return
     */
    List<ExerciseBookDto> findUnCorrectAnswerBooks(@Param("userId") String userId,
                                                   @Param("bookName") String bookName);


    /**
     * 查询校对的练习册
     * @param userId
     * @param bookName
     * @return
     */
    List<ExerciseBookDto> findCorrectedAnswerBooks(@Param("userId") String userId,
                                                   @Param("bookName") String bookName);

    /**
     * 查询练习册列表
     * @param ids
     * @return
     */
    List<ExerciseBookDto> findExerciseBookListByIds(@Param("ids") List<String> ids);

    /**
     * 根据大题id查询题目（包括大题和smallQuestionSum道小题）
     * @param parentId 大题id
     * @param smallQuestionSum 小题数量，若为null则不限制数量
     * @return 练习册题目
     */
    List<TrainRecommendQuestionDTO> findByParentIdLimitSmallSum(@Param("parentId") String parentId,
                                                                @Param("smallQuestionSum") Integer smallQuestionSum);


    /**
     * 分页查询作业批改的练习册  kmt_exercise_book  scon_homework_exercise_except
     * @param subject
     * @param semester
     * @param versionType
     * @param grade
     * @param page
     * @return
     */
    List<HomeworkExerciseBookDto> findHomeworkCorrectFilterBooks(@Param("subject") String subject,
                                                                 @Param("semester") int semester,
                                                                 @Param("versionType") int versionType,
                                                                 @Param("grade") String grade,
                                                                 Page page);

    /**
     * 分页查询作业批改的练习册  kmt_exercise_book  scon_homework_exercise_except
     * @param subject
     * @param semester
     * @param versionType
     * @param grade
     * @param school
     * @param page
     * @return
     */
    List<HomeworkExerciseBookDto> findHomeworkCorrectFilterBooksBySchool(@Param("subject") String subject,
                                                                         @Param("semester") int semester,
                                                                         @Param("versionType") int versionType,
                                                                         @Param("grade") String grade,
                                                                         @Param("school") String school,
                                                                         Page page);

    /**
     * 查询所有练习册
     * @param page
     * @param params
     * @return
     */
    List<String> getBookId(Page page, @Param("map") Map<String, Object> params);

    /**
     * 查询练习册
     * @param id
     * @return
     */
    KmtExerciseBook findExerciseBookById(@Param("bookId") String id);

    /**
     * 查询练习册
     * @return
     */
    KmtExerciseBook findExerciseBookByBookIdAndYearAndType(@Param("bookId") String bookId,
                                                           @Param("bookYear") int bookYear,
                                                           @Param("bookType") int bookType);

    /**
     * 查询单元课时记录
     * @param bookIds
     * @return
     */
    List<KmtExerciseBookCourse> findByBookIds(@Param("bookIds") List<String> bookIds);

    /**
     * 查询所有小题
     * @param parentId 大题id
     * @return 小题列表
     */
    List<TrainRecommendQuestionDTO> findAllChild(@Param("parentId") String parentId);

    /**
     * 更新kmt题目的es加载状态
     * @param kmtExerciseQuestionKnowIdList 题目id列表
     * @param newLoaded 新的es加载状态
     * @return 更新行数
     */
    int updateExerciseQuestionKnowEsLoadStatus(@Param("kmtExerciseQuestionKnowIdList") List<String> kmtExerciseQuestionKnowIdList,
                                               @Param("newLoaded") int newLoaded);

    /**
     * 分页查询所有练习册
     *
     *
     * @param selectedExerciseBookIdList 练习册id list
     * @param offset 从第？条开始
     * @param pageSize 获取？条记录
     *
     * @return 练习册list
     */
    List<KmtExerciseBook> findAllExerciseBookPage(@Param("selectedExerciseBookIdList") List<String> selectedExerciseBookIdList,
                                                  @Param("offset") int offset, @Param("pageSize") int pageSize);

    /**
     * 查询最新的打回理由记录
     * @param questionId
     * @return
     */
    KmtExerciseQuestionRollback findLastExerciseRollbackByQuestionId(@Param("questionId") String questionId);

    /**
     * 分页查询练习册
     * @param page
     * @param params
     * @return
     */
    List<Exercise1Dto> findExerciseList(Page page, @Param("map") Map<String, Object> params);

    /**
     * 分页查询练习册
     * @param page
     * @param params
     * @return
     */
    List<Exercise1Dto> findTeacherExerciseList(Page page, @Param("map") Map<String, Object> params);

    /**
     * 分页查询机构
     * @param page
     * @param params
     * @return
     */
    List<TbLibJoin> findLibList(Page page, @Param("map") Map<String, Object> params);

    /**
     * 删除练习册状态统计数据
     * @param exerciseBookIdSet 练习册id
     * @return 删除数量
     */
    int deleteKmtExerciseBookStatusCountByExerciseBookIds(@Param("exerciseBookIdSet") Set<String> exerciseBookIdSet);

    /**
     * 查询练习册统计
     * @return 练习册状态统计数据列表
     */
    List<ExerciseBookCountDTO> findExerciseBookCount();

    /**
     * 查询单科练习册列表
     * @param page 分页
     * @param req 入参
     * @return 单科练习册列表分页结果
     */
    @Select("select book_id, book_name, book_year from kmt_exercise_book_status_count where status = #{req.status} and course_name = #{req.subject}")
    Page<ExerciseBookCountSubjectDetailDTO> findExerciseBookCountSubjectDetail(IPage<ExerciseBookCountSubjectDetailDTO> page,
                                                                               @Param("req") ExerciseBookCountSubjectDetailReq req);
    /**
     * 查询所有的馆
     */
    List<Map<String,Object>> findAllLib(Page page, @Param("subject") String subject);

    /**
     * 查询馆里所有的练习册
     */
    List<KmtExerciseBookLibDto> findAllExerciseBook(@Param("libId") String libId, @Param("subject") String subject);

    /**
     * 查询所有的馆
     */
    List<Map<String,Object>> findAllExportLib(@Param("subject") String subject);

    /**
     * 查询大标题以及大标题下的所有小题 kmt_exercise_questions
     * @param parentIds
     * @return
     */
    List<KmtExerciseQuestion> findQuestionByParentId(@Param("parentIds") List<String> parentIds);


    /**
     * 根据题目id查询新老用户
     */
    List<KmtExerciseQuestionRollback> findKmtExerciseQuestionRollbackListByQuestionId(@Param("questionId") String questionId);

    TbLibManager findByUserIdAndTypeIn(@Param("userId") String userId);

    /**
     * 查询签约数
     */
    List<ExercisePriorityDto> findLibSignCount();

    /**
     * 更新练习册涉及到的机构签约数
     */
    void updateKmtExerciseBookByExerciseBookId(@Param("exerciseRelevancyNum") int exerciseRelevancyNum, @Param("exerciseBooId") String exerciseBookId);

    /**
     * 查询所有的有签约数的练习册
     */
     List<KmtExerciseBook> findAllExerciseBookBySignNum();

    /**
     * 更新优先级
     */
    void updateKmtExerciseBookById(@Param("priority") String priority, @Param("id") String id);

    /**
     * 更新优先级
     */
    void updateKmtExerciseBookByPriority(@Param("totalGradePriority") String totalGradePriority, @Param("id") String id);

    /**
     * 查询练习册的所有题目
     * @param exerciseBookId
     * @return
     */
    List<KmtExerciseQuestion> findExerciseQuestionByExerciseBookId(@Param("exerciseBookId") String exerciseBookId);

    /**
     * 查询题目列表
     * @param ids
     * @return
     */
    List<KmtExerciseQuestion> findExerciseQuestionByIds(@Param("ids") List<String> ids);

    /**
     * 查询答案报错练习册列表
     *
     * @param page 分页
     * @param req 入参
     */
    IPage<AnswerProofreadExerciseBookDTO> findAnswerProofreadExerciseBookList(IPage<AnswerProofreadExerciseBookDTO> page,
                                                                              @Param("req") AnswerProofreadExerciseBookListReq req);

    /**
     * 查询答案校对后需要修改答案的题目(即答案错误的题目)
     * @param page 分页
     * @param req 入参
     */
    IPage<ExerciseQuetionDto> findQuestionListAnswerWrong(IPage<ExerciseQuetionDto> page,
                                                          @Param("req") AnswerProofreadQuestionListReq req);

    /**
     * 查询打回的题目
     *
     * @param req 入参
     * @param dealStatusList 题目状态
     *
     * @return 题目列表
     */
    List<ExerciseQuetionDto> findRepulsedQuestion(@Param("req") ExerciseTeacherReviseQuestionReq req,
                                                  @Param("dealStatusList") List<Integer> dealStatusList);

    /**
     *
     * @param
     * @return
     */
    List<Map<String,Object>> findUnproofreadExerciseId();

    List<KmtExerciseQuestion> findExerciseStatusByBookId(@Param("bookId") String bookId);

    void updateExerciseBookStatusByIdAndStatus(@Param("proofreadStatus") Integer status,@Param("id") String id);

    /**
     * 更新练习册的校对状态
     * @param type
     * @param exerciseBookId
     */
    void updateExerciseBookProofreadResult(@Param("type") int type,
                                           @Param("exerciseBookId") String exerciseBookId);

    /**
     * 统计答案错误的题目
     *
     * @param exerciseBookId 练习册id
     * @param excludeQuestionIdSet 排除这些题目
     */
    int countAnswerWrongQuestion(@Param("exerciseBookId") String exerciseBookId, @Param("excludeQuestionIdSet") Set<String> excludeQuestionIdSet);

    /**
     * 更新练习册校对状态
     *
     * @param exerciseBookId 练习册id
     * @param newProofread 新校对状态
     */
    @Update("update kmt_exercise_book set proofread_status = #{newProofread} where id = #{exerciseBookId}")
    int updateKmtExerciseBookProofreadStatus(@Param("exerciseBookId") String exerciseBookId, @Param("newProofread") int newProofread);

    Map<String, Object> teacherAnswerProofreadDetail(@Param("userId") String userId);

    /**
     * 注销后更新校对中的老师状态
     */
    @Update("update kmt_exercise_book set answer_correcter_id=null where answer_correcter_id=#{answerCorrecterId} and answer_corrected_status=0")
    int updateKmtExerciseBookAnswerCorrecterId(@Param("answerCorrecterId") String answerCorrecterId);

    /**
     * 查询练习册单元课时列表2
     *
     * @param request 入参
     *
     * @return 单元课时列表
     */
    List<ExerciseUnitBookcourseDto> findUnitAndPeriodList(@Param("request") UnitAndPeriodListRequest request);

    /**
     * 查询题目的报错记录
     * @param questionIds
     * @param beType 被报错人的角色类型
     * @return
     */
    List<KmtExerciseQuestionErrors> findKmtExerciseQuestionErrorsByQuestionIds (@Param("questionIds") List<String> questionIds,
                                                                                @Param("beType") int beType);

    /**
     * 查询报错明细， kmt_exercise_question_errors
     * @param userId
     * @param page
     * @return
     */
    List<KmtExerciseQuestionErrors> findKmtExerciseQuestionByErrorUserId (@Param("userId") String userId, Page page);

    /**
     * 计算练习册老师的角色下的错误题数
     * @param userId
     * @param exerciseBookId
     * @param type
     * @return
     */
    int countQuestionErrorCountByExerciseBookId(@Param("userId") String userId, @Param("exerciseBookId") String exerciseBookId,
                                                @Param("type") int type);

    /**
     * 找出重复的练习册
     *
     * @return
     */
    List<KmtExerciseBook> findSameExerciseBookList();

    /**
     * 计算未加工数量
     * @param exerciseBookId
     * @param type
     * @return
     */
    int countUnFinishQuestionsByExerciseBookId (@Param("exerciseBookId") String exerciseBookId,
                                                @Param("type") int type);

    /**
     * 统计练习册分配情况
     */
    ExerciseDistributionCountDTO findDistributionCount();

    /**
     * 待分配/已分配练习册列表
     *
     * @param req 入参
     */
    List<DistributionExerciseBookDTO> findDistributionExerciseBookList(@Param("req") DistributionExerciseBookListReq req,
                                                                       @Param("offset") int offset,
                                                                       @Param("pageSize") int pageSize);

    /**
     * 统计待分配练习册数量
     *
     * @param req 入参
     */
    int countDistributionExerciseBook(@Param("req") DistributionExerciseBookListReq req);

    /**
     * 更新kmt_exercise_book校对老师
     * @param teacherId
     * @param exerciseBookIds
     */
    void updateAnswerCorrecterIdByIds(@Param("teacherId") String teacherId, @Param("exerciseBookIds") List<String> exerciseBookIds);
    /**
     * 更新kmt_exercise_question校对老师
     * @param teacherId
     * @param exerciseBookIds
     */
    void updateAnswerCorrecterIdByExerciseBookIds(@Param("teacherId") String teacherId, @Param("exerciseBookIds") List<String> exerciseBookIds);

    /**
     * 查询需要导出的已分配练习册列表
     *
     * @param req 入参
     * @param offset 查询？条
     */
    List<ExportDistributionExerciseBookDTO> findExportDistributionExerciseBookList(@Param("req") ExportDistributionExerciseBookListReq req, @Param("offset") int offset);

    /**
     * 查询题目处理人（加工、加审、解析、解审）信息
     *
     * @param exerciseBookId 练习册id
     * @param userId 处理人userId
     * @param authorityType 处理人类型
     */
    DistributionTeacherDTO findDistributionTeacher(@Param("exerciseBookId") String exerciseBookId,
                                                   @Param("userId") String userId,
                                                   @Param("authorityType") int authorityType);

    /**
     * 查询未校对的题目数量
     * @param exerciseBookId
     * @return
     */
    int countNotCheckAnswerCount (@Param("exerciseBookId") String exerciseBookId);

    /**
     * 计算练习册下proofread = 0的数量
     * @param exerciseBookId
     * @return
     */
    int countAllNotCheckAnswerCount (@Param("exerciseBookId") String exerciseBookId);

    /**
     * 查询练习册的所有记录
     * @param bookId
     * @return
     */
    List<KmtExerciseBook> findExerciseBooksByBookId (@Param("bookId") String bookId);

    /**
     * 查询分配老师的记录
     * @return
     */
    List<KmtExerciseBookTeacherRecord> findExerciseTeacherByExerciseBookIdsAndAuthType (@Param("exerciseBookIds") List<String> exerciseBookIds,
                                                                                        @Param("authType") int authType);

    /**
     * 查询book_count记录
     * @param exerciseBookId
     * @param type
     * @return
     */
    KmtExerciseBookCount findBookCountByExerciseBookIdAndType (@Param("exerciseBookId") String exerciseBookId,
                                                               @Param("type") int type);

    /**
     * 更新正确率
     * @param bookCountId
     * @param accuracy
     */
    void updateKmtExerciseBookCountById (@Param("bookCountId") String bookCountId,
                                         @Param("accuracy") int accuracy);

    /**
     * 查询练习册已分配导出数据
     *
     * @param exerciseBookId 练习册id
     *
     * @return 练习册已分配导出数据
     */
    @Select("select * from kmt_exercise_book_distribution_count where exercise_book_id = #{exerciseBookId}")
    KmtExerciseBookDistributionCount findKmtExerciseBookDistributionCountByExerciseBookId(@Param("exerciseBookId") String exerciseBookId);

    /**
     * 统计单元和课时的数量
     *
     * @param exerciseBookId 练习册id
     *
     * @return 单元和课时的数量map
     */
    @Select("select count(*) courseCount, count(distinct unit_id) unitCount from kmt_exercise_book_course where exercise_book_id = #{exerciseBookId}")
    Map<String, Long> countUnitAndCourse(@Param("exerciseBookId") String exerciseBookId);

    /**
     * 查询各加工身份最新提交时间
     *
     * @param exerciseBookId 练习册id
     *
     * @return 最新提交时间map
     */
    @Select("select max(handler_submit_time) handlerLastSubmitTime,\n" +
            "       max(publish_time) handleAuditUserLastSubmitTime,\n" +
            "       max(analysis_handler_submit_time) analyserLastSubmitTime,\n" +
            "       max(analysis_submit_time) analysisAuditUserLastSubmitTime\n" +
            "from kmt_exercise_questions\n" +
            "where exercise_book_id = #{exerciseBookId}")
    Map<String, Date> findLastSubmitTime(@Param("exerciseBookId") String exerciseBookId);

    /**
     * 查询各加工身份正确率
     *
     * @param exerciseBookId 练习册id
     *
     * @return 正确率map
     */
    @Select("select type, accuracy from kmt_exercise_book_count where exercise_book_id = #{exerciseBookId} and type between 1 and 3")
    List<Map<String, Integer>> findAccuracy(@Param("exerciseBookId") String exerciseBookId);

    /**
     * 查询练习册各状态统计
     *
     * @param exerciseBookId 练习册id
     * @param status 状态 com.ssj.service.kmt.exercisesys.enums.ExerciseBookStatusEnum
     *
     * @return 练习册状态数据
     */
    @Select("select * from kmt_exercise_book_status_count where exercise_book_id = #{exerciseBookId} and status = #{status}")
    KmtExerciseBookStatusCount findKmtExerciseBookStatusCountByExerciseBookIdAndStatus(@Param("exerciseBookId") String exerciseBookId,
                                                                                       @Param("status") int status);

    /**
     * 查询练习册加工情况
     *
     * @param exerciseBookId 练习册
     * @param type 身份类型(1练习册加工，2练习册审核，3练习册解析，4练习册解审，5KMT加工，6KMT审核)
     *
     * @return 练习册加工情况
     */
    @Select("select * from kmt_exercise_book_count where exercise_book_id = #{exerciseBookId} and type = #{type}")
    KmtExerciseBookCount findKmtExerciseBookCountByExerciseBookIdAndType(@Param("exerciseBookId") String exerciseBookId,
                                                                         @Param("type") int type);
}
