$(()=>{ const ENDPOINT_URL = "https://school.one-way.dev/chtm/tableExporter/api~lesson-viewed"; const STORAGE_PREFIX = 'tableExporter.lessonViewed.v1'; function isLessonPage() { const href = window.location.href || ''; return href.includes('/lesson/view') || href.includes('/lesson/webview'); } function extractPageID() { let pageID = null; const searchParams = new URLSearchParams(window.location.search); if (searchParams.has('id')) { pageID = parseInt(searchParams.get('id'), 10); if (!isNaN(pageID)) return pageID; } const pathMatch = window.location.pathname.match(/(\\d+)/); if (pathMatch && pathMatch[1]) { pageID = parseInt(pathMatch[1], 10); if (!isNaN(pageID)) return pageID; } const hrefMatch = (window.location.href || '').match(/[\\?&]id=(\\d+)/); if (hrefMatch && hrefMatch[1]) { pageID = parseInt(hrefMatch[1], 10); if (!isNaN(pageID)) return pageID; } return null; } function getGcUserId() { try { const ui = window.userInfo || {}; const candidates = [ui.id, ui.userId, ui.user_id, ui.gcId, ui.gc_id, window.accountUserId]; for (const c of candidates) { const n = Number(c); if (!isNaN(n) && n > 0) return n; } } catch (e) {} return null; } async function sendViewed(gcId, lessonId) { try { await fetch(ENDPOINT_URL, { method: 'POST', credentials: 'include', headers: { 'Content-Type': 'application/json' }, body: JSON.stringify({ gcId, lessonId }) }); } catch (e) { // noop } } if (!isLessonPage()) return; const lessonId = extractPageID(); const gcId = getGcUserId(); if (!lessonId || !gcId) return; const key = STORAGE_PREFIX + '.' + gcId + '.' + lessonId; try { if (localStorage.getItem(key)) return; localStorage.setItem(key, String(Date.now())); } catch (e) {} sendViewed(gcId, lessonId); });