linzhijie
2021-04-06 8728733ad60e1698bb6cf0fa2e428c28a6bffbe7
需求提交。
8个文件已添加
20个文件已修改
1899 ■■■■■ 已修改文件
.idea/workspace.xml 202 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/ots/project/exam/controller/EntTestPackageController.java 132 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/ots/project/exam/controller/TExamReportController.java 127 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/ots/project/exam/controller/TReportTemplateController.java 32 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/ots/project/exam/domain/EntEmailTemplate.java 92 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/ots/project/exam/domain/EntTestPackage.java 7 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/ots/project/exam/domain/TExamReport.java 11 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/ots/project/exam/mapper/EntEmailTemplateMapper.java 19 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/ots/project/exam/service/IEntEmailTemplateService.java 29 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/ots/project/exam/service/impl/EntEmailTemplateServiceImpl.java 74 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/java/com/ots/project/exam/service/impl/TExamPaperServiceImpl.java 5 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/application-local.yml 4 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/application-tencent.yml 92 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/application.yml 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/mybatis/exam/EntEmailTemplateMapper.xml 175 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/mybatis/exam/EntTestPackageMapper.xml 12 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/mybatis/exam/TExamReportMapper.xml 18 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/static/i18n/messages_en_US.properties 7 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/static/i18n/messages_th_TH.properties 7 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/static/i18n/messages_zh_CN.properties 7 ●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/static/ots/css/ry-ui.css 61 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/exam/distributor/distributor.html 8 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/exam/report/evaluationReport.html 216 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/exam/report/report.html 2 ●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/exam/template/emailEdit.html 252 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/exam/template/template.html 10 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/exam/test_package/add.html 144 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/main/resources/templates/exam/test_package/edit.html 152 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
.idea/workspace.xml
@@ -20,14 +20,34 @@
  </component>
  <component name="ChangeListManager">
    <list default="true" id="cd72c5cc-17e9-4269-9d87-e1dc29ad79ec" name="Default Changelist" comment="去除泰国接口调用">
      <change afterPath="$PROJECT_DIR$/src/main/java/com/ots/project/exam/domain/EntEmailTemplate.java" afterDir="false" />
      <change afterPath="$PROJECT_DIR$/src/main/java/com/ots/project/exam/mapper/EntEmailTemplateMapper.java" afterDir="false" />
      <change afterPath="$PROJECT_DIR$/src/main/java/com/ots/project/exam/service/IEntEmailTemplateService.java" afterDir="false" />
      <change afterPath="$PROJECT_DIR$/src/main/java/com/ots/project/exam/service/impl/EntEmailTemplateServiceImpl.java" afterDir="false" />
      <change afterPath="$PROJECT_DIR$/src/main/resources/application-tencent.yml" afterDir="false" />
      <change afterPath="$PROJECT_DIR$/src/main/resources/mybatis/exam/EntEmailTemplateMapper.xml" afterDir="false" />
      <change afterPath="$PROJECT_DIR$/src/main/resources/templates/exam/report/evaluationReport.html" afterDir="false" />
      <change afterPath="$PROJECT_DIR$/src/main/resources/templates/exam/template/emailEdit.html" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/.idea/workspace.xml" beforeDir="false" afterPath="$PROJECT_DIR$/.idea/workspace.xml" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/java/com/ots/project/exam/controller/EntTestPackageController.java" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/java/com/ots/project/exam/controller/EntTestPackageController.java" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/java/com/ots/project/exam/controller/TExamReportController.java" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/java/com/ots/project/exam/controller/TExamReportController.java" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/java/com/ots/project/exam/controller/TReportTemplateController.java" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/java/com/ots/project/exam/controller/TReportTemplateController.java" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/java/com/ots/project/exam/domain/EntTestPackage.java" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/java/com/ots/project/exam/domain/EntTestPackage.java" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/java/com/ots/project/exam/domain/TExamReport.java" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/java/com/ots/project/exam/domain/TExamReport.java" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/java/com/ots/project/exam/service/impl/TExamPaperServiceImpl.java" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/java/com/ots/project/exam/service/impl/TExamPaperServiceImpl.java" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/resources/application-local.yml" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/resources/application-local.yml" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/resources/application.yml" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/resources/application.yml" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/resources/mybatis/exam/EntTestPackageMapper.xml" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/resources/mybatis/exam/EntTestPackageMapper.xml" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/resources/mybatis/exam/TExamReportMapper.xml" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/resources/mybatis/exam/TExamReportMapper.xml" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/resources/static/i18n/messages_en_US.properties" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/resources/static/i18n/messages_en_US.properties" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/resources/static/i18n/messages_th_TH.properties" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/resources/static/i18n/messages_th_TH.properties" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/resources/static/i18n/messages_zh_CN.properties" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/resources/static/i18n/messages_zh_CN.properties" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/resources/templates/exam/test_package/test_package.html" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/resources/templates/exam/test_package/test_package.html" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/resources/templates/main.html" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/resources/templates/main.html" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/resources/static/ots/css/ry-ui.css" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/resources/static/ots/css/ry-ui.css" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/resources/templates/exam/distributor/distributor.html" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/resources/templates/exam/distributor/distributor.html" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/resources/templates/exam/report/report.html" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/resources/templates/exam/report/report.html" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/resources/templates/exam/template/template.html" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/resources/templates/exam/template/template.html" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/resources/templates/exam/test_package/add.html" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/resources/templates/exam/test_package/add.html" afterDir="false" />
      <change beforePath="$PROJECT_DIR$/src/main/resources/templates/exam/test_package/edit.html" beforeDir="false" afterPath="$PROJECT_DIR$/src/main/resources/templates/exam/test_package/edit.html" afterDir="false" />
    </list>
    <option name="SHOW_DIALOG" value="false" />
    <option name="HIGHLIGHT_CONFLICTS" value="true" />
@@ -58,6 +78,7 @@
    <option name="showLibraryContents" value="true" />
  </component>
  <component name="PropertiesComponent">
    <property name="DatabaseDriversLRU" value="mysql" />
    <property name="RequestMappingsPanelOrder0" value="0" />
    <property name="RequestMappingsPanelOrder1" value="1" />
    <property name="RequestMappingsPanelWidth0" value="75" />
@@ -68,7 +89,7 @@
    <property name="WebServerToolWindowFactoryState" value="false" />
    <property name="aspect.path.notification.shown" value="true" />
    <property name="ignore_missing_gitignore" value="true" />
    <property name="last_opened_file_path" value="$PROJECT_DIR$/../../Project/engine" />
    <property name="last_opened_file_path" value="$PROJECT_DIR$/../tai-ots-framework" />
    <property name="nodejs_package_manager_path" value="npm" />
    <property name="project.structure.last.edited" value="Project" />
    <property name="project.structure.proportion" value="0.0" />
@@ -77,11 +98,16 @@
    <property name="vue.rearranger.settings.migration" value="true" />
  </component>
  <component name="RecentsManager">
    <key name="CopyClassDialog.RECENTS_KEY">
      <recent name="com.ots.project.exam.service.impl" />
      <recent name="com.ots.project.exam.service" />
    </key>
    <key name="CopyFile.RECENT_KEYS">
      <recent name="D:\测评系统\tai-ots-master\src\main\resources\mybatis\exam" />
      <recent name="D:\测评系统\tai-ots-master\src\main\java\com\ots\project\exam\mapper" />
      <recent name="D:\测评系统\tai-ots-master\src\main\java\com\ots\project\exam\domain" />
      <recent name="D:\测评系统\tai-ots-master\src\main\resources\templates\exam\template" />
      <recent name="D:\测评系统\tai-ots-master\src\main\resources" />
      <recent name="D:\测评系统\tai-ots-master\src\main\resources\templates" />
      <recent name="D:\测评系统\tai-ots-master" />
      <recent name="D:\测评系统\tai-ots-master\src\main" />
    </key>
  </component>
  <component name="RunAnythingCache">
@@ -101,12 +127,77 @@
      </extension>
      <option name="SPRING_BOOT_MAIN_CLASS" value="com.ots.OtsApplication" />
      <option name="ALTERNATIVE_JRE_PATH" />
      <option name="UPDATE_ACTION_UPDATE_POLICY" value="UpdateResources" />
      <option name="FRAME_DEACTIVATION_UPDATE_POLICY" value="UpdateResources" />
      <method v="2">
        <option name="Make" enabled="true" />
      </method>
    </configuration>
    <configuration default="true" type="#com.intellij.j2ee.web.tomcat.TomcatRunConfigurationFactory" factoryName="Local" ALTERNATIVE_JRE_ENABLED="false">
      <deployment />
      <server-settings>
        <option name="BASE_DIRECTORY_NAME" value="_tai-ots-master" />
      </server-settings>
      <predefined_log_file enabled="true" id="Tomcat" />
      <predefined_log_file enabled="true" id="Tomcat Catalina" />
      <predefined_log_file id="Tomcat Manager" />
      <predefined_log_file id="Tomcat Host Manager" />
      <predefined_log_file id="Tomcat Localhost Access" />
      <RunnerSettings RunnerId="Debug">
        <option name="DEBUG_PORT" value="59553" />
      </RunnerSettings>
      <ConfigurationWrapper VM_VAR="JAVA_OPTS" RunnerId="Cover">
        <option name="USE_ENV_VARIABLES" value="true" />
        <STARTUP>
          <option name="USE_DEFAULT" value="true" />
          <option name="SCRIPT" value="" />
          <option name="VM_PARAMETERS" value="" />
          <option name="PROGRAM_PARAMETERS" value="" />
        </STARTUP>
        <SHUTDOWN>
          <option name="USE_DEFAULT" value="true" />
          <option name="SCRIPT" value="" />
          <option name="VM_PARAMETERS" value="" />
          <option name="PROGRAM_PARAMETERS" value="" />
        </SHUTDOWN>
      </ConfigurationWrapper>
      <ConfigurationWrapper VM_VAR="JAVA_OPTS" RunnerId="Debug">
        <option name="USE_ENV_VARIABLES" value="true" />
        <STARTUP>
          <option name="USE_DEFAULT" value="true" />
          <option name="SCRIPT" value="" />
          <option name="VM_PARAMETERS" value="" />
          <option name="PROGRAM_PARAMETERS" value="" />
        </STARTUP>
        <SHUTDOWN>
          <option name="USE_DEFAULT" value="true" />
          <option name="SCRIPT" value="" />
          <option name="VM_PARAMETERS" value="" />
          <option name="PROGRAM_PARAMETERS" value="" />
        </SHUTDOWN>
      </ConfigurationWrapper>
      <ConfigurationWrapper VM_VAR="JAVA_OPTS" RunnerId="Run">
        <option name="USE_ENV_VARIABLES" value="true" />
        <STARTUP>
          <option name="USE_DEFAULT" value="true" />
          <option name="SCRIPT" value="" />
          <option name="VM_PARAMETERS" value="" />
          <option name="PROGRAM_PARAMETERS" value="" />
        </STARTUP>
        <SHUTDOWN>
          <option name="USE_DEFAULT" value="true" />
          <option name="SCRIPT" value="" />
          <option name="VM_PARAMETERS" value="" />
          <option name="PROGRAM_PARAMETERS" value="" />
        </SHUTDOWN>
      </ConfigurationWrapper>
      <method v="2">
        <option name="Make" enabled="true" />
      </method>
    </configuration>
    <recent_temporary>
      <list>
        <item itemvalue="Spring Boot.OtsApplication" />
        <item itemvalue="Spring Boot.OtsApplication" />
      </list>
    </recent_temporary>
@@ -149,6 +240,16 @@
      <workItem from="1616341817344" duration="977000" />
      <workItem from="1616379322437" duration="2089000" />
      <workItem from="1616384832741" duration="4189000" />
      <workItem from="1616944302613" duration="2595000" />
      <workItem from="1616982316816" duration="15696000" />
      <workItem from="1617025944252" duration="1147000" />
      <workItem from="1617031413719" duration="2534000" />
      <workItem from="1617069207465" duration="212000" />
      <workItem from="1617076614568" duration="21243000" />
      <workItem from="1617162388942" duration="14644000" />
      <workItem from="1617202312034" duration="2278000" />
      <workItem from="1617205486701" duration="476000" />
      <workItem from="1617267163012" duration="5048000" />
    </task>
    <task id="LOCAL-00001" summary="测评项目最新代码">
      <created>1615212708854</created>
