tame JSCE

tame JSCE sites

// ==UserScript==
// @name        tame JSCE
// @namespace   Violentmonkey Scripts

// @match       *://www.jsce.gov.cn/*
// @match       *://course.jsce.gov.cn/*

// @grant       none
// @version     2.1.2
// @author      someone
// @license     MIT
// @description tame JSCE sites

// @run-at      document-idle

// @grant       GM_openInTab
// @grant       GM_notification
// @grant       unsafeWindow
// @grant       window.close
// @grant       window.focus

// @require     https://update.greasyfork.org/scripts/425782/fetchElements.js
// @require     https://update.greasyfork.org/scripts/425790/multiOpenCloseTabs.js

// @require     https://unpkg.com/tesseract.js/dist/tesseract.min.js
// @require     https://update.greasyfork.org/scripts/489988/tesseractJSautofill.js

// ==/UserScript==

/**
 * 为便于调试,课程需全局拦截:||www.jsce.gov.cn/elms/js/checkFrame.js
 * 专题培训班: http://www.jsce.gov.cn/elms/web/university/clazz/index.jsp#
 */

if (location.host === 'www.jsce.gov.cn') {
  const autoAll = async () => {
    const body_elements = await fetchElements(`//www.jsce.gov.cn/elms/web/body.jsp`);
    const infos = body_elements.querySelectorAll('tbody > tr');
    // 尚未登录
    if (infos.length === 0) {
      /**
       * 登录页面尝试登录失败会有文字提醒
       * document.getElementById('showWarning').className
       * 从 '' 变成 'alert ' 等
       */
      auto_fill_captcha_text('#imgrand', '#rand', '#login');
      const showWarning_observer = new MutationObserver(() => {
        if (document.getElementById('showWarning').className.startsWith('alert ')) {
          const alertMessage = document.getElementById('showWarning').textContent;
          /**
           * ×验证码输入错误
           *
           * ×请输入验证码
           * ×请输入用户名/手机号
           * ×用户名或密码输入错误
           * ×您的账号由于三次输入密码错误被封30分钟!请在xx:xx:xx以后再尝试登陆!
           */
          switch (alertMessage) {
            case '×验证码输入错误':
              location.reload();
              break;
            default:
              GM_notification(alertMessage, 'Alert');
          }
        }
      });
      showWarning_observer.observe(document.getElementById('showWarning'), {
        attributes: true,
      });
      // 避免未登录情况下继续执行后续代码
      return;
    }
    // 常规课程考核状态
    let nomal_assessment = infos[6].textContent.trim().split(':')[1];
    sessionStorage.setItem('nomal_assessment', nomal_assessment);
    // 已获得必修学时
    let now_compulsory = Number(infos[4].textContent.trim().split(':')[1]);
    // 已获得总学时
    let now_total = Number(infos[5].textContent.trim().split(':')[1]);

    const lanmu_elements = await fetchElements(`//www.jsce.gov.cn/elms/web/lanmu.jsp`);
    const targets = lanmu_elements.querySelectorAll('p.font');
    if (targets.length === 0) return;
    // 常规课程目标学时
    let normal_target_compulsory;
    let normal_target_total;
    for (let i of targets) {
      if (i.textContent.trim().startsWith('应获必修学时:')) {
        normal_target_compulsory = Number(i.textContent.split(':')[1]);
      } else if (i.textContent.trim().startsWith('应获总学时:')) {
        normal_target_total = Number(i.textContent.split(':')[1]);
      }
    }
    let gap_compulsory = normal_target_compulsory - now_compulsory;
    let gap_total = normal_target_total - now_total;

    // 避免弹出大量通知
    let status = `考核状态:\n${nomal_assessment}`;
    if (nomal_assessment === '未通过') {
      if (gap_compulsory > 0) {
        status += `\n必修差${gap_compulsory}学时`;
      } else {
        status += `\n必修已满`;
      }
      if (gap_total > 0) {
        status += `\n总体差${gap_total}学时`;
      } else {
        status += `\n总体已满`;
      }
      if (gap_compulsory <= 0 && gap_total <= 0) {
        status += `考核规则变了!`;
      }
      if (window.top === window.self) {
        GM_notification(status);
        window.top.postMessage('start auto learn', '*');
      }
    } else {
      if (window.top === window.self) {
        GM_notification(status);
      }
    }

    // 接收信息在top层不在iframe中,所以要穿透选择元素
    const receiveMessage = (event) => {
      const data = event.data;
      const origin = event.origin;
      if (data === 'reload main frame' && window.top === window.self) {
        // 刷新顶层页面
        location.reload();
      } else if (data === 'active this tab' && origin === 'http://course.jsce.gov.cn') {
        // 自动激活课程播放页面
        window.focus();
      } else if (data === 'pass this course') {
        // 关闭使用flash的课程并存储
        const courseId = location.search.split('courseId=')[1].split('&')[0];
        localStorage.setItem(courseId, 'flash');
        window.close();
      } else if (data === 'switch to select course') {
        // 选课中心下拉菜单
        if (!document.querySelector('#menuChooseCourse > a.dropdown-toggle')) return;
        document.querySelector('#menuChooseCourse > a.dropdown-toggle').click();
        // 根据分数差距跳转到选课页面
        if (gap_compulsory > 0) {
          // 必修
          document
            .querySelector(
              `#tow-menu a[onclick="javascript:directory2Page('/elms/web/course/browse/course_select.jsp?nature=2','hidden');"]`
            )
            .click();
        } else if (gap_total > 0) {
          // 选修
          document
            .querySelector(
              `#tow-menu a[onclick="javascript:directory2Page('/elms/web/course/browse/course_select.jsp?nature=1','hidden');"]`
            )
            .click();
        }
      } else if (data === 'start auto learn') {
        // 学习中心下拉菜单
        if (!document.getElementById('menuStudyCenter')) return;
        document.querySelector('#menuStudyCenter > a.dropdown-toggle').click();
        // 课程学习
        document
          .querySelector(
            `#menuStudyCenter > #tow-menu a[onclick="javascript:directory2Page('/elms/web/lanmu.jsp','hidden');"]`
          )
          .click();
      } else if (data === 'switch to zjtj') {
        // 进入课程学习后从最近学习课程自动切换到最近选择课程
        if (
          document.getElementById('center') &&
          document.getElementById('center').contentDocument.getElementById('lizjxx') &&
          document.getElementById('center').contentDocument.getElementById('lizjxx')
            .classList[0] === 'active'
        ) {
          document
            .getElementById('center')
            .contentDocument.querySelector('a[href="#zjtj"]')
            .click();
        }
      } else if (data === 'switch to clazz select') {
        // 专题跳转选修标签
        document.getElementById('center').contentDocument.querySelector('a[index="1"]').click();
      }
    };
    window.addEventListener('message', receiveMessage, false);
  };

  (async () => {
    await autoAll();
  })();

  // 专题学习页面
  if (location.pathname === '/elms/web/university/clazz/index.jsp') {
    const clazzInterval = setInterval(() => {
      // 基本信息未载入
      if (document.querySelectorAll('#headerStat div.bs-callout div.col-md-2').length === 0) return;
      // 信息已载入
      clearInterval(clazzInterval);
      if (
        document
          .querySelectorAll('#headerStat div.bs-callout div.col-md-2')[1]
          .textContent.trim() === '是否完成:已完成'
      ) {
        sessionStorage.setItem('clazz_assessment', 'finished');
        if (window.top === window.self) {
          GM_notification(`专题学习:\n完成`);
        }
        // 常规课程未完成则跳转回首页
        if (sessionStorage.getItem('nomal_assessment') !== '通过') {
          location.href = '/elms/web/index.jsp';
        }
      } else {
        sessionStorage.setItem('clazz_assessment', 'notFinished');
        GM_notification(`专题学习:\n未完成`);
        // "选修学时:0.0/5.0"
        const xuanxiuStatus = document.querySelectorAll('#headerStat .col-md-10 div.col-md-2')[1]
          .textContent;
        const getXuanxiuScore = Number(xuanxiuStatus.split('/')[0].split(':')[1]);
        const needXuanxiuScore = Number(xuanxiuStatus.split('/')[1]);
        GM_notification(`专题选修学时:${getXuanxiuScore}/${needXuanxiuScore}`);
        if (getXuanxiuScore >= needXuanxiuScore) {
          sessionStorage.setItem('clazz_xuanxiu', 'finished');
        }
      }
    }, 1000);
  }

  // 选课中心iframe
  // 尚未找到方法远程判断课程是否为flash播放器
  // 选课成功后需要刷新iframe重新载入,故用存储值来判断是否有待检测课程,是否需要翻下一页。
  if (
    // 最新课程
    location.pathname === '/elms/web/getNewestCourse.action' ||
    // 必修和选修课程
    location.pathname === '/elms/web/course/browse/listCourseFilterAuthor.action'
  ) {
    if (sessionStorage.getItem('nomal_assessment') === '通过') return;
    if (
      document.getElementById('myModal') &&
      document.getElementById('myModal').classList[2] === 'in' &&
      document.getElementById('myModal').style.display === 'block'
    ) {
      // 点击选课后弹出新iframe,#myModal 属性会变化,相应排除本块执行
      return;
    }
    const courses = document.querySelectorAll('tr[align="center"]');
    let flashCount = 0;
    let finishedCount = 0;
    let selescedCount = 0;
    for (let i of courses) {
      // 跳过第一行标题
      if (!i.querySelector('a.cc')) continue;
      const parameters = i.querySelector('a.cc').getAttribute('onclick').split("'");
      const courseId = parameters[3];
      // 跳过 flash 课程
      if (localStorage.getItem(courseId) === 'flash') {
        flashCount++;
        i.style.backgroundColor = 'grey';
      } else if (i.querySelector('span[id^="span_"] > button').textContent === '完成') {
        finishedCount++;
        continue;
      } else if (i.querySelector('span[id^="span_"] > button').textContent === '已选') {
        selescedCount++;
        continue;
      } else {
        i.querySelector('span[id^="span_"] > button').click();
        // 然后转入确认选课iframe
      }
    }
    if (flashCount + finishedCount + selescedCount === courses.length - 1) {
      if (sessionStorage.getItem('checkFlash') === 'end') {
        // 本页无可报名课程,自动翻下一页
        document.querySelectorAll('div.btn')[2].click();
      } else if (sessionStorage.getItem('checkFlash') === 'ing') {
        // 已报名部分课程,返回学习页面
        window.top.postMessage('start auto learn');
      }
    }
  }

  // 确认选课iframe
  if (
    // 最新课程
    location.pathname === '/elms/web/getNewestCourse.action' ||
    // 必修和选修课程
    location.pathname === '/elms/web/course/browse/course_select.jsp'
  ) {
    setInterval(() => {
      if (!document.querySelector('button[id^="chooseCourse"]')) return;
      if (document.querySelector('button[id^="chooseCourse"]').style.display !== 'none') {
        document.querySelector('button[id^="chooseCourse"]').click();
        sessionStorage.setItem('checkFlash', 'ing');
        // console.debug(sessionStorage.getItem('checkFlash'));
      } else {
        // 选课成功后若点击关闭按钮则页面不刷新,导致重复打开同一节课程,用刷新iframe的方式可以完美解决。
        location.reload();
      }
    }, 1000);
  }

  // 课程学习列表iframe
  // /elms/web/university/clazz/listMyClazzCourses!train.action
  // /elms/web/university/clazz/listMyClazzCourses!obtainClazzCourseTag.action
  if (
    location.pathname === '/elms/web/listMyCourses.action' ||
    location.pathname.startsWith('/elms/web/university/clazz/listMyClazzCourses!')
  ) {
    const autoOpenCourses = (maxTimes) => {
      // 先循环分类:首先把必修考试完成,其次把flash课程删除,最后继续听课
      let examCourse = [];
      let flashCourse = [];
      let greatCourse = [];
      let progressCourse = [];

      const courseInterval = setInterval(() => {
        // 默认载入时不能直接获取该元素
        if (document.querySelectorAll('tr[align="center"]').length === 0) return;
        // 避免重复打开
        clearInterval(courseInterval);
        // 批量处理学习
        for (let i of document.querySelectorAll('tr[align="center"]')) {
          // 跳过第一行标题
          if (!i.querySelector('img[src="/elms/web/images/xxzx/xuexi.png"]')) continue;
          const imgXuexi = i.querySelector('img[src="/elms/web/images/xxzx/xuexi.png"]');
          const time = Number(i.querySelectorAll('td')[1].textContent.trim());
          const progress = Number(i.querySelectorAll('td')[2].textContent.trim().replace('%', ''));
          const type = i.querySelectorAll('td')[3].textContent.trim();
          // 专题中需要判断是否已经完成,日常课程中为空值。专题必修有7列,选修有6列,少一列考试按钮
          const isFinished = i
            .querySelectorAll('td')
            [i.querySelectorAll('td').length - 1].textContent.trim();
          const parameters = imgXuexi.getAttribute('onclick').split("'");
          // userId=ONU034375&courseId=TOC002908&typeId=11
          const courseId = parameters[3];

          if (progress >= 90) {
            /**
             * 常规课程进度超过90%的必修课程就是等待考试的课程。
             * 理论上说进度超过90%的选修课应当自动消失,
             * 但如果还存在,就会自动点击考试按钮,提示“暂无相关考试”而阻塞。
             * 此时刷新iframe或者main frame可以解决绝大多数问题,
             * 但有例外情形如:
             * 《刑法修正案(十一)》安全生产的法条解读(三)
             * 无论如何刷新,进度到了100%就一直存在。
             * 如果选择跳过继续执行循环,可能在继续选课时自动跳回学习该课程,导致死循环。
             * 因此与flash课程一样对待列入黑名单可能是最安全的处理方式。
             */
            if (location.pathname === '/elms/web/listMyCourses.action') {
              if (type === '选修') {
                i.style.backgroundColor = 'grey';
                localStorage.setItem(courseId, 'flash');
                flashCourse.push(i);
              } else {
                examCourse.push(i);
              }
            } else {
              if (
                /**
                 * 专题页面中已完成课程会保留
                 * 但也有特殊情况会有选修课进度超过90%但无法正确判断是否完成
                 * 因此需要确认课程类型为必修方可列入待考课程否则可能造成阻塞
                 * 大多学满100%即可正常判断为已完成
                 */
                isFinished === '未完成'
              ) {
                if (type === '必修') {
                  examCourse.push(i);
                } else if (progress < 100) {
                  greatCourse.push(i);
                  progressCourse.push(time * (1 - progress / 100));
                }
              }
            }
          } else if (localStorage.getItem(courseId) === 'flash') {
            // 标记flash课程
            i.style.backgroundColor = 'grey';
            flashCourse.push(i);
          } else {
            greatCourse.push(i);
            progressCourse.push(time * (1 - progress / 100));
          }
        }
        GM_notification(`
        待考试课程数量:${examCourse.length}
        Flash课程数量:${flashCourse.length}
        待学习课程数量:${greatCourse.length}
        `);
        // 分类处理
        if (examCourse.length > 0) {
          // GM_notification(`首个待考:${examCourse[0].textContent.trim().split(/\s/)[0]}`);
          // 先考试
          examCourse[0].querySelector('button').click();
          const autoExam = setInterval(() => {
            if (document.getElementById('toCourseExam')) {
              clearInterval(autoExam);
              // javascript:openUrl('getExamPaper.action?paperId=1329&cId=10019&autoDel=0&random=2&attemptLimit=0&paperType=1&md5Str=8c50308878897d68a89a683954cc39a8&clazzId=93');
              const examSearch = document
                .getElementById('toCourseExam')
                .getAttribute('onclick')
                .split("'")[1];
              // console.debug(examSearch);
              let examPage = '';
              if (location.pathname === '/elms/web/listMyCourses.action') {
                examPage = `//www.jsce.gov.cn/elms/web/${examSearch}`;
              } else {
                examPage = `//www.jsce.gov.cn/elms/web/university/clazz/${examSearch}`;
              }
              const autoOpenExam = GM_openInTab(examPage);
              autoOpenExam.onclose = () => location.reload();
            }
          }, 1000);
        } else if (flashCourse.length > 0) {
          // 再删除flash课程
          flashCourse[0].querySelector('a[onclick^="javascript:removeCourse"]').click();
          setInterval(() => {
            if (document.querySelector('button[onclick="removeCourseSubmit();"]')) {
              document.querySelector('button[onclick="removeCourseSubmit();"]').click();
            }
          }, 1000);
        } else if (greatCourse.length > 0) {
          // 获取最小可以完成的时间
          const minLastProgress = Math.min(...progressCourse);
          // console.debug(minLastProgress);
          // 最后继续听课
          const getUrlFunc = (g) => {
            const parameters = g
              .querySelector('img[src="/elms/web/images/xxzx/xuexi.png"]')
              .getAttribute('onclick')
              .split("'");
            const userId = parameters[1];
            const courseId = parameters[3];
            const typeId = parameters[5];
            const courseURL = `//www.jsce.gov.cn/elms/web/viewScormCourse.action?userId=${userId}&courseId=${courseId}&typeId=${typeId}`;
            // console.debug(courseURL);
            return courseURL;
          };
          const closeTimeout = minLastProgress * 60 * 60 * 1000;
          // console.debug(closeTimeout);
          const parentTabFunc = () => {
            // 对顶层frame刷新,避免登录过期
            window.top.postMessage('reload main frame', '*');
          };
          // 一次性批量打开待学习课程
          multiOpenCloseTabs(greatCourse, getUrlFunc, true, closeTimeout, parentTabFunc, maxTimes);
        } else if (greatCourse.length === 0) {
          // 专题必修课已全部完成则跳转到专题选修课
          if (
            location.pathname.startsWith('/elms/web/university/clazz/listMyClazzCourses!') &&
            location.search === '?courseNature=2'
          ) {
            window.top.postMessage('switch to clazz select', '*');
          }
        }
      }, 1000);
    };
    if (location.pathname === '/elms/web/listMyCourses.action') {
      // 常规任务
      if (sessionStorage.getItem('nomal_assessment') === '通过') {
        return;
      }
      // 从最近学习课程切换到最近选择课程
      if (location.search === '?num=2') {
        window.top.postMessage('switch to zjtj', '*');
        return;
      } else if (document.querySelectorAll('tr[align="center"]').length === 1) {
        // 常规任务已选课程已经完成
        sessionStorage.setItem('checkFlash', 'end');
        // console.debug(sessionStorage.getItem('checkFlash'));
        window.top.postMessage('switch to select course', '*');
      } else {
        // 一次性批量打开常规课程以10个为限
        autoOpenCourses(10);
      }
    } else {
      // 专题学习
      if (
        sessionStorage.getItem('clazz_assessment') === 'finished' ||
        sessionStorage.getItem('clazz_xuanxiu') === 'finished'
      ) {
        return;
      } else if (!sessionStorage.getItem('listMyClazzCourses')) {
        sessionStorage.setItem('listMyClazzCourses', 'true');
        return;
      } else {
        // 一次性批量打开专题课程以5个为限,因为专题选修一般只要修满5分即可
        autoOpenCourses(5);
      }
    }
  }

  /**
   * http://www.jsce.gov.cn/elms/web/getExamPaper.action?paperId=873&cId=5621&autoDel=0&random=2&attemptLimit=0&paperType=1&md5Str=22ac73f0c1d64d332f0e5afe4c91f21a
   * http://www.jsce.gov.cn/elms/web/university/clazz/getExamPaper.action?paperId=1219&cId=8855&autoDel=0&random=2&attemptLimit=0&paperType=1&md5Str=f0293f8f2a5028d3d5c0ff0ea9f294a7&clazzId=38
   * 考试iframe
   * http://www.jsce.gov.cn/elms/web/getExamPaperQuestion.action?paperId=873&random=2&clazzId=null
   * http://www.jsce.gov.cn/elms/web/university/clazz/getExamPaperQuestion.action?paperId=1219&random=2&clazzId=38
   */
  if (location.pathname.endsWith('/getExamPaperQuestion.action')) {
    // 交卷 confirm 弹出
    unsafeWindow.confirm = (message) => {
      // GM_notification(message);
      return true;
    };
    const paperId = location.search.split('?')[1].split('paperId=')[1].split('&')[0];
    const clazzId = location.search.split('?')[1].split('clazzId=')[1];
    const questions = document.querySelectorAll('a.title_1');
    let hasAnswers = 0;
    for (i = 0; i < questions.length; i++) {
      const question_text = questions[i].textContent.trim();
      const queestion_index = question_text.indexOf('、');
      const real_question = question_text.slice(queestion_index + 1);
      localStorage.getItem(real_question) ? hasAnswers++ : 0;
      const this_question_answers = document
        .querySelectorAll('table.areaborder')
        [i].querySelectorAll(`input`);
      for (let a of this_question_answers) {
        this_answer_text = a.parentNode.textContent.trim();
        if (localStorage.getItem(`${real_question}#${this_answer_text}`)) {
          a.click();
        }
      }
      console.debug(hasAnswers / questions.length);
      if (hasAnswers / questions.length >= 0.8) {
        // 交卷函数
        confirmSubmit();
        // window.close();
      } else {
        const getAnswer = async () => {
          const option = {
            headers: {
              'Content-Type': 'application/x-www-form-urlencoded',
            },
            body: `paperId=${paperId}&random=2&clazzId=${clazzId}`,
            method: 'POST',
          };
          // 先执行会导致提交试卷时404,因此上面的if块不能放在异步函数中
          const elements = await fetchElements(
            `//www.jsce.gov.cn/elms/web/paperQuestionTempSave.action?checkType=submitExam`,
            option
          );
          // 虽然每次题目随机,但获取到的题目和答案顺序与本次一致,无需特别匹配处理
          const QAs = elements.querySelectorAll('table[id="tb_nojudge"]');
          // console.debug(QAs);
          for (i = 0; i < QAs.length; i++) {
            const q = QAs[i].querySelector('table').textContent.split('得分')[0].trim();
            // 去除每次随机生成的不同序号获取真正的题干
            const q_index = q.indexOf('、');
            const this_question = q.slice(q_index + 1);
            console.debug(this_question);
            // 正确选项的序号
            const a_index = QAs[i]
              .querySelectorAll('table')[1]
              .textContent.trim()
              .split('正确答案:')[1]
              .split('');
            for (let a of a_index) {
              // 通过序号获取正确选项的内容
              const this_answer = document
                .querySelectorAll('table.areaborder')
                [i].querySelector(`input[value="${a}"]`)
                .parentNode.textContent.trim();
              // console.info(this_question, a_index, this_answer);
              localStorage.setItem(this_question, 1);
              localStorage.setItem(`${this_question}#${this_answer}`, 1);
            }
          }
          // iframe刷新不能实现,干脆关闭页面重新打开实现刷新
          window.close();
        };
        getAnswer();
      }
    }
  }
  /**
   * 自动关闭必修课程结束考试的页面
   * //www.jsce.gov.cn/elms/web/university/clazz/paperQuestionTempSave.action?checkType=submitExam
   * //www.jsce.gov.cn/elms/web/university/clazz/saveExamResult.action?checkType=submitExam
   */
  if (
    location.href.endsWith('.action?checkType=submitExam')
    // 404 报错可能造成阻塞,一般关闭重来一次能解决问题,但也有陷入无限循环的可能
    // && document.querySelector('img').src !== 'http://www.jsce.gov.cn/elms/error/404.jpg'
  ) {
    window.close();
  }
}

