codeck-speech — independently scanned and version-tracked by SaferSkills.
SaferSkills independently audited codeck-speech (Agent Skill) and scored it 96/100 (green). The audit ran 55 deterministic rules across Security, Supply Chain, Maintenance, Transparency, and Community; it found 0 high-severity and 1 lower-severity findings. The full rule-by-rule trace and per-finding evidence are below. Free, methodology-open.
Findings & checks · 1 flagged
The text {match} tells the agent to skip the normal "ask the user first" gate. Used adversarially it removes the human-in-the-loop check before destructive or sensitive actions, turning a normally-gated agent into a fire-and-forget executor.
Every scanned point with the score it earned and what moved between them.
First recorded scan — no prior version to compare against.
The primary manifest — the file an agent reads to learn what this artifact does.
<!-- [INPUT]: Depends on deck content, HTML notes, MEMORY.md, tasks/tasks.md, and threads/threads.md. [OUTPUT]: Provides speech.md and fragment-synced HTML data-notes. [POS]: skills/codeck-speech lane; turns the deck into a presenter-ready talk track. [PROTOCOL]: 变更时更新此头部,然后检查 CLAUDE.md -->
@speech owns the talk track, presenter rhythm, and fragment-synced notes.
Write boundaries:
$DECK_DIR/speech.mddata-notes in $DECK_DIR/slides.html$DECK_DIR/roles/speech.md, $DECK_DIR/tasks/tasks.md, and $DECK_DIR/channel/YYYY-MM-DD.mddeck.md, DESIGN.md, custom.css, review.md, or export files$DECK_DIR/threads/threads.mdRead $DECK_DIR/diagnosis.md. If a speech role is recommended, use it. Otherwise, pick a coach based on domain and audience:
Technical → Feynman: simplify the complex, bridge with analogy
>
Business → Jobs: build anticipation, one "one more thing"
>
Academic → Hans Rosling: let data tell the story
DECK_DIR="$HOME/.codeck/projects/$(basename "$(pwd)")"
CODECK_SKILL_DIR="${CODECK_SKILL_DIR:-}"
if [ -z "$CODECK_SKILL_DIR" ]; then
for d in "$HOME/.agents/skills/codeck" "$HOME/.codex/skills/codeck" "$HOME/.claude/skills/codeck"; do
if [ -d "$d/scripts" ]; then CODECK_SKILL_DIR="$d"; break; fi
done
fi
[ -n "$CODECK_SKILL_DIR" ] || { echo "codeck skill scripts not found" >&2; exit 1; }
mkdir -p "$DECK_DIR"
mkdir -p "$DECK_DIR/channel" "$DECK_DIR/tasks" "$DECK_DIR/threads" "$DECK_DIR/roles"
bash "$CODECK_SKILL_DIR/scripts/init-room.sh" "$DECK_DIR"
bash "$CODECK_SKILL_DIR/scripts/status.sh" "$DECK_DIR"Read:
*-r*.html) — actual slide contentoutline.mdIf no HTML and no deck.md, run /codeck to build the missing deck state first.
If only deck.md exists, write based on deck.md — note that the script is based on structure, not final visuals.
Do not read channel/YYYY-MM-DD.md unless debugging history.
Smart skip: skip Decision Ask if the user's instruction, MEMORY.md, open threads/threads.md rows, deck.md, or existing speech.md already specifies style and duration.
Before writing, claim the work ticket:
@orchestrator
Owner: @speech. Task: create presenter script and sync data-notes.
@speech
I claim the speech pass. I will write `speech.md`, sync fragment notes, and leave source conflicts in threads.Append the exchange to today's channel file and update tasks/tasks.md.
Speech Style is one allowed Decision Ask moment under /codeck.
Use the shared /codeck Decision Ask Policy. Create one D-YYYYMMDD-NN decision only when style or duration is missing. Bundle both into one choice so the user is deciding the speech shape, not filling a form.
codeck needs the speech shape.
Current read: {deck audience and rhythm}.
I suggest {recommended package} because {reason}.
A) {style + duration package} (recommended)
B) {contrasting style + duration package}
C) {deeper/shorter package}Use these defaults when the deck gives no signal:
If the decision is non-blocking and the user does not answer, use the recommended package and write assumed default to MEMORY.md. If the speech commitment is blocking and no structured AskUser UI is available, leave it open in threads/threads.md and stop before writing speech.md.
Record the final style and duration in speech.md front matter and MEMORY.md.
Before writing, build a fragment map. For each slide in the HTML, list: slide number, title, fragment count (data-f elements). This map determines the speech structure — slides with fragments get ### [on enter] + ### [fragment N] sections, slides without get a single block. Do not skip this step.
Write a complete, readable-aloud transcript. Page by page.
[pause 2s], [slow down], [look at audience]. For other languages, translate the stage directions so the speaker never has to switch languages while presenting.TED: use "you" / "we", mix short and long sentences, pause after key points, end by echoing the opening.
Formal: complete sentences, logical progression, summarize + outlook at the end.
Casual: colloquial, self-deprecating ok, casual transitions, end with a surprise.
| Slide | Title | Words | Estimate |
|---|---|---|---|
| 1 | ... | ... | ... |
If a section is over budget, trim it directly before writing the final script. Do not ask another question.
The engine's buildNotes() concatenates the slide's data-notes with each visible fragment's data-notes as the presenter steps through. Use this to sync speech rhythm with fragment rhythm.
data-f="N" to know the stepping orderdata-notes → what to say when the slide first appears (before any fragment)data-f="1" element's data-notes → what to say when fragment 1 revealsdata-f="2" element's data-notes → what to say when fragment 2 revealsSpeech for slide 3:
"Let's talk about the three ideas behind codeck. [pause 2s] First, it recruits people, not rules. [pause] Second, isomorphic mapping. [pause] Third, no schema ceiling."
Slide 3 has data-f="1", data-f="2", data-f="3":
<section class="slide" data-notes="Let's talk about the three ideas behind codeck. [pause 2s]">
<h2 data-f="1" data-notes="First, it recruits people, not rules. [pause]">People, not rules</h2>
<p data-f="2" data-notes="Second, isomorphic mapping. [pause]">Isomorphic mapping</p>
<p data-f="3" data-notes="Third, no schema ceiling.">No schema ceiling</p>
</section>Presenter presses → three times. Notes build up progressively:
data-notesdata-notes attribute values[pause], [slow down], etc.) in the notes---
style: "{style}"
duration: "{target}"
totalEstimate: "{estimate}"
---
# Speech: {topic}
---
## Slide 1: {title}
<!-- estimate: {N}s | {M} words | fragments: 0 -->
{verbatim speech text}
[pause 2s]
---
## Slide 2: {title}
<!-- estimate: {N}s | {M} words | fragments: 3 -->
### [on enter]
{what to say when slide appears, before any fragment}
### [fragment 1]
{what to say when fragment 1 reveals}
### [fragment 2]
{what to say when fragment 2 reveals}
### [fragment 3]
{what to say when fragment 3 reveals}
---After writing:
MEMORY.md Active Context, Latest Channel Summary, Task Index, and Artifacts.@speech task done in tasks/tasks.md.threads/threads.md.Point to the single strongest moment in the script — the line or pause that will land hardest:
codeck speech done.
>
@speech I wrote speech.md, synced fragment notes, and recorded the speech shape in memory.>
Strongest moment: {slide N — what happens and why it works. e.g., "Slide 4, the three-second pause after the question. That silence is where the audience decides you're worth listening to."}
>
{one line — readiness assessment}
>
Output: $DECK_DIR/speech.md + HTML data-notes updated Press P in the deck for speaker mode to see the script.>
Export:/codeck export. Overview:/codeck.
~30 seconds. Free. No account. Every finding cites a rule and a line of evidence.