@@ -255,74 +356,78 @@
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state x="440" y="94" key="#Project_Structure/0.0.1920.1040@0.0.1920.1040" timestamp="1615515318160" />
    <state x="414" y="174" key="#com.intellij.execution.impl.EditConfigurationsDialog" timestamp="1615688571928">
    <state x="414" y="174" key="#com.intellij.execution.impl.EditConfigurationsDialog" timestamp="1617179034831">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state x="414" y="174" key="#com.intellij.execution.impl.EditConfigurationsDialog/0.0.1920.1040@0.0.1920.1040" timestamp="1615688571928" />
    <state x="456" y="74" key="CommitChangelistDialog2" timestamp="1616585341087">
    <state x="414" y="174" key="#com.intellij.execution.impl.EditConfigurationsDialog/0.0.1920.1040@0.0.1920.1040" timestamp="1617179034831" />
    <state x="710" y="220" key="#com.intellij.ide.util.MemberChooser" timestamp="1617180566416">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state x="456" y="74" key="CommitChangelistDialog2/0.0.1920.1040@0.0.1920.1040" timestamp="1616585341087" />
    <state x="135" y="145" width="1736" height="856" key="DiffContextDialog" timestamp="1616585339922">
    <state x="710" y="220" key="#com.intellij.ide.util.MemberChooser/0.0.1920.1040@0.0.1920.1040" timestamp="1617180566416" />
    <state x="456" y="74" key="CommitChangelistDialog2" timestamp="1617202615253">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state x="135" y="145" width="1736" height="856" key="DiffContextDialog/0.0.1920.1040@0.0.1920.1040" timestamp="1616585339922" />
    <state x="740" y="274" key="FileChooserDialogImpl" timestamp="1616588718176">
    <state x="456" y="74" key="CommitChangelistDialog2/0.0.1920.1040@0.0.1920.1040" timestamp="1617202615253" />
    <state x="135" y="145" width="1736" height="856" key="DiffContextDialog" timestamp="1617202614473">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state x="740" y="274" key="FileChooserDialogImpl/0.0.1920.1040@0.0.1920.1040" timestamp="1616588718176" />
    <state x="135" y="145" width="1736" height="856" key="DiffContextDialog/0.0.1920.1040@0.0.1920.1040" timestamp="1617202614473" />
    <state x="740" y="274" key="FileChooserDialogImpl" timestamp="1617203062677">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state x="740" y="274" key="FileChooserDialogImpl/0.0.1920.1040@0.0.1920.1040" timestamp="1617203062677" />
    <state width="283" height="373" key="Git.Branch.Popup" timestamp="1616585343736">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state width="283" height="373" key="Git.Branch.Popup/0.0.1920.1040@0.0.1920.1040" timestamp="1616585343736" />
    <state width="1877" height="266" key="GridCell.Tab.0.bottom" timestamp="1616590336140">
    <state width="1877" height="251" key="GridCell.Tab.0.bottom" timestamp="1617275733566">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state width="1877" height="266" key="GridCell.Tab.0.bottom/0.0.1920.1040@0.0.1920.1040" timestamp="1616590336140" />
    <state width="1877" height="266" key="GridCell.Tab.0.center" timestamp="1616590336140">
    <state width="1877" height="251" key="GridCell.Tab.0.bottom/0.0.1920.1040@0.0.1920.1040" timestamp="1617275733566" />
    <state width="1877" height="251" key="GridCell.Tab.0.center" timestamp="1617275733566">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state width="1877" height="266" key="GridCell.Tab.0.center/0.0.1920.1040@0.0.1920.1040" timestamp="1616590336140" />
    <state width="1877" height="266" key="GridCell.Tab.0.left" timestamp="1616590336140">
    <state width="1877" height="251" key="GridCell.Tab.0.center/0.0.1920.1040@0.0.1920.1040" timestamp="1617275733566" />
    <state width="1877" height="251" key="GridCell.Tab.0.left" timestamp="1617275733566">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state width="1877" height="266" key="GridCell.Tab.0.left/0.0.1920.1040@0.0.1920.1040" timestamp="1616590336140" />
    <state width="1877" height="266" key="GridCell.Tab.0.right" timestamp="1616590336140">
    <state width="1877" height="251" key="GridCell.Tab.0.left/0.0.1920.1040@0.0.1920.1040" timestamp="1617275733566" />
    <state width="1877" height="251" key="GridCell.Tab.0.right" timestamp="1617275733566">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state width="1877" height="266" key="GridCell.Tab.0.right/0.0.1920.1040@0.0.1920.1040" timestamp="1616590336140" />
    <state width="1877" height="266" key="GridCell.Tab.1.bottom" timestamp="1616590336140">
    <state width="1877" height="251" key="GridCell.Tab.0.right/0.0.1920.1040@0.0.1920.1040" timestamp="1617275733566" />
    <state width="1877" height="251" key="GridCell.Tab.1.bottom" timestamp="1617273606880">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state width="1877" height="266" key="GridCell.Tab.1.bottom/0.0.1920.1040@0.0.1920.1040" timestamp="1616590336140" />
    <state width="1877" height="266" key="GridCell.Tab.1.center" timestamp="1616590336140">
    <state width="1877" height="251" key="GridCell.Tab.1.bottom/0.0.1920.1040@0.0.1920.1040" timestamp="1617273606880" />
    <state width="1877" height="251" key="GridCell.Tab.1.center" timestamp="1617273606879">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state width="1877" height="266" key="GridCell.Tab.1.center/0.0.1920.1040@0.0.1920.1040" timestamp="1616590336140" />
    <state width="1877" height="266" key="GridCell.Tab.1.left" timestamp="1616590336140">
    <state width="1877" height="251" key="GridCell.Tab.1.center/0.0.1920.1040@0.0.1920.1040" timestamp="1617273606879" />
    <state width="1877" height="251" key="GridCell.Tab.1.left" timestamp="1617273606879">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state width="1877" height="266" key="GridCell.Tab.1.left/0.0.1920.1040@0.0.1920.1040" timestamp="1616590336140" />
    <state width="1877" height="266" key="GridCell.Tab.1.right" timestamp="1616590336140">
    <state width="1877" height="251" key="GridCell.Tab.1.left/0.0.1920.1040@0.0.1920.1040" timestamp="1617273606879" />
    <state width="1877" height="251" key="GridCell.Tab.1.right" timestamp="1617273606879">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state width="1877" height="266" key="GridCell.Tab.1.right/0.0.1920.1040@0.0.1920.1040" timestamp="1616590336140" />
    <state width="1877" height="385" key="GridCell.Tab.2.bottom" timestamp="1615889660606">
    <state width="1877" height="251" key="GridCell.Tab.1.right/0.0.1920.1040@0.0.1920.1040" timestamp="1617273606879" />
    <state width="1877" height="270" key="GridCell.Tab.2.bottom" timestamp="1617108907135">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state width="1877" height="385" key="GridCell.Tab.2.bottom/0.0.1920.1040@0.0.1920.1040" timestamp="1615889660606" />
    <state width="1877" height="385" key="GridCell.Tab.2.center" timestamp="1615889660605">
    <state width="1877" height="270" key="GridCell.Tab.2.bottom/0.0.1920.1040@0.0.1920.1040" timestamp="1617108907135" />
    <state width="1877" height="270" key="GridCell.Tab.2.center" timestamp="1617108907135">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state width="1877" height="385" key="GridCell.Tab.2.center/0.0.1920.1040@0.0.1920.1040" timestamp="1615889660605" />
    <state width="1877" height="385" key="GridCell.Tab.2.left" timestamp="1615889660605">
    <state width="1877" height="270" key="GridCell.Tab.2.center/0.0.1920.1040@0.0.1920.1040" timestamp="1617108907135" />
    <state width="1877" height="270" key="GridCell.Tab.2.left" timestamp="1617108907135">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state width="1877" height="385" key="GridCell.Tab.2.left/0.0.1920.1040@0.0.1920.1040" timestamp="1615889660605" />
    <state width="1877" height="385" key="GridCell.Tab.2.right" timestamp="1615889660605">
    <state width="1877" height="270" key="GridCell.Tab.2.left/0.0.1920.1040@0.0.1920.1040" timestamp="1617108907135" />
    <state width="1877" height="270" key="GridCell.Tab.2.right" timestamp="1617108907135">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state width="1877" height="385" key="GridCell.Tab.2.right/0.0.1920.1040@0.0.1920.1040" timestamp="1615889660605" />
    <state width="1877" height="270" key="GridCell.Tab.2.right/0.0.1920.1040@0.0.1920.1040" timestamp="1617108907135" />
    <state x="490" y="174" key="Maven.ArtifactSearchDialog" timestamp="1615427932582">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
@@ -343,14 +448,18 @@
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state width="968" height="528" key="XDebugger.FullValuePopup/0.0.1920.1040@0.0.1920.1040" timestamp="1615866063087" />
    <state x="540" y="174" key="com.intellij.database.dbimport.ImportDialog" timestamp="1617179046190">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state x="540" y="174" key="com.intellij.database.dbimport.ImportDialog/0.0.1920.1040@0.0.1920.1040" timestamp="1617179046190" />
    <state x="754" y="432" key="com.intellij.openapi.vcs.update.UpdateOrStatusOptionsDialogupdate-v2" timestamp="1615427969273">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state x="754" y="432" key="com.intellij.openapi.vcs.update.UpdateOrStatusOptionsDialogupdate-v2/0.0.1920.1040@0.0.1920.1040" timestamp="1615427969273" />
    <state x="1083" y="283" width="603" height="748" key="find.popup" timestamp="1616590485815">
    <state x="563" y="274" width="827" height="748" key="find.popup" timestamp="1617273466453">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state x="1083" y="283" width="603" height="748" key="find.popup/0.0.1920.1040@0.0.1920.1040" timestamp="1616590485815" />
    <state x="563" y="274" width="827" height="748" key="find.popup/0.0.1920.1040@0.0.1920.1040" timestamp="1617273466453" />
    <state x="727" y="231" key="git4idea.branch.GitSmartOperationDialog" timestamp="1616585254266">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
@@ -359,14 +468,14 @@
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state x="761" y="426" key="git4idea.remote.GitConfigureRemotesDialog/0.0.1920.1040@0.0.1920.1040" timestamp="1615460537318" />
    <state x="616" y="240" width="672" height="677" key="run.anything.popup" timestamp="1615795422622">
    <state x="616" y="240" width="672" height="677" key="run.anything.popup" timestamp="1617273606783">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state x="616" y="240" width="672" height="677" key="run.anything.popup/0.0.1920.1040@0.0.1920.1040" timestamp="1615795422622" />
    <state x="623" y="225" width="672" height="678" key="search.everywhere.popup" timestamp="1615864418427">
    <state x="616" y="240" width="672" height="677" key="run.anything.popup/0.0.1920.1040@0.0.1920.1040" timestamp="1617273606783" />
    <state x="623" y="225" width="672" height="678" key="search.everywhere.popup" timestamp="1617032712590">
      <screen x="0" y="0" width="1920" height="1040" />
    </state>
    <state x="623" y="225" width="672" height="678" key="search.everywhere.popup/0.0.1920.1040@0.0.1920.1040" timestamp="1615864418427" />
    <state x="623" y="225" width="672" height="678" key="search.everywhere.popup/0.0.1920.1040@0.0.1920.1040" timestamp="1617032712590" />
  </component>
  <component name="XDebuggerManager">
    <breakpoint-manager>
@@ -441,6 +550,11 @@
          <line>514</line>
          <option name="timeStamp" value="64" />
        </line-breakpoint>
        <line-breakpoint enabled="true" type="java-line">
          <url>file://$PROJECT_DIR$/src/main/java/com/ots/project/exam/controller/TExamReportController.java</url>
          <line>678</line>
          <option name="timeStamp" value="67" />
        </line-breakpoint>
        <line-breakpoint enabled="true" type="javascript">
          <url>file://$PROJECT_DIR$/src/main/resources/static/ots/js/ry-ui.js</url>
          <line>750</line>
