SSD Nodes Learn 🎉 VPS החל מ־$5.50/חודש
מדריכים Matt Connorמאת Matt Connor · עודכן 2026-08-07

התקנת Memmy כמרכז זיכרון משותף לסוכני AI על שרת VPS

למדו כיצד להקים את Memmy על שרת Ubuntu כדי להעניק לסוכני AI כמו Claude Code ו-Cursor זיכרון משותף. הפעילו את השירות בפורט 18960 ונהלו את כל נתוני הסוכנים בבסיס SQLite מקומי.

Verified Every command ran end-to-end on a fresh Ubuntu 24.04 server, July 31, 2026.

מהו Memmy ומה הוא מאחסן

Memmy הוא מרכז זיכרון מקומי עבור סוכני AI, הפועל על ה-VPS (שרת וירטואלי פרטי) שלכם. הוא מנהל מסד נתונים מסוג SQLite אחד שבו נשמר כל מה שהסוכנים שלכם למדו, וכל סוכן על השרת קורא וכותב לאותו מאגר. הפרויקט הוא memmy-agent מבית MemTensor, מופץ תחת רישיון MIT, ובגרסה 1.0.4 נכון ליולי 2026.

רק חלק מהרכיבים רלוונטיים לשרת. Memmy מספק שירות זיכרון המאזין ב-http://127.0.0.1:18960, ממשק שורת פקודה (CLI) מסוג memmy-memory המתקשר עם שירות זה, וסביבת עבודה שולחנית. סביבת העבודה ארוזה עבור macOS ו-Windows בלבד, לכן ב-Linux VPS אתם מריצים את השירות ואת ה-CLI. זה מספיק כדי להעניק ל-Claude Code, ל-Codex ול-Cursor זיכרון משותף.

Memmy ממיין את המידע שהוא מאחסן לארבע שכבות. L1 Trace הוא התיעוד הגולמי של האינטראקציה: הבקשה, התגובה וקריאות הכלים. L2 Policy הוא נוהל שהוסק מתוך התיעודים והוכח כמועיל. L3 World Model הוא ידע יציב אודות פרויקט או סביבה. Skill הוא נוהל בר-הפעלה שהתגבש מתוך מדיניות. השירות מקצה שכבה בעת קליטת אינטראקציה, כך שאין צורך ליצור אותן ידנית.

מה משתנה במרכז זיכרון משותף לעומת זיכרון נפרד לכל כלי

כיום, כל סוכן (agent) מנהל זיכרון משלו. Claude Code שומר קובצי הנחיות בתוך ה-repository. Cursor שומר חוקים בתוך מסד הנתונים של ה-workspace. Codex שומר לוגים של סשנים תחת ~/.codex. כל מאגר שייך לכלי אחד בלבד, לכן עובדה שלימדת ביום שני בכלי אחד, אינה ידועה ביום שלישי בכלי אחר. אתם משלמים על כך פעמיים: פעם אחת ב-tokens שמתבזבזים על הסבר חוזר של אותו פרויקט, ופעם שנייה בעבודה שגויה כאשר סוכן פועל על סמך הנחה שכבר תיקנתם במקום אחר.

מרכז (hub) מוציא את האחסון מתוך הכלי. Memmy קורא גם את המאגרים הקיימים, כך שלא מתחילים ממסד נתונים ריק. הסורק שלו מכיר שישה מקורות: Claude Code ב-~/.claude/projects/**/*.jsonl, Codex ב-~/.codex/sessions/<YYYY>/<MM>/<DD>/rollout-*.jsonl, OpenCode ב-~/.local/share/opencode/opencode.db, קובצי ה-state.vscdb של Cursor, מסדי הנתונים מסוג SQLite של OpenClaw תחת ~/.openclaw, ו-Hermes תחת ~/.hermes. ניתן להוסיף מקור באופן ידני על ידי ציון שם ונתיב מקומי.

מוני הייבוא לא יתאימו זה לזה, וזה צפוי. הסורק מקבץ הודעות לפי מקור ושיחה, ואז כותב זיכרון L1 אחד לכל סבב (turn) מלא. סבב נחשב למלא כאשר יש בו תוכן משתמש שאינו ריק והוא מסתיים בהודעת עוזר שאינה ריקה, לכן סשן שנקטע אינו תורם דבר. הודעות עוברות דה-דופליקציה (deduplication) באמצעות נקודות ביקורת של שיחה ומזהי סבב יציבים. מספר הפריטים שנסרקו, מספר ההודעות שיובאו ומספר הזיכרונות החדשים יהיו שונים באותה הרצה.

