Borrowing it
Nothing to install: this file belongs to scorbo2/TalkWithMe. Take a copy, put it at the same path in your own repository, and replace the rules that are about this project with yours.
curl -O https://raw.githubusercontent.com/scorbo2/TalkWithMe/master/AGENTS.mdgit clone --depth 1 https://github.com/scorbo2/TalkWithMeWrote this? Show the measurements
A badge with what this costs and how it scanned, read live from this page, so it follows the numbers instead of freezing them. Markdown for a README, HTML for a documentation site or a project page.
[](https://agentmods.dev/instructions/scorbo2/talkwithme/agents-md)<a href="https://agentmods.dev/instructions/scorbo2/talkwithme/agents-md"><img src="https://agentmods.dev/badge/instructions/scorbo2/talkwithme/agents-md/github.svg" alt="Measured on agentmods" height="20"></a>Or the 80×15 button, for a site that already has a row of RSS and ATOM ones. Only the verdict fits; the numbers stay here.
<a href="https://agentmods.dev/instructions/scorbo2/talkwithme/agents-md"><img src="https://agentmods.dev/badge/instructions/scorbo2/talkwithme/agents-md.svg" alt="Reviewed on agentmods" width="80" height="20"></a>What it costs to keep this loaded
Counted locally with the o200k_base tokenizer, which is exact for GPT models; Claude uses its own tokenizer and its counts differ. Treat this as one consistent yardstick across the catalogue rather than a bill. Prices are per million input tokens.
| Model | Per session | Once invoked |
|---|---|---|
| Fable 5.1 | $0.12834 | $0.12834 |
| Opus 5.5 | $0.05134 | $0.05134 |
| Sonnet 5.5 | $0.02567 | $0.02567 |
| Haiku 4.5 | $0.01283 | $0.01283 |
Grade A, and why
TalkWithMe AGENTS.md scanned grade A with 0 findings against 26 rules in 11 categories — prompt injection, anti-refusal, data exfiltration, privilege escalation, supply chain, agent snooping, system-prompt leakage, SSRF and excessive agency — measured 1mo ago.
A static scan of the body, not an audit. Every finding is printed with the line that produced it so you can judge whether it matters here. A mod is markdown that instructs an agent; that is exactly why what it instructs is worth reading.
Nothing flagged
None of the 26 patterns this scan looks for appear in this file: no shell pipes, no recursive deletes, no credential paths, no hidden text, no instruction-override or anti-refusal phrasing, no agent-config snooping. That is not a guarantee, it is the absence of the things that are checkable.
How it starts
The opening of the file, as written. The whole thing — 219 lines — stays where its author put it; the contents beside it link to each section on GitHub.
TalkWithMe — Agent Instructions
Run the app
source .venv/bin/activate
pip install -r requirements.txt
uvicorn app.main:app --host 0.0.0.0 --port 8000 --reload
deactivate
Requires a locally running llama.cpp server with an OpenAI-compatible API (or any OpenAI-compatible LLM, local or remote). TTS and STT servers are optional.
Open http://localhost:8000 in a browser.
A remote LLM that needs an API key is supported: set the TALKWITHME_LLM_API_KEY env var or create an llm_api_key file in the project root (copy llm_api_key.example) — see the README "LLM API key (remote LLMs)" section. The key is never in settings.yaml, never in the UI, and never logged.
Testing — pytest, fully offline
source .venv/bin/activate
pip install -r requirements-dev.txt
python -m pytest # config in pytest.ini
deactivate
- No servers needed. The suite is hermetic: every external HTTP endpoint (LLM, TTS, STT, MCP) is faked via
tests/factories.py(fakehttpx.AsyncClients, config factories, SSE helpers). It must run — and pass — with nothing but Python installed. - Isolation:
tests/conftest.pyhas an autouse fixture that points every module-level global at per-testtmp_pathstate: the config caches inapp/config.py,_PERSISTENCE_ROOT(in bothapp/persistence.pyandapp/routers/persistence.py— the router imported it by value, so it needs its own patch), thesessionsingleton, the MCP tool registry, the TTS capabilities cache inapp/services/tts_client.py, the LLM API key cache inapp/services/llm_auth.py(its_PROJECT_ROOTis re-pointed totmp_pathandTALKWITHME_LLM_API_KEYis deleted from the environment, so a test's key — or the developer's real one — never leaks into another test), and the once-per-URL cleartext-warning dedupe set inapp/services/llm.py. Realsettings.yaml/Personas//chatrooms.yaml/chatrooms//llm_api_keydata is never read or written. If you add a new module-level global to the app, add it to that fixture. - Lifespan: the
clientfixture usesTestClientwithout the startup lifespan, because the lifespan re-reads the real YAML files (clobbering test caches) and attempts MCP discovery. Tests that exercise the lifespan do so explicitly with a localTestClientin awithblock and monkeypatchedload_*/load_tools(seetests/test_main.py). - Coverage map:
test_config.py(config models + YAML load/save),test_persona_store.py(persona directory discovery: frontmatter, file ops, language/avatar helpers, memory-file append/purge/dedupe, YAML→dir migration),test_builtin.py(the built-inadd_memorytool: registry, availability gating, save/error paths),test_models.py(API request/response models),test_persistence.py(disk persistence + audio staging),test_mime.py(the shared deterministic MIME→extension helper inapp/services/mime.py: the rule table plus the never-consult-the-OS-mime-database invariant — the macOS.webabug class),test_session_manager.py,test_llm.py(SSE parsing + agentic tool loop incl. the mid-stream abort retry/LLMStreamAborted+ the LLM API key header + thehttp://cleartext warning),test_llm_auth.py(LLM API key resolution: env-var/file priority, thellm_api_key = <value>file format, lazy load, the never-logged invariant),test_mcp_client.py,test_tool_registry.py,test_tts_stt_clients.py,test_tts_fixtures.py(the two copies of the four capabilities snapshots — pytest'stests/factories.pyvs the plain-Nodetests/fixtures/*.json— must not drift; re-copy both from tts-serve in the same commit),test_chat_sse.py(the/api/chatSSE endpoint — LLM stubbed, selection/persistence/echo/tool events for real),test_main.py,test_docs.py(the AGENTS.md API endpoints table must match the routes actually registered on the app — run it after adding/removing endpoints and update the table), onetest_routers_*.pyper API router,test_persona_form.js(plain Node, not part of pytest — see below: the persona editor form logic instatic/persona.js),test_tts_settings.js(plain Node, not part of pytest: the dynamic TTS parameter section instatic/tts-params.js+ the TTS wiring instatic/settings.js),test_speaking_highlight.js(plain Node, not part of pytest: the speaking-bubble highlight — the playback queues instatic/tts.js+setSpeakingHighlight/playPersistedAudioinstatic/chat.js), andtest_stop_button.js(plain Node, not part of pytest: the top-bar stop button — a temporary "mute" over the playback queues: the button tracks theactiveAudioSourcesset and is enabled exactly while some source plays, stop halts every active source and disables the button immediately (before the asynconendedfires), muted items are still fetched and persisted with their replay buttons but never play (both the non-streaming queue and the streaming sentence pipeline; the TTS fetch pipeline itself is untouched), and the mute is cleared by the next user prompt (exercised through the realsendMessage()with a stubbed SSE stream) or a manual replay click — an item whose playback start falls after the lift plays normally). - Frontend tests (Node):
tests/test_persona_form.jsruns with plain Node 20+ — no npm packages, no network:node tests/test_persona_form.js. It evaluates the realstatic/utils.js+state.js+persona.jsin a freshvm.Contextper test against a minimal DOM stub, stubsfetchto capture the multipartFormData, and drives the realopenPersonaForm(), Remove-button listeners, file-input change handlers, andsubmitPersonaForm(). It exists to lock in the invariants thatremove_avatar_image/remove_reference_audioare sent only after an explicit "Remove" click — never derived from server-side file presence (that bug silently deleted a persona's avatar and reference audio on every plain text save) — and, by the same rule, thatclear_memoriesis sent only after an explicit "Clear saved memories" click whilememory_sizeis always sent (the update endpoint requires it; an omitted value must not silently reset the persona's memory budget).tests/test_tts_settings.jsuses the same harness (freshvm.Contextper test, minimal DOM stub, stubbedfetch) but loadsstatic/utils.js+state.js+tts-params.js+settings.jsand drives the realopenSettings(), the TTS enabled/Base-URL change listeners, and form submission against the real tts-serve capabilities snapshots intests/fixtures/. It locks in the T9 widget table (incl. "null default ⇒ not a slider" and the integer-span rule), the app-managed-fields exclusion (text/audio_base64/reference_text/languageare never rendered), the "blank = let the engine decide" collection semantics (blank optionals omitted; checkboxes/sliders/selects-with-default always sent), thearrayparameter widget (flat scalar item lists, tts-serve schema v2: a fixed item count renders one labeled row per item — the engine'sitem_labels[i]when the spec advertises a well-formed list (exactly one non-empty string per item), else thename[i]fallback, which mirrors the validators' item naming; malformed labels degrade to the fallback and never to the JSON hatch — all-blank omits the parameter, a partially filled one is a validation error and blank slots are never filled with invented values; variable-size or malformed array specs fall to the raw-JSON escape hatch — tested with synthetic docs since no shipped snapshot has an array param yet), the T10 version gate, and the pass-through rule that a save with no capabilities document sends the savedtts.parametersunchanged rather than{}(never silently wipe). It also locks in the reconnect feature (Refresh button + Base-URL change listener probe the field's url via?base_url=; a scheme-less url gets the specific 422 line, not "not reachable"; a same-URL refetch keeps in-flight slider edits instead of re-filling from saved values, only a real engine switch shows the "edits discarded" note, and opening the dialog is a fresh connect — the in-memory doc is cleared on open so unsaved edits from a cancelled session cannot leak across opens), the "Reset to defaults" button above the parameter list (re-renders the section from an empty saved-values map — the first-connect state: no network traffic, a no-op when no document is renderable so the no-doc save pass-through still protects the saved parameters, local until Save — an unsaved reset is discarded on reopen while a same-URL refresh keeps the reset state on screen — and a save after a reset sends the always-sent widgets at the engine's declared defaults while every blankable field is omitted, dropping the saved customization), and — critically — the DOM stub'schildrenare array-like non-Array lists (HTMLCollection mimic), so the suite catches the regression class where code gates onArray.isArray(element.children): in real browsers that silently collects zero parameter values on every save, wipingtts.parameters(the save→reopen round-trip test reproduces the user-visible symptom: values reverting to the engine's doc defaults). Both files are kept out of the pytest suite on purpose: pytest must stay runnable with nothing but Python installed. - Two expected deprecation warnings: a clean run is "all tests pass", even when the
warnings summarycontains exactly two third-party deprecation warnings. Both come from Starlette 1.x's own testclient (pulled in via thefastapi.testclientimport), not from app or test code: aStarletteDeprecationWarningthat the httpx-based testclient will one day be replaced by a newhttpx2package, and ananyio.abc.BlockingPortalalias deprecation raised from insidestarlette/testclient.py. Neither is harmful today — the testclient works fine on httpx as of Starlette 1.6 — so don't chase them and don't "fix" app/test code in response. The eventual resolution, if it ever comes, is a future Starlette/httpx2 bump, not a code change here. - Rules:
- Every code change must be followed by a clean run:
.venv/bin/python -m pytest, all green. No exceptions, no skipped tests. Changes tostatic/persona.js(or anything else covered by the Node tests) additionally requirenode tests/test_persona_form.jsall green; changes touching the dynamic TTS section (static/tts-params.js, the TTS wiring instatic/settings.js, or the capabilities fixtures) additionally requirenode tests/test_tts_settings.jsall green; changes to the speaking-highlight paths (the playback queues instatic/tts.js, orsetSpeakingHighlight/beginSpeaking/endSpeaking/playPersistedAudioinstatic/chat.js) additionally requirenode tests/test_speaking_highlight.jsall green; changes to the stop-button paths (the stop button instatic/tts.js—stopAudioPlayback/stopAllAudioSources/updateStopButtonUI/playAudioSource— or the mute clearing insendMessage/playPersistedAudioinstatic/chat.js) additionally requirenode tests/test_stop_button.jsall green. - New functionality or API endpoints require new tests in the matching
test_*.pyfile before the change is complete. - API tests use the
clientfixture + config caches (re-pointapp.config._settings_cache/_personas_cache/_chatrooms_cacheviamonkeypatch); router-level stubs are applied at the router's import site (e.g.app.routers.chat.stream_chat), since routers import service functions by name. - All fake responses in
tests/factories.pyattach anhttpx.Requestbefore returning: the httpx versions this project supports (0.24–0.28) raiseRuntimeErrorfromresponse.url/raise_for_status()if norequestis attached to aResponse, and the public.requestgetter itself raises when unset (check the privateresponse._requestattribute instead).
- Every code change must be followed by a clean run:
What this file has done since we first saw it
Hashed on every crawl. A supply-chain change to an agent config is a question of when, not whether, so the history is kept rather than the latest state alone.
- 1mo ago Changed · +1 lines · +2,053 tokens per session b6d1219f472a
- 1mo ago Changed · +1 lines · +356 tokens per session 3b1210f03166
- 1mo ago Changed · +16 lines · +3,167 tokens per session 5f522dea76df
- 2mo ago Changed · +38 lines · +2,328 tokens per session 4516d510de7b
- 2mo ago First seen · 163 lines · 4,930 tokens per session scan A 6587f0bee30b
TalkWithMe AGENTS.md is an instructions file published in the GitHub repository scorbo2/TalkWithMe (274 stars, last pushed 21d ago), licensed MIT. It adds 12,834 tokens to every session, about $0.0513 per session on Opus 5.5. A static security scan graded it A with 0 findings. No closer match exists in the catalogue, so it is treated as the original; first seen 2026-08-30.
TalkWithMe AGENTS.md compared with instructions from other repositories
| Mod | Type | Stars | Last push | Licence | Scan | Tokens | Works with |
|---|---|---|---|---|---|---|---|
| TalkWithMe AGENTS.mdscorbo2/TalkWithMe | Instructions file | 274 | 21d ago | MIT | A | 12,834 | Codex, OpenCode |
| vscode buildNext.instructions.mdmicrosoft/vscode | Instructions file | 195k | today | MIT | A | 9,719 | GitHub Copilot |
| next.js AGENTS.mdvercel/next.js | Instructions file | 143k | yesterday | MIT | A | 7,461 | Codex, OpenCode |
| langchain AGENTS.mdlangchain-ai/langchain | Instructions file | 149k | today | MIT | A | 4,680 | Codex, OpenCode |
| vscode oss-third-party-notices.instructions.mdmicrosoft/vscode | Instructions file | 195k | today | MIT | A | 5,516 | GitHub Copilot |
| vscode copilot-instructions.mdmicrosoft/vscode | Instructions file | 195k | today | MIT | A | 3,093 | GitHub Copilot |
| deepseek-harness AGENTS.mddeepseek-ai/deepseek-harness | Instructions file | 275k | 2d ago | MIT | A | 4,313 | Codex, OpenCode |