src/main/java/com/ots/project/exam/controller/EntTestPackageController.java
@@ -11,12 +11,10 @@
import com.ots.framework.web.domain.AjaxResult;
import com.ots.framework.web.page.TableDataInfo;
import com.ots.project.exam.domain.EntDemographyParam;
import com.ots.project.exam.domain.EntEmailTemplate;
import com.ots.project.exam.domain.EntTestPackage;
import com.ots.project.exam.domain.SysUserExtend;
import com.ots.project.exam.service.IEntDemographyParamService;
import com.ots.project.exam.service.IEntTestPackageService;
import com.ots.project.exam.service.ISysUserExtendService;
import com.ots.project.exam.service.ITReportTemplateService;
import com.ots.project.exam.service.*;
import com.ots.project.system.user.domain.User;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.jetbrains.annotations.NotNull;
@@ -59,13 +57,16 @@
    @Autowired
    private ITReportTemplateService reportTemplateService;
    @Autowired
    private IEntEmailTemplateService entEmailTemplateService;
    @RequiresPermissions("exam:test_package:view")
    @GetMapping()
    public String test_package() {
        return prefix + "/test_package";
    }
    @RequiresPermissions("exam:test_package:search")
    @RequiresPermissions("exam:test_package:view")
    @GetMapping("/searchTestPackage")
    public String search(String testName, ModelMap mmap) {
        if (Objects.nonNull(testName)) {
@@ -150,67 +151,14 @@
        mmap.put("roles", list);
        //报告模板编码  t_report_template
//        mmap.put("templateList", reportTemplateService.getReportTemplates(ShiroUtils.getSysUser()));
        mmap.put("template", getTemplate());
//        mmap.put("template", getTemplate());
        //默认邮件内容模板配置
        EntEmailTemplate eet = entEmailTemplateService.getOnly();
        mmap.put("eet", eet);
        SysUserExtend sysUserExtend = sysUserExtendService.selectSysUserExtendById(ShiroUtils.getUserId());
        String mailContent = sysUserExtend.getMailContent();
        if (StringUtils.isBlank(mailContent)) {
            mailContent = getHrTemplate();
        }
        mmap.put("hrTemplate", mailContent);
        mmap.put("hrTemplate",mailContent);
        return prefix + "/add";
    }
    @NotNull
    private String getHrTemplate() {
        String template = "亲爱的{Company}人力资源部,\n" +
                "Dear HR Staff at {Company},\n" +
                "เรียนฝ่ายบุคคลของ {Company}\n" +
                "\n" +
                "附件是{FullName} 最近完成的{prodName}测评报告。\n" +
                "Attached please find the assessment report on {prodName} of {FullName}\n" +
                "กรุณาตรวจสอบเอกสารแนบ ของ {FullName} ของ {prodName}. \n" +
                "\n" +
                "如有疑问,请与客服联系,邮箱是:support@tai-online.com。\n" +
                "Should you have questions, please contact our customer service at support@tai-online.com. \n" +
                "หากมีข้อสงสัยหรือคำถามเพิ่มเติม กรุณาติดต่อฝ่ายบริการลูกค้าสัมพันธ์ ที่ support@tai-online.com\n" +
                "\n" +
                "\n" +
                "谢谢!\n" +
                "All the best,\n" +
                "ขอขอบคุณเป็นอย่างยิ่ง\n" +
                "\n" +
                "\n" +
                "TAI公司客户服务部\n" +
                "Customer Service Dept., TAI, LLC\n" +
                "ฝ่ายบริการลูกค้าสัมพันธ์บริษท TAI";
        return template;
    }
    @NotNull
    private String getTemplate() {
        String template = "亲爱的{FullName},\n" +
                "<br>Dear {FullName},\n" +
                "<br>เรียน {FullName},\n" +
                "<br>\n" +
                "<br>{Company} 邀请您完成一份测试,大概需要20-25分钟时间。您可以直接点击下面的链接开始该测试。如果不能直接访问,请复制地址到浏览器中直接打开。\n" +
                "<br>You've been invited to take an assessment by {Company}, which shall take about 20-25 minutes to complete. Please click the link below, or copy the link to your browser, to begin the assessment.\n" +
                "<br>คุณได้รับเชิญให้ทำแบบประเมินจาก {Company} กรุณาใช้ลิงค์ด้านล่างเพื่อเริ่มดำเนินการ โดยคุณสามารถคลิกที่ลิงค์ด้านล่างโดยตรง หรือจะคัดลอกแล้วนำลิงค์ไปวางบนเบราว์เซอร์ของคุณก็ได้\n" +
                "<br>链接地址是:<a href='{url}' target='_blank'>{url}</a>\n" +
                "<br>The link is: <a href='{url}' target='_blank'>{url}</a>\n" +
                "<br>ตามลิงค์นี้: <a href='{url}' target='_blank'>{url}</a>\n" +
                "<br>\n" +
                "<br>如有疑问,请与客服联系,邮箱是:support@tai-online.com。\n" +
                "<br>Should you have problem assessing the above link, please contact our customer service at support@tai-online.com.\n" +
                "<br>หากคุณมีปัญหาในการเข้าสู่ลิงค์ข้างต้น โปรดติดต่อฝ่ายบริการลูกค้าของเราที่ support@tai-online.com\n" +
                "<br>\n" +
                "<br>\n" +
                "<br>谢谢!\n" +
                "<br>All the best,\n" +
                "<br>ด้วยความเคารพ\n" +
                "<br>\n" +
                "<br>{Company}\n" +
                "<br>";
        return template;
    }
    /**
@@ -270,6 +218,12 @@
            });
        }
        mmap.put("roles", list);
        //默认邮件内容模板配置
        EntEmailTemplate eet = entEmailTemplateService.getOnly();
        mmap.put("eet", eet);
        SysUserExtend sysUserExtend = sysUserExtendService.selectSysUserExtendById(ShiroUtils.getUserId());
        String mailContent = sysUserExtend.getMailContent();
        mmap.put("hrTemplate",mailContent);
        //报告模板编码  t_report_template
        mmap.put("templateList", reportTemplateService.getReportTemplates(ShiroUtils.getSysUser(), entTestPackage.getProdId()));
@@ -298,5 +252,57 @@
        return toAjax(entTestPackageService.deleteEntTestPackageByIds(ids));
    }
    @NotNull
    private String getHrTemplate() {
        String template = "亲爱的{Company}人力资源部,\n" +
                "Dear HR Staff at {Company},\n" +
                "เรียนฝ่ายบุคคลของ {Company}\n" +
                "\n" +
                "附件是{FullName} 最近完成的{prodName}测评报告。\n" +
                "Attached please find the assessment report on {prodName} of {FullName}\n" +
                "กรุณาตรวจสอบเอกสารแนบ ของ {FullName} ของ {prodName}. \n" +
                "\n" +
                "如有疑问,请与客服联系,邮箱是:support@tai-online.com。\n" +
                "Should you have questions, please contact our customer service at support@tai-online.com. \n" +
                "หากมีข้อสงสัยหรือคำถามเพิ่มเติม กรุณาติดต่อฝ่ายบริการลูกค้าสัมพันธ์ ที่ support@tai-online.com\n" +
                "\n" +
                "\n" +
                "谢谢!\n" +
                "All the best,\n" +
                "ขอขอบคุณเป็นอย่างยิ่ง\n" +
                "\n" +
                "\n" +
                "TAI公司客户服务部\n" +
                "Customer Service Dept., TAI, LLC\n" +
                "ฝ่ายบริการลูกค้าสัมพันธ์บริษท TAI";
        return template;
    }
    @NotNull
    private String getTemplate() {
        String template = "亲爱的{FullName},\n" +
                "<br>Dear {FullName},\n" +
                "<br>เรียน {FullName},\n" +
                "<br>\n" +
                "<br>{Company} 邀请您完成一份测试,大概需要20-25分钟时间。您可以直接点击下面的链接开始该测试。如果不能直接访问,请复制地址到浏览器中直接打开。\n" +
                "<br>You've been invited to take an assessment by {Company}, which shall take about 20-25 minutes to complete. Please click the link below, or copy the link to your browser, to begin the assessment.\n" +
                "<br>คุณได้รับเชิญให้ทำแบบประเมินจาก {Company} กรุณาใช้ลิงค์ด้านล่างเพื่อเริ่มดำเนินการ โดยคุณสามารถคลิกที่ลิงค์ด้านล่างโดยตรง หรือจะคัดลอกแล้วนำลิงค์ไปวางบนเบราว์เซอร์ของคุณก็ได้\n" +
                "<br>链接地址是:<a href='{url}' target='_blank'>{url}</a>\n" +
                "<br>The link is: <a href='{url}' target='_blank'>{url}</a>\n" +
                "<br>ตามลิงค์นี้: <a href='{url}' target='_blank'>{url}</a>\n" +
                "<br>\n" +
                "<br>如有疑问,请与客服联系,邮箱是:support@tai-online.com。\n" +
                "<br>Should you have problem assessing the above link, please contact our customer service at support@tai-online.com.\n" +
                "<br>หากคุณมีปัญหาในการเข้าสู่ลิงค์ข้างต้น โปรดติดต่อฝ่ายบริการลูกค้าของเราที่ support@tai-online.com\n" +
                "<br>\n" +
                "<br>\n" +
                "<br>谢谢!\n" +
                "<br>All the best,\n" +
                "<br>ด้วยความเคารพ\n" +
                "<br>\n" +
                "<br>{Company}\n" +
                "<br>";
        return template;
    }
}
src/main/java/com/ots/project/exam/controller/TExamReportController.java
@@ -40,6 +40,7 @@
import com.ots.project.exam.dto.QuestionObject;
import com.ots.project.exam.dto.QuestionReport;
import com.ots.project.exam.dto.RelatedParty;
import com.ots.project.exam.mapper.TExamPaperQuestionMapper;
import com.ots.project.exam.service.IEntDemographyInfoService;
import com.ots.project.exam.service.IEntTestPackageService;
import com.ots.project.exam.service.ISysUserExtendService;
@@ -122,7 +123,6 @@
    private IExamUtilService iExamUtilService;
    @Autowired
    private IEntTestPackageService entTestPackageService;
    @Autowired
    private ITExamPaperService itExamPaperService;
@@ -198,6 +198,19 @@
    }
    /**
     * 测评列表
     * @return
     */
    @RequiresPermissions("exam:evaluation_report:view")
    @GetMapping("/reportView/evaluationReport")
    public String evaluationReport(ModelMap mmap) {
        //返回所有产品
        List<TExamPaper> dictList = itExamPaperService.getUserPapers();
        mmap.put("dictList",dictList);
        return prefix + "/evaluationReport";
    }
    /**
     * 查询评测报告列表(头部)
     */
    @RequiresPermissions("exam:hrEmailReport:view")
@@ -252,6 +265,45 @@
        List<Map<String, String>> filedList = new ArrayList<>();
        filedList.add(title);
        return getDataTable(filedList);
    }
    /**
     * 查询评测报告列表(数据列)
     * 根据用户角色显示不同列表
     * @param tExamReport
     * @return
     */
    @RequiresPermissions("exam:report:list")
    @PostMapping("/newListData")
    @ResponseBody
    public TableDataInfo newListData(TExamReport tExamReport) {
        startPage();
        List<TExamReport> list = new ArrayList<>();
        // 完成的
        tExamReport.setFinish(1);
        //根据权限返回不同测评人员列表
        User sysUser = ShiroUtils.getSysUser();
        String userType = sysUser.getUserType();
        if (UserTypeEnum.ENT_USER.getUserType().equals(userType)) {
            tExamReport.setUserId(sysUser.getUserId());
        }
        //分销商可以看到分销商下的企业信息
        if (UserTypeEnum.DIS_USER.getUserType().equals(userType)) {
            SysUserExtend sysUserExtend = new SysUserExtend();
            sysUserExtend.setParentUserId(sysUser.getUserId());
            List<SysUserExtend> sysUserExtends = sysUserExtendService.selectSysUserExtendList(sysUserExtend);
            List<Long> collect = sysUserExtends.stream().map(extend -> extend.getUserId()).collect(Collectors.toList());
            collect.add(sysUser.getUserId());
            tExamReport.setUserIds(collect);
        }
        list = tExamReportService.selectViewReportList(tExamReport);
        // 多语言翻译
        for (TExamReport tExamReportTemp : list) {
            tExamReportTemp.setProductName(examUtilService.getLangOrLocalLangString("", tExamReportTemp.getProductName()));
        }
        return getDataTable(list);
    }
    /**
@@ -381,6 +433,75 @@
        // 拼接生成report的键值对
        User sysUser = ShiroUtils.getSysUser();
        boolean isRight = Objects.equals(UserTypeEnum.SYS_USER.getUserType(), sysUser.getUserType());
        // 人口学变量
        // 三行
        DataReportHead dataReportHead = new DataReportHead();
        String fileNameResult = EssConfig.getDownloadPath() + examUtilService.getLangOrLocalLangString("", tExamReportList.get(0).getProductName()) + "_DateReport.xlsx";
        // 把sheet放在map里面
        Map<String, List<List<Object>>> reportResultMap = new HashMap<>();
        Map<String, Map<String, String>> demograpyMap = new HashMap<>();
        // 人口学
        setDemograyMap(tExamReportList, dataReportHead, demograpyMap);
        // 报告类型
        String reportType = getReportType(tExamReport);
        // 模版的内容
        setDataReportHeader(dataReportHead, reportResultMap, reportType, isRight);
        // Map<sheet名, Map<姓名, Map<key, value>>> 数据
        Map<String, Map<String, Map<String, String>>> sheetExcelMap = new HashMap<>();
        // 如果是JAQ要调用泰国团队的接口,如果不是,去表里面找
        setDealTaiData(ids, tExamReportList, reportType, sheetExcelMap);
        // 构造值
        setRportListValue(reportResultMap, demograpyMap, sheetExcelMap, reportType);
        // 弄成和他们原来一样
        setSysHeadToEnglish(tExamReportList, reportResultMap, reportType);
        // 写文件
        writeFile(fileNameResult, reportResultMap);
        // 返回下载
        return AjaxResult.success(examUtilService.getLangOrLocalLangString("", tExamReportList.get(0).getProductName()) + "_DateReport.xlsx");
    }
    // 导出数据报告
    @RequiresPermissions("exam:report:export")
    @PostMapping("/exportEvaluationReport")
    @ResponseBody
    public AjaxResult exportReport(TExamReport tExamReport) throws IOException {
        // 完成的
        tExamReport.setFinish(1);
        //根据权限返回不同测评人员列表
        User sysUser = ShiroUtils.getSysUser();
        String userType = sysUser.getUserType();
        if (UserTypeEnum.ENT_USER.getUserType().equals(userType)) {
            tExamReport.setUserId(sysUser.getUserId());
        }
        //分销商可以看到分销商下的企业信息
        if (UserTypeEnum.DIS_USER.getUserType().equals(userType)) {
            SysUserExtend sysUserExtend = new SysUserExtend();
            sysUserExtend.setParentUserId(sysUser.getUserId());
            List<SysUserExtend> sysUserExtends = sysUserExtendService.selectSysUserExtendList(sysUserExtend);
            List<Long> collect = sysUserExtends.stream().map(extend -> extend.getUserId()).collect(Collectors.toList());
            collect.add(sysUser.getUserId());
            tExamReport.setUserIds(collect);
        }
        //查询当前筛选结果集
        List<TExamReport> tExamReportList = tExamReportService.selectViewReportList(tExamReport);
        //List<Long> getIds = tExamReportList.stream().map(TExamReport::getId).collect(Collectors.toList());
        List<String> getIds = tExamReportList.stream().map(t -> t.getId().toString()).collect(Collectors.toList());
        String[] ids = getIds.stream().toArray(String[]::new);
        // 拼接生成report的键值对
        //User sysUser = ShiroUtils.getSysUser();
        boolean isRight = Objects.equals(UserTypeEnum.SYS_USER.getUserType(), sysUser.getUserType());
        // 人口学变量
        // 三行
@@ -577,6 +698,10 @@
    }
    private void setDataReportHeader(DataReportHead dataReportHead, Map<String, List<List<Object>>> reportResultMap, String reportType, boolean isRight) {
        //如果为空重新获取
        if(Objects.isNull(reportType)){
        }
        if (Objects.equals(reportType, ReportTypeEnum.RuiLin.getCode())) {
            setDataReportHeaderRuilin(dataReportHead, reportResultMap, isRight);
        } else if (Objects.equals(reportType, ReportTypeEnum.CAQ.getCode())) {
src/main/java/com/ots/project/exam/controller/TReportTemplateController.java
@@ -6,7 +6,9 @@
import com.ots.framework.web.controller.BaseController;
import com.ots.framework.web.domain.AjaxResult;
import com.ots.framework.web.page.TableDataInfo;
import com.ots.project.exam.domain.EntEmailTemplate;
import com.ots.project.exam.domain.TReportTemplate;
import com.ots.project.exam.service.IEntEmailTemplateService;
import com.ots.project.exam.service.ITReportTemplateService;
import org.apache.shiro.authz.annotation.RequiresPermissions;
import org.springframework.beans.factory.annotation.Autowired;
@@ -30,6 +32,9 @@
    @Autowired
    private ITReportTemplateService tReportTemplateService;
    @Autowired
    private IEntEmailTemplateService entEmailTemplateService;
    @RequiresPermissions("exam:template:view")
    @GetMapping()
@@ -115,4 +120,31 @@
    public AjaxResult remove(String ids) {
        return toAjax(tReportTemplateService.deleteTReportTemplateByIds(ids));
    }
    /**
     * 邮件模板配置
     * @return
     */
    @RequiresPermissions("exam:email:edit")
    @GetMapping("/emailEdit")
    public String emailEdit(ModelMap mmap) {
        EntEmailTemplate eet = entEmailTemplateService.getOnly();
        mmap.put("emailTemplate",eet);
        return prefix + "/emailEdit";
    }
    /**
     * 新增保存邮件模板配置
     */
    @RequiresPermissions("exam:email:edit")
    @Log(title = "邮件模板配置", businessType = BusinessType.INSERT)
    @PostMapping("/emailEdit")
    @ResponseBody
    public AjaxResult emailEdit(EntEmailTemplate entEmailTemplate) {
        if(entEmailTemplate.getId() == null){
            return error("未初始化模板,联系管理员!");
        }
        return toAjax(entEmailTemplateService.insertEntEmailTemplate(entEmailTemplate));
    }
}
src/main/java/com/ots/project/exam/domain/EntEmailTemplate.java
New file
@@ -0,0 +1,92 @@
package com.ots.project.exam.domain;
import java.io.Serializable;
import java.util.Date;
import lombok.Getter;
import lombok.Setter;
/**
 * ent_email_template
 * 邮件内容模板
 * @author
 */
