feat: exporteren van vers-gegenereerde wachtwoorden als CSV (v0.4.30-beta)
All checks were successful
dev - build & deploy naar test / build-and-deploy (push) Successful in 38s
All checks were successful
dev - build & deploy naar test / build-and-deploy (push) Successful in 38s
- "Exporteer als CSV"-knop toegevoegd aan het bestaande multireset- resultatenscherm (klas-wachtwoorden resetten in de School-navigator), naast de bestaande "kopieer alles"-knop. - BELANGRIJKE BEPERKING, bewust zo: dit exporteert alleen wat op dit scherm al staat (net-gegenereerde wachtwoorden). Wachtwoorden worden na het zetten nergens leesbaar bewaard (alleen gehashet in de database) - er is dus geen "haal wachtwoorden van bestaande accounts op"-mogelijkheid en die komt er ook niet. - CSV bevat gebruikersnaam (het echte inlogveld) naast de naam, ook al toont het scherm zelf alleen de naam - zonder gebruikersnaam is een uitdeelvel niet bruikbaar om mee in te loggen. - Hergebruikt de csvValue()/downloadCsv()-helpers uit de vorige resultaten-exportfeature (v0.4.29-beta) - eerste echte tweede gebruiker, dus die keuze om ze lokaal in admin.js te houden i.p.v. te verplaatsen was terecht. - Geverifieerd met de volledige testsuite (112/112) en een live browserdoorloop: klas-wachtwoorden resetten (dubbele bevestigingsklik) → CSV-download met correcte escaping van een leerlingnaam met komma én aanhalingsteken. Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_014EPxzBVRXZZnBPvSAaPAbJ
This commit is contained in:
parent
8fe6fc10cc
commit
4e4aeb4b6d
3 changed files with 20 additions and 2 deletions
2
VERSION
2
VERSION
|
|
@ -1 +1 @@
|
||||||
0.4.29-beta
|
0.4.30-beta
|
||||||
|
|
@ -615,6 +615,22 @@
|
||||||
copyAll.type = "button";
|
copyAll.type = "button";
|
||||||
copyAll.addEventListener("click", e=>{ e.preventDefault(); copyText(copyAll, all); });
|
copyAll.addEventListener("click", e=>{ e.preventDefault(); copyText(copyAll, all); });
|
||||||
box.appendChild(copyAll);
|
box.appendChild(copyAll);
|
||||||
|
/* export als uitdeelvel - alleen mogelijk zolang dit scherm openstaat: de
|
||||||
|
wachtwoorden zijn hierna nergens meer in leesbare vorm te achterhalen
|
||||||
|
(alleen het gehashte wachtwoord blijft in de database), dus dit is
|
||||||
|
bewust "exporteer wat nu net gegenereerd is", niet "haal wachtwoorden
|
||||||
|
van bestaande accounts op". Gebruikersnaam (het echte inlog-veld) staat
|
||||||
|
er wél bij, ook al toont de schermlijst hierboven alleen de naam. */
|
||||||
|
const exportBtn = h("button","am-btn", T("amExportCsv"));
|
||||||
|
exportBtn.type = "button";
|
||||||
|
exportBtn.addEventListener("click", e=>{
|
||||||
|
e.preventDefault();
|
||||||
|
const header = [T("amExportColPupil"), T("amExportColUsername"), T("amResultPw")];
|
||||||
|
const rows = [header, ...resetResults.entries.map(en=>[en.displayName, en.username, en.password])];
|
||||||
|
const safeName = resetResults.title.replace(/[^a-z0-9]+/gi, "-");
|
||||||
|
downloadCsv(`${safeName}.csv`, rows);
|
||||||
|
});
|
||||||
|
box.appendChild(exportBtn);
|
||||||
const list = h("div","am-reset-list");
|
const list = h("div","am-reset-list");
|
||||||
resetResults.entries.forEach(en=>{
|
resetResults.entries.forEach(en=>{
|
||||||
const row = h("div","am-reset-row");
|
const row = h("div","am-reset-row");
|
||||||
|
|
|
||||||
|
|
@ -2,7 +2,7 @@
|
||||||
"use strict";
|
"use strict";
|
||||||
/* version — shown until /api/version resolves (or if the fetch fails, e.g. offline).
|
/* version — shown until /api/version resolves (or if the fetch fails, e.g. offline).
|
||||||
Kept in sync by hand with the VERSION file at the repo root on every release. */
|
Kept in sync by hand with the VERSION file at the repo root on every release. */
|
||||||
const VERSION = "0.4.29-beta";
|
const VERSION = "0.4.30-beta";
|
||||||
(function(){
|
(function(){
|
||||||
const tag = document.getElementById("verTag");
|
const tag = document.getElementById("verTag");
|
||||||
tag.textContent = "v"+VERSION;
|
tag.textContent = "v"+VERSION;
|
||||||
|
|
@ -352,6 +352,7 @@ const I18N = {
|
||||||
amExportClass:"Exporteren per klas", amExportCsv:"Exporteer als CSV", amPickClassHint:"Kies eerst een klas.",
|
amExportClass:"Exporteren per klas", amExportCsv:"Exporteer als CSV", amPickClassHint:"Kies eerst een klas.",
|
||||||
amExportColPupil:"Leerling", amExportColWidget:"Widget", amExportColAttempts:"Pogingen",
|
amExportColPupil:"Leerling", amExportColWidget:"Widget", amExportColAttempts:"Pogingen",
|
||||||
amExportColCorrect:"Goed", amExportColStars:"Sterren", amExportColDate:"Datum",
|
amExportColCorrect:"Goed", amExportColStars:"Sterren", amExportColDate:"Datum",
|
||||||
|
amExportColUsername:"Gebruikersnaam",
|
||||||
amExportDone:"Export gedownload ✓",
|
amExportDone:"Export gedownload ✓",
|
||||||
amConfirmDel:"Weet je zeker dat je deze gebruiker wilt verwijderen?",
|
amConfirmDel:"Weet je zeker dat je deze gebruiker wilt verwijderen?",
|
||||||
amCopy:"kopieer", amCopyAll:"kopieer alles",
|
amCopy:"kopieer", amCopyAll:"kopieer alles",
|
||||||
|
|
@ -690,6 +691,7 @@ const I18N = {
|
||||||
amExportClass:"Export by class", amExportCsv:"Export as CSV", amPickClassHint:"Pick a class first.",
|
amExportClass:"Export by class", amExportCsv:"Export as CSV", amPickClassHint:"Pick a class first.",
|
||||||
amExportColPupil:"Pupil", amExportColWidget:"Widget", amExportColAttempts:"Attempts",
|
amExportColPupil:"Pupil", amExportColWidget:"Widget", amExportColAttempts:"Attempts",
|
||||||
amExportColCorrect:"Correct", amExportColStars:"Stars", amExportColDate:"Date",
|
amExportColCorrect:"Correct", amExportColStars:"Stars", amExportColDate:"Date",
|
||||||
|
amExportColUsername:"Username",
|
||||||
amExportDone:"Export downloaded ✓",
|
amExportDone:"Export downloaded ✓",
|
||||||
amConfirmDel:"Are you sure you want to delete this user?",
|
amConfirmDel:"Are you sure you want to delete this user?",
|
||||||
amCopy:"copy", amCopyAll:"copy all",
|
amCopy:"copy", amCopyAll:"copy all",
|
||||||
|
|
|
||||||
Loading…
Reference in a new issue