זהו הרכיב שמשתלב עם האופן שבו Claude Code מנהל הקשר בתוך סשן בודד. ניהול הקשר קובע מה נכנס לחלון בודד. מרכז זיכרון קובע מה שורד לאחר שהחלון הזה נסגר.

מה נדרש בשרת ה-VPS

  • גרסת Node.js 22 ומעלה. התיעוד של Memmy מחייב זאת, בעוד ש-Ubuntu 24.04 מספקת את Node 18.
  • git וכלי פיתוח (build toolchain), כיוון ש-better-sqlite3 הוא מודול מקורי שעשוי לעבור הידור (compile) במהלך ההתקנה.
  • כ-2 GB של זיכרון RAM. התקנת ה-root מושכת סביבת עבודה גדולה ושרשרת הידור עבור ה-frontend.
  • מספר GB פנויים בדיסק עבור node_modules ומסד הנתונים.
sudo apt update
sudo apt install -y git build-essential python3 curl ca-certificates sqlite3
curl -fsSL https://deb.nodesource.com/setup_22.x | sudo -E bash -
sudo apt install -y nodejs
node --version

node --version אמור להדפיס v22 או גרסה גבוהה יותר. v18 כאן מעיד על כך ששלב ה-NodeSource לא הושלם בהצלחה, וההתקנה תיכשל בהמשך בבדיקת ה-engine של הפרויקט.

התקנת Memmy ממקור על Ubuntu 24.04

git clone https://github.com/MemTensor/memmy-agent.git
cd memmy-agent
cp .env.example .env
npm install
npm run memory:build

npm run memory:build מהדר את ה-workspace של @memmy/memory לתוך Memory/dist. אין צורך לבנות שום דבר אחר בעץ עבור שרת ללא ממשק גרפי (headless). ודאו שהמודול המקורי נטען:

node -e "require('better-sqlite3'); console.log('better-sqlite3 loads')"

אם השורה הזו זורקת שגיאה במקום להדפיס פלט, המודול המקורי אינו תואם לגרסת ה-Node שלכם. הריצו את npm rebuild better-sqlite3, שזה בדיוק מה שסקריפט ההפעלה של הפרויקט עושה לפני שהוא מפעיל כל דבר אחר.

ה-README מתעד את bash scripts/dev-start.sh כפקודה אחת להפעלה. אל תריצו אותה על שרת VPS ללא ממשק גרפי. היא מפעילה את מעטפת שולחן העבודה Electron ושרת פיתוח Vite בפורט 19000 לצד שירות הזיכרון, ו-Electron זקוק לתצוגה. לכן, בשרת ללא סשן גרפי, הסקריפט ייתקע או ייסגר.

הפעלת שירות הזיכרון ובדיקת תקינות המענה

npm run memory:serve:dev

זוהי הדרך המתועדת להרצת שירות הזיכרון מתוך קוד המקור. השירות מאזין ל-127.0.0.1:18960, שומר את מסד הנתונים ב-~/.memmy/memory-service/memory.sqlite, וקורא את התצורה מ-~/.memmy/config.yaml. ה-README מפרט את אותם הערכים כאשר נדרשת הגדרה מפורשת:

npm run memory:serve:dev -- \
  --host 127.0.0.1 --port 18960 \
  --db ~/.memmy/memory-service/memory.sqlite \
  --config ~/.memmy/config.yaml

מתוך טרמינל שני, בדקו אם השירות פעיל:

curl -sS http://127.0.0.1:18960/api/v1/health

נקודת הקצה health היא היחידה שאינה דורשת אסימון (token), ולכן היא הבדיקה המתאימה ביותר. אם הפקודה curl מסתיימת עם קוד 7 והודעת Failed to connect to 127.0.0.1 port 18960, סימן שאין תהליך שמאזין בפורט. עיינו בטרמינל שבו רץ השירות, שכן קריסה בעת העלייה תודפס שם; הסיבה הנפוצה לכך היא כשל בטעינת מודול ה-SQLite המקומי. ss -lntp | grep 18960 מאשר את קיום ה-socket ברגע שהשירות עלה.

