feat: add Gemini CLI session JSON normalizer#155
Open
adv3nt3 wants to merge 1 commit intoMemPalace:developfrom
Open
feat: add Gemini CLI session JSON normalizer#155adv3nt3 wants to merge 1 commit intoMemPalace:developfrom
adv3nt3 wants to merge 1 commit intoMemPalace:developfrom
Conversation
proxysoul
approved these changes
Apr 7, 2026
Contributor
Author
|
@bensig Same CI failure as PR #44 — not from this PR. Both failing tests are in
Pre-existing test-vs-code mismatch on |
This was referenced Apr 7, 2026
de3bd94 to
c5669b9
Compare
Add _try_gemini_json parser for Gemini CLI session files stored at
~/.gemini/tmp/{project_hash}/chats/session-{timestamp}-{id}.json.
Gemini sessions are single JSON files (not JSONL) with a messages
array. User messages have type "user" with content as a list of
{"text": "..."} blocks (no "type" key — differs from Claude/OpenAI
content blocks). Assistant messages have type "gemini" with content
as a plain string.
Uses custom content extraction because Gemini content blocks omit
the "type" field that the shared _extract_content helper expects.
Fingerprints on "sessionId" + "messages" keys to avoid false
positives on other JSON formats.
Tested against real local Gemini CLI sessions. Session format
confirmed via Gemini CLI docs (session management, /resume command,
~/.gemini/tmp/{hash}/chats/ path).
Refs: MemPalace#59
c5669b9 to
44c9d2b
Compare
web3guru888
approved these changes
Apr 11, 2026
web3guru888
left a comment
There was a problem hiding this comment.
✨ Review of #155 — feat: add Gemini CLI session JSON normalizer
Scope: +47/−1 · 1 file(s)
mempalace/normalize.py(modified: +47/−1)
Suggestions
- 💡 No tests included — consider adding coverage for the new code paths
🟢 Approved — clean, well-structured PR. Good work @adv3nt3!
🏛️ Reviewed by MemPalace-AGI · Autonomous research system with perfect memory · Showcase: Truth Palace of Atlantis
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Summary
Add
_try_gemini_jsonparser for Gemini CLI session files stored at~/.gemini/tmp/{project_hash}/chats/session-{timestamp}-{id}.json. This is the 7th normalize format for MemPalace, alongside Claude AI JSON, ChatGPT JSON, Claude Code JSONL, Codex CLI JSONL (#61), Slack JSON, and plain text.Gemini CLI session format
Gemini CLI auto-saves every conversation as a single JSON file per session. Sessions are project-scoped — stored under a hash of the working directory. Retention defaults to 30 days / 100 sessions (configurable via
settings.json).Path:
~/.gemini/tmp/{project_hash}/chats/session-{timestamp}-{short_id}.jsonStructure:
{ "sessionId": "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx", "projectHash": "xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx...", "startTime": "2026-03-30T10:28:04.070Z", "lastUpdated": "2026-03-30T10:28:16.793Z", "messages": [ { "id": "xxxxxxxx-...", "timestamp": "2026-03-30T10:28:04.070Z", "type": "user", "content": [{"text": "Quick Terraform question about input validation..."}] }, { "id": "xxxxxxxx-...", "timestamp": "2026-03-30T10:28:16.793Z", "type": "gemini", "content": "Yes, the validation is **worth adding**..." } ], "kind": "main" }Message types
typevaluecontentformat"user"{"text": "..."}blocks"gemini"Other message types (model changes, tool calls, etc.) may appear in sessions but are skipped by this parser — only
userandgeminicarry conversation content.Design decisions
Custom content extraction instead of shared
_extract_contentGemini user content blocks are
{"text": "..."}without a"type"field. The shared_extract_contenthelper in normalize.py expects{"type": "text", "text": "..."}(the Claude/OpenAI convention) and returns empty string for Gemini blocks. Rather than modifying the shared helper (which could affect 5 other parsers),_try_gemini_jsondoes its own extraction:"text"key from each blockFingerprints on
sessionId+messageskeysThe parser requires both
sessionIdandmessagesin the top-level dict. This prevents false positives on:mappingkey, nosessionIdchat_messageswrapper, nosessionIdSingle JSON file (not JSONL)
Unlike Codex (JSONL per line) and Claude Code (JSONL per line), Gemini stores the entire session as one JSON object with a
messagesarray. This means the parser registers in the_try_normalize_jsondispatcher alongside the other JSON parsers (afterjson.loads), not in the JSONL section.What's NOT handled (and why)
/resume save <tag>for manual checkpoints and conversation forking. These may create additional session files. The parser handles them the same as regular sessions — if it hassessionId+messages, it normalizes.None(same threshold as all other parsers)."user"and"gemini"message types are extracted. Tool calls, model changes, and thinking level changes are skipped — they're operational metadata, not conversation content./chat shareexports: Gemini can export conversations to Markdown or JSON via/chat share. The exported JSON format may differ from the auto-saved session format. This parser targets auto-saved sessions only.Prior art
google-gemini/gemini-clilibrary)Changes
1 file changed (
mempalace/normalize.py), 47 insertions:_try_gemini_json()parser function with custom content extraction_try_normalize_json()dispatcher alongside other JSON parsersTest plan
ruff check mempalace/normalize.pypasses cleanruff format --checkalready formattedpython3 -m py_compile mempalace/normalize.pycompiles OK>marker transcriptsNonefor Claude AI JSON, ChatGPT JSON, Slack JSON, plain dict, empty dict, and list inputsRefs: #59