import { getCourseId, getUserIconUrl, getCourseParticipantsUrl } from "./utils-ENV.js"; import { fetchGraduation } from "./graduation-common.js"; /** * Class to represent Students. */ class Student { graduation = null; constructor(id, name, group) { this.id = id; this.name = name; this.group = group; } async getIconUrl() { return await getUserIconUrl(this.id); } getGroup() { return this.group; } async getGraduation() { if(!this.graduation) { // fetchGraduation(this) sets this.graduation await fetchGraduation(this); } return this.graduation; } static async fetchById(id) { let name = ""; let group = ""; const res = await fetch(`/user/view.php?id=${id}&course=${getCourseId()}`); const doc = new DOMParser().parseFromString(await res.text(), "text/html"); name = doc.querySelector("div.page-header-headings > h2").textContent; const cards = doc.querySelectorAll("div.card-body dl"); for (const card of cards) { if (card.querySelector("dt").textContent !== "Gruppe") continue; group = card.querySelector("dd > a").textContent; break; } return new Student(id, name, group); } } // Cache the fetched students. let students = []; const idRegex = /id=(\d+)/; async function _fetchStudents() { const res = await fetch(getCourseParticipantsUrl()); const doc = new DOMParser().parseFromString(await res.text(), "text/html"); const table = doc.querySelector("tbody"); let fetchedStudents = []; table.querySelectorAll("tr").forEach(row => { if (row.classList.contains("emptyrow")) return; const roleCell = row.querySelector(".c4"); // TODO(muhq): Is this locale dependent? if (roleCell.innerHTML.includes("Lehrer")) { return; } const nameCell = row.querySelector(".c1"); let name; if (nameCell.firstChild.firstChild.tagName == "SPAN") name = nameCell.firstChild.firstChild.title; else name = nameCell.innerText; const profileUrl = nameCell.querySelector("a.aabtn").href; const match = idRegex.exec(profileUrl); const id = match[1]; const groupCell = row.querySelector(".c5"); const group = groupCell.querySelector("a.quickeditlink").textContent; fetchedStudents.push(new Student(id, name, group)); }); return fetchedStudents; } async function fetchStudents(idFilter, nameFilter, groupFilter) { if (!students.size) { const studentsPromise = _fetchStudents() const storedStudents = localStorage.getItem("students"); if (storedStudents) { studentsPromise.then((fetched) => localStorage.setItem("students", JSON.stringify(fetched))); for (const o of JSON.parse(storedStudents)) { students.push(new Student(o.id, o.name, o.group)); } } else { students = await studentsPromise; localStorage.setItem("students", JSON.stringify(students)); } } return students.filter((s) => (!idFilter || s.id === idFilter) && (!nameFilter || s.name.includes(nameFilter)) && (!groupFilter || s.group.includes(groupFilter))); } async function fetchStudent(idFilter, nameFilter, groupFilter) { const students = await fetchStudents(idFilter, nameFilter, groupFilter); return students[0]; } export { Student, fetchStudents, fetchStudent };