שאר ה-API (ממשק תכנות יישומים) מבוסס ה-HTTP נמצא תחת /api/v1.

  • POST /api/v1/memory/add כותב זיכרון ו-POST /api/v1/memory/search מבצע שאילתה.
  • GET /api/v1/memory/:id ו-DELETE /api/v1/memory/:id קוראים ומוחקים רשומה בודדת.
  • POST /api/v1/sessions/open ו-POST /api/v1/sessions/:sessionId/close מגדירים את תחילת וסוף הסשן של הסוכן.
  • POST /api/v1/turns/start ו-POST /api/v1/turns/:turnId/complete מתעדים תור (turn) בודד.
  • GET /api/v1/panel/overview, /api/v1/panel/analysis ו-/api/v1/panel/items מזינים את לוח הבקרה (dashboard).

Memmy שומר לעצמו טווח פורטים. בגרסה ללא ממשק גרפי (headless) נעשה שימוש רק בראשון: 18960 עבור הזיכרון, 18970 עבור תקינות ה-gateway, 18980 עבור ממשק ה-web וניהול ה-HTTP, 18990 עבור ה-API התואם ל-OpenAI ש-memmy serve מפעיל, ולאחר מכן 19000 ו-19010 עבור שרת הפיתוח של ה-frontend. אם שירות אחר במכונה שלכם כבר תופס אחד מהפורטים הללו, זהו המקום לבדוק בו.

מקור הפקודה memmy-memory

כאן מתרחשות בדרך כלל טעויות בהתקנה הראשונית, לכן מומלץ לקרוא את המידע מהחבילה במקום לנחש. שם הפקודה אינו קשור לשם המאגר (repository). הוא מגיע מהשדה bin של סביבת העבודה המגדירה אותו:

node -p "JSON.stringify(require('./Memory/package.json').bin)"

פעולה זו מדפיסה את {"memmy-memory":"./dist/src/cli/index.js"}. לכן, נקודת הכניסה שנבנתה היא Memory/dist/src/cli/index.js, והיא קיימת רק לאחר npm run memory:build, כיוון שהתהליך שיוצר את dist הוא זה שמסמן את הקובץ כניתן להרצה. הריצו אותו ישירות:

node Memory/dist/src/cli/index.js health

אם ברצונכם להשתמש בשם הקצר בתוך ה-PATH שלכם, צרו קישור לאותו קובץ:

sudo ln -s "$PWD/Memory/dist/src/cli/index.js" /usr/local/bin/memmy-memory
memmy-memory health

ה-CLI משתמש ב-http://127.0.0.1:18960 כברירת מחדל ומקבל את --url, --token, --config, --source ו---user-id. תתי-הפקודות שלו הן init, health, search, add, get ו-delete, בנוסף לקריאות session ו-turn שסוכנים (agents) משתמשים בהן ולא בני אדם. memmy-memory search "deploy steps" ו-memmy-memory add "staging migrates on deploy" הן השתיים שסוכן מריץ בתדירות הגבוהה ביותר.

כיצד מחברים את Claude Code ל-Memmy?

ל-Claude Code אין ממשק תוספי זיכרון, ולכן Memmy לא מתחבר אליו ישירות. האינטגרציה פשוטה יותר. Claude Code מריץ את memmy-memory כפקודת shell רגילה, וקובץ הוראות מנחה אותו מתי לעשות זאת. מתקין ה-Memmy המתועד כותב עבורך את הקובץ הזה: memmy-memory init --agent מציב קובץ הוראות זיכרון בתיקיית הכללים של הסוכן (agent) המיועד.

כתבו את ההוראה ידנית פעם אחת, כך תדעו בדיוק מה נאמר לסוכן. Claude Code קורא את CLAUDE.md משורש הפרויקט בתחילת כל סשן, לכן מקטע כזה מהווה את כל האינטגרציה:

## Memory

Before starting a task, run `memmy-memory search "<topic>"` and read what comes back.
When a task is done, run `memmy-memory add "<what you learned>"` for anything that will matter next session.

