v13
This commit is contained in:
parent
cda49bbdad
commit
ef2c01f69f
2 changed files with 60 additions and 24 deletions
|
|
@ -269,6 +269,13 @@
|
|||
.legend h4{margin:0 0 8px;font-size:12px;text-transform:uppercase;letter-spacing:.5px;color:var(--muted)}
|
||||
.legend dt{font-weight:700;font-size:13px}
|
||||
.legend dd{margin:2px 0 8px;color:var(--muted);font-size:13px}
|
||||
.lgItem{padding:8px 0;border-top:1px solid var(--line)}
|
||||
.lgItem:first-of-type{border-top:0;padding-top:2px}
|
||||
.lgName{font-weight:700;font-size:13px;color:var(--ink)}
|
||||
.lgIdee{margin:2px 0 4px;font-size:13px;color:var(--ink)}
|
||||
.lgBed{margin:2px 0 4px;padding-left:18px;color:var(--muted);font-size:12px}
|
||||
.lgBed li{margin:1px 0}
|
||||
.lgBsp{font-size:12px;color:var(--muted)}
|
||||
.hint{font-weight:600;margin:8px 0}
|
||||
.hint.bad{color:var(--bad)} .hint.ok{color:var(--ok)}
|
||||
.phaseRow{display:grid;grid-template-columns:repeat(5,1fr);gap:8px;margin:14px 0}
|
||||
|
|
@ -399,12 +406,39 @@ const CHANGE_TYPES = [
|
|||
"Standard Change",
|
||||
"Emergency Change"
|
||||
];
|
||||
/* Legende-Inhalte, Index parallel zu CHANGE_TYPES (0 Major, 1 Normal, 2 Standard, 3 Emergency).
|
||||
Quelle: DIGITOM-Definitionen. Emergency wurde nicht mitgeliefert -> bestehende Beschreibung. */
|
||||
const CHANGE_LEGEND = [
|
||||
"Strategisch/grundlegend, braucht ein echtes Design — durchläuft den vollen Lebenszyklus ab dem Design. Freigabe in der SOR; reicht deren Ressourcen-/Entscheidungshoheit nicht, wird daraus ein Demand (Routing DPM → Mission Board).",
|
||||
"Geplant und dokumentiert, aber nicht strategisch — Einstieg an Gate 1 (Bauen oder Konfigurieren), meist Konfiguration.",
|
||||
"Vorab genehmigt und im Katalog hinterlegt — keine Gates, kein Design, direkt im laufenden Betrieb.",
|
||||
"Muss eine Störung sofort beheben — beschleunigt umgesetzt; die formale Freigabe erfolgt nachgelagert."
|
||||
{ idee:"Sonderform der Normal Change mit hohem Risiko, hohen Kosten oder breiter Auswirkung — höchste Eskalations- und Genehmigungsstufe.",
|
||||
bed:["Hohes Risiko und/oder hohe Kosten und/oder weitreichende Auswirkung (viele Nutzer/Services betroffen)",
|
||||
"Genehmigung oft durch erweitertes Gremium / Management / Lenkungsebene (nicht nur Standard-CAB)",
|
||||
"Vollständige Bewertung, Business Case, ausführliche Planung & Tests, Kommunikationsplan",
|
||||
"Häufig an Schwellenwerte gebunden (z. B. Kosten über X €, Ausfall kritischer Dienste)"],
|
||||
bsp:"Rechenzentrumsumzug, Austausch eines Kernsystems, organisationsweite Plattformmigration." },
|
||||
{ idee:"Der Regelfall für alles, was nicht vorab genehmigt ist und kein Notfall ist. Durchläuft den vollen Bewertungs- und Genehmigungsprozess.",
|
||||
bed:["RfC (Request for Change) wird erfasst",
|
||||
"Risiko- und Impact-Bewertung wird durchgeführt",
|
||||
"Genehmigung durch Change-Manager bzw. CAB (Change Advisory Board) vor Umsetzung",
|
||||
"Terminplanung (Scheduling), Test, ggf. Rollback-Plan",
|
||||
"Geringes bis mittleres Risiko (die hochriskanten landen bei „Major“)"],
|
||||
bsp:"Einführung einer neuen Software-Version, Konfigurationsänderung an einem produktiven System." },
|
||||
{ idee:"Routine. Vorab genehmigt, weil sie oft vorkommt, das Risiko bekannt und niedrig ist und der Ablauf dokumentiert ist.",
|
||||
bed:["Es existiert ein vorab freigegebenes Muster/Template für genau diese Änderung",
|
||||
"Geringes, bekanntes Risiko, Auswirkung vorhersehbar",
|
||||
"Wiederholbar, klar dokumentierter Ablauf",
|
||||
"Keine Einzelfall-Genehmigung durch CAB/Change-Manager nötig — die Autorisierung gilt generell"],
|
||||
bsp:"Standard-Passwort-Reset, Austausch eines defekten Standard-Geräts, Einspielen eines geprüften Routine-Patches." },
|
||||
{ idee:"Muss eine Störung sofort beheben — beschleunigt umgesetzt; die formale Freigabe erfolgt nachgelagert.",
|
||||
bed:["Akuter Notfall / drohender oder laufender Ausfall kritischer Dienste",
|
||||
"Beschleunigtes Verfahren (Emergency-CAB bzw. Notfall-Autorisierung)",
|
||||
"Umsetzung sofort — Dokumentation und formale Freigabe nachgelagert"],
|
||||
bsp:"Sofort-Sperrung einer kompromittierten VPN-Zertifikatskette, Notfall-Hotfix einer kritischen Sicherheitslücke." }
|
||||
];
|
||||
// Anzeige-Reihenfolge der Change-Arten (Indizes in CHANGE_TYPES): Standard, Emergency, Normal, Major
|
||||
const CT_ORDER = [2, 3, 1, 0];
|
||||
// Feste, EINMALIG gemischte Deck-Reihenfolge ([service, change]) — bei jedem Start gleich, nicht gruppiert.
|
||||
const DECK_ORDER = [[2,1],[0,3],[4,0],[1,2],[5,3],[3,0],[0,1],[2,3],[4,2],[1,0],[5,1],[3,2],
|
||||
[2,0],[0,2],[4,3],[1,3],[5,0],[3,1],[2,2],[0,0],[4,1],[1,1],[5,2],[3,3]];
|
||||
const USE_CASES = [
|
||||
{ service:"Zentrale VDI (Virtual-Desktop-Infrastructure)",
|
||||
desc:"Bereitstellung von virtuellen Windows-Desktops über das interne Rechenzentrum.",
|
||||
|
|
@ -1140,20 +1174,16 @@ function renderCardBadge(){
|
|||
|
||||
/* ---------- Schritt 1: Action Card ziehen (Raster aller Karten) ---------- */
|
||||
function renderDeck(){
|
||||
let grid = "";
|
||||
USE_CASES.forEach((u,si)=>{
|
||||
grid += `<div class="deckGroup"><div class="deckSvc">${u.service}</div><div class="deckRow">`;
|
||||
u.changes.forEach((c,ci)=>{
|
||||
grid += `<button class="deckCard" data-s="${si}" data-c="${ci}" title="${c.titel}">
|
||||
<img src="cards/s${si}-c${ci}.png" alt="${c.titel}" loading="lazy"></button>`;
|
||||
});
|
||||
grid += `</div></div>`;
|
||||
});
|
||||
const cards = DECK_ORDER.map(([si,ci])=>{
|
||||
const c = USE_CASES[si].changes[ci];
|
||||
return `<button class="deckCard" data-s="${si}" data-c="${ci}" title="${c.titel}">
|
||||
<img src="cards/s${si}-c${ci}.png" alt="${c.titel}" loading="lazy"></button>`;
|
||||
}).join("");
|
||||
$("#panel").innerHTML = `
|
||||
<div class="setupHead">Schritt 1 · Action Card ziehen</div>
|
||||
<h2 class="setupTitle">Welche Karte zieht ihr?</h2>
|
||||
<p class="muted">Tippt auf eine Action Card, um sie zu ziehen.</p>
|
||||
<div class="deck">${grid}</div>`;
|
||||
<h2 class="setupTitle">Welche Karte habt ihr gezogen?</h2>
|
||||
<p class="muted">Tippt auf die Action Card, die ihr gezogen habt.</p>
|
||||
<div class="deck"><div class="deckRow">${cards}</div></div>`;
|
||||
$("#panel").querySelectorAll(".deckCard").forEach(el=>{
|
||||
el.onclick=()=>{ S.service=+el.dataset.s; S.change=+el.dataset.c;
|
||||
S.classifyDone=false; S.classifyWrong=null; S.entryDone=false; S.entryWrong=null;
|
||||
|
|
@ -1167,10 +1197,15 @@ function renderClassify(){
|
|||
const card = acard(S.service,S.change);
|
||||
const cardBig = `<img class="classifyCard" src="cards/s${S.service}-c${S.change}.png" alt="${card.titel}">`;
|
||||
if(!S.classifyDone){
|
||||
const choices = CHANGE_TYPES.map((t,i)=>
|
||||
`<button class="choice ${S.classifyWrong===i?'bad':''}" data-i="${i}">${t}</button>`).join("");
|
||||
const legend = `<div class="legend"><h4>Legende — Change-Arten</h4><dl>` +
|
||||
CHANGE_TYPES.map((t,i)=>`<dt>${t}</dt><dd>${CHANGE_LEGEND[i]}</dd>`).join("") + `</dl></div>`;
|
||||
const choices = CT_ORDER.map(i=>
|
||||
`<button class="choice ${S.classifyWrong===i?'bad':''}" data-i="${i}">${CHANGE_TYPES[i]}</button>`).join("");
|
||||
const legend = `<div class="legend"><h4>Legende: Change-Arten im DIGITOM</h4>` +
|
||||
CT_ORDER.map(i=>{ const L = CHANGE_LEGEND[i];
|
||||
return `<div class="lgItem"><div class="lgName">${CHANGE_TYPES[i]}</div>`
|
||||
+ `<div class="lgIdee">${L.idee}</div>`
|
||||
+ `<ul class="lgBed">${L.bed.map(b=>`<li>${b}</li>`).join("")}</ul>`
|
||||
+ `<div class="lgBsp"><b>Beispiel:</b> ${L.bsp}</div></div>`;
|
||||
}).join("") + `</div>`;
|
||||
const hint = S.classifyWrong!=null
|
||||
? `<div class="hint bad">Nicht ganz — überlegt nochmal und probiert es erneut.</div>` : ``;
|
||||
$("#panel").innerHTML = `
|
||||
|
|
@ -1178,11 +1213,11 @@ function renderClassify(){
|
|||
<div class="classifyTop">
|
||||
${cardBig}
|
||||
<div class="classifyMain">
|
||||
<h2 class="setupTitle" style="margin-top:0">Welche Art von Change ist das?</h2>
|
||||
<h2 class="setupTitle" style="margin-top:0">Welche Art von Change könnte das sein?</h2>
|
||||
<p class="muted">Überlegt gemeinsam und wählt die passende Change-Art. Die Legende hilft beim Einordnen.</p>
|
||||
${legend}
|
||||
${hint}
|
||||
<div class="choiceGrid grid2">${choices}</div>
|
||||
${legend}
|
||||
</div>
|
||||
</div>
|
||||
<div class="actions"><button class="ghost" id="backDeck">← Andere Karte</button></div>`;
|
||||
|
|
@ -1200,7 +1235,8 @@ function renderClassify(){
|
|||
<div class="classifyMain">
|
||||
<div class="hint ok">✓ Richtig: ${CHANGE_TYPES[correct]}</div>
|
||||
<div class="recBox"><h4>Warum?</h4>
|
||||
<p style="margin:0;color:var(--muted)">${CHANGE_LEGEND[correct]}</p></div>
|
||||
<p style="margin:0 0 6px;color:var(--muted)">${CHANGE_LEGEND[correct].idee}</p>
|
||||
<p style="margin:0;color:var(--muted)"><b>Beispiel:</b> ${CHANGE_LEGEND[correct].bsp}</p></div>
|
||||
</div>
|
||||
</div>
|
||||
<div class="actions">
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue