mirror of
https://github.com/basicmachines-co/basic-memory
synced 2026-06-21 13:47:35 +00:00
194 lines
5.2 KiB
Python
194 lines
5.2 KiB
Python
"""Tests for note tools that exercise the full stack with SQLite."""
|
|
|
|
import pytest
|
|
from mcp.server.fastmcp.exceptions import ToolError
|
|
|
|
from basic_memory.mcp.tools import notes
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_write_note(app):
|
|
"""Test creating a new note.
|
|
|
|
Should:
|
|
- Create entity with correct type and content
|
|
- Save markdown content
|
|
- Handle tags correctly
|
|
- Return valid permalink
|
|
"""
|
|
permalink = await notes.write_note(
|
|
title="Test Note",
|
|
content="# Test\nThis is a test note",
|
|
tags=["test", "documentation"]
|
|
)
|
|
|
|
assert permalink # Got a valid permalink
|
|
|
|
# Try reading it back
|
|
content = await notes.read_note(permalink)
|
|
assert "# Test\nThis is a test note" in content
|
|
assert "tags:" in content
|
|
assert "- '#test'" in content
|
|
assert "- '#documentation'" in content
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_write_note_no_tags(app):
|
|
"""Test creating a note without tags."""
|
|
permalink = await notes.write_note(
|
|
title="Simple Note",
|
|
content="Just some text"
|
|
)
|
|
|
|
# Should be able to read it back
|
|
content = await notes.read_note(permalink)
|
|
assert "Just some text" in content
|
|
assert "tags:" not in content
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_read_note_not_found(app):
|
|
"""Test trying to read a non-existent note."""
|
|
with pytest.raises(ToolError, match="Error calling tool: Client error '404 Not Found'"):
|
|
await notes.read_note("notes/does-not-exist")
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_write_note_update_existing(app):
|
|
"""Test creating a new note.
|
|
|
|
Should:
|
|
- Create entity with correct type and content
|
|
- Save markdown content
|
|
- Handle tags correctly
|
|
- Return valid permalink
|
|
"""
|
|
permalink = await notes.write_note(
|
|
title="Test Note",
|
|
content="# Test\nThis is a test note",
|
|
tags=["test", "documentation"]
|
|
)
|
|
|
|
assert permalink # Got a valid permalink
|
|
|
|
permalink = await notes.write_note(
|
|
title="Test Note",
|
|
content="# Test\nThis is an updated note",
|
|
tags=["test", "documentation"]
|
|
)
|
|
|
|
|
|
# Try reading it back
|
|
content = await notes.read_note(permalink)
|
|
assert "# Test\nThis is an updated note" in content
|
|
assert "tags:" in content
|
|
assert "- '#test'" in content
|
|
assert "- '#documentation'" in content
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_read_note_by_title(app):
|
|
"""Test reading a note by its title."""
|
|
# First create a note
|
|
await notes.write_note(
|
|
title="Special Note",
|
|
content="Note content here"
|
|
)
|
|
|
|
# Should be able to read it by title
|
|
content = await notes.read_note("Special Note")
|
|
assert "Note content here" in content
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_link_notes(app):
|
|
"""Test creating links between notes."""
|
|
# Create two notes
|
|
note1 = await notes.write_note(
|
|
title="Design Doc",
|
|
content="# Design\nSome design notes"
|
|
)
|
|
|
|
note2 = await notes.write_note(
|
|
title="Implementation",
|
|
content="# Implementation\nCode details"
|
|
)
|
|
|
|
# Link them
|
|
permalink = await notes.link_notes(
|
|
from_note=note1,
|
|
to_note=note2,
|
|
relationship="inspires",
|
|
context="Design informs implementation"
|
|
)
|
|
|
|
content = await notes.read_note(permalink)
|
|
assert "- inspires [[Implementation]] (Design informs implementation)" in content
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_note_unicode_content(app):
|
|
"""Test handling of unicode content in notes."""
|
|
content = "# Test 🚀\nThis note has emoji 🎉 and unicode ♠♣♥♦"
|
|
permalink = await notes.write_note(
|
|
title="Unicode Test",
|
|
content=content
|
|
)
|
|
|
|
# Read back should preserve unicode
|
|
result = await notes.read_note(permalink)
|
|
assert content in result
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_multiple_notes(app):
|
|
"""Test creating and managing multiple notes."""
|
|
# Create several notes
|
|
notes_data = [
|
|
("Note 1", "Content 1", ["tag1"]),
|
|
("Note 2", "Content 2", ["tag1", "tag2"]),
|
|
("Note 3", "Content 3", []),
|
|
]
|
|
|
|
permalinks = []
|
|
for title, content, tags in notes_data:
|
|
permalink = await notes.write_note(title=title, content=content, tags=tags)
|
|
permalinks.append(permalink)
|
|
|
|
# Should be able to read each one
|
|
for i, permalink in enumerate(permalinks):
|
|
content = await notes.read_note(permalink)
|
|
assert f"Content {i+1}" in content
|
|
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_delete_note_existing(app):
|
|
"""Test deleting a new note.
|
|
|
|
Should:
|
|
- Create entity with correct type and content
|
|
- Return valid permalink
|
|
- Delete the note
|
|
"""
|
|
permalink = await notes.write_note(
|
|
title="Test Note",
|
|
content="# Test\nThis is a test note",
|
|
tags=["test", "documentation"]
|
|
)
|
|
|
|
assert permalink # Got a valid permalink
|
|
|
|
deleted = await notes.delete_note(permalink)
|
|
assert deleted is True
|
|
|
|
@pytest.mark.asyncio
|
|
async def test_delete_note_doesnt_exist(app):
|
|
"""Test deleting a new note.
|
|
|
|
Should:
|
|
- Delete the note
|
|
- verify returns false
|
|
"""
|
|
deleted = await notes.delete_note("doesnt-exist")
|
|
assert deleted is False
|