@Getter
@Setter
public class EntEmailTemplate implements Serializable {
    private Integer id;
    /**
     * 邀请者邮件通知中文模板
     */
    private String inviteCnTemplate;
    /**
     * 邀请者邮件通知英文模板
     */
    private String inviteUsTemplate;
    /**
     * 邀请者邮件通知泰文模板
     */
    private String inviteThTemplate;
    /**
     * HR邮件通知中文模板
     */
    private String hrCnTemplate;
    /**
     * HR邮件通知英文模板
     */
    private String hrUsTemplate;
    /**
     * HR邮件通知泰文模板
     */
    private String hrThTemplate;
    /**
     * 测试者报告中文模板
     */
    private String memberCnTemplate;
    /**
     * 测试者报告英文模板
     */
    private String memberUsTemplate;
    /**
     * 测试者报告泰文模板
     */
    private String memberThTemplate;
    /**
     * 创建时间
     */
    private Date createTime;
    /**
     * 创建者
     */
    private String createBy;
    private static final long serialVersionUID = 1L;
    @Override
    public String toString() {
        return "EntEmailTemplate{" +
                "id=" + id +
                ", inviteCnTemplate='" + inviteCnTemplate + '\'' +
                ", inviteUsTemplate='" + inviteUsTemplate + '\'' +
                ", inviteThTemplate='" + inviteThTemplate + '\'' +
                ", hrCnTemplate='" + hrCnTemplate + '\'' +
                ", hrUsTemplate='" + hrUsTemplate + '\'' +
                ", hrThTemplate='" + hrThTemplate + '\'' +
                ", memberCnTemplate='" + memberCnTemplate + '\'' +
                ", memberUsTemplate='" + memberUsTemplate + '\'' +
                ", memberThTemplate='" + memberThTemplate + '\'' +
                ", createTime=" + createTime +
                ", createBy='" + createBy + '\'' +
                '}';
    }
}
src/main/java/com/ots/project/exam/domain/EntTestPackage.java
@@ -172,7 +172,11 @@
    private String phonenumber;
    /**
     * 测试者接收报告模板
     * @return
     */
    private String memberTemplate;
    @Override
@@ -193,6 +197,7 @@
                .append("invalidTime", getInvalidTime())
                .append("status", getStatus())
                .append("remark", getRemark())
                .append("memberTemplate", getMemberTemplate())
                .toString();
    }
}
src/main/java/com/ots/project/exam/domain/TExamReport.java
@@ -186,6 +186,17 @@
    private Integer retriesTime;
    /**
     * 测试者接收报告模板
     * @return
     */
    private String memberTemplate;
    /**
     * 测试包类型
     * @return
     */
    private String testType;
    @Override
src/main/java/com/ots/project/exam/mapper/EntEmailTemplateMapper.java
New file
@@ -0,0 +1,19 @@
package com.ots.project.exam.mapper;
import com.ots.project.exam.domain.EntEmailTemplate;
public interface EntEmailTemplateMapper {
    int deleteByPrimaryKey(Integer id);
    int insert(EntEmailTemplate record);
    int insertSelective(EntEmailTemplate record);
    EntEmailTemplate selectByPrimaryKey(Integer id);
    int updateByPrimaryKeySelective(EntEmailTemplate record);
    int updateByPrimaryKey(EntEmailTemplate record);
    EntEmailTemplate getOnly();
}
src/main/java/com/ots/project/exam/service/IEntEmailTemplateService.java
New file
@@ -0,0 +1,29 @@
package com.ots.project.exam.service;
import com.ots.project.exam.domain.EntEmailTemplate;
import com.ots.project.exam.domain.TReportTemplate;
import com.ots.project.system.user.domain.User;
import java.util.List;
/**
 * 邮件内容模板配置Service接口
 *
 * @author ots
 * @date 2020-03-24
 */
public interface IEntEmailTemplateService {
    /**
     * 保存邮件内容配置
     * @param entEmailTemplate
     * @return
     */
    int insertEntEmailTemplate(EntEmailTemplate entEmailTemplate);
    /**
     * 查询唯一记录
     * @return
     */
    EntEmailTemplate getOnly();
}
src/main/java/com/ots/project/exam/service/impl/EntEmailTemplateServiceImpl.java
New file
@@ -0,0 +1,74 @@
package com.ots.project.exam.service.impl;
import cn.hutool.core.collection.CollUtil;
import com.ots.common.enums.LangTypeEnum;
import com.ots.common.enums.ReportTypeEnum;
import com.ots.common.enums.TemplateTypeEnum;
import com.ots.common.utils.DateUtils;
import com.ots.common.utils.StringUtils;
import com.ots.common.utils.Threads;
import com.ots.common.utils.poi.WordUtil;
import com.ots.common.utils.security.ShiroUtils;
import com.ots.common.utils.text.Convert;
import com.ots.framework.config.EssConfig;
import com.ots.project.exam.domain.*;
import com.ots.project.exam.dto.QuestionReport;
import com.ots.project.exam.dto.RelatedParty;
import com.ots.project.exam.dto.WordParam;
import com.ots.project.exam.mapper.EntEmailTemplateMapper;
import com.ots.project.exam.mapper.SysUserExtendMapper;
import com.ots.project.exam.mapper.TExamReportMapper;
import com.ots.project.exam.service.*;
import com.ots.project.system.dict.domain.DictData;
import com.ots.project.system.dict.service.IDictDataService;
import com.ots.project.tool.BarChart;
import com.ots.project.tool.exam.DateTimeUtil;
import com.ots.project.tool.exam.ExamUtil;
import com.ots.project.tool.exam.ImageUtil;
import com.ots.project.tool.exam.JsonUtil;
import com.ots.project.tool.report.CAQ.CAQReport;
import com.ots.project.tool.report.MAQ.MAQReport;
import com.ots.project.tool.report.ReportResultData;
import com.ots.project.tool.report.RuilinMAQ.RuilinMAQReport;
import com.ots.project.tool.report.SAQ.SAQReport;
import com.ots.project.tool.report.reportCalculation.response.ReportAPIResult;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import javax.imageio.ImageIO;
import java.awt.*;
import java.awt.image.BufferedImage;
import java.io.File;
import java.io.IOException;
import java.util.List;
import java.util.*;
import java.util.stream.Collectors;
/**
 * 邮件内容模板Service业务层处理
 *
 * @author ots
 * @date 2019-12-26
 */
