package cn.com.qmth.stmms.admin.user;

import cn.com.qmth.stmms.admin.exam.BaseExamController;
import cn.com.qmth.stmms.biz.exam.model.MarkerClass;
import cn.com.qmth.stmms.biz.exam.service.ExamStudentService;
import cn.com.qmth.stmms.biz.exam.service.MarkerClassService;
import cn.com.qmth.stmms.biz.user.model.User;
import cn.com.qmth.stmms.biz.user.service.UserService;
import cn.com.qmth.stmms.common.annotation.Logging;
import cn.com.qmth.stmms.common.domain.WebUser;
import cn.com.qmth.stmms.common.enums.LogType;
import cn.com.qmth.stmms.common.enums.MarkerExcelError;
import cn.com.qmth.stmms.common.enums.Role;
import cn.com.qmth.stmms.common.enums.UserSource;
import cn.com.qmth.stmms.common.utils.EncryptUtils;
import cn.com.qmth.stmms.common.utils.ExportExcel;
import cn.com.qmth.stmms.common.utils.ImportExcel;
import cn.com.qmth.stmms.common.utils.RequestUtils;

import org.apache.commons.lang.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Controller;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RequestMethod;
import org.springframework.web.multipart.MultipartFile;
import org.springframework.web.servlet.mvc.support.RedirectAttributes;

import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;

import java.util.*;

@Controller
@RequestMapping("/admin/user/class")
public class UserClassController extends BaseExamController {

    public static final String USER_PASSWORD = "123456";

    @Autowired
    private UserService userService;

    @Autowired
    private MarkerClassService markerClassService;

    @Autowired
    private ExamStudentService studentService;

    @RequestMapping(value = "/template")
    public String importFileTemplate(HttpServletResponse response, RedirectAttributes redirectAttributes) {
        try {
            String fileName = "评卷员机组导入模板.xlsx";
            List<MarkerClass> list = new ArrayList<MarkerClass>();
            list.add(new MarkerClass());
            new ExportExcel("评卷员机组数据", MarkerClass.class, 2).setDataList(list).write(response, fileName).dispose();
            return null;
        } catch (Exception e) {
            addMessage(redirectAttributes, "导入模板下载失败！失败信息：" + e.getMessage());
        }
        return "redirect:/admin/user/list";
    }

    @Logging(menu = "评卷员机组导入", type = LogType.IMPORT_FILE)
    @RequestMapping(value = "/import", method = RequestMethod.POST)
    public String importFile(HttpServletRequest request, MultipartFile file, RedirectAttributes redirectAttributes) {
        WebUser wu = RequestUtils.getWebUser(request);
        try {
            int successNum = 0;
            int failureNum = 0;
            StringBuilder failureMsg = new StringBuilder();
            ImportExcel ei = new ImportExcel(file, 1, 0);
            List<MarkerClass> list = ei.getDataList(MarkerClass.class);
            Map<String, User> userMap = new HashMap<String, User>();
            List<MarkerClass> saveList = new ArrayList<MarkerClass>();
            Map<Integer, List<String>> classMap = new HashMap<Integer, List<String>>();
            Map<String, MarkerClass> markerClassMap = new HashMap<String, MarkerClass>();
            Integer schoolId = wu.getUser().getSchoolId();
            for (MarkerClass markerClass : list) {
                if (markerClass.getExamId() == null) {
                    failureMsg.append("<br/>用户名 " + markerClass.getLoginName() + MarkerExcelError.EXAMNULL.getName());
                    failureNum++;
                    continue;
                }
                if (StringUtils.isBlank(markerClass.getClassName())) {
                    failureMsg.append("<br/>用户名 " + markerClass.getLoginName() + MarkerExcelError.CLASSNULL.getName());
                    failureNum++;
                    continue;
                }
                List<String> classes = classMap.get(markerClass.getExamId());
                if (classes == null) {
                    classes = studentService.findDistinctClassName(markerClass.getExamId());
                    classMap.put(markerClass.getExamId(), classes);
                }
                if (!classes.contains(markerClass.getClassName())) {
                    failureMsg.append("<br/>考试 " + markerClass.getExamId() + " 机组 " + markerClass.getClassName()
                            + MarkerExcelError.EXAMCLASSNULL.getName());
                    failureNum++;
                    continue;
                }
                if (StringUtils.isBlank(markerClass.getLoginName())) {
                    failureMsg.append("<br/> " + markerClass.getLoginName() + MarkerExcelError.NAMENULL.getName());
                    failureNum++;
                    continue;
                }
                User user = userMap.get(markerClass.getLoginName().trim());
                if (user == null) {
                    user = userService.findByLoginName(markerClass.getLoginName().trim());
                    if (user != null && !schoolId.equals(user.getSchoolId())) {
                        failureMsg.append("<br/>用户名 " + markerClass.getLoginName()
                                + MarkerExcelError.NAMEUSED.getName());
                        failureNum++;
                        continue;
                    }
                    if (user != null && !user.getRole().equals(Role.MARKER)) {
                        failureMsg.append("<br/>用户名 " + markerClass.getLoginName()
                                + MarkerExcelError.NAMENOTMARKER.getName());
                        failureNum++;
                        continue;
                    }
                    if (user == null) {
                        user = getUser(userMap, markerClass.getLoginName().trim(), schoolId);
                    }
                }
                markerClass = getMarkerClass(user.getId(), markerClass.getExamId(), markerClass.getClassName(),
                        markerClassMap);
                if (markerClass != null) {
                    saveList.add(markerClass);
                }
            }
            successNum = markerClassService.batchSave(saveList);
            if (failureNum > 0) {
                failureMsg.insert(0, "，失败 " + failureNum + " 条记录！");
            }
            String message = "已成功导入 " + successNum + " 条 ";
            addMessage(redirectAttributes, message + failureMsg);
            RequestUtils.setLog(request, message);
        } catch (Exception e) {
            log.error("Batch import user class error!", e);
            addMessage(redirectAttributes, "导入用户机组失败！失败信息：" + e.getMessage());
        }
        return "redirect:/admin/user/list";
    }

    private MarkerClass getMarkerClass(Integer userId, Integer examId, String className,
            Map<String, MarkerClass> markerClassMap) {
        MarkerClass m = markerClassMap.get(userId + "_" + examId + "_" + className);
        if (m != null) {
            return null;
        }
        m = markerClassService.findByUserIdAndExamIdAndClassName(userId, examId, className);
        if (m == null) {
            m = new MarkerClass(userId, examId, className);
        }
        markerClassMap.put(userId + "_" + examId + "_" + className, m);
        return m;
    }

    private User getUser(Map<String, User> saveMap, String loginName, Integer schoolId) {
        User user = saveMap.get(loginName);
        if (user == null) {
            user = new User();
            user.setLoginName(loginName);
            user.setName(loginName);
            user.setPassword(EncryptUtils.md5(USER_PASSWORD));
            user.setRole(Role.MARKER);
            user.setSchoolId(schoolId);
            user.setEnable(true);
            user.setCreatedTime(new Date());
            user.setSource(UserSource.INTERNAL);
            userService.save(user);
            saveMap.put(loginName, user);
        }
        return user;
    }

}