היו ברורים לגבי התועלת בכך. זוהי אינטגרציה ברמת ההוראה, לכן היא פועלת רק כאשר המודל מחליט להריץ את הפקודה, ולא מעבר לכך. שום דבר לא כופה את הקריאה. אם סשן מסתיים ללא add, דבר לא נשמר, והסימן היחיד לכך הוא תוצאה ריקה בחיפוש הבא שלכם. זהו אותו פשר (trade-off) הקיים ב-קבצי הזיכרון של Claude Code עצמו, עם הבדל אחד: המאגר משותף, כך שההערה מגיעה גם ל-Codex ול-Cursor באותה מכונה.

הכיוון השני אינו דורש הגדרה כלל. הסורק של Memmy כבר קורא את ~/.claude/projects/**/*.jsonl, המקום שבו Claude Code כותב את תמלילי הסשנים שלו. הריצו את Memmy על אותו שרת שבו אתם מריצים את Claude Code בתוך סשן tmux, והעבודה של אתמול הופכת לזיכרון מבלי שתצטרכו להגדיר דבר.

האם Memmy עובד כשרת MCP עבור Claude Code?

לא, והכרת הכיוון הנכון תחסוך לכם אחר צהריים שלם. ל־MCP (פרוטוקול הקשר למודלים) יש לקוחות ושרתים. Memmy הוא לקוח. הוא מתחבר לשרתי MCP ומציע את הכלים שלהם לסביבת ההרצה של הסוכן שלו. הוא אינו מפרסם נקודת קצה (endpoint) של MCP ש־claude mcp add יכול להצביע אליה. גשר ה־MCP היחיד במאגר שייך לאינטגרציה של Composio בתוך ה-API המקומי של שולחן העבודה, ו־API זה מאזין לפורט אקראי ב-127.0.0.1 מאחורי ה-header מסוג x-memmy-mcp-token.

צד הלקוח מוגדר ב-~/.memmy/config.yaml, הקובץ ש-MEMMY_CONFIG מצביע עליו, תחת tools.mcpServers:

tools:
  mcpServers:
    example:
      type: stdio
      command: npx
      args:
        - "-y"
        - "your-mcp-server"
      toolTimeout: 30
      enabledTools:
        - "*"

type מקבל stdio, sse ו-streamableHttp. שרת stdio רץ כתהליך בן (child process) של Memmy, מה שאומר שהפקודה שלו חייבת להיות קיימת על אותו שרת ולרוץ תחת אותו משתמש. אם אתם כבר מחזיקים שרתי MCP רצים על VPS, אלו השרתים שיש לרשום כאן.

שמירה על פרטיות מאגר הזיכרון

כל מה ש־Memmy מחזיק נמצא תחת ~/.memmy: config.yaml, סביבת העבודה, memory-service/memory.sqlite וקבצי זמן הריצה. הסריקה והקליטה מתבצעות מקומית, והזיכרונות נכתבים לקובץ SQLite מקומי, כך שברירת המחדל היא פעולה מקומית בלבד.

שני נתיבים מגיעים לרשת. MEMMY_CLOUD_SERVICE מוגדר כברירת מחדל ל־https://memmy-api.memtensor.cn ומגבה את מצב החשבון עם אסימוני הניסיון שלו, לכן מצב מפתח API לעולם אינו פונה אליו. תוכנית שיפור הזיכרון היא מתג נפרד בהגדרות הפרטיות, והיא כבויה עד שתפעיל אותה.

נתיב שלישי קל יותר לפספס. אם תגדיר ספק הטמעות (embedding provider) מאוחסן, הטקסט של כל זיכרון יישלח לאותו ספק כדי להפוך אותו לוקטור. אחסון מקומי אינו מונע זאת. נקודת קצה להטמעות שאתה מארח בעצמך היא הדרך היחידה לסגור נתיב זה.

שמור על פורט 18960 בכתובת ה-loopback. אין צורך בחוק firewall, כיוון ששירות המאזין ל-127.0.0.1 אינו נגיש כלל מחוץ למכונה. גש אליו מהמחשב הנייד שלך באמצעות SSH במקום זאת:

ssh -N -L 18960:127.0.0.1:18960 you@your-vps

