Self-Updating Instructions (Procedural Memory)
Table of content
Your CLAUDE.md file is static. You write it once, update it manually when something breaks, and hope you remember to capture lessons learned. Most don’t. The same mistakes recur across sessions because the agent can’t learn from its own failures.
Self-updating instructions flip this model. The agent observes what works, what fails, and what you correct. It modifies its own operating instructions automatically. This is procedural memory: the “know-how” that persists across sessions.
CoALA’s memory model
The Cognitive Architectures for Language Agents (CoALA) paper by Sumers et al. divides agent memory into four types:
| Memory Type | Contents | Update Frequency |
|---|---|---|
| Working | Current context | Every turn |
| Episodic | Past experiences | Per session |
| Semantic | Facts and knowledge | When learned |
| Procedural | Operating instructions | When behavior changes |
Procedural memory stores the agent’s operational knowledge. This includes prompt templates, code snippets for common tasks, and decision-making rules. Unlike episodic memory (what happened), procedural memory encodes how to act.
Most AI tools only implement working memory. Some add episodic (conversation history). Almost none update procedural memory automatically.
Generative agents: where this started
The 2023 Generative Agents paper from Stanford built a simulated town where 25 AI agents lived, formed relationships, and organized events without scripting. The agents decided what to do based on memories of past interactions.
Their memory architecture:
Observe → Store → Retrieve → Reflect → Plan → Act
Observations feed into a memory stream. Each observation gets scored on recency and importance. When accumulated importance exceeds a threshold (roughly 2-3 times per day), the agent generates reflections: higher-level, abstract thoughts synthesized from recent observations.
These reflections become retrievable alongside raw observations. When planning actions, the agent queries its memory for relevant observations and reflections, then decides what to do.
Reflections are not summaries. They’re generalizations. An agent that observes “Isabella always greets me warmly” and “Isabella invited me to her party” might reflect “Isabella considers me a friend.” That reflection changes how the agent behaves toward Isabella going forward.
Ablation studies showed all three components matter. Remove reflection and agents lose coherence over time.
Lance Martin’s Claude Diary
Lance Martin of LangChain built a working implementation of self-updating instructions for Claude Code. His claude-diary plugin transforms session logs into persistent rules that update CLAUDE.md automatically.
The approach:
- Session logs accumulate in
~/.claude/projects/ - At session end, an LLM reads the logs
- It extracts generalizable lessons (“when X happens, do Y”)
- These become new rules in
CLAUDE.md
Episodic memory becomes procedural memory. The agent learns your preferences without you encoding them by hand.
Example transformation:
Session log: "User corrected agent's TypeScript. Agent used 'any' type,
user requested explicit types. Agent redid with interfaces."
Generated rule: "Always use explicit TypeScript types. Prefer interfaces
over 'any'. Ask for type definitions if unclear."
The rule persists across sessions. Future Claude instances start with this knowledge built in.
Alex Newman’s claude-mem
Alex Newman’s claude-mem takes a different approach to the same problem. Rather than extracting rules, it compresses observations and injects relevant context at session start.
The philosophy: “Memory isn’t storage. It’s compression.”
Observe → Compress → Store → Retrieve → Inject
Each tool call during a session generates an observation. These get compressed to roughly 500 tokens each, then stored with embeddings for retrieval. At the next session start, relevant memories load automatically.
This preserves context without manual CLAUDE.md updates. The agent remembers what it did, which tools worked, and what you corrected. It can’t modify its base instructions, but it can recall similar situations.
The difference:
| Approach | What Updates | Granularity | Explicitness |
|---|---|---|---|
| Claude Diary | Instructions in CLAUDE.md | Broad rules | Human-readable rules |
| claude-mem | Contextual memories | Specific observations | Implicit patterns |
Both beat static instructions. Claude Diary writes explicit rules. claude-mem retrieves relevant past observations.
Implementation patterns
Extract-and-write
The simplest form. Parse session logs, extract lessons, append to instructions.
def update_instructions(session_log, instructions_file):
lessons = llm.extract(
session_log,
prompt="What reusable lessons should be added to the agent's instructions?"
)
if lessons:
with open(instructions_file, "a") as f:
f.write(f"\n## Learned from session {session_id}\n")
f.write(lessons)
Simple, explicit, auditable. But instructions grow without bound and duplicates pile up.
Reflection triggers
Like Generative Agents, trigger reflection when importance accumulates past a threshold.
class AgentMemory:
def __init__(self, reflection_threshold=100):
self.observations = []
self.importance_sum = 0
self.threshold = reflection_threshold
def observe(self, event):
importance = self.score_importance(event)
self.observations.append((event, importance))
self.importance_sum += importance
if self.importance_sum > self.threshold:
self.reflect()
self.importance_sum = 0
def reflect(self):
recent = self.observations[-20:] # Last 20 observations
reflection = llm.synthesize(
recent,
prompt="What patterns or lessons emerge from these observations?"
)
self.observations.append((reflection, high_importance))
Self-regulating. Can produce useful generalizations. But reflection quality varies and failures are hard to trace.
Correction detection
When users override agent output, that’s signal. Watch for corrections specifically.
def on_user_edit(original, corrected, context):
if significant_difference(original, corrected):
lesson = llm.extract(
f"Original: {original}\nCorrected: {corrected}\nContext: {context}",
prompt="What should the agent do differently next time?"
)
add_to_procedural_memory(lesson)
Corrections are failures. Capturing them builds memory around your actual preferences and edge cases.
What to update
Not all observations should become instructions. Filter for:
| Update Type | Example | Value |
|---|---|---|
| Preferences | “Use tabs not spaces” | High |
| Corrections | “Don’t commit .env files” | High |
| Patterns | “Always run tests before commit” | High |
| One-off fixes | “Fixed typo in config.json” | Low |
| Context | “Working on auth feature” | Episodic only |
Preferences and corrections become procedural memory. One-off fixes and contextual notes stay episodic.
What goes wrong
Self-updating instructions fail in predictable ways:
| Risk | Example | Mitigation |
|---|---|---|
| Overfitting | One bad experience becomes absolute rule | Require multiple observations before rule creation |
| Contradiction | New rule conflicts with existing rule | Check for conflicts before adding |
| Unbounded growth | Instructions file becomes unmanageable | Set size limits, prune old rules |
| Drift | Agent behavior diverges from intent | Human review of new rules |
| Lock-in | Early mistakes become permanent | Version control, periodic review |
The CoALA paper warns that procedural updates “are risky both for the agent’s functionality and alignment.” Review generated rules before they take effect.
Practical setup
For Claude Code users, start with one of these approaches:
Manual reflection (no plugins required):
End each session with: “What lessons from this session should be added to CLAUDE.md?”
Review suggestions, add the good ones manually. This builds the habit without automation risk.
claude-diary (automated rules):
Install from Lance Martin’s repo. Configure which sessions should trigger reflection. Review generated rules in git diffs before committing.
claude-mem (automated context):
Install via /plugin marketplace add thedotmack/claude-mem. Memories inject automatically at session start. No instruction modification; context comes from retrieval.
Why bother
Static instructions rot. You write them once, update when something breaks badly enough to notice, and lose most lessons along the way.
Self-updating instructions make the agent learn from its own sessions. It observes what works, encodes that as procedural knowledge, and starts smarter next time.
The risk is drift. Automated updates can accumulate bad rules. But manual updates require discipline most people lack. I’d rather review auto-generated rules than pretend I’ll maintain a CLAUDE.md file by hand.
Next: AI Memory Compression
Get updates
New guides, workflows, and AI patterns. No spam.
Thank you! You're on the list.