Compare commits

..
Author SHA1 Message Date
jarvis-at-skic 9ac6e2bc6f Merge pull request 'docs: concrete workflow and skill metrics on slide 14' (#46) from docs/slide14-concrete-metrics into main
Build and publish Eldorado documentation / build (push) Successful in 44s
2026-10-09 00:13:50 -07:00
jarvis-at-skic 946b6f1cbb docs: give slide 14 concrete workflow and skill metrics
Build and publish Eldorado documentation / build (pull_request) Successful in 46s
2026-10-09 07:08:51 +00:00
jarvis-at-skic accca0cb1f Merge pull request 'fix: clarify slide 13 weekly allocation' (#45) from fix/slide13-weekly-allocation into main
Build and publish Eldorado documentation / build (push) Successful in 48s
2026-10-08 23:54:18 -07:00
jarvis-at-skic b33b59659c fix: label slide 13 as an example weekly allocation
Build and publish Eldorado documentation / build (pull_request) Successful in 47s
2026-10-09 06:49:30 +00:00
jarvis-at-skic 86b1c769a3 Merge pull request 'fix: refine presentation slides 2, 5 and 7' (#44) from fix/slide-2-headings into main
Build and publish Eldorado documentation / build (push) Successful in 46s
2026-10-08 23:37:45 -07:00
5 changed files with 56 additions and 7 deletions

No files matched your search

@@ -172,7 +172,7 @@ export const slides = [
"id": "capacity", "id": "capacity",
"title": "One architect. One active live pilot.", "title": "One architect. One active live pilot.",
"minutes": 1, "minutes": 1,
"body": "<div class=\"capacity\" aria-label=\"Proposed weekly allocation: two days hands-on, one evaluation, one relationships, one support and decisions\"><div class=\"pair\">2 days<br><b>Pair + build</b></div><div>1 day<br><b>Evaluate</b></div><div>1 day<br><b>Relationships</b></div><div>1 day<br><b>Decisions + buffer</b></div></div><p class=\"statement\">Support is work.<br>Put it in the budget.</p><p class=\"small\">Proposed capacity envelope—not known company availability.</p>", "body": "<p>Example weekly allocation for the AI architect</p><div class=\"capacity\" aria-label=\"Proposed weekly allocation: two days hands-on, one evaluation, one relationships, one support and decisions\"><div class=\"pair\">2 days<br><b>Pair + build</b></div><div>1 day<br><b>Evaluate</b></div><div>1 day<br><b>Relationships</b></div><div>1 day<br><b>Decisions + buffer</b></div></div><p class=\"statement\">Support is work.<br>Put it in the budget.</p><p class=\"small\">Proposed capacity envelope—not known company availability.</p>",
"notes": "This five-day allocation is a planning envelope, not a claim about company staffing. Two days are hands-on, one evaluation, one coaching/relationships, one sponsor decisions, support and contingency. Team lead agreement must include review time. A second team begins only when the first is supportable. Offer reusable examples and bounded office hours, not a permanent help desk to more than ten teams. Excess support demand becomes a CTO investment decision or a smaller scope.", "notes": "This five-day allocation is a planning envelope, not a claim about company staffing. Two days are hands-on, one evaluation, one coaching/relationships, one sponsor decisions, support and contingency. Team lead agreement must include review time. A second team begins only when the first is supportable. Offer reusable examples and bounded office hours, not a permanent help desk to more than ten teams. Excess support demand becomes a CTO investment decision or a smaller scope.",
"sources": [ "sources": [
"six-months-roadmap" "six-months-roadmap"
@@ -183,13 +183,19 @@ export const slides = [
}, },
{ {
"id": "measures", "id": "measures",
"title": "Three measures. One decision.", "title": "Measure better work—and skill health",
"minutes": 2, "minutes": 2,
"body": "<div class=\"measure-list\"><div><b>Accepted work</b><span>Accepted / all matured eligible starts</span></div><div><b>Review + rework</b><span>Comparable effort, including shifted burden</span></div><div><b>Escaped defects</b><span>Severity and complete follow-up</span></div></div><div class=\"rail\">Alongside: setup, support, upkeep and tool cost. Critical effects stop work.</div><p class=\"small\">Task / PR / CI / defect links + a small effort record; no individual league tables.</p>", "body": "<div class=\"measurement-panels\"><div class=\"workflow-panel\"><h3>Is the work improving?</h3><p class=\"metric-context\">Baseline → pilot · like-for-like cohorts</p><div class=\"metric\"><b>Validated task success (%)</b><span>Independently accepted tasks ÷ all matured eligible starts.</span></div><div class=\"metric\"><b>Changes with escaped quality issues (%)</b><span>Changes with confirmed defects ÷ accepted changes with completed follow-up.</span></div><div class=\"metric\"><b>Cost per accepted outcome <em>(currency/outcome)</em></b><span>Allocated cohort cost, including failures and review/rework ÷ independently accepted tasks.</span></div></div><div class=\"skill-panel\"><h3>Are skills fit and maintained?</h3><p class=\"metric-context\">Separate qualification + catalog populations</p><div class=\"metric\"><b>Skill selection precision (%)</b><span>Correct activations ÷ all scored activations in labeled evaluation.</span></div><div class=\"metric\"><b>Skills within substantive review window (%)</b><span>Owned, reviewed, not-overdue revisions ÷ all active approved revisions.</span></div><p class=\"qualification-note\">Independent quality qualification still required.</p></div></div><p class=\"measurement-caution\">Choose relevant measures · Unknown is not zero<br>Skill health is not productivity proof.</p>",
"notes": "Use a small balanced set matched to the mechanism, not all sixteen optional metric contracts. Predeclare eligibility, maturity horizons, denominator and follow-up. Register every eligible task start, including failures, abandoned work and unresolved matured starts; pending tasks stay separate. Link tasks to exact PR/CI acceptance and defect records, with a minimal effort log. Record checked reasons for returns, such as missing regression evidence. Agree access, purpose and retention; avoid raw prompt collection and individual performance ranking. Show total setup and recurring cost beside outcomes. If linkage is incomplete, hold the claim.", "notes": "Choose a small relevant subset from the sixteen optional contracts, not a requirement to collect all five shown here or all sixteen. These are candidate definitions, not actual company values or installed telemetry: task success, escaped quality, cost and precision have prototype calculations without network collectors; substantive-review coverage is unimplemented. Workflow only: compare like-for-like periods/cohorts with the same eligibility, task mix, observation and follow-up horizons, acceptance rubric and source coverage; record staffing, model/client and concurrent process changes. Before/after differences are not causal ROI. Validated task success is 100 times distinct independently accepted tasks by as_of divided by all eligible starts whose preregistered observation horizon has matured. Count each task once across retries, clients and skills. Failures, abandonment and unresolved matured starts remain in the denominator; unknown outcomes are not labeled failures. Exclude pre-start cancellations, sandbox/evaluation and out-of-scope tasks; flag invalid/missing starts and show unknown counts and coverage. Escaped quality is 100 times accepted changes with at least one linked confirmed post-acceptance defect during approved follow-up divided by accepted changes whose predeclared follow-up is complete. Count affected changes, not raw defects; separate severity and absolute defect/severe-incident counts. Show immature changes and pending triage separately; missing linkage or incomplete follow-up is not a clean result. Cost divides allocated costs for every task/attempt in the matured start cohort through as_of, including failed and abandoned attempts and shared period costs, by distinct independently accepted tasks in that same cohort. Include licenses, compute, tooling, setup, qualification, onboarding, support, upkeep and human quality review/rework effort at approved rates without double counting; exclude unrelated projects and documented accounting-basis exclusions. Use one approved reporting currency or dated approved conversion. Missing cost buckets mean a partial estimate with coverage, not total cost; zero accepted outcomes means null with full cost shown. Restate late invoices. Skill selection precision is 100 times true-positive activations divided by true-positive plus false-positive activations in candidate/client evaluation trials with independently labeled relevance and known activation. Freeze the corpus, retain negative/failed trials; unknown activation/relevance is unscorable, reported with coverage and blocks qualification if planned coverage is incomplete. This does not measure artifact success or live workflow acceptance. Substantive-review coverage is 100 times active approved revisions with current owner, linked substantive review evidence and review_due_at at or after as_of divided by all active approved revisions in the catalog snapshot. Experimental/retired revisions are excluded; report deprecated/revoked-in-use and ownerless counts separately. Missing owner/date/evidence stays outside the numerator. Review evidence includes regression, security and usefulness, not a rubber-stamped date. Independent Quality qualification still tests artifact fitness, safe execution and revision regression. Keep qualification trials and live workflow starts separate; never pool their denominators. No applicable skill population is N/A, not a baseline zero; missing evidence for an existing population is unknown, not good health. Predeclared live skill/version slices may reuse the workflow contract unchanged, without summing overlapping slices. Agree access, purpose and retention; link tracker, PR/CI, defect, cost and minimal effort evidence without individual rankings. If evidence is incomplete, limit or hold the claim; critical policy effects stop work regardless of averages.",
"sources": [ "sources": [
"measurement", "measurement",
"six-months-roadmap" "six-months-roadmap",
"measurement/validated-task-success",
"measurement/changes-with-escaped-quality-issues",
"measurement/cost-per-accepted-outcome",
"measurement/skill-selection-precision",
"measurement/skills-within-substantive-review-window",
"skills-quality"
], ],
"kind": "", "kind": "",
"section": "6 Months Roadmap", "section": "6 Months Roadmap",
@@ -113,3 +113,29 @@ html.print-pdf .toolbar{display:none}html.print-pdf .reveal.deck{top:0;height:10
.portrait .deck .learning-loop{grid-template-columns:1fr 16px 1fr 16px 1fr 16px 1fr;gap:0 3px;margin:30px 0} .portrait .deck .learning-loop{grid-template-columns:1fr 16px 1fr 16px 1fr 16px 1fr;gap:0 3px;margin:30px 0}
.portrait .deck .learning-loop span{font-size:24px;padding:14px 2px} .portrait .deck .learning-loop span{font-size:24px;padding:14px 2px}
.portrait .deck .horizon b{font-size:32px} .portrait .deck .horizon b{font-size:32px}
/* Slide 14: outcomes lead; skill indicators remain a separate population. */
.deck .slides #measures{padding-top:32px}
.deck #measures h2{font-size:48px;margin-bottom:20px}
#measures .measurement-panels{display:grid;grid-template-columns:1.3fr 1fr;gap:24px}
#measures .workflow-panel,#measures .skill-panel{padding:16px 22px;font-size:21px;line-height:1.3;background:#e9e9ec;border-top:6px solid var(--gold)}
#measures .skill-panel{background:#eeedf0;border-top-color:#8b8994}
#measures h3{font-size:28px;line-height:1.15;letter-spacing:-.025em;font-weight:900;margin:0;text-transform:none;color:var(--ink)}
.deck #measures .metric-context{font-size:19px;line-height:1.3;margin:8px 0 12px;color:#62616b}
#measures .metric{border-top:1px solid #bbb9c2;padding:10px 0 0;margin-top:10px}
#measures .metric b{display:block;font-size:25px;line-height:1.2}
#measures .metric em{font-style:normal;font-size:20px;white-space:nowrap}
#measures .metric span{display:block;font-size:21px;line-height:1.3;margin-top:7px}
.deck #measures .qualification-note{border-left:4px solid var(--gold);padding-left:12px;font-size:21px;font-weight:700;line-height:1.25;margin:22px 0 0}
.deck #measures .measurement-caution{font-size:20px;line-height:1.4;color:#62616b;margin:16px 0 0}
.portrait .deck .slides #measures{padding-top:20px}
.portrait .deck #measures h2{font-size:38px;margin:12px 0 14px}
.portrait #measures .measurement-panels{grid-template-columns:1fr;gap:12px}
.portrait #measures .workflow-panel,.portrait #measures .skill-panel{padding:12px 16px}
.portrait #measures h3{font-size:29px}
.portrait .deck #measures .metric-context{font-size:20px;margin:6px 0 8px}
.portrait #measures .metric{padding-top:4px;margin-top:4px}
.portrait #measures .metric b{font-size:26px}
.portrait #measures .metric span{font-size:22px;line-height:1.2;margin-top:5px}
.portrait .deck #measures .qualification-note{font-size:22px;margin-top:12px}
.portrait .deck #measures .measurement-caution{font-size:21px;margin-top:12px}
+1 -1
View File
@@ -22,7 +22,7 @@ const assert=require('node:assert/strict');const fs=require('node:fs');
const visited=[]; const visited=[];
for(let i=0;i<23;i++){ for(let i=0;i<23;i++){
assert.equal(await f.evaluate(()=>Reveal.getIndices().h),i);visited.push(await f.evaluate(()=>Reveal.getCurrentSlide().id)); assert.equal(await f.evaluate(()=>Reveal.getIndices().h),i);visited.push(await f.evaluate(()=>Reveal.getCurrentSlide().id));
const bad=await f.evaluate(()=>{const r=Reveal.getCurrentSlide().getBoundingClientRect();return [...Reveal.getCurrentSlide().querySelectorAll('svg,text,.journey,.learning-loop,.contribution-grid,h1,h2,p,li,table,.flow,.roles,.timeline')].filter(e=>!e.closest('.notes')&&e.getBoundingClientRect().width>0).filter(e=>{const b=e.getBoundingClientRect();return b.bottom>r.bottom+1||b.right>r.right+1||b.left<r.left-1}).map(e=>e.textContent)});assert.deepEqual(bad,[]); const bad=await f.evaluate(()=>{const r=Reveal.getCurrentSlide().getBoundingClientRect();return [...Reveal.getCurrentSlide().querySelectorAll('.measurement-panels,.metric,.metric b,.metric span,.qualification-note,h3,svg,text,.journey,.learning-loop,.contribution-grid,h1,h2,p,li,table,.flow,.roles,.timeline')].filter(e=>!e.closest('.notes')&&e.getBoundingClientRect().width>0).filter(e=>{const b=e.getBoundingClientRect();return b.bottom>r.bottom+1||b.right>r.right+1||b.left<r.left-1}).map(e=>e.textContent)});assert.deepEqual(bad,[]);
if(i===6)assert(await f.evaluate(staircaseFits),'staircase aligns each arrow with its intended steps'); if(i===6)assert(await f.evaluate(staircaseFits),'staircase aligns each arrow with its intended steps');
if(i===4)assert(await f.evaluate(()=>[...document.querySelectorAll('#contributors .contribution-grid>div')].every(e=>{const a=e.querySelector('span').getBoundingClientRect(), arrow=e.querySelector('i').getBoundingClientRect(), b=e.querySelector('b').getBoundingClientRect();return a.bottom<=arrow.top+2&&arrow.bottom<=b.top+2&&Math.abs((a.left+a.right-b.left-b.right)/2)<2&&getComputedStyle(e.querySelector('i')).transform==='matrix(0, 1, -1, 0, 0, 0)'})),'contribution arrows must point down to their own phase'); if(i===4)assert(await f.evaluate(()=>[...document.querySelectorAll('#contributors .contribution-grid>div')].every(e=>{const a=e.querySelector('span').getBoundingClientRect(), arrow=e.querySelector('i').getBoundingClientRect(), b=e.querySelector('b').getBoundingClientRect();return a.bottom<=arrow.top+2&&arrow.bottom<=b.top+2&&Math.abs((a.left+a.right-b.left-b.right)/2)<2&&getComputedStyle(e.querySelector('i')).transform==='matrix(0, 1, -1, 0, 0, 0)'})),'contribution arrows must point down to their own phase');
await iframe.screenshot({path:`${out}/${viewport.width}-${i+1}.png`}); await iframe.screenshot({path:`${out}/${viewport.width}-${i+1}.png`});
+1 -1
View File
@@ -19,7 +19,7 @@ const fs=require('node:fs'); const assert=require('node:assert/strict');
await page.evaluate(i=>Reveal.slide(i),i);await page.waitForTimeout(60); await page.evaluate(i=>Reveal.slide(i),i);await page.waitForTimeout(60);
const bad=await page.evaluate(()=>{ const bad=await page.evaluate(()=>{
const slide=Reveal.getCurrentSlide(),r=slide.getBoundingClientRect(); const slide=Reveal.getCurrentSlide(),r=slide.getBoundingClientRect();
return [...slide.querySelectorAll('svg,text,.journey,.learning-loop,.contribution-grid,h1,h2,p,li,td,th,.rail,.gate,.facts,.flow,.roles,.timeline,.capacity,.measure-list,.contrast,.comparison,.choices,.ledger')].filter(e=>!e.closest('.notes')&&e.getBoundingClientRect().width>0).filter(e=>{const b=e.getBoundingClientRect();return b.bottom>r.bottom+1||b.right>r.right+1||b.left<r.left-1||b.top<r.top-1}).map(e=>e.textContent.slice(0,60)); return [...slide.querySelectorAll('.measurement-panels,.metric,.metric b,.metric span,.qualification-note,h3,svg,text,.journey,.learning-loop,.contribution-grid,h1,h2,p,li,td,th,.rail,.gate,.facts,.flow,.roles,.timeline,.capacity,.measure-list,.contrast,.comparison,.choices,.ledger')].filter(e=>!e.closest('.notes')&&e.getBoundingClientRect().width>0).filter(e=>{const b=e.getBoundingClientRect();return b.bottom>r.bottom+1||b.right>r.right+1||b.left<r.left-1||b.top<r.top-1}).map(e=>e.textContent.slice(0,60));
}); });
if(i===6)assert(await page.evaluate(staircaseFits),'staircase aligns each arrow with its intended steps'); if(i===6)assert(await page.evaluate(staircaseFits),'staircase aligns each arrow with its intended steps');
if(i===4)assert(await page.evaluate(()=>[...document.querySelectorAll('#contributors .contribution-grid>div')].every(e=>{const a=e.querySelector('span').getBoundingClientRect(), arrow=e.querySelector('i').getBoundingClientRect(), b=e.querySelector('b').getBoundingClientRect();return a.bottom<=arrow.top+2&&arrow.bottom<=b.top+2&&Math.abs((a.left+a.right-b.left-b.right)/2)<2&&getComputedStyle(e.querySelector('i')).transform==='matrix(0, 1, -1, 0, 0, 0)'})),'contribution arrows must point down to their own phase'); if(i===4)assert(await page.evaluate(()=>[...document.querySelectorAll('#contributors .contribution-grid>div')].every(e=>{const a=e.querySelector('span').getBoundingClientRect(), arrow=e.querySelector('i').getBoundingClientRect(), b=e.querySelector('b').getBoundingClientRect();return a.bottom<=arrow.top+2&&arrow.bottom<=b.top+2&&Math.abs((a.left+a.right-b.left-b.right)/2)<2&&getComputedStyle(e.querySelector('i')).transform==='matrix(0, 1, -1, 0, 0, 0)'})),'contribution arrows must point down to their own phase');
+17
View File
@@ -27,6 +27,23 @@ test('contributors explains human-controlled AI tools below the diagram',()=>{
assert(body.indexOf(definition)>body.indexOf('contribution-grid')); assert(body.indexOf(definition)>body.indexOf('contribution-grid'));
assert(body.includes('Dashed ⇢ contribution from outside the cycle.')); assert(body.includes('Dashed ⇢ contribution from outside the cycle.'));
}); });
test('capacity visibly frames the days as an example weekly allocation',()=>{
const slide=slides.find(s=>s.id==='capacity');
assert.equal(slide.title,'One architect. One active live pilot.');
assert(slide.body.startsWith('<p>Example weekly allocation for the AI architect</p><div class="capacity"'));
for(const text of ['2 days','Pair + build','Evaluate','Relationships','Decisions + buffer','Proposed capacity envelope—not known company availability.']) assert(slide.body.includes(text));
});
test('measurement names five numerical candidates and separates populations',()=>{
const s=slides.find(s=>s.id==='measures');
assert.equal(s.minutes,2);
assert.equal(s.title,'Measure better work—and skill health');
for(const label of ['Validated task success (%)','Changes with escaped quality issues (%)','Cost per accepted outcome','currency/outcome','Skill selection precision (%)','Skills within substantive review window (%)','Baseline → pilot','Independent quality qualification still required','Choose relevant measures','Unknown is not zero','Skill health is not productivity proof']) assert(s.body.includes(label),label);
assert.equal((s.body.match(/class="metric"/g)||[]).length,5);
for(const text of ['matured eligible starts','completed follow-up','labeled evaluation','active approved revisions'])assert(s.body.includes(text),text);
for(const name of ['validated-task-success','changes-with-escaped-quality-issues','cost-per-accepted-outcome','skill-selection-precision','skills-within-substantive-review-window'])assert(s.sources.includes('measurement/'+name));
for(const term of ['N/A','unknown','unimplemented','partial','review/rework','like-for-like','zero accepted'])assert(s.notes.includes(term),term);
assert.doesNotMatch(s.body,/Accepted work<|\d+%/);
});
test('learning loop staircase preserves the original semantic sequence',()=>{ test('learning loop staircase preserves the original semantic sequence',()=>{
const body=slides.find(s=>s.id==='learning-loop').body; const body=slides.find(s=>s.id==='learning-loop').body;
const loop=body.split('</div>')[0]; const loop=body.split('</div>')[0];