@Service
public class EntEmailTemplateServiceImpl implements IEntEmailTemplateService {
    @Autowired
    private EntEmailTemplateMapper entEmailTemplateMapper;
    private static final Logger logger = LoggerFactory.getLogger(Threads.class);
    @Override
    public int insertEntEmailTemplate(EntEmailTemplate entEmailTemplate) {
        entEmailTemplate.setCreateTime(DateUtils.getNowDate());
        entEmailTemplate.setCreateBy(String.valueOf(ShiroUtils.getSysUser().getUserId()));
        return entEmailTemplateMapper.updateByPrimaryKeySelective(entEmailTemplate);
    }
    @Override
    public EntEmailTemplate getOnly() {
        return entEmailTemplateMapper.getOnly();
    }
}
src/main/java/com/ots/project/exam/service/impl/TExamPaperServiceImpl.java
@@ -868,12 +868,15 @@
        log.error("报告标题:{}",title);
        String content = tExamReportResult.getMailContent();
        //测试者接收报告模板优先使用测试包保存的报告模板
        String memberContent = tExamReportResult.getMemberTemplate();
        StringBuilder remark = new StringBuilder();
        remark.append("失败邮箱:");
        if (justMember) {
            // 用户发邮件
            sendMemberEmail(tExamReport, fileNameResult, tExamReportResult, title, content, remark);
            sendMemberEmail(tExamReport, fileNameResult, tExamReportResult, title, memberContent, remark);
        }
        if (justHr) {
            // 发送给Hr,但取testEmail
src/main/resources/application-local.yml
@@ -26,7 +26,7 @@
        druid:
            # 主库数据源
            master:
                url: jdbc:mysql://192.168.8.171:3306/ots-sand?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8
                url: jdbc:mysql://159.75.69.232:3306/ots-sand?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8
                username: root
                password: Cc19970921
            # 从库数据源
@@ -84,7 +84,7 @@
# 远程泰国计算服务
ATSTai:
    host: 192.168.8.171
    host: 159.75.69.232
    port: 9123
jasypt:
    encryptor:
src/main/resources/application-tencent.yml
New file
@@ -0,0 +1,92 @@
# 项目相关配置
ots:
    # 名称
    name: ots
    # 版本
    version: 1.0.5
    # 版权年份
    copyrightYear: 2020
    # 实例演示开关
    demoEnabled: false
    # 文件路径 示例( Windows配置D:/ots/uploadPath,Linux配置 /home/data/ots/uploadPath)
    profile: /home/data/ots/uploadPath
    # 图片的url,如:vue端读http://139.199.11.114/images地址
    imagePath: http://127.0.0.1:8090/profile/images
    # 获取ip地址开关
    addressEnabled: true
    # 报告模版地址
    reportTemplates: /home/data/ots/reportTemplates/
    # http profile
    httpProfilePath: http://127.0.0.1:8090/profile
# 数据源配置
spring:
    datasource:
        type: com.alibaba.druid.pool.DruidDataSource
        driverClassName: com.mysql.cj.jdbc.Driver
        druid:
            # 主库数据源
            master:
                url: jdbc:mysql://127.0.0.1:3306/ots-sand?useUnicode=true&characterEncoding=utf8&zeroDateTimeBehavior=convertToNull&useSSL=true&serverTimezone=GMT%2B8
                username: root
                password: Cc19970921
            # 从库数据源
            slave:
                # 从数据源开关/默认关闭
                enabled: false
                url:
                username:
                password:
            # 初始连接数
            initialSize: 5
            # 最小连接池数量
            minIdle: 10
            # 最大连接池数量
            maxActive: 20
            # 配置获取连接等待超时的时间
            maxWait: 60000
            # 配置间隔多久才进行一次检测,检测需要关闭的空闲连接,单位是毫秒
            timeBetweenEvictionRunsMillis: 60000
            # 配置一个连接在池中最小生存的时间,单位是毫秒
            minEvictableIdleTimeMillis: 300000
            # 配置一个连接在池中最大生存的时间,单位是毫秒
            maxEvictableIdleTimeMillis: 900000
            # 配置检测连接是否有效
            validationQuery: SELECT 1 FROM DUAL
            testWhileIdle: true
            testOnBorrow: false
            testOnReturn: false
            webStatFilter:
                enabled: true
            statViewServlet:
                enabled: true
                # 设置白名单,不填则允许所有访问
                allow:
                url-pattern: /druid/*
                # 控制台管理用户名和密码
                login-username:
                login-password:
            filter:
                stat:
                    enabled: true
                    # 慢SQL记录
                    log-slow-sql: true
                    slow-sql-millis: 1000
                    merge-sql: true
                wall:
                    config:
                        multi-statement-allow: true
# 邮件服务
mail:
# VUE端访问地址
vue:
    url: http://127.0.0.1/exam-stu/#/ots/{0}/login
# 远程泰国计算服务
ATSTai:
    host: 127.0.0.1
    port: 9123
jasypt:
    encryptor:
        password: 5ciqxnka5s02w9qu
        algorithm: PBEWithMD5AndDES
src/main/resources/application.yml
@@ -40,7 +40,7 @@
    time-zone: GMT+8
    date-format: yyyy-MM-dd HH:mm:ss
  profiles:
    active: local
    active: tencent
  # 文件上传
  servlet:
    multipart:
src/main/resources/mybatis/exam/EntEmailTemplateMapper.xml
New file
@@ -0,0 +1,175 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE mapper PUBLIC "-//mybatis.org//DTD Mapper 3.0//EN" "http://mybatis.org/dtd/mybatis-3-mapper.dtd">
<mapper namespace="com.ots.project.exam.mapper.EntEmailTemplateMapper">
  <resultMap id="BaseResultMap" type="EntEmailTemplate">
    <id column="id" jdbcType="INTEGER" property="id" />
    <result column="invite_cn_template" jdbcType="VARCHAR" property="inviteCnTemplate" />
    <result column="invite_us_template" jdbcType="VARCHAR" property="inviteUsTemplate" />
    <result column="invite_th_template" jdbcType="VARCHAR" property="inviteThTemplate" />
    <result column="hr_cn_template" jdbcType="VARCHAR" property="hrCnTemplate" />
    <result column="hr_us_template" jdbcType="VARCHAR" property="hrUsTemplate" />
    <result column="hr_th_template" jdbcType="VARCHAR" property="hrThTemplate" />
    <result column="member_cn_template" jdbcType="VARCHAR" property="memberCnTemplate" />
    <result column="member_us_template" jdbcType="VARCHAR" property="memberUsTemplate" />
    <result column="member_th_template" jdbcType="VARCHAR" property="memberThTemplate" />
    <result column="create_time" jdbcType="TIMESTAMP" property="createTime" />
    <result column="create_by" jdbcType="VARCHAR" property="createBy" />
  </resultMap>
  <sql id="Base_Column_List">
    id, invite_cn_template, invite_us_template, invite_th_template, hr_cn_template, hr_us_template,
    hr_th_template, member_cn_template, member_us_template, member_th_template, create_time,
    create_by
  </sql>
  <select id="selectByPrimaryKey" parameterType="java.lang.Integer" resultMap="BaseResultMap">
    select
    <include refid="Base_Column_List" />
    from ent_email_template
    where id = #{id,jdbcType=INTEGER}
  </select>
  <delete id="deleteByPrimaryKey" parameterType="java.lang.Integer">
    delete from ent_email_template
    where id = #{id,jdbcType=INTEGER}
  </delete>
  <insert id="insert" keyColumn="id" keyProperty="id" parameterType="EntEmailTemplate" useGeneratedKeys="true">
    insert into ent_email_template (invite_cn_template, invite_us_template,
      invite_th_template, hr_cn_template, hr_us_template,
      hr_th_template, member_cn_template, member_us_template,
      member_th_template, create_time, create_by
      )
    values (#{inviteCnTemplate,jdbcType=VARCHAR}, #{inviteUsTemplate,jdbcType=VARCHAR},
      #{inviteThTemplate,jdbcType=VARCHAR}, #{hrCnTemplate,jdbcType=VARCHAR}, #{hrUsTemplate,jdbcType=VARCHAR},
      #{hrThTemplate,jdbcType=VARCHAR}, #{memberCnTemplate,jdbcType=VARCHAR}, #{memberUsTemplate,jdbcType=VARCHAR},
      #{memberThTemplate,jdbcType=VARCHAR}, #{createTime,jdbcType=TIMESTAMP}, #{createBy,jdbcType=VARCHAR}
      )
  </insert>
  <insert id="insertSelective" keyColumn="id" keyProperty="id" parameterType="EntEmailTemplate" useGeneratedKeys="true">
    insert into ent_email_template
    <trim prefix="(" suffix=")" suffixOverrides=",">
      <if test="inviteCnTemplate != null">
        invite_cn_template,
      </if>
      <if test="inviteUsTemplate != null">
        invite_us_template,
      </if>
      <if test="inviteThTemplate != null">
        invite_th_template,
      </if>
      <if test="hrCnTemplate != null">
        hr_cn_template,
      </if>
      <if test="hrUsTemplate != null">
        hr_us_template,
      </if>
      <if test="hrThTemplate != null">
        hr_th_template,
      </if>
      <if test="memberCnTemplate != null">
        member_cn_template,
      </if>
      <if test="memberUsTemplate != null">
        member_us_template,
      </if>
      <if test="memberThTemplate != null">
        member_th_template,
      </if>
      <if test="createTime != null">
        create_time,
      </if>
      <if test="createBy != null">
        create_by,
      </if>
    </trim>
    <trim prefix="values (" suffix=")" suffixOverrides=",">
      <if test="inviteCnTemplate != null">
        #{inviteCnTemplate,jdbcType=VARCHAR},
      </if>
      <if test="inviteUsTemplate != null">
        #{inviteUsTemplate,jdbcType=VARCHAR},
      </if>
      <if test="inviteThTemplate != null">
        #{inviteThTemplate,jdbcType=VARCHAR},
      </if>
      <if test="hrCnTemplate != null">
        #{hrCnTemplate,jdbcType=VARCHAR},
      </if>
      <if test="hrUsTemplate != null">
        #{hrUsTemplate,jdbcType=VARCHAR},
      </if>
      <if test="hrThTemplate != null">
        #{hrThTemplate,jdbcType=VARCHAR},
      </if>
      <if test="memberCnTemplate != null">
        #{memberCnTemplate,jdbcType=VARCHAR},
      </if>
      <if test="memberUsTemplate != null">
        #{memberUsTemplate,jdbcType=VARCHAR},
      </if>
      <if test="memberThTemplate != null">
        #{memberThTemplate,jdbcType=VARCHAR},
      </if>
      <if test="createTime != null">
        #{createTime,jdbcType=TIMESTAMP},
      </if>
      <if test="createBy != null">
        #{createBy,jdbcType=VARCHAR},
      </if>
    </trim>
  </insert>
  <update id="updateByPrimaryKeySelective" parameterType="EntEmailTemplate">
    update ent_email_template
    <set>
      <if test="inviteCnTemplate != null">
        invite_cn_template = #{inviteCnTemplate,jdbcType=VARCHAR},
      </if>
      <if test="inviteUsTemplate != null">
        invite_us_template = #{inviteUsTemplate,jdbcType=VARCHAR},
      </if>
      <if test="inviteThTemplate != null">
        invite_th_template = #{inviteThTemplate,jdbcType=VARCHAR},
      </if>
      <if test="hrCnTemplate != null">
        hr_cn_template = #{hrCnTemplate,jdbcType=VARCHAR},
      </if>
      <if test="hrUsTemplate != null">
        hr_us_template = #{hrUsTemplate,jdbcType=VARCHAR},
      </if>
      <if test="hrThTemplate != null">
        hr_th_template = #{hrThTemplate,jdbcType=VARCHAR},
      </if>
      <if test="memberCnTemplate != null">
        member_cn_template = #{memberCnTemplate,jdbcType=VARCHAR},
      </if>
      <if test="memberUsTemplate != null">
        member_us_template = #{memberUsTemplate,jdbcType=VARCHAR},
      </if>
      <if test="memberThTemplate != null">
        member_th_template = #{memberThTemplate,jdbcType=VARCHAR},
      </if>
      <if test="createTime != null">
        create_time = #{createTime,jdbcType=TIMESTAMP},
      </if>
      <if test="createBy != null">
        create_by = #{createBy,jdbcType=VARCHAR},
      </if>
    </set>
    where id = #{id,jdbcType=INTEGER}
  </update>
  <update id="updateByPrimaryKey" parameterType="EntEmailTemplate">
    update ent_email_template
    set invite_cn_template = #{inviteCnTemplate,jdbcType=VARCHAR},
      invite_us_template = #{inviteUsTemplate,jdbcType=VARCHAR},
      invite_th_template = #{inviteThTemplate,jdbcType=VARCHAR},
      hr_cn_template = #{hrCnTemplate,jdbcType=VARCHAR},
      hr_us_template = #{hrUsTemplate,jdbcType=VARCHAR},
      hr_th_template = #{hrThTemplate,jdbcType=VARCHAR},
      member_cn_template = #{memberCnTemplate,jdbcType=VARCHAR},
      member_us_template = #{memberUsTemplate,jdbcType=VARCHAR},
      member_th_template = #{memberThTemplate,jdbcType=VARCHAR},
      create_time = #{createTime,jdbcType=TIMESTAMP},
      create_by = #{createBy,jdbcType=VARCHAR}
    where id = #{id,jdbcType=INTEGER}
  </update>
  <select id="getOnly" resultMap="BaseResultMap">
    SELECT * FROM ent_email_template limit 0,1
  </select>
</mapper>
src/main/resources/mybatis/exam/EntTestPackageMapper.xml
@@ -32,19 +32,20 @@
        <result property="professionalCategory"    column="professional_category"    />
        <result property="superiorPosition"    column="superior_position"    />
        <result property="phonenumber"    column="phonenumber"    />
        <result property="memberTemplate"    column="member_template"    />
    </resultMap>
    <sql id="selectEntTestPackageVo">
        select id,prod_id, p.user_id, test_name,prod_name, test_type, test_area, lang_type, test_email, frame_text_content_id, create_by, create_time, update_by, update_time, invalid_time,p.param_codes, status, template,remark, auto_send_report,report_template_id,p.hrTemplate, p.position,p.superior_position, p.professional_category from ent_test_package p
        select id,prod_id, p.user_id, test_name,prod_name, test_type, test_area, lang_type, test_email, frame_text_content_id, create_by, create_time, update_by, update_time, invalid_time,p.param_codes, status, template,remark, auto_send_report,report_template_id,p.hrTemplate, p.position,p.superior_position, p.professional_category,p.member_template from ent_test_package p
    </sql>
    <sql id="selectEntTestPackageSuVo">
        select p.id, p.prod_id, p.user_id, p.test_name, p.prod_name, p.test_type, p.test_area, p.lang_type, p.test_email, p.frame_text_content_id, p.create_by, p.create_time, p.update_by, p.update_time, p.invalid_time,p.param_codes, p.status, p.template, p.remark, p.auto_send_report, p.report_template_id,p.hrTemplate, p.position,p.superior_position, p.professional_category, u.user_name from ent_test_package p
        select p.id, p.prod_id, p.user_id, p.test_name, p.prod_name, p.test_type, p.test_area, p.lang_type, p.test_email, p.frame_text_content_id, p.create_by, p.create_time, p.update_by, p.update_time, p.invalid_time,p.param_codes, p.status, p.template, p.remark, p.auto_send_report, p.report_template_id,p.hrTemplate, p.position,p.superior_position, p.professional_category, u.user_name,p.member_template from ent_test_package p
        left join sys_user u on u.user_id = p.user_id
    </sql>
    <select id="selectEntTestPackageList" parameterType="EntTestPackage" resultMap="EntTestPackageResult">
        select id,prod_id, p.user_id, p.test_name,p.prod_name, p.test_type, p.test_area, p.lang_type, p.test_email, p.frame_text_content_id, p.create_by, p.create_time, p.update_by, p.update_time, p.invalid_time,p.param_codes, p.status, p.template,p.remark,u.user_name,p.auto_send_report,p.report_template_id,p.hrTemplate,u.phonenumber from ent_test_package p
        select id,prod_id, p.user_id, p.test_name,p.prod_name, p.test_type, p.test_area, p.lang_type, p.test_email, p.frame_text_content_id, p.create_by, p.create_time, p.update_by, p.update_time, p.invalid_time,p.param_codes, p.status, p.template,p.remark,u.user_name,p.auto_send_report,p.report_template_id,p.hrTemplate,u.phonenumber,p.member_template from ent_test_package p
        left join sys_user u on u.user_id = p.user_id
        <where>  
            <if test="userId != null "> and p.user_id = #{userId}</if>
@@ -69,7 +70,7 @@
    <select id="selectEntTestPackageMainList" parameterType="EntTestPackage" resultMap="EntTestPackageResult">
        select id,prod_id, p.user_id, p.test_name,p.prod_name, p.test_type, p.test_area, p.lang_type, p.test_email, p.frame_text_content_id, p.create_by, p.create_time, p.update_by, p.update_time, p.invalid_time,p.param_codes, p.status, p.template,p.remark,u.user_name,p.auto_send_report,p.report_template_id,p.hrTemplate,u.phonenumber from ent_test_package p
        select id,prod_id, p.user_id, p.test_name,p.prod_name, p.test_type, p.test_area, p.lang_type, p.test_email, p.frame_text_content_id, p.create_by, p.create_time, p.update_by, p.update_time, p.invalid_time,p.param_codes, p.status, p.template,p.remark,u.user_name,p.auto_send_report,p.report_template_id,p.hrTemplate,u.phonenumber,p.member_template from ent_test_package p
        left join sys_user u on u.user_id = p.user_id
        <where>
            <if test="userId != null "> and p.user_id = #{userId}</if>
@@ -136,6 +137,7 @@
            <if test="position != null  and position != ''">position,</if>
            <if test="professionalCategory != null  and professionalCategory != ''">professional_category,</if>
            <if test="superiorPosition != null  and superiorPosition != ''">superior_position,</if>
            <if test="memberTemplate != null  and memberTemplate != ''">member_template,</if>
         </trim>
        <trim prefix="values (" suffix=")" suffixOverrides=",">
            <if test="userId != null ">#{userId},</if>
@@ -162,6 +164,7 @@
            <if test="position != null  and position != ''">#{position},</if>
            <if test="professionalCategory != null  and professionalCategory != ''">#{professionalCategory},</if>
            <if test="superiorPosition != null  and superiorPosition != ''">#{superiorPosition},</if>
            <if test="memberTemplate != null  and memberTemplate != ''">#{memberTemplate},</if>
         </trim>
    </insert>
@@ -190,6 +193,7 @@
            <if test="position != null  and position != ''">position = #{position},</if>
            <if test="professionalCategory != null  and professionalCategory != ''">professional_category = #{professionalCategory},</if>
            <if test="superiorPosition != null  and superiorPosition != ''">superior_position = #{superiorPosition},</if>
            <if test="memberTemplate != null  and memberTemplate != ''">member_template = #{memberTemplate},</if>
            <choose>
                <when test="autoSendReport==true">
                    auto_send_report = 1,
src/main/resources/mybatis/exam/TExamReportMapper.xml
@@ -52,6 +52,7 @@
        <result property="hrSendTime"    column="hrSendTime"    />
        <result property="hrUpdateTime"    column="hrUpdateTime"    />
        <result property="retriesTime"    column="retriesTime"    />
        <result property="memberTemplate"    column="member_template"    />
    </resultMap>
    <sql id="selectTExamReportVo">
@@ -64,7 +65,7 @@
        t.finish,m.member_name,p.test_name,u.user_name,t.question_order, t.question_report, t.question_template_id, t.interface_content,
        t.lang_type, t.report_address, p.report_template_id, t.send_hr_status, t.send_tester_status, m.member_email, p.test_email,
        t.member_name, p.auto_send_report, e.hr_email, e.mail_content, t.option_order, t.remain_part_time,
         t.report_address_new,t.hrReportEmail,t.hrTitle,t.hrSendTime,t.hrUpdateTime,t.retriesTime
         t.report_address_new,t.hrReportEmail,t.hrTitle,t.hrSendTime,t.hrUpdateTime,t.retriesTime,p.member_template
         from t_exam_report t
        left join sys_user u on u.user_id = t.user_id
        left join ent_test_member m on m.member_id = t.member_id
@@ -149,11 +150,26 @@
            <if test="finish == 1"> and t.finish in (1,2,6) </if>
            <if test="sendTesterStatus != null"> and t.send_tester_status = #{sendTesterStatus}</if>
            <if test="sendHrStatus != null"> and t.send_hr_status = #{sendHrStatus}</if>
            <if test="userId != null "> and t.user_id = #{userId}</if>
            <if test="testType != null  and testType != ''"> and p.test_type = #{testType}</if>
            <!-- 开始时间检索 -->
            <if test="params.beginTime != null and params.beginTime != ''">
                and date_format(p.create_time,'%y%m%d') &gt;= date_format(#{params.beginTime},'%y%m%d')
            </if>
            <!-- 结束时间检索 -->
            <if test="params.endTime != null and params.endTime != ''">
                and date_format(p.create_time,'%y%m%d') &lt;= date_format(#{params.endTime},'%y%m%d')
            </if>
            <if test="sendHrStatusList != null"> and t.send_hr_status in
                <foreach collection="sendHrStatusList" item="sendStatus" open="(" separator="," close=")">
                    #{sendStatus}
                </foreach>
            </if>
            <if test="userIds != null"> and t.user_id in
                <foreach collection="userIds" item="userId" open="(" separator="," close=")">
                    #{userId}
                </foreach>
            </if>
        </where>
    </select>
src/main/resources/static/i18n/messages_en_US.properties
@@ -627,6 +627,7 @@
dict.ic172=Add how many 
dict.ic173=Client Recycle
dict.ic174=Recycling Due
dict.ic175=Email Template Configuration
demography.level.ic1=Employee
demography.level.ic2=First-line Supervisor
demography.level.ic3=Mid-level Manager
@@ -954,4 +955,8 @@
jsp.main.other.001=Recently Completed Tests
jsp.main.other.002=Recently Abandoned Tests or Tests Being Completed
jsp.main.other.003=Recently Created Test Packages
menu.exam.test_package.search=Search Test Package
menu.exam.test_package.search=Search Test Package
jsp.exam.package.langtype=Mail Language Type
jsp.exam.test_package.memberEmailContent=Tester Report Message Content
menu.exam.evaluation_report.view=Evaluation Report List
jsp.exam.evaluation_report.export.msg=Does not support exporting all at the moment
src/main/resources/static/i18n/messages_th_TH.properties
@@ -627,6 +627,7 @@
dict.ic172=\u589E\u52A0\u6B21\u6570
dict.ic173=\u4F01\u4E1A\u56DE\u6536
dict.ic174=\u5230\u671F\u56DE\u6536
dict.ic175=Email Template Configuration
demography.level.ic1=\u0E25\u0E39\u0E01\u0E08\u0E49\u0E32\u0E07
demography.level.ic2=\u0E1C\u0E39\u0E49\u0E14\u0E39\u0E41\u0E25\u0E23\u0E30\u0E14\u0E31\u0E1A\u0E15\u0E49\u0E19
demography.level.ic3=\u0E1C\u0E39\u0E49\u0E08\u0E31\u0E14\u0E01\u0E32\u0E23\u0E23\u0E30\u0E14\u0E31\u0E1A\u0E01\u0E25\u0E32\u0E07
@@ -950,4 +951,8 @@
jsp.main.other.001=\u6700\u8FD1\u5B8C\u6210\u6D4B\u8BD5\u8BB0\u5F55
jsp.main.other.002=\u6700\u8FD1\u6B63\u5728\u7B54\u9898\u6D4B\u8BD5\u8BB0\u5F55
jsp.main.other.003=\u6700\u8FD1\u521B\u5EFA\u7684\u6D4B\u8BD5\u5305
menu.exam.test_package.search=\u641C\u7D22\u6D4B\u8BD5\u5305
menu.exam.test_package.search=\u641C\u7D22\u6D4B\u8BD5\u5305
jsp.exam.package.langtype=Mail Language Type
jsp.exam.test_package.memberEmailContent=Tester Report Message Content
menu.exam.evaluation_report.view=Evaluation Report List
jsp.exam.evaluation_report.export.msg=Does not support exporting all at the moment
src/main/resources/static/i18n/messages_zh_CN.properties
@@ -627,6 +627,7 @@
dict.ic172=\u589E\u52A0\u6B21\u6570
dict.ic173=\u4F01\u4E1A\u56DE\u6536
dict.ic174=\u5230\u671F\u56DE\u6536
dict.ic175=\u90AE\u4EF6\u6A21\u677F\u914D\u7F6E
demography.level.ic1=\u975E\u7BA1\u7406\u4EBA\u5458
demography.level.ic2=\u57FA\u5C42\uFF08\u4E00\u7EBF\uFF09\u7BA1\u7406\u4EBA\u5458
demography.level.ic3=\u4E2D\u5C42\u7BA1\u7406\u4EBA\u5458
@@ -954,4 +955,8 @@
jsp.main.other.001=\u6700\u8FD1\u5B8C\u6210\u6D4B\u8BD5\u8BB0\u5F55
jsp.main.other.002=\u6700\u8FD1\u6B63\u5728\u7B54\u9898\u6D4B\u8BD5\u8BB0\u5F55
jsp.main.other.003=\u6700\u8FD1\u521B\u5EFA\u7684\u6D4B\u8BD5\u5305
menu.exam.test_package.search=\u641C\u7D22\u6D4B\u8BD5\u5305
menu.exam.test_package.search=\u641C\u7D22\u6D4B\u8BD5\u5305
jsp.exam.package.langtype=\u90AE\u4EF6\u8BED\u8A00\u7C7B\u578B
jsp.exam.test_package.memberEmailContent=\u6D4B\u8BD5\u8005\u62A5\u544A\u90AE\u4EF6\u5185\u5BB9
menu.exam.evaluation_report.view=\u8BC4\u6D4B\u62A5\u544A\u5217\u8868
jsp.exam.evaluation_report.export.msg=\u6682\u4E0D\u652F\u6301\u5BFC\u51FA\u5168\u90E8
src/main/resources/static/ots/css/ry-ui.css
@@ -362,6 +362,67 @@
    max-width: none;
}
/**
 * Checkbox Five
 */
.checkboxFive {
    width: 25px;
    margin: 20px 100px;
    position: relative;
}
/**
 * Create the box for the checkbox
 */
.checkboxFive label {
    cursor: pointer;
    position: absolute;
    width: 25px;
    height: 25px;
    top: 0;
    left: 0;
    background: #eee;
    border:1px solid #ddd;
}
/**
 * Display the tick inside the checkbox
 */
.checkboxFive label:after {
    opacity: 0.2;
    content: '';
    position: absolute;
    width: 9px;
    height: 5px;
    background: transparent;
    top: 6px;
    left: 7px;
    border: 3px solid #333;
    border-top: none;
    border-right: none;
    -webkit-transform: rotate(-45deg);
    -moz-transform: rotate(-45deg);
    -o-transform: rotate(-45deg);
    -ms-transform: rotate(-45deg);
    transform: rotate(-45deg);
}
/**
 * Create the hover event of the tick
 */
.checkboxFive label:hover::after {
    opacity: 0.5;
}
/**
 * Create the checkbox state for the tick
 */
.checkboxFive input[type=checkbox]:checked + label:after {
    opacity: 1;
}
/** 复选框&单选框  **/
.check-box,.radio-box {
    display: inline-block;
src/main/resources/templates/exam/distributor/distributor.html
@@ -57,7 +57,9 @@
        var editFlag = [[${@permission.hasPermi('exam:distributor:edit')}]];
        var removeFlag = [[${@permission.hasPermi('exam:distributor:remove')}]];
        var freeloginFlag = [[${@permission.hasPermi('exam:distributor:freelogin')}]];
        var resetpwdFlag = [[${@permission.hasPermi('exam:extend:resetpwd')}]];
        var prefix = ctx + "exam/distributor";
        var paper_prefix =  ctx + "exam/paper";
        $(function() {
            var options = {
@@ -101,6 +103,7 @@
                        actions.push('<a class="btn btn-success btn-xs ' + editFlag + '" href="javascript:void(0)" onclick="$.operate.editTab(\'' + row.userId + '\')"><i class="fa fa-edit"></i>'+[[#{basis.edit}]]+'</a> ');
                        actions.push('<a class="btn btn-danger btn-xs ' + removeFlag + '" href="javascript:void(0)" onclick="$.operate.remove(\'' + row.userId + '\')"><i class="fa fa-remove"></i>'+[[#{basis.del}]]+'</a> ');
                        actions.push('<a class="btn btn-danger btn-xs ' + freeloginFlag + '" href="javascript:void(0)" onclick="freelogin(\'' + row.userId + '\')"><i class="fa fa-eye"></i>'+[[#{basis.freelogin}]]+'</a>');
                        actions.push('<a class="btn btn-success btn-xs ' + resetpwdFlag + '" href="javascript:void(0)" onclick="authUser(\'' + row.userId + '\')"><i class="fa fa-edit"></i>'+[[#{jsp.product.package.authorization}]]+'</a> ');
                        return actions.join('');
                    }
                }]
@@ -176,6 +179,11 @@
            });
        }
        function authUser(id) {
            var url = paper_prefix + '/edit/' + id;
            $.modal.open([[#{jsp.product.package.authorization}]], url);
        }
    </script>
</body>
</html>
src/main/resources/templates/exam/report/evaluationReport.html
New file
@@ -0,0 +1,216 @@
<!DOCTYPE html>
<html lang="zh" xmlns:th="http://www.thymeleaf.org" xmlns:shiro="http://www.pollix.at/thymeleaf/shiro">
<head>
    <th:block th:include="include :: header('评测报告列表')"/>
</head>
<body class="gray-bg">
<div class="container-div">
    <div class="row">
        <div class="col-sm-12 search-collapse">
            <form id="formId">
                <div class="select-list">
                    <ul>
                        <li>
                            <p>[[#{jsp.exam.test_package.002}]]:</p>
                            <select name="productId" id="productId">
                                <option value="">All</option>
                                <option th:each="dict : ${dictList}" th:text="${dict.name}"
                                        th:value="${dict.id}"></option>
                            </select>
                        </li>
                        <li class="select-time">
                            <p>[[#{jsp.exam.test_package.004}]]:</p>
                            <input type="text" class="time-input" id="startTime" th:placeholder="#{jsp.system.user.profile.027}"
                                   name="params[beginTime]"/>
                            <span>-</span>
                            <input type="text" class="time-input" id="endTime" th:placeholder="#{jsp.system.user.profile.028}"
                                   name="params[endTime]"/>
                        </li>
                        <li>
                            <a class="btn btn-primary btn-rounded btn-sm" onclick="$.table.search()"><i
                                    class="fa fa-search"></i>&nbsp;find</a>
                            <a class="btn btn-warning btn-rounded btn-sm" onclick="$.form.reset()"><i
                                    class="fa fa-refresh"></i>&nbsp;[[#{basis.reset}]]</a>
                        </li>
                    </ul>
                </div>
            </form>
        </div>
        <div class="btn-group-sm" id="toolbar" role="group">
            <a class="btn btn-warning" onclick="exportDataReport();" shiro:hasPermission="exam:report:export">
                <i class="fa fa-download"></i> [[#{jsp.exam.report.exportEvaluationUserAnswerRecords}]]
            </a>
<!--            <a class="btn btn-info" onclick="exportDetailReportExcel();"
               shiro:hasPermission="exam:report:detailReportexport">
                <i class="fa fa-download"></i> [[#{jsp.exam.report.regenerateReport}]]
            </a>
            <a class="btn btn-inverse" onclick="exportSendedReportExcel();">
                <i class="fa fa-download"></i> [[#{jsp.exam.report.exportSendedReport}]]
            </a>-->
        </div>
        <div class="col-sm-12 select-table table-striped">
            <table id="bootstrap-table" data-mobile-responsive="true"></table>
        </div>
    </div>
    <!--多语言的弹出-->
    <div class="modal inmodal fade" id="langTypSelect" name = "langTypSelect" tabindex="-1" role="dialog" aria-hidden="true" data-backdrop="false">
        <div class="modal-dialog modal-lg">
            <div class="modal-content">
                <div class="modal-header">
                    <button type="button" class="close" data-dismiss="modal"><span
                            aria-hidden="true">&times;</span><span class="sr-only">Close</span>
                    </button>
                    <h4 class="modal-title">[[#{jsp.exam.demographyParam.languagetype}]]</h4>
                </div>
                <div class="modal-body">
                    <div class="form-group">
                        <label class="col-sm-3 control-label">[[#{jsp.exam.product.questionnaireType}]]:</label>
                        <div class="col-sm-8" id="langTypeDiv" th:fragment="langTypeDiv">
                            <select th:if="${dictDatas} != null" name="langType"
                                    class="form-control m-b">
                                <option th:each="dict, iterStat : ${dictDatas}" th:text="${dict.dictLabel}"
                                        th:value="${dict.dictValue}"></option>
                            </select>
                            <div class="select-must" style="color: red" hidden="true">*[[#{jsp.exam.product.pleaseSelectLangType}]]</div>
                        </div>
                    </div>
                </div>
                <div class="modal-footer">
                    <button type="button" class="btn btn-white" data-dismiss="modal">close</button>
                    <button type="button" class="btn btn-primary next-step">next</button>
                </div>
            </div>
        </div>
    </div>
</div>
<th:block th:include="include :: footer"/>
<script th:inline="javascript">
    var editFlag = [[${@permission.hasPermi('exam:report:edit')}]];
    var removeFlag = [[${@permission.hasPermi('exam:report:remove')}]];
    var statusDatas = [[${@dict.getType('downloadDetailedReport_status')}]];
    var test_member_status = [[${@dict.getType('test_member_status')}]];
    var prefix = ctx + "exam/report";
    $(function () {
        var columns = [{field: 'ID', checkbox: true}];
        var options = {
            url: prefix + "/newListData",
            createUrl: prefix + "/add",
            updateUrl: prefix + "/edit/{id}",
            removeUrl: prefix + "/remove",
            exportUrl: prefix + "/exportReport",
            modalName: "评测报告",
            pageSize: 50,
            pageList: [50, 100, 200],
            onLoadSuccess: function (data) {
            },
            columns: [{
                checkbox: true
            },
                {
                    field: 'id',
                    title: 'ID',
                    visible: false
                },
                {
                    field: 'memberId',
                    title: [[#{jsp.exam.test_package.033}]]
                },
                {
                    field: 'memberDept',
                    title: [[#{jsp.testPackage.department}]],
                    sortable: true
                },
                {
                    field: 'memberName',
                    title: [[#{jsp.system.user.profile.011}]]
                },
                {
                    field: 'downloadTimes',
                    title: [[#{jsp.exam.report.downloadRight}]],
                    formatter: function (value, row, index) {
                        return $.table.selectDictLabel(statusDatas, value);
                    },
                    visible: false
                },
                {
                    field: 'verifyStatus',
                    title: [[#{jsp.exam.report.questionStatus}]],
                    formatter: function (value, row, index) {
                        return $.table.selectDictLabel(test_member_status, value);
                    }
                },
                {
                    field: 'productId',
                    title: [[#{jsp.exam.product.productPackageNumber}]],
                    visible: false
                },
                {
                    field: 'productName',
                    title: [[#{jsp.exam.report.productName}]]
                },
                {
                    field: 'userId',
                    title: 'userId',
                    visible: false
                },
                {
                    title: [[#{basis.operate}]],
                    align: 'center',
                    formatter: function (value, row, index) {
                        var actions = [];
                        actions.push('<a class="btn btn-info btn-xs ' + editFlag + '" href="javascript:void(0)" onclick="testerReport(\'' + row.memberId + '\')"><i class="fa fa-edit"></i>'+[[#{jsp.exam.textPackageExport}]]+'</a> ');
                        return actions.join('');
                    }
                },
            ]
        };
        $.table.init(options);
    });
    function exportDataReport(formId) {
        var productId = $("#productId").val();
        if (productId == '') {
            $.modal.alertWarning([[#{jsp.exam.evaluation_report.export.msg}]]);
            return;
        }
/*        var ids = $.table.selectColumns("id");
        if (ids.length == 0) {
            $.modal.alertWarning([[#{please.choose.user}]]);
            return;
        }*/
        $.modal.loading([[#{jsp.exam.report.003}]]);
        var currentId = $.common.isEmpty(formId) ? $('form').attr('id') : formId;
        console.log(currentId);
        $.post(prefix + "/exportEvaluationReport", $("#" + currentId).serializeArray(), function(result) {
            if (result.code == web_status.SUCCESS) {
                window.location.href = ctx + "common/download?fileName=" + encodeURI(result.msg) + "&delete=" + true;
            } else if (result.code == web_status.WARNING) {
                $.modal.alertWarning(result.msg)
            } else {
                $.modal.alertError(result.msg);
            }
            $.modal.closeLoading();
        });
    }
    // 下载用户的测试报告
    function testerReport(memberId) {
        $.modal.loading([[#{jsp.exam.report.003}]]);
        $.post(prefix + "/testerReport/" + memberId, "", function (result) {
            if (result.code == web_status.SUCCESS) {
                window.location.href = ctx + "common/download?fileName=" + encodeURI(result.msg) + "&delete=" + true;
            } else if (result.code == web_status.WARNING) {
                $.modal.alertWarning(result.msg)
            } else {
                $.modal.alertError(result.msg);
            }
            $.modal.closeLoading();
        });
    }
</script>
</body>
</html>
src/main/resources/templates/exam/report/report.html
@@ -1,7 +1,7 @@
<!DOCTYPE html>
<html lang="zh" xmlns:th="http://www.thymeleaf.org" xmlns:shiro="http://www.pollix.at/thymeleaf/shiro">
<head>
    <th:block th:include="include :: header('评测报告列表')"/>
    <th:block th:include="include :: header('评测人员报告列表')"/>
</head>
<body class="gray-bg">
<div class="container-div">
src/main/resources/templates/exam/template/emailEdit.html
New file
@@ -0,0 +1,252 @@
<!DOCTYPE html>
<html lang="zh" xmlns:th="http://www.thymeleaf.org">
<head>
    <th:block th:include="include :: header('邮件模板配置')"/>
    <th:block th:include="include :: datetimepicker-css"/>
    <th:block th:include="include :: select2-css" />
    <th:block th:include="include :: bootstrap-select-css" />
</head>
<body class="white-bg">
<div class="wrapper wrapper-content animated fadeInRight ibox-content">
    <form class="form-horizontal m" id="form-email_edit-add">
        <input th:type="hidden" id="id" name="id" th:value="${emailTemplate.id}">
        <!--测试者邀请邮件模板 -->
        <div class="form-group">
            <label class="col-sm-3 control-label">[[#{jsp.exam.test_package.005}]]:</label>
            <div class="col-sm-8">
                <select name="inviteType" id="inviteType" class="form-control noselect2 selectpicker" th:with="type=${@dict.getType('lang_type')}" multiple>
                    <option th:each="dict : ${type}" th:text="${dict.dictLabel}"
                            th:value="${dict.dictValue}"
                            th:selected="${dict.dictValue} eq 'Chinese' and ${emailTemplate.inviteCnTemplate} != null
                            or ${dict.dictValue} eq 'English' and ${emailTemplate.inviteUsTemplate} != null
                            or ${dict.dictValue} eq 'Thai' and ${emailTemplate.inviteThTemplate} != null ">
                    </option>
                </select>
            </div>
        </div>
        <div class="form-group" id="inviteCnTemplateDiv" th:style="'display:' + @{(*{emailTemplate.inviteCnTemplate} ? 'block' : 'none')} + ''">
            <label class="col-sm-3 control-label">[[#{dict.ic124}]]:</label>
            <div class="col-sm-8">
                <textarea id="inviteCnTemplate" name="inviteCnTemplate" th:text="${emailTemplate.inviteCnTemplate}" class="form-control" rows="10" cols="60"></textarea>
            </div>
        </div>
        <div class="form-group" id="inviteUsTemplateDiv" th:style="'display:' + @{(*{emailTemplate.inviteUsTemplate} ? 'block' : 'none')} + ''">
            <label class="col-sm-3 control-label">[[#{dict.ic125}]]:</label>
            <div class="col-sm-8">
                <textarea id="inviteUsTemplate" name="inviteUsTemplate" th:text="${emailTemplate.inviteUsTemplate}" class="form-control" rows="10" cols="60"></textarea>
            </div>
        </div>
        <div class="form-group" id="inviteThTemplateDiv" th:style="'display:' + @{(*{emailTemplate.inviteThTemplate} ? 'block' : 'none')} + ''">
            <label class="col-sm-3 control-label">[[#{dict.ic126}]]:</label>
            <div class="col-sm-8">
                <textarea id="inviteThTemplate" name="inviteThTemplate" th:text="${emailTemplate.inviteThTemplate}" class="form-control" rows="10" cols="60"></textarea>
            </div>
        </div>
        <!--HR邮件模板 -->
        <div class="form-group">
            <label class="col-sm-3 control-label">[[#{jsp.exam.test_package.hrinvitationEmailContent}]]:</label>
            <div class="col-sm-8">
                <select name="hrType" id="hrType" class="form-control noselect2 selectpicker" th:with="type=${@dict.getType('lang_type')}" multiple>
                    <option th:each="dict : ${type}" th:text="${dict.dictLabel}"
                            th:value="${dict.dictValue}"
                            th:selected="${dict.dictValue} eq 'Chinese' and ${emailTemplate.hrCnTemplate} != null
                            or ${dict.dictValue} eq 'English' and ${emailTemplate.hrUsTemplate} != null
                            or ${dict.dictValue} eq 'Thai' and ${emailTemplate.hrThTemplate} != null ">
                    </option>
                </select>
            </div>
        </div>
        <div class="form-group" id="hrCnTemplateDiv" th:style="'display:' + @{(*{emailTemplate.hrCnTemplate} ? 'block' : 'none')} + ''">
            <label class="col-sm-3 control-label">[[#{dict.ic124}]]:</label>
            <div class="col-sm-8">
                <textarea id="hrCnTemplate" name="hrCnTemplate" th:text="${emailTemplate.hrCnTemplate}" class="form-control" rows="10" cols="60"></textarea>
            </div>
        </div>
        <div class="form-group" id="hrUsTemplateDiv" th:style="'display:' + @{(*{emailTemplate.hrUsTemplate} ? 'block' : 'none')} + ''">
            <label class="col-sm-3 control-label">[[#{dict.ic125}]]:</label>
            <div class="col-sm-8">
                <textarea id="hrUsTemplate" name="hrUsTemplate" th:text="${emailTemplate.hrUsTemplate}" class="form-control" rows="10" cols="60"></textarea>
            </div>
        </div>
        <div class="form-group" id="hrThTemplateDiv" th:style="'display:' + @{(*{emailTemplate.hrThTemplate} ? 'block' : 'none')} + ''">
            <label class="col-sm-3 control-label">[[#{dict.ic126}]]:</label>
            <div class="col-sm-8">
                <textarea id="hrThTemplate" name="hrThTemplate" th:text="${emailTemplate.hrThTemplate}" class="form-control" rows="10" cols="60"></textarea>
            </div>
        </div>
        <!-- 测试者接收报告邮件 -->
        <div class="form-group">
            <label class="col-sm-3 control-label">[[#{jsp.exam.test_package.memberEmailContent}]]:</label>
            <div class="col-sm-8">
                <select name="memberType" id="memberType" class="form-control noselect2 selectpicker" th:with="type=${@dict.getType('lang_type')}" multiple>
                    <option th:each="dict : ${type}" th:text="${dict.dictLabel}"
                            th:value="${dict.dictValue}"
                            th:selected="${dict.dictValue} eq 'Chinese' and ${emailTemplate.memberCnTemplate} != null
                            or ${dict.dictValue} eq 'English' and ${emailTemplate.memberUsTemplate} != null
                            or ${dict.dictValue} eq 'Thai' and ${emailTemplate.memberThTemplate} != null ">
                </select>
            </div>
        </div>
        <div class="form-group" id="memberCnTemplateDiv" th:style="'display:' + @{(*{emailTemplate.memberCnTemplate} ? 'block' : 'none')} + ''">
            <label class="col-sm-3 control-label">[[#{dict.ic124}]]:</label>
            <div class="col-sm-8">
                <textarea id="memberCnTemplate" name="memberCnTemplate" th:text="${emailTemplate.memberCnTemplate}" class="form-control" rows="10" cols="60"></textarea>
            </div>
        </div>
        <div class="form-group" id="memberUsTemplateDiv" th:style="'display:' + @{(*{emailTemplate.memberUsTemplate} ? 'block' : 'none')} + ''">
            <label class="col-sm-3 control-label">[[#{dict.ic125}]]:</label>
            <div class="col-sm-8">
                <textarea id="memberUsTemplate" name="memberUsTemplate" th:text="${emailTemplate.memberUsTemplate}" class="form-control" rows="10" cols="60"></textarea>
            </div>
        </div>
        <div class="form-group" id="memberThTemplateDiv" th:style="'display:' + @{(*{emailTemplate.memberThTemplate} ? 'block' : 'none')} + ''">
            <label class="col-sm-3 control-label">[[#{dict.ic126}]]:</label>
            <div class="col-sm-8">
                <textarea id="memberThTemplate" name="memberThTemplate" th:text="${emailTemplate.memberThTemplate}" class="form-control" rows="10" cols="60"></textarea>
            </div>
        </div>
    </form>
</div>
<th:block th:include="include :: footer"/>
<th:block th:include="include :: datetimepicker-js"/>
<th:block th:include="include :: select2-js" />
<th:block th:include="include :: bootstrap-select-js" />
<script type="text/javascript">
    var prefix = ctx + "exam/template"
    $("#form-email_edit-add").validate({
        focusCleanup: true
    });
    function submitHandler() {
        if ($.validate.form()) {
            $.operate.save(prefix + "/emailEdit", $('#form-email_edit-add').serialize());
        }
    }
    $(function () {
        $.table.testPackDefault();
    });
    /**
     * 邀请测试者通知模板
     */
    $("#inviteType").change(function(){
        var opt = $("#inviteType").val();
        //没有选中
        if (opt != null){
            var Chinese = 0;
            var English = 0;
            var Thai = 0;
            //选中后拼接语言赋值模板
            for(var i = 0;i < opt.length;i++){
                if(opt[i] == 'Chinese'){
                    $('#inviteCnTemplateDiv').attr("style","display:block;");
                    Chinese = 1;
                }else if(opt[i] == 'English'){
                    $('#inviteUsTemplateDiv').attr("style","display:block;");
                    English = 1;
                }else if(opt[i] == 'Thai'){
                    $('#inviteThTemplateDiv').attr("style","display:block;");
                    Thai = 1;
                }
            }
            if(Chinese == 0){
                $('#inviteCnTemplateDiv').attr("style","display:none;");
            }
            if(English == 0){
                $('#inviteUsTemplateDiv').attr("style","display:none;");
            }
            if(Thai == 0){
                $('#inviteThTemplateDiv').attr("style","display:none;");
            }
        }else{
            $('#inviteCnTemplateDiv').attr("style","display:none;");
            $('#inviteUsTemplateDiv').attr("style","display:none;");
            $('#inviteThTemplateDiv').attr("style","display:none;");
        }
    });
    /**
     * HR通知模板
     */
    $("#hrType").change(function(){
        var opt = $("#hrType").val();
        //没有选中
        if (opt != null){
            var Chinese = 0;
            var English = 0;
            var Thai = 0;
            //选中后拼接语言赋值模板
            for(var i = 0;i < opt.length;i++){
                if(opt[i] == 'Chinese'){
                    $('#hrCnTemplateDiv').attr("style","display:block;");
                    Chinese = 1;
                }else if(opt[i] == 'English'){
                    $('#hrUsTemplateDiv').attr("style","display:block;");
                    English = 1;
                }else if(opt[i] == 'Thai'){
                    $('#hrThTemplateDiv').attr("style","display:block;");
                    Thai = 1;
                }
            }
            if(Chinese == 0){
                $('#hrCnTemplateDiv').attr("style","display:none;");
            }
            if(English == 0){
                $('#hrUsTemplateDiv').attr("style","display:none;");
            }
            if(Thai == 0){
                $('#hrThTemplateDiv').attr("style","display:none;");
            }
        }else{
            $('#hrCnTemplateDiv').attr("style","display:none;");
            $('#hrUsTemplateDiv').attr("style","display:none;");
            $('#hrThTemplateDiv').attr("style","display:none;");
        }
    });
    /**
     * 测试者通知模板
     */
    $("#memberType").change(function(){
        var opt = $("#memberType").val();
        //没有选中
        if (opt != null){
            var Chinese = 0;
            var English = 0;
            var Thai = 0;
            //选中后拼接语言赋值模板
            for(var i = 0;i < opt.length;i++){
                if(opt[i] == 'Chinese'){
                    $('#memberCnTemplateDiv').attr("style","display:block;");
                    Chinese = 1;
                }else if(opt[i] == 'English'){
                    $('#memberUsTemplateDiv').attr("style","display:block;");
                    English = 1;
                }else if(opt[i] == 'Thai'){
                    $('#memberThTemplateDiv').attr("style","display:block;");
                    Thai = 1;
                }
            }
            if(Chinese == 0){
                $('#memberCnTemplateDiv').attr("style","display:none;");
            }
            if(English == 0){
                $('#memberUsTemplateDiv').attr("style","display:none;");
            }
            if(Thai == 0){
                $('#memberThTemplateDiv').attr("style","display:none;");
            }
        }else{
            $('#memberCnTemplateDiv').attr("style","display:none;");
            $('#memberUsTemplateDiv').attr("style","display:none;");
            $('#memberThTemplateDiv').attr("style","display:none;");
        }
    });
</script>
</body>
</html>
src/main/resources/templates/exam/template/template.html
@@ -52,7 +52,10 @@
                </a>
                <a class="btn btn-warning" onclick="$.table.exportExcel()" shiro:hasPermission="exam:template:export">
                    <i class="fa fa-download"></i> [[#{dict.ic22}]]
                 </a>
                </a>
                <a class="btn btn-danger+" onclick="emailEdit()" shiro:hasPermission="exam:email:edit">
                    <i class="fa fa-edit"></i> [[#{dict.ic175}]]
                </a>
            </div>
            <div class="col-sm-12 select-table table-striped">
                <table id="bootstrap-table" data-mobile-responsive="true"></table>
@@ -126,6 +129,11 @@
            };
            $.table.init(options);
        });
        function emailEdit() {
            var url = prefix + '/emailEdit';
            $.modal.open([[#{dict.ic175}]], url);
        }
    </script>
</body>
</html>
src/main/resources/templates/exam/test_package/add.html
@@ -77,6 +77,20 @@
                </div>
            </div>
        </div>
        <!--测试者邀请邮件模板 -->
        <input name="CNTemplate" id="CNTemplate" th:value="${eet.inviteCnTemplate}" class="form-control" type="hidden">
        <input name="USTemplate" id="USTemplate" th:value="${eet.inviteUsTemplate}" class="form-control" type="hidden">
        <input name="THTemplate" id="THTemplate" th:value="${eet.inviteThTemplate}" class="form-control" type="hidden">
        <div class="form-group">
            <label class="col-sm-3 control-label">[[#{jsp.exam.package.langtype}]]:</label>
            <div class="col-sm-8">
                <select name="templateLangType" id="templateLangType" class="form-control noselect2 selectpicker" th:with="type=${@dict.getType('lang_type')}" multiple>
                    <option th:each="dict : ${type}" th:text="${dict.dictLabel}"
                            th:value="${dict.dictValue}"></option>
                </select>
            </div>
        </div>
        <div class="form-group">
            <label class="col-sm-3 control-label">[[#{jsp.exam.test_package.005}]]:</label>
            <div class="col-sm-8">
@@ -84,6 +98,19 @@
            </div>
        </div>
        <!--HR邮件模板 -->
        <input name="HrCNTemplate" id="HrCNTemplate" th:value="${eet.hrCnTemplate}" class="form-control" type="hidden">
        <input name="HrUSTemplate" id="HrUSTemplate" th:value="${eet.hrUsTemplate}" class="form-control" type="hidden">
        <input name="HrTHTemplate" id="HrTHTemplate" th:value="${eet.hrThTemplate}" class="form-control" type="hidden">
        <div class="form-group">
            <label class="col-sm-3 control-label">[[#{jsp.exam.package.langtype}]]:</label>
            <div class="col-sm-8">
                <select name="hrTemplateLangType" id="hrTemplateLangType" class="form-control noselect2 selectpicker" th:with="type=${@dict.getType('lang_type')}" multiple>
                    <option th:each="dict : ${type}" th:text="${dict.dictLabel}"
                            th:value="${dict.dictValue}"></option>
                </select>
            </div>
        </div>
        <div class="form-group">
            <label class="col-sm-3 control-label">[[#{jsp.exam.test_package.hrinvitationEmailContent}]]:</label>
            <div class="col-sm-8">
@@ -124,12 +151,32 @@
            </div>
        </div>
        <!-- 测试者接收报告邮件 -->
        <input name="TesterCNTemplate" id="TesterCNTemplate" th:value="${eet.memberCnTemplate}" class="form-control" type="hidden">
        <input name="TesterUSTemplate" id="TesterUSTemplate" th:value="${eet.memberUsTemplate}" class="form-control" type="hidden">
        <input name="TesterTHTemplate" id="TesterTHTemplate" th:value="${eet.memberThTemplate}" class="form-control" type="hidden">
        <div class="form-group">
            <label class="col-sm-3 control-label">[[#{jsp.exam.testPackage.autoSendReport}]]:</label>
            <div class="col-sm-8">
                <label class='check-box'><input th:type="checkbox" id="autoSendReport" name="autoSendReport"></label>
                <input th:type="checkbox" id="autoSendReport" name="autoSendReport" onchange="isSelectAutoSendReport()">
            </div>
        </div>
        <div class="form-group" id="memberTemplateLangTypeDiv" style="display: none">
            <label class="col-sm-3 control-label">[[#{jsp.exam.package.langtype}]]:</label>
            <div class="col-sm-8">
                <select name="memberTemplateLangType" id="memberTemplateLangType" class="form-control noselect2 selectpicker" th:with="type=${@dict.getType('lang_type')}" multiple>
                    <option th:each="dict : ${type}" th:text="${dict.dictLabel}"
                            th:value="${dict.dictValue}"></option>
                </select>
            </div>
        </div>
        <div class="form-group" id="memberTemplateDiv" style="display: none">
            <label class="col-sm-3 control-label">[[#{jsp.exam.test_package.memberEmailContent}]]:</label>
            <div class="col-sm-8">
                <textarea id="memberTemplate" name="memberTemplate" th:text="${memberTemplate}" class="form-control" rows="10" cols="60"></textarea>
            </div>
        </div>
        <div class="row">
            <div class="col-sm-12">
@@ -150,10 +197,12 @@
<th:block th:include="include :: select2-js" />
<th:block th:include="include :: bootstrap-select-js" />
<script type="text/javascript">
    var prefix = ctx + "exam/test_package"
    $("#form-test_package-add").validate({
        focusCleanup: true
    });
    function submitHandler() {
        if ($.validate.form()) {
@@ -236,6 +285,99 @@
    $(function () {
        $.table.testPackDefault();
    });
    function isSelectAutoSendReport() {
        if($("#autoSendReport").prop("checked") == true){
            $('#memberTemplateLangTypeDiv').attr("style","display:block;");
            $('#memberTemplateDiv').attr("style","display:block;");
        }else{
            $('#memberTemplateLangTypeDiv').attr("style","display:none;");
            $('#memberTemplateDiv').attr("style","display:none;");
        }
    }
    /**
     * 遍历邀请测试者通知模板
     */
    $("#templateLangType").change(function(){
        var opt = $("#templateLangType").val();
        //没有选中
        if (opt == null){
            $('[name="template"]').val("");
        }else{
            //选中后拼接语言赋值模板
            var template = "";
            $('[name="template"]').val(template);
            for(var i = 0;i < opt.length;i++){
                if(opt[i] == 'Chinese'){
                    template += $("#CNTemplate").val()+"\n\n";
                }else if(opt[i] == 'English'){
                    template += $("#USTemplate").val()+"\n\n";
                }else if(opt[i] == 'Thai'){
                    template += $("#THTemplate").val()+"\n\n";
                }
            }
            //去掉最后面的换行符\n
            template = template.slice(0,-2);
            $('[name="template"]').val(template);
        }
    });
    /**
     * HR通知模板
     */
    $("#hrTemplateLangType").change(function(){
        var opt = $("#hrTemplateLangType").val();
        //没有选中
        var isEdit;
        if (opt == null) {
            $('[name="hrTemplate"]').val("");
        } else {
            //选中后拼接语言赋值模板
            var hrTemplate = "";
            $('[name="hrTemplate"]').val(hrTemplate);
            for (var i = 0; i < opt.length; i++) {
                if (opt[i] == 'Chinese') {
                    hrTemplate += $("#HrCNTemplate").val() +"\n\n";
                } else if (opt[i] == 'English') {
                    hrTemplate += $("#HrUSTemplate").val() +"\n\n";
                } else if (opt[i] == 'Thai') {
                    hrTemplate += $("#HrTHTemplate").val() +"\n\n";
                }
            }
            //去掉最后面的换行符\n
            hrTemplate = hrTemplate.slice(0, -2);
            $('[name="hrTemplate"]').val(hrTemplate);
        }
    });
    /**
     * 测试者通知模板
     */
    $("#memberTemplateLangType").change(function(){
        var opt = $("#memberTemplateLangType").val();
        //没有选中
        var isEdit;
        if (opt == null) {
            $('[name="memberTemplate"]').val("");
        } else {
            //选中后拼接语言赋值模板
            var memberTemplate = "";
            $('[name="memberTemplate"]').val(memberTemplate);
            for (var i = 0; i < opt.length; i++) {
                if (opt[i] == 'Chinese') {
                    memberTemplate += $("#HrCNTemplate").val() +"\n\n";
                } else if (opt[i] == 'English') {
                    memberTemplate += $("#HrUSTemplate").val() +"\n\n";
                } else if (opt[i] == 'Thai') {
                    memberTemplate += $("#HrTHTemplate").val() +"\n\n";
                }
            }
            //去掉最后面的换行符\n
            memberTemplate = memberTemplate.slice(0, -2);
            $('[name="memberTemplate"]').val(memberTemplate);
        }
    });
</script>
</body>
</html>
src/main/resources/templates/exam/test_package/edit.html
@@ -74,10 +74,38 @@
                    </div>
                </div>
            </div>
            <!--测试者邀请邮件模板 -->
            <input name="CNTemplate" id="CNTemplate" th:value="${eet.inviteCnTemplate}" class="form-control" type="hidden">
            <input name="USTemplate" id="USTemplate" th:value="${eet.inviteUsTemplate}" class="form-control" type="hidden">
            <input name="THTemplate" id="THTemplate" th:value="${eet.inviteThTemplate}" class="form-control" type="hidden">
            <div class="form-group">
                <label class="col-sm-3 control-label">[[#{jsp.exam.package.langtype}]]:</label>
                <div class="col-sm-8">
                    <select name="templateLangType" id="templateLangType" class="form-control noselect2 selectpicker" th:with="type=${@dict.getType('lang_type')}" multiple>
                        <option th:each="dict : ${type}" th:text="${dict.dictLabel}"
                                th:value="${dict.dictValue}"></option>
                    </select>
                </div>
            </div>
            <div class="form-group">
                <label class="col-sm-3 control-label">[[#{jsp.exam.test_package.005}]]:</label>
                <div class="col-sm-8">
                    <textarea id="template" name="template" th:field="*{template}" class="form-control"  rows="10" cols="60"></textarea>
                </div>
            </div>
            <!--HR邮件模板 -->
            <input name="HrCNTemplate" id="HrCNTemplate" th:value="${eet.hrCnTemplate}" class="form-control" type="hidden">
            <input name="HrUSTemplate" id="HrUSTemplate" th:value="${eet.hrUsTemplate}" class="form-control" type="hidden">
            <input name="HrTHTemplate" id="HrTHTemplate" th:value="${eet.hrThTemplate}" class="form-control" type="hidden">
            <div class="form-group">
                <label class="col-sm-3 control-label">[[#{jsp.exam.package.langtype}]]:</label>
                <div class="col-sm-8">
                    <select name="hrTemplateLangType" id="hrTemplateLangType" class="form-control noselect2 selectpicker" th:with="type=${@dict.getType('lang_type')}" multiple>
                        <option th:each="dict : ${type}" th:text="${dict.dictLabel}"
                                th:value="${dict.dictValue}"></option>
                    </select>
                </div>
            </div>
            <div class="form-group">
@@ -86,6 +114,7 @@
                    <textarea id="hrTemplate" name="hrTemplate" th:text="*{hrTemplate}" class="form-control" rows="10" cols="60" ></textarea>
                </div>
            </div>
            <div class="form-group">
                <label class="col-sm-3 control-label">[[#{basis.remark}]]:</label>
                <div class="col-sm-8">
@@ -124,12 +153,32 @@
                </div>
            </div>
            <!-- 测试者接收报告邮件 -->
            <input name="TesterCNTemplate" id="TesterCNTemplate" th:value="${eet.memberCnTemplate}" class="form-control" type="hidden">
            <input name="TesterUSTemplate" id="TesterUSTemplate" th:value="${eet.memberUsTemplate}" class="form-control" type="hidden">
            <input name="TesterTHTemplate" id="TesterTHTemplate" th:value="${eet.memberThTemplate}" class="form-control" type="hidden">
            <div class="form-group">
                <label class="col-sm-3 control-label">[[#{jsp.exam.testPackage.autoSendReport}]]:</label>
                <div class="col-sm-8">
                    <label class='check-box'><input th:type="checkbox" id="autoSendReport" name="autoSendReport" th:checked="*{autoSendReport}"></label>
                    <input th:type="checkbox" id="autoSendReport" name="autoSendReport" onchange="isSelectAutoSendReport()" th:checked="*{autoSendReport}" >
                </div>
            </div>
            <div class="form-group" id="memberTemplateLangTypeDiv" th:style="'display:' + @{(*{autoSendReport} ? 'block' : 'none')} + ''">
                <label class="col-sm-3 control-label">[[#{jsp.exam.package.langtype}]]:</label>
                <div class="col-sm-8">
                    <select name="memberTemplateLangType" id="memberTemplateLangType" class="form-control noselect2 selectpicker" th:with="type=${@dict.getType('lang_type')}" multiple>
                        <option th:each="dict : ${type}" th:text="${dict.dictLabel}"
                                th:value="${dict.dictValue}"></option>
                    </select>
                </div>
            </div>
            <div class="form-group" id="memberTemplateDiv" th:style="'display:' + @{(*{autoSendReport} ? 'block' : 'none')} + ''">
                <label class="col-sm-3 control-label">[[#{jsp.exam.test_package.memberEmailContent}]]:</label>
                <div class="col-sm-8">
                    <textarea id="memberTemplate" name="memberTemplate" th:text="*{memberTemplate}" class="form-control" rows="10" cols="60"></textarea>
                </div>
            </div>
            <div class="row">
                <div class="col-sm-12">
                    <div class="form-group">
@@ -146,11 +195,15 @@
    </div>
    <th:block th:include="include :: footer" />
    <th:block th:include="include :: datetimepicker-js" />
    <th:block th:include="include :: select2-js" />
    <th:block th:include="include :: select2-js" />-->
    <th:block th:include="include :: bootstrap-select-js" />
    <script type="text/javascript">
        var prefix = ctx + "exam/test_package";
        var reportTemplateId = '[[${entTestPackage.reportTemplateId}]]';
        $('.check-box').click(function(){
            alert(1);
        })
        $(document).ready(function () {
            //回写select
@@ -239,7 +292,100 @@
                        }
                    }
                }
        })}
        })};
        function isSelectAutoSendReport() {
            if($("#autoSendReport").prop("checked") == true){
                $('#memberTemplateLangTypeDiv').attr("style","display:block;");
                $('#memberTemplateDiv').attr("style","display:block;");
            }else{
                $('#memberTemplateLangTypeDiv').attr("style","display:none;");
                $('#memberTemplateDiv').attr("style","display:none;");
            }
        }
        /**
         * 遍历邀请测试者通知模板
         */
        $("#templateLangType").change(function(){
            var opt = $("#templateLangType").val();
            //没有选中
            if (opt == null){
                $('[name="template"]').val("");
            }else{
                //选中后拼接语言赋值模板
                var template = "";
                $('[name="template"]').val(template);
                for(var i = 0;i < opt.length;i++){
                    if(opt[i] == 'Chinese'){
                        template += $("#CNTemplate").val()+"\n\n";
                    }else if(opt[i] == 'English'){
                        template += $("#USTemplate").val()+"\n\n";
                    }else if(opt[i] == 'Thai'){
                        template += $("#THTemplate").val()+"\n\n";
                    }
                }
                //去掉最后面的换行符\n
                template = template.slice(0,-2);
                $('[name="template"]').val(template);
            }
        });
        /**
         * HR通知模板
         */
        $("#hrTemplateLangType").change(function(){
            var opt = $("#hrTemplateLangType").val();
            //没有选中
            var isEdit;
            if (opt == null) {
                $('[name="hrTemplate"]').val("");
            } else {
                //选中后拼接语言赋值模板
                var hrTemplate = "";
                $('[name="hrTemplate"]').val(hrTemplate);
                for (var i = 0; i < opt.length; i++) {
                    if (opt[i] == 'Chinese') {
                        hrTemplate += $("#HrCNTemplate").val() +"\n\n";
                    } else if (opt[i] == 'English') {
                        hrTemplate += $("#HrUSTemplate").val() +"\n\n";
                    } else if (opt[i] == 'Thai') {
                        hrTemplate += $("#HrTHTemplate").val() +"\n\n";
                    }
                }
                //去掉最后面的换行符\n
                hrTemplate = hrTemplate.slice(0, -2);
                $('[name="hrTemplate"]').val(hrTemplate);
            }
        });
        /**
         * 测试者通知模板
         */
        $("#memberTemplateLangType").change(function(){
            var opt = $("#memberTemplateLangType").val();
            //没有选中
            var isEdit;
            if (opt == null) {
                $('[name="memberTemplate"]').val("");
            } else {
                //选中后拼接语言赋值模板
                var memberTemplate = "";
                $('[name="memberTemplate"]').val(memberTemplate);
                for (var i = 0; i < opt.length; i++) {
                    if (opt[i] == 'Chinese') {
                        memberTemplate += $("#TesterCNTemplate").val() +"\n\n";
                    } else if (opt[i] == 'English') {
                        memberTemplate += $("#TesterUSTemplate").val() +"\n\n";
                    } else if (opt[i] == 'Thai') {
                        memberTemplate += $("#TesterTHTemplate").val() +"\n\n";
                    }
                }
                //去掉最后面的换行符\n
                memberTemplate = memberTemplate.slice(0, -2);
                $('[name="memberTemplate"]').val(memberTemplate);
            }
        });
    </script>
</body>
</html>