אם תבחר להגדיר האזנה רחבה יותר, הגדר תחילה אסימון (token). הגדרת storage.token בקובץ התצורה, או שימוש במשתני הסביבה MEMMY_MEMORY_TOKEN או MEMORY_SERVICE_TOKEN, מחייבים שימוש ב-bearer token עבור כל נקודת קצה, למעט נקודת ה-health. ערכי התצורה תומכים בהפניות ${ENV_NAME}, כך שהאסימון ומפתחות ה-API של המודל שלך נשארים מחוץ לקובץ עצמו. זהו אותו הרגל כמו שמירה על סודות מחוץ לסוכני AI בכל מקום אחר, ו-מדיניות ufw של דחייה כברירת מחדל היא רשת הביטחון שלך אם גרסה עתידית תשנה את כתובת ההאזנה המוגדרת כברירת מחדל.

בצעו גיבוי ל-~/.memmy לפני שתסתמכו עליו

memory.sqlite הוא המאגר המלא. הווקטורים נמצאים באותו קובץ דרך הסיומת sqlite-vec, לכן קובץ אחד מהווה את הגיבוי. העתקתו באמצעות cp בזמן שהשירות כותב אליו עלולה להוביל לבסיס נתונים פגום. השתמשו בפקודת הגיבוי המובנית של SQLite:

mkdir -p ~/memmy-backup
sqlite3 ~/.memmy/memory-service/memory.sqlite ".backup '$HOME/memmy-backup/memory.sqlite'"

פעולה זו יוצרת עותק עקבי בזמן שהשירות ממשיך לרוץ. העבירו את הגיבוי מחוץ לשרת לפי לוח זמנים, לשם כך נועד restic לאחסון מרוחק. אובדן של config.yaml יעלה לכם בהגדרות הספק שניתן להקליד מחדש. אובדן של memory.sqlite יעלה לכם בכל הזיכרונות, ושום דבר אחר במכונה לא מחזיק עותק נוסף שלהם.

הרצת שירות הזיכרון תחת systemd

הרצה של npm run memory:serve:dev בתוך shell מסתיימת עם סגירת ה-shell. קובץ unit שומר על השירות פעיל גם לאחר אתחול המערכת.

[Unit]
Description=Memmy memory service
After=network-online.target

[Service]
Type=simple
User=memmy
WorkingDirectory=/opt/memmy/memmy-agent
EnvironmentFile=/etc/memmy/memory.env
ExecStart=/usr/bin/npm run memory:serve:dev
Restart=on-failure
RestartSec=5

[Install]
WantedBy=multi-user.target

שמרו את ה-token מחוץ לקובץ ה-unit. הציבו אותו בתוך /etc/memmy/memory.env, בבעלות root ועם הרשאות 600:

MEMMY_CONFIG=/home/memmy/.memmy/config.yaml
MEMMY_MEMORY_TOKEN=replace-this-with-a-long-random-string
sudo systemctl daemon-reload
sudo systemctl enable --now memmy-memory
systemctl status memmy-memory --no-pager
curl -sS http://127.0.0.1:18960/api/v1/health

הערך status=203/EXEC בפלט הסטטוס מציין ש-systemd לא הצליח להריץ את ExecStart כלל, לכן בדקו את which npm: בדרך כלל מדובר ב-/usr/bin/npm בהתקנת NodeSource, או בנתיב תחת ספריית הבית של המשתמש בשימוש ב-nvm, נתיב ש-systemd לא ימצא. יחידה שמתחילה ונסגרת מיד נכשלה בתוך npm, ו-journalctl -u memmy-memory -n 50 ידפיס את סיבת הכשל. המנגנון זהה לכל שירות systemd אחר ב-VPS.

