163 lines
No EOL
9.6 KiB
Text
163 lines
No EOL
9.6 KiB
Text
{
|
|
"cells": [
|
|
{
|
|
"cell_type": "markdown",
|
|
"metadata": {},
|
|
"source": "# Hindsight-LangMem: Drop-in Semantic Memory for LangGraph\n\nReplace your LangGraph memory store in one line and get advanced semantic capabilities."
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"metadata": {},
|
|
"source": "## What is Hindsight-LangMem?\n\n`hindsight-langmem` implements LangGraph's `BaseStore` interface using Hindsight as the backend.\n\n### What You Get vs Standard LangGraph Memory\n\n| Feature | Standard Memory | Hindsight-LangMem |\n|---------|-----------------|-------------------|\n| Basic Key-Value Storage | ✅ | ✅ |\n| Semantic Search | ✅ Basic | ✅ **Enhanced with spreading activation** |\n| Namespace Support | ✅ | ✅ |\n| **Personality-Driven Retrieval** | ❌ | ✅ |\n| **Automatic Fact Extraction** | ❌ | ✅ |\n| **Entity Recognition** | ❌ | ✅ |\n| **Temporal Reasoning** | ❌ | ✅ |\n| **Opinion Formation** | ❌ | ✅ |\n| **Background Knowledge** | ❌ | ✅ |\n| **Thinking/Reasoning API** | ❌ | ✅ |\n\n### When to Use\n- Conversational agents needing long-term memory\n- Personalized AI with context-aware responses \n- Multi-agent systems with distinct personalities\n- Knowledge management with semantic search"
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"source": "## Installation\n\nRun this cell to install dependencies:",
|
|
"metadata": {}
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"source": "!pip install langgraph langmem",
|
|
"metadata": {},
|
|
"execution_count": null,
|
|
"outputs": []
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"source": "Make sure Hindsight API is running at `http://localhost:8888`",
|
|
"metadata": {}
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"source": "## Setup API Keys\n\nSet up your OpenAI API key and Hindsight URL:",
|
|
"metadata": {}
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"source": "import os\nimport getpass\n\n# Set OpenAI API key\nif \"OPENAI_API_KEY\" not in os.environ:\n os.environ[\"OPENAI_API_KEY\"] = getpass.getpass(\"Enter your OpenAI API key: \")\n\n# Set Hindsight API URL\nif \"HINDSIGHT_API_URL\" not in os.environ:\n os.environ[\"HINDSIGHT_API_URL\"] = input(\"Enter Hindsight API URL (default: http://localhost:8888): \") or \"http://localhost:8888\"\n\nprint(\"✅ API keys configured\")",
|
|
"metadata": {},
|
|
"execution_count": null,
|
|
"outputs": []
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"metadata": {},
|
|
"source": [
|
|
"## The Drop-in Replacement\n",
|
|
"\n"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"source": "### Before: Standard LangGraph Memory",
|
|
"metadata": {}
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"source": "from langmem import create_manage_memory_tool, create_search_memory_tool\nfrom langgraph.prebuilt import create_react_agent\nfrom langgraph.store.memory import InMemoryStore\n\n# Standard store - basic key-value with optional vector search\nstore = InMemoryStore()\n\nagent = create_react_agent(\n \"openai:gpt-4o\",\n tools=[\n create_manage_memory_tool(namespace=(\"memories\",)),\n create_search_memory_tool(namespace=(\"memories\",)),\n ],\n store=store\n)",
|
|
"metadata": {},
|
|
"execution_count": null,
|
|
"outputs": []
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"source": "### After: With Hindsight-LangMem\n\n**Just change one line!**",
|
|
"metadata": {},
|
|
"execution_count": null,
|
|
"outputs": []
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"metadata": {},
|
|
"source": "import os\nfrom langmem import create_manage_memory_tool, create_search_memory_tool\nfrom langgraph.prebuilt import create_react_agent\nfrom hindsight_langmem import HindsightStore # ← Only import change!\n\n# Replace InMemoryStore with HindsightStore\nbase_url = os.getenv(\"HINDSIGHT_API_URL\", \"http://localhost:8888\")\nstore = HindsightStore(base_url=base_url, default_agent_id=\"my_agent\") # ← One line change!\n\n# Everything else stays exactly the same\nagent = create_react_agent(\n \"openai:gpt-4o\", # ← Use OpenAI\n tools=[\n create_manage_memory_tool(namespace=(\"memories\",)),\n create_search_memory_tool(namespace=(\"memories\",)),\n ],\n store=store # ← Now using Hindsight with enhanced capabilities!\n)\n\nprint(\"✅ Agent created with Hindsight-powered memory\")",
|
|
"execution_count": null,
|
|
"outputs": []
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"metadata": {},
|
|
"outputs": [],
|
|
"source": "import os\nfrom langmem import create_manage_memory_tool, create_search_memory_tool\nfrom langgraph.prebuilt import create_react_agent\nfrom hindsight_langmem import HindsightStore # ← Only import change!\n\n# Replace InMemoryStore with HindsightStore\nbase_url = os.getenv(\"HINDSIGHT_API_URL\", \"http://localhost:8888\")\nstore = HindsightStore(base_url=base_url, default_agent_id=\"my_agent\") # ← One line change!\n\n# Everything else stays exactly the same\nagent = create_react_agent(\n \"anthropic:claude-3-5-sonnet-latest\",\n tools=[\n create_manage_memory_tool(namespace=(\"memories\",)),\n create_search_memory_tool(namespace=(\"memories\",)),\n ],\n store=store # ← Now using Hindsight with enhanced capabilities!\n)\n\nprint(\"✅ Agent created with Hindsight-powered memory\")"
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"metadata": {},
|
|
"source": [
|
|
"## Example: Conversational Memory in Action"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"metadata": {},
|
|
"outputs": [],
|
|
"source": [
|
|
"import time\n",
|
|
"\n",
|
|
"# Store information\n",
|
|
"result1 = agent.invoke({\n",
|
|
" \"messages\": [{\n",
|
|
" \"role\": \"user\",\n",
|
|
" \"content\": \"\"\"Remember: I'm David, a software engineer working on AI projects. \n",
|
|
" I love Python and machine learning. Currently building a chatbot with LangGraph.\"\"\"\n",
|
|
" }]\n",
|
|
"})\n",
|
|
"print(\"Agent:\", result1[\"messages\"][-1].content)\n",
|
|
"\n",
|
|
"time.sleep(2)\n",
|
|
"\n",
|
|
"# Recall information\n",
|
|
"result2 = agent.invoke({\n",
|
|
" \"messages\": [{\"role\": \"user\", \"content\": \"What do you remember about me?\"}]\n",
|
|
"})\n",
|
|
"print(\"\\nAgent:\", result2[\"messages\"][-1].content)"
|
|
]
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"metadata": {},
|
|
"source": "## What Happens Behind the Scenes\n\nWhen your agent stores memories with Hindsight, automatically:\n\n1. **Fact Extraction**: Natural language → structured facts\n2. **Entity Recognition**: Identifies people, places, concepts\n3. **Semantic Indexing**: Spreading activation for better retrieval\n4. **Temporal Awareness**: Event dates tracked for time queries\n5. **Opinion Formation**: Agent develops perspectives over time\n6. **Personality Influence**: Memory retrieval shaped by personality traits\n\n**You use the standard LangGraph API - Hindsight does the rest!**"
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"metadata": {},
|
|
"source": "# Different agents with different personalities\ncreative_store = HindsightStore(base_url=base_url, default_agent_id=\"creative_writer\")\nanalyst_store = HindsightStore(base_url=base_url, default_agent_id=\"data_analyst\")\n\ncreative_agent = create_react_agent(\n \"openai:gpt-4o\",\n tools=[\n create_manage_memory_tool(namespace=(\"creative\",)),\n create_search_memory_tool(namespace=(\"creative\",))\n ],\n store=creative_store\n)\n\nanalyst_agent = create_react_agent(\n \"openai:gpt-4o\",\n tools=[\n create_manage_memory_tool(namespace=(\"analysis\",)),\n create_search_memory_tool(namespace=(\"analysis\",))\n ],\n store=analyst_store\n)\n\nprint(\"✅ Two agents with isolated memories and distinct personalities\")",
|
|
"execution_count": null,
|
|
"outputs": []
|
|
},
|
|
{
|
|
"cell_type": "code",
|
|
"execution_count": null,
|
|
"metadata": {},
|
|
"outputs": [],
|
|
"source": "# Different agents with different personalities\ncreative_store = HindsightStore(base_url=base_url, default_agent_id=\"creative_writer\")\nanalyst_store = HindsightStore(base_url=base_url, default_agent_id=\"data_analyst\")\n\ncreative_agent = create_react_agent(\n \"anthropic:claude-3-5-sonnet-latest\",\n tools=[\n create_manage_memory_tool(namespace=(\"creative\",)),\n create_search_memory_tool(namespace=(\"creative\",))\n ],\n store=creative_store\n)\n\nanalyst_agent = create_react_agent(\n \"anthropic:claude-3-5-sonnet-latest\",\n tools=[\n create_manage_memory_tool(namespace=(\"analysis\",)),\n create_search_memory_tool(namespace=(\"analysis\",))\n ],\n store=analyst_store\n)\n\nprint(\"✅ Two agents with isolated memories and distinct personalities\")"
|
|
},
|
|
{
|
|
"cell_type": "markdown",
|
|
"metadata": {},
|
|
"source": "## Summary\n\n### The Change\n```python\n# Before\nstore = InMemoryStore()\n\n# After \nstore = HindsightStore(base_url=\"http://localhost:8888\", default_agent_id=\"my_agent\")\n```\n\n### What You Get\n- ✅ Semantic search with spreading activation\n- ✅ Automatic fact extraction from conversations\n- ✅ Entity recognition and linking\n- ✅ Temporal reasoning (time-aware queries)\n- ✅ Personality-driven memory retrieval\n- ✅ Opinion formation over time\n- ✅ Multi-agent support with isolated memories\n\n**Same LangGraph API. Smarter memory. Zero code changes (except the store line).**"
|
|
}
|
|
],
|
|
"metadata": {
|
|
"kernelspec": {
|
|
"display_name": "Python 3 (ipykernel)",
|
|
"language": "python",
|
|
"name": "python3"
|
|
},
|
|
"language_info": {
|
|
"codemirror_mode": {
|
|
"name": "ipython",
|
|
"version": 3
|
|
},
|
|
"file_extension": ".py",
|
|
"mimetype": "text/x-python",
|
|
"name": "python",
|
|
"nbconvert_exporter": "python",
|
|
"pygments_lexer": "ipython3",
|
|
"version": "3.11.10"
|
|
}
|
|
},
|
|
"nbformat": 4,
|
|
"nbformat_minor": 4
|
|
} |