Imported from raj7vasani/munich-ehl-hackathon-2026 (
AGENTS.md). Install upstream withnpx skills add raj7vasani/munich-ehl-hackathon-2026. Copyright stays with the author.
Project notes
Entire + Devin CLI integration
Entire captures agent sessions in this repo. It has no built-in Devin agent, so Devin is wired in two ways. They are mutually exclusive and hand over automatically:
entire-agent-devin plugin |
entire-devin-bridge.py |
|
|---|---|---|
| Sessions labelled | Devin | Claude Code |
| Needs | binary on $PATH (per machine) |
nothing but python3 |
| Transcript format | Devin native | Claude-Code-shaped |
| Wired via | .devin/hooks.v1.json |
.claude/settings.json |
The plugin is the real integration; the bridge is the fallback for anyone who
hasn't installed the plugin. When the plugin is on $PATH and hooked into
the repo, the bridge detects it and stands down (devin_plugin_active()), so
the same session is never recorded twice under two identities.
The plugin (preferred)
.devin/entire-agent-devin implements Entire's
external agent protocol:
Entire scans $PATH for entire-agent-<name> executables, so this registers a
real devin agent. It materializes Devin's SQLite session
(~/.local/share/devin/cli/sessions.db) to JSONL under
~/.local/share/devin/entire-transcripts/<repo-slug>/<session-id>.jsonl in
Devin's native message shape, and implements the transcript-analyzer and
token-calculator subcommands against that shape.
Install it (per machine — the repo checkout alone is not enough):
ln -sf "$PWD/.devin/entire-agent-devin" /opt/homebrew/bin/entire-agent-devin
entire enable --agent devin # NOT `entire agent add devin` -- see below
/opt/homebrew/bin is used because it is already on $PATH (it is where entire
itself lives) and /usr/local/bin is not writable here. It is a Homebrew-managed
directory, so brew doctor may list the symlink as an unexpected file — harmless.
Any other directory on your login $PATH works just as well. A symlink (rather
than a copy) keeps the repo the single source of truth, at the cost of breaking if
the checkout moves.
Gotchas found the hard way:
entire agent add devindoes not work.agent addcallsagent.Get()without running external-agent discovery first (agent_group.go:107upstream), so it always reportsUnknown agent "devin".entire enable --agent devindoes discover, and auto-enables theexternal_agentssetting.- The binary must sit in a directory on your login
$PATH, since Devin's hooks inherit it. Entire's managed plugin dir (~/.local/share/entire/plugins/bin) is not auto-prepended in CLI 0.10.2. - Offsets in the protocol are opaque to Entire, so the plugin uses line counts
consistently for both
--offsetandget-transcript-position.
The bridge (fallback)
Devin CLI reads hooks from .claude/settings.json for compatibility, so the
hooks Entire installed there already fire during Devin sessions. That alone gets
prompts, file changes and commit-linked checkpoints into Entire — but not
transcripts.
How the bridge works
Devin CLI reads hooks from .claude/settings.json for compatibility, so the
hooks Entire installed there already fire during Devin sessions. That alone gets
prompts, file changes and commit-linked checkpoints into Entire — but not
transcripts: Entire takes the transcript location from the transcript_path
field of the hook payload, and Devin's payloads don't have one (Devin keeps
sessions in SQLite at ~/.local/share/devin/cli/sessions.db, not in per-session
JSONL files). Without it, Entire's turn-end handler aborts with "transcript file
not specified", so tool calls, assistant messages, token counts and the model
never reach entire.io.
.devin/entire-devin-bridge.py closes that gap. The four lifecycle hooks in
.claude/settings.json
(SessionStart, UserPromptSubmit, Stop, SessionEnd) call the bridge
instead of entire hooks claude-code <verb> directly. For each event the bridge:
- Exports the live Devin session from
sessions.dbinto a Claude-Code-shaped JSONL transcript under~/.local/share/devin/entire-bridge/<cwd-slug>/<session-id>.jsonl(read-only DB access; written atomically). - Adds
transcript_pathandmodelto the payload. - Forwards it to
entire hooks claude-code <verb>, passing Entire's stdout response back through so context injection still works.
Payloads that already carry a transcript_path are forwarded untouched, so real
Claude Code sessions in this repo are unaffected. If entire, python3, or the
bridge script is missing, the hook falls back to calling entire directly and
never fails the turn.
Devin tool names are mapped to Claude Code equivalents during export
(write→Write, edit/apply_patch→Edit, notebook_edit→NotebookEdit,
skill→Skill, ...). The first three are load-bearing: Entire's claude-code
analyzer detects touched files only from those tool names.
Verifying either path
entire session list # look for "Devin · <model> · ... session <id>"
entire session tokens <session-id> # non-zero tokens + API calls => transcript parsed
tail -f .entire/logs/entire.log # turn-end should show agent=devin + a session_ref
A turn-end log line with "session_ref":"" means neither path ran, and only
prompts and diffs are being captured for that session.
To sanity-check the plugin without involving Entire, drive it directly — every subcommand is JSON in, JSON out:
echo '{"session_id":"<id>"}' | .devin/entire-agent-devin parse-hook --hook stop
.devin/entire-agent-devin extract-prompts --session-ref <transcript>
Caveats
- Devin loads hook config at session start, so changes to
.claude/settings.jsonor.devin/hooks.v1.jsononly take effect in new Devin sessions. - The agent label is stamped into each checkpoint when it is condensed, and is
never recomputed. entire.io renders that stored value, so a session captured
through the bridge shows as "Claude Code" there permanently — even after
entire session listlocally starts reporting "Devin" because Entire re-derived the agent from the transcript path. Only checkpoints condensed while the plugin is driving the session carry the Devin label. - The session badge in entire.io's Sessions list is pinned by whichever
agent first ingested that
session_id, and later checkpoints inherit it. Adding a Devin-stamped checkpoint to a session Entire first saw as Claude Code does not reclassify it — the checkpoint's ownmetadata.jsonsays"agent": "Devin"while the session row still reads Claude Code. Only asession_idEntire has never seen shows up as a Devin session. - Re-running
entire agent add claude-codeorentire configuremay rewrite.claude/settings.jsonand drop the bridge wrappers. Re-apply them if transcripts stop appearing. - Devin's
created_atcolumns are epoch seconds. Treating them as microseconds (an easy assumption) puts every transcript timestamp in 1970. /tools/,/schemas/,/catalog/,/corpus/,/docs/0*.mdand*.pdfare hidden from the team repo via.git/info/exclude(local-only TraceForge work). Don't put shared code there — it will not be committed.