מה Memmy עדיין לא מבצע

  • לא קיימת גרסה לשולחן עבודה עבור Linux. סקריפטי האריזה תומכים ב-macOS וב-Windows בלבד, לכן סביבת העבודה (workbench), אשף ההגדרה הראשונית ולוח הבקרה של הזיכרון אינם זמינים על השרת עצמו.
  • memory:serve:dev מריץ את נקודת הכניסה של TypeScript דרך tsx, נתיב המיועד לפיתוח. המאגר מספק גם את memory:serve עבור פלט שעבר הידור (compiled). הריצו את npm run ללא ארגומנטים כדי לראות אילו סקריפטים קיימים בפועל בגרסה שהורדתם.
  • מנגנון השליפה בונה את חלון החיפוש מ-2,000 שורות הווקטור האחרונות, ולאחר מכן מבצע בחירת Top-K בתוך חלון זה. במאגר נתונים גדול מאוד, זיכרון ישן עלול להישאר מחוץ לטווח זה.
  • הטמעת וקטורים (embedding) מתבצעת לאחר הלכידה, וכשל בתהליך זה מועבר לתור ניסיונות חוזרים במקום לחסום את פעולת הסוכן. זיכרון שנוסף לפני רגע עשוי שלא להיות זמין לחיפוש וקטורי באופן מיידי.
  • קובץ SQLite אחד משמעו צומת (node) אחד. אין תמיכה ב-clustering, לכן שרת שני מהווה זיכרון נפרד ועצמאי.

גרסה 1.0.4 וסביב 329 כוכבים נכון ליולי 2026 מעידים על פרויקט בשלבי פיתוח מוקדמים. דגלים (flags), נתיבים ושמות סקריפטים משתנים בין גרסאות. קראו את השדה bin ואת הפלט של npm run בגרסה המקומית שלכם, במקום להסתמך על פקודה שהועתקה ממקור חיצוני, כולל מכאן.

FAQ

מדוע בדיקת התקינות (health check) מחזירה connection refused?

שום תהליך אינו מאזין בפורט 18960. קוד יציאה 7 של curl עם Failed to connect to 127.0.0.1 port 18960 מציין ששירות הזיכרון אינו רץ או שקרס בעת העלייה, לכן יש לקרוא את הפלט בטרמינל או ב-journal שבו הוא הופעל. שתי הסיבות הנפוצות הן מודול native מסוג better-sqlite3 שאינו תואם לגרסת ה-Node שלכם, דבר שנפתר באמצעות npm rebuild better-sqlite3, או גרסת Node הנמוכה מ-22. ודאו את ה-socket באמצעות ss -lntp | grep 18960 ברגע שהשירות פעיל.

מאיפה מגיע הפקודה memmy-memory לאחר בנייה מקוד המקור?

מהשדה bin בחבילת ה-workspace של @memmy/memory, ולא משם המאגר (repository). הריצו את node -p "JSON.stringify(require('./Memory/package.json').bin)" בתוך ה-checkout והיא תדפיס את {"memmy-memory":"./dist/src/cli/index.js"}. קובץ זה קיים רק לאחר npm run memory:build, כיוון שהבנייה יוצרת את dist ומסמנת את הקובץ כניתן להרצה. הריצו אותו כ-node Memory/dist/src/cli/index.js health, או צרו קישור סימבולי (symlink) לתוך /usr/local/bin עבור שם מקוצר.

האם ניתן להוסיף את Memmy ל-Claude Code באמצעות claude mcp add?

לא. Memmy הוא לקוח MCP, לא שרת MCP. הוא מתחבר החוצה לשרתים המפורטים תחת tools.mcpServers ב-~/.memmy/config.yaml ומציע את הכלים שלהם לסביבת הריצה שלו. Claude Code מגיע ל-Memmy בכיוון ההפוך, על ידי הרצת ה-CLI של memmy-memory כפקודת shell, בהנחיית קובץ הוראות ש-memmy-memory init --agent כותב לתוך ספריית הכללים של הסוכן (agent).

האם הרצת Memmy שולחת את הזיכרונות שלי לשירות ענן?

הסריקה והקליטה מתבצעות מקומית, והזיכרונות נכתבים ל-~/.memmy/memory-service/memory.sqlite על הדיסק שלכם. MEMMY_CLOUD_SERVICE מצביע על https://memmy-api.memtensor.cn עבור מצב חשבון ואסימוני ניסיון (trial tokens), ותוכנית שיפור הזיכרון נשארת כבויה עד שתפעילו אותה. הנתיב שיש להשגיח עליו הוא ספק ה-embedding: מודל embedding מאוחסן מקבל את הטקסט של כל זיכרון שהוא הופך לוקטור, לכן השתמשו ב-endpoint שאתם מריצים בעצמכם אם הדבר חשוב לכם.