Автор скрипта @OlegROA

Дисклеймер публикации

Я не против. Но не обещаю их поддерживать из-за недостатка свободного времени. На правах "as is".OlegROA

Не забывайте читать комментарии внутри скрипта!

Сам скрипт: Браузерный скрипт пропущенных ДЗ с журналами

 

Список уроков без ДЗ в указанном интервале дат

Список уроков без ДЗ в указанном интервале дат для указанных учителей или для всех учителей.
В данный список будут включены уроки, на которые не задано ДЗ явно или не поставлена метка «Без ДЗ».

1. ОБЯЗАТЕЛЬНО заходите в старую админку, на любую страницу.
2. Открываете в браузере панель инструментов разработчика.
3. Переходите на закладку Консоль.
4. Открываете файл со скриптом и копируете все его содержимое в окно консоли (в ФайрФоксе возможно придется подтвердить вставку кода ручным вводом указанной фразы).
5. Проверяете начальные параметры — код учебного года, интервал дат, список учителей.
6. Жмете Enter. В зависимости от браузера или будет предложено сохранить csv-файл или он автоматически будет сохранен в папку «Загрузки».
Наименование файла — «Без ДЗ (ГГГГ-ММ-ДД — ГГГГ-ММ-ДД).csv».
Сортировка по ФИО учителя, дате, номеру урока.
Кодировка текста в файле «Windows-1251», так что его сразу можно открывать в Excel и сортировать/фильтровать по нужным критериям.

 

Как просто узнать ИД нужных учителей:

1. Заходите в справочник кадров и открываете карточку нужного учителя.
2. Кликаете мышкой в адресную строку браузера и видите число в конце адреса — это и есть ИД учителя.

var year_id = 13; // Идентификатор учебного года (2025-2026)

// Основные параметры
// Список (через запятую) ИД проверяемых учителей.
// Если список пустой - проверка по всем учителям.
var th_ids     = [];
var date_start = "2025-09-16"; // Начало интервала дат (обязательно с ведущим нулём!)
var date_end   = "2025-09-16"; // Конец интервала дат (обязательно с ведущим нулём!)
// Если date_start не указана (date_start = ""), то будет принята текущая дата
//   а для date_end будет принята завтрашняя дата.
// Если date_start указана, но не указана date_end (date_end = ""), то для date_end
//   будет принята дата date_start + 1 день.

// Глобальные переменные
var no_dz = [];

(async () => {
  // Функция преобразования текста из кодировки UTF-8
  // в кодовый массив Windows-1251
  async function toWin(s){
    let code = [];
    for(let i = 0; i < s.length; i++){
      let c = s.charCodeAt(i);
      if (c == 0x401){
         code.push(0xA8);
      } else if (c == 0x451){
         code.push(0xB8);
      } else if (c < 0x410){
         code.push(c);
      } else {
         code.push(c - 848);
      };
    };
    return (new Uint8Array(code));
  };

  // Функция чтения одной страницы данных в формате JSON
  async function fetchOne(url) {
    const res = await fetch(url);
    const json = await res.json();
    return(json);
  };

  // Функция чтения всех страниц данных в формате JSON
  async function fetchAll(url, pagesProp="x-pagination-total-pages") {
    if (url.indexOf("?") == -1){
       url += "?per_page=1000";
    } else {
       url += "&per_page=1000";
    }
    let recs = [];
    let page = 0, pages = 0;
    while (true){
      page += 1;
      const res = await fetch(url +"&page="+ page);
      const hdr = await res.headers;
      recs.push(...(await res.json()));

      pages = hdr.get(pagesProp);
      if (!pages || (page >= pages)){break};
    };
    return(recs);
  };

  if (!th_ids || !th_ids.length){
     // Если список учителей пустой - формируем словарь всех учителей
     let th = await fetchAll("core/api/teacher_profiles");
     for(let i = 0; i < th.length; i++){
       th_ids.push(th[i].id);
     };
  };

  if (!date_start){
     date_start = (new Date()).toISOString().slice(0, 10);
     date_end = "";
  };
  if (!date_end){
     date_end = (new Date((new Date(date_start))
                          .getTime() + 24*60*60*1000)).toISOString().slice(0, 10);
  };

  // Основной цикл - обход учителей
  let sch_dates = "&from="+ date_start +"&to="+ date_end;
  let hw_dates = "&begin_date="+ date_start.split("-").reverse().join(".") +
                 "&end_date="+ date_end.split("-").reverse().join(".");
  for (let th of th_ids){
    // Словарь меток "Без ДЗ" учителя
    let dz_mark = new Map();

    // Читаем расписание учителя
    let sch = await fetchAll("jersey/api/schedule_items?academic_year_id="+ year_id +
                             "&teacher_id="+ th + sch_dates +
                             "&with_lesson_info=true&with_group_class_subject_info=true");
    if (!sch || !sch.length){continue};

    console.log(sch[0].teacher_name || "???");
    for (let ls of sch){
      if ((ls.homeworks_to_verify || []).length){continue};

      // Явного ДЗ на данный урок нет, проверяем наличие метки "Без ДЗ"
      marks = dz_mark.get(ls.group_id)
      if (marks === undefined){
         // Для данной группы еще не запрашивали метки "Без ДЗ"
         marks = [];
         let hw_abs = await fetchAll("core/api/homework_absences?group_id="+ ls.group_id + hw_dates);
         for (let mark of hw_abs){
           marks.push(mark.date.split(".").reverse().map(Number).join("-"));
         };
         dz_mark.set(ls.group_id, marks);
      };

      if (!marks.includes(ls.date.join("-"))){
         no_dz.push((ls.teacher_name || "???") +";"+ 
                     ls.date[0] +"-"+ ("0"+ls.date[1]).substr(-2) +"-"+ ("0"+ls.date[2]).substr(-2) +";"+ 
                     ls.study_ordinal +";"+ ls.class_unit_name +";"+ ls.subject_name +";"+ ls.group_name + ";" + "https://school.mos.ru/teacher/study-process/journal/grade/" + ls.group_id +"?scheduleItemId="+ ls.id);
      };
    };
  };

  if (!no_dz.length){
     console.log("Нет уроков без ДЗ!");
  } else {
     no_dz.sort();
     let csv = "ФИО учителя;Дата урока;Урок;Класс;Предмет;Группа;Журнал\n"+ no_dz.join("\n");
     
     // Создание файла формата CSV в кодировке Windows-1251
     // и сохранение его браузером
     const link = document.createElement("a");
     const file = new Blob([await toWin(csv)], {type:'text/csv'});
     link.href = URL.createObjectURL(file);
     link.download = "Без ДЗ ("+ date_start +" - "+ date_end +").csv";
     link.click();
     URL.revokeObjectURL(link.href);
     
     console.log("Всего уроков без ДЗ: "+ no_dz.length);
  };
})()

 


Добавить комментарий

Ваш адрес email не будет опубликован. Обязательные поля помечены *