|
1 | | -# CodeCart Developer API Guide (v1.3) |
| 1 | +# CodeCart Protocol Specification (v2.0) |
2 | 2 |
|
3 | 3 | **English** | [简体中文](DEVELOPER_API.zh-CN.md) | [繁體中文](DEVELOPER_API.zh-TW.md) | [日本語](DEVELOPER_API.ja.md) |
4 | 4 |
|
5 | 5 | ## Purpose |
6 | 6 |
|
7 | | -This guide is for developers and researchers who work through API calls, scripts, multi-agent frameworks, or CI/CD pipelines rather than manually copying text in a browser. |
| 7 | +This document specifies the CodeCart round-trip protocol so that any AI product, agent framework, browser extension or script can read, write and stay compatible with a user's memory wallet. The protocol is deliberately tiny: it must survive being emitted by any LLM inside a plain chat reply. |
8 | 8 |
|
9 | | -## Core Architecture |
| 9 | +## The three artifacts |
10 | 10 |
|
11 | | -CodeCart v1.3 functions as a crystallized external memory layer. The architecture separates the human interface from the machine-readable state: |
| 11 | +1. **Carry block** — what the user pastes *into* an AI chat: active cards + an instruction asking the model to emit updates. |
| 12 | +2. **`codecart` block** — what the model appends to its replies: memory updates in a fenced code block. |
| 13 | +3. **Wallet file** — the exported JSON that holds all cards; the user's canonical, portable store. |
12 | 14 |
|
13 | | -- **Human-facing UI**: The portable HTML file. |
14 | | -- **Machine memory**: The exported JSON cartridge (v1.3 format). |
15 | | -- **Prompt builder**: Extracts only active (non-superseded) nodes to minimize token costs. |
16 | | -- **Model contract**: The LLM is instructed to output strictly in CodeCart DSL (`+CLAIM`, `>SUPERSEDE`, `+ANCHOR`). |
| 15 | +## 1. Carry block |
17 | 16 |
|
18 | | -## Standard API Workflow |
| 17 | +``` |
| 18 | +[My personal memory — CodeCart wallet, <date>. Use it to personalize every answer.] |
| 19 | +- (preference) Answer concisely, conclusion first |
| 20 | +- (fact) I run a small online store |
| 21 | +- (boundary) Never suggest options over my $200/month budget |
| 22 | +--- |
| 23 | +<instruction asking the model to append a codecart block — see the app for canonical wording> |
| 24 | +``` |
19 | 25 |
|
20 | | -### Step 1: Export the Cartridge |
21 | | -Export your current project state as a JSON file using the **Advanced Mode** in the CodeCart UI. |
| 26 | +Card types: `preference` (how to answer), `fact` (stable info), `status` (current focus, expected to change), `boundary` (hard rule). |
| 27 | + |
| 28 | +## 2. `codecart` block grammar |
| 29 | + |
| 30 | +The model appends, at the end of a reply: |
| 31 | + |
| 32 | + ```codecart |
| 33 | + + <type> | <content> |
| 34 | + ~ <fragment copied from an outdated memory line> => <corrected content> |
| 35 | + - <fragment of a memory line to retire> |
| 36 | + ``` |
| 37 | + |
| 38 | +- `+` adds a card. `<type>` is one of the four types; if omitted (`+ <content>`), consumers should default to `fact` — but only inside a fenced block, to avoid false positives. |
| 39 | +- `~` supersedes: the consumer finds the active card whose text contains `<fragment>` (case-insensitive), archives it, and adds the corrected card. This is what keeps wallets current instead of ever-growing. |
| 40 | +- `-` retires a card without replacement (fenced block only). |
| 41 | +- Recommended model rules (already in the carry instruction): max 5 lines, only durable personal info, write contents in the user's language, omit the block when nothing qualifies. |
| 42 | + |
| 43 | +Parsers should accept the lines outside a fence too, but only when an explicit `<type> |` prefix is present. |
| 44 | + |
| 45 | +## 3. Wallet file (JSON) |
| 46 | + |
| 47 | +```json |
| 48 | +{ |
| 49 | + "version": 2, |
| 50 | + "cards": [ |
| 51 | + { |
| 52 | + "id": "m3k9x1ab2", |
| 53 | + "type": "preference", |
| 54 | + "text": "Answer concisely, conclusion first", |
| 55 | + "status": "active", |
| 56 | + "created": 1720300000000, |
| 57 | + "updated": 1720300000000 |
| 58 | + } |
| 59 | + ] |
| 60 | +} |
| 61 | +``` |
22 | 62 |
|
23 | | -### Step 2: Build a Compact Context Block |
24 | | -Extract only relevant information to inject into your prompt. The following logic ensures you don't waste tokens on superseded nodes. |
| 63 | +`status` is `active` or `archived`. Consumers must carry only active cards, and must merge imports by skipping duplicate `text` values (case-insensitive, trimmed). |
25 | 64 |
|
26 | | -**Python Example:** |
| 65 | +## Reference: consuming a wallet in an API pipeline |
27 | 66 |
|
28 | 67 | ```python |
29 | 68 | import json |
30 | 69 |
|
31 | | -# Load v1.3 exported cartridge |
32 | | -with open('codecart_export.json', 'r', encoding='utf-8') as f: |
33 | | - cart = json.load(f) |
34 | | - |
35 | | -active_nodes = [] |
36 | | -for n in cart.get('nodes', []): |
37 | | - # Filter: Keep all anchors and only active claims |
38 | | - if n.get('type') == 'anchor' or not n.get('isSuperseded'): |
39 | | - active_nodes.append(f"[{n['id']}] {n['content']}") |
| 70 | +with open("codecart-wallet.json", encoding="utf-8") as f: |
| 71 | + wallet = json.load(f) |
40 | 72 |
|
41 | | -context_block = "[CODECART CONTEXT]\n" + "\n".join(active_nodes) |
42 | | -print(context_block) |
43 | | -``` |
44 | | - |
45 | | -### Step 3: Inject into Your Model Call |
46 | | -Force the LLM to process the context and return updates strictly in DSL format. |
47 | | - |
48 | | -```python |
49 | | -from openai import OpenAI |
50 | | - |
51 | | -client = OpenAI() |
52 | | - |
53 | | -system_prompt = ( |
54 | | - "You are an assistant with access to a CodeCart memory cartridge. " |
55 | | - "After analysis, summarize stable updates using CodeCart DSL only. " |
56 | | - "Use +CLAIM(id, 'content') for new logic and >SUPERSEDE(old, new, 'why') for updates." |
| 73 | +carry = "\n".join( |
| 74 | + f"- ({c['type']}) {c['text']}" |
| 75 | + for c in wallet["cards"] if c["status"] == "active" |
57 | 76 | ) |
58 | | - |
59 | | -messages = [ |
60 | | - {"role": "system", "content": f"{system_prompt}\n\n{context_block}"}, |
61 | | - {"role": "user", "content": "Review the current architecture and propose a scaling strategy."} |
62 | | -] |
63 | | - |
64 | | -resp = client.chat.completions.create( |
65 | | - model="gpt-4o", |
66 | | - messages=messages |
67 | | -) |
68 | | - |
69 | | -# The model returns raw DSL |
70 | | -print(resp.choices[0].message.content) |
| 77 | +# Prepend `carry` to your system prompt; parse ```codecart``` blocks |
| 78 | +# from model output with the grammar above and merge back. |
71 | 79 | ``` |
72 | 80 |
|
73 | | -### Step 4: Merge Back |
74 | | -Paste the model's DSL output back into the CodeCart **Advanced Mode** console and click **⚡ EXECUTE** to update your visual logic tree. |
75 | | - |
76 | | -## Rules for Good API Usage |
| 81 | +## Compatibility promises |
77 | 82 |
|
78 | | -1. **Token Efficiency**: Never inject "dead" (superseded) nodes into the prompt. |
79 | | -2. **Anchor Stability**: Use `+ANCHOR` for immutable project rules to prevent "model drift". |
80 | | -3. **Atomic Claims**: Ensure the LLM generates one node per discrete logical conclusion. |
81 | | -4. **Automated Snapshots**: Save JSON snapshots after major decision points in your pipeline. |
| 83 | +- The block tag is always the literal string `codecart`. |
| 84 | +- Unknown card types must be treated as `fact`, unknown JSON fields must be preserved on round-trip. |
| 85 | +- v1.3 legacy exports (`nodes` with `+CLAIM`/`+ANCHOR` semantics) map as: `anchor → boundary`, `claim → fact`, `isSuperseded → archived`. |
0 commit comments