if (location.host === 'course.jsce.gov.cn') {
  // 必修课程中答题正确答案用 alert 弹出
  unsafeWindow.alert = (message) => {
    console.debug(message);
  };

  const autoLearn = () => {
    /**
     * iframe 内无法直接判断 courseId
     * 部分课程也无法判断 title 如
     * http://www.jsce.gov.cn/elms/web/viewScormCourse.action?userId=ONU034375&courseId=guochen356704618&typeId=11
     * 故用信息传输到 top 来记录存储 courseId 比较现实
     * 部分页面可能需要反复判断才会生效:
     * http://www.jsce.gov.cn/elms/web/viewScormCourse.action?userId=ONU041481&courseId=guochen280903299&typeId=11
     * http://www.jsce.gov.cn/elms/web/viewScormCourse.action?userId=ONU041481&courseId=guochen217502312&typeId=11
     */
    if (
      document.getElementById('flashObj') ||
      (document.getElementById('player') &&
        document.getElementById('player').textContent.includes('flash'))
    ) {
      window.top.postMessage('pass this course', '*');
    }

    // 进入课程
    // http://course.jsce.gov.cn/ScormCourse/ZJSP/X822/study.html
    if (
      document.getElementById('initPanel') &&
      document.getElementById('initPanel').style.display !== 'none' &&
      document.getElementById('continueStudyButton')
    ) {
      // console.debug('try continueStudyButton');
      document.getElementById('continueStudyButton').click();
      // console.debug('continueStudyButton');
    }
    // http://course.jsce.gov.cn/ScormCourse/GJXZXY/031117021/index.htm
    if (document.getElementsByClassName('img2').length === 1) {
      // console.debug('try img2');
      document.getElementsByClassName('img2')[0].click();
      // console.debug('img2');
    }
    if (document.getElementsByClassName('learn').length === 1) {
      // console.debug('try learn');
      document.getElementsByClassName('learn')[0].click();
      // console.debug('learn');
    }

    // http://www.jsce.gov.cn/elms/web/viewScormCourse.action?userId=S51981&courseId=hguochen4988&typeId=11
    if (
      document.getElementsByClassName('cover').length > 0 &&
      document.getElementsByClassName('cover')[0].style.display !== 'none'
    ) {
      document.querySelector('button.continue-study').click();
    }
    if (
      document.getElementsByClassName('continue').length === 1 &&
      document.getElementsByClassName('continue')[0].style.display !== 'none'
    ) {
      // 自动开始学习
      // console.debug('try user_choise');
      document.getElementsByClassName('user_choise')[0].click();
      // console.debug('user_choise');
    }
    if (document.getElementById('confirm')) {
      // console.debug('try confirm');
      document.getElementById('confirm').click();
      // console.debug('confirm');
    } else {
      // console.debug('#confirm is ' + document.getElementById('confirm'));
    }

    /**
     * 静音以自动播放:
     * #course_player
     * http://www.jsce.gov.cn/elms/web/viewScormCourse.action?userId=ONU034375&courseId=ORG-291A3885A80D95B583EC60591EBE4B8A02274&typeId=11
     *
     * #media1_video
     * http://www.jsce.gov.cn/elms/web/viewScormCourse.action?userId=ONU034375&courseId=TOC002908&typeId=11
     *
     * #media1 #media2
     * http://www.jsce.gov.cn/elms/web/viewScormCourse.action?userId=S51981&courseId=zjw1417&typeId=11
     *
     * container_media
     * http://www.jsce.gov.cn/elms/web/viewScormCourse.action?userId=ONU041481&courseId=guochen4171&typeId=11
     *
     * jwvideo
     * http://www.jsce.gov.cn/elms/web/viewScormCourse.action?userId=S51981&courseId=hguochen4988&typeId=11
     */
    // 不判断条件后赋值,若元素不存在就会报错
    let course_player = '';
    let media1_video = '';
    let media1 = '';
    let media2 = '';
    let container_media = '';
    let jwvideo = '';
    if (document.getElementById('course_player')) {
      course_player = document.getElementById('course_player');
      course_player.muted = true;
      course_player.play();
    } else if (document.getElementById('media1_video')) {
      media1_video = document.getElementById('media1_video');
      media1_video.muted = true;
      media1_video.play();
    } else if (document.getElementById('media1')) {
      media1 = document.getElementById('media1');
      media1.muted = true;
      media1.play();
    } else if (document.getElementById('media2')) {
      media2 = document.getElementById('media2');
      media2.muted = true;
      media2.play();
    } else if (
      document.getElementById('content') &&
      document.getElementById('content').contentDocument.querySelector('video')
    ) {
      container_media = document.getElementById('content').contentDocument.querySelector('video');
      container_media.muted = true;
      container_media.play();
    } else if (document.querySelector('.jwvideo video')) {
      jwvideo = document.querySelector('.jwvideo video');
      jwvideo.muted = true;
      jwvideo.play();
    } else {
      // console.debug('all players are null');
    }

    // sessionStorage 尝试用于保证只执行一次
    if (!sessionStorage.getItem('active this tab')) {
      if (course_player || media1_video || media1 || media2 || container_media || jwvideo) {
        window.top.postMessage('active this tab', '*');
        sessionStorage.setItem('active this tab', true);
      }
    }

    // 必修课程中答题
    if (
      document.getElementById('testPanel') &&
      document.getElementById('testPanel').style.display !== 'none'
    ) {
      const tests = document.querySelectorAll('#testPanel div.testContent');
      if (tests.length > 1) {
        tests[0].click();
        tests[1].click();
        document.getElementById('checkAnswer0').click();
        document.getElementsByClassName('exitTestButton')[0].click();
      }
    }
    /**
     * 答案错误不给通过
     * http://www.jsce.gov.cn/elms/web/viewScormCourse.action?userId=S51981&courseId=hguochen4988&typeId=11
     * http://www.jsce.gov.cn/elms/web/viewScormCourse.action?userId=ONU041481&courseId=hguochen5197&typeId=11
     * http://www.jsce.gov.cn/elms/web/viewScormCourse.action?userId=ONU041481&courseId=hguochen5204&typeId=11
     */
    if (
      document.getElementById('questionsList') &&
      document.getElementById('questionsList').style.display !== 'none'
    ) {
      const questionNow = document.querySelector('#questionsList li.dis_block');
      const questionId = questionNow.getAttribute('id');
      const questionIndex = questionId.replace('ques_', '');
      const answer = questionNow.querySelector('span.error').textContent.split(':')[1].split('');
      // console.debug(answer);
      for (let a of answer) {
        document.getElementById(`ques_${questionIndex}${a}`).click();
      }
      questionNow.querySelector('input[type="button"][value="提交"]').click();
    }
    // http://www.jsce.gov.cn/elms/web/viewScormCourse.action?userId=ONU034375&courseId=ORG-291A3885A80D95B583EC60591EBE4B8A02274&typeId=11
    if (
      document.querySelector('div.relaxing') &&
      document.querySelector('div.relaxing').style.display === 'block'
    ) {
      const ques = document.querySelectorAll('input[name="que"]');
      for (let q of ques) {
        q.click();
      }
      if (document.querySelector('div.button')) {
        // 提交
        document.querySelector('div.button').click();
      } else if (document.querySelector('div.button_xia')) {
        // 下一题
        document.querySelector('div.button_xia').click();
      } else if (document.querySelector('div.button_wan')) {
        // 完成
        document.querySelector('div.button_wan').click();
      }
    }
  };
  setInterval(autoLearn, 1000);
}