npc-clients-python/tests/test_list_saved_integration.py

222 lines
7.3 KiB
Python

#!/usr/bin/env python3
"""Integration tests for list_saved returning chattable NPC objects"""
import pytest
import asyncio
from typing import List
from gumyum_npc_client import GumYumClient as AsyncClient, NPC, ChatCompletion
from gumyum_npc_sync import GumYumClient as SyncClient
@pytest.mark.asyncio
@pytest.mark.integration
async def test_list_saved_returns_npcs_with_chat_async():
"""Test that list_saved returns NPC objects with chat functionality (async)"""
client = AsyncClient("http://localhost:8081")
try:
# Authenticate
await client.auth.register(
"test_list_saved_async", "password123", "test_list_saved@example.com"
)
# Create a universe
universe_data = {
"name": "List Saved Test Universe",
"description": "Testing list_saved functionality",
"theme": {"setting": "fantasy", "time_period": "medieval"},
}
universe_id = await client.universes.create(universe_data)
# Spawn and save some NPCs
saved_npc_ids = []
for i in range(3):
npc = await client.npc.spawn(universe_id, seed=12345 + i, npc_id=5000 + i)
saved = await client.npc.save(
universe_id=universe_id,
seed=12345 + i,
npc_id=npc.npc_id,
custom_name=f"Saved NPC {i+1}",
)
saved_npc_ids.append(saved.npc_id)
# List saved NPCs
saved_npcs = await client.npc.list_saved()
# Verify we get NPC objects
assert isinstance(saved_npcs, list)
assert len(saved_npcs) >= 3
# Find our saved NPCs
our_npcs = [npc for npc in saved_npcs if npc.npc_id in saved_npc_ids]
assert len(our_npcs) == 3
# Test that each NPC can chat
for npc in our_npcs:
# Verify it's an NPC object
assert isinstance(npc, NPC)
assert hasattr(npc, "chat")
assert hasattr(npc, "completions")
assert npc.client is not None
# Test chat.completions()
response = await npc.chat.completions(
[{"role": "user", "content": "Hello! What's your name?"}]
)
assert isinstance(response, ChatCompletion)
assert response.choices[0].message.content
assert len(response.choices[0].message.content) > 0
# Test completions() alias
response2 = await npc.completions(
[{"role": "user", "content": "What do you do?"}]
)
assert isinstance(response2, ChatCompletion)
assert response2.choices[0].message.content
# Test streaming
stream = await npc.chat.completions(
[{"role": "user", "content": "Count to three"}], stream=True
)
chunks = []
async for chunk in stream:
chunks.append(chunk)
assert len(chunks) > 0
# Test conversation with history
test_npc = our_npcs[0]
messages = [
{"role": "user", "content": "My favorite color is purple"},
{"role": "assistant", "content": "Purple is a lovely color!"},
{"role": "user", "content": "What's my favorite color?"},
]
response = await test_npc.completions(messages)
assert "purple" in response.choices[0].message.content.lower()
# Clean up - delete saved NPCs
for npc_id in saved_npc_ids:
await client.npc.delete(npc_id)
finally:
await client.close()
@pytest.mark.integration
def test_list_saved_returns_npcs_with_chat_sync():
"""Test that list_saved returns NPC objects with chat functionality (sync)"""
client = SyncClient("http://localhost:8081")
try:
# Authenticate
client.auth.register(
"test_list_saved_sync", "password123", "test_list_saved_sync@example.com"
)
# Create a universe
universe_data = {
"name": "List Saved Test Universe Sync",
"description": "Testing list_saved functionality sync",
"theme": {"setting": "sci-fi", "time_period": "future"},
}
universe_id = client.universes.create(universe_data)
# Spawn and save some NPCs
saved_npc_ids = []
for i in range(3):
npc = client.npc.spawn(universe_id, seed=22222 + i, npc_id=6000 + i)
saved = client.npc.save(
universe_id=universe_id,
seed=22222 + i,
npc_id=npc.npc_id,
custom_name=f"Sync Saved NPC {i+1}",
)
saved_npc_ids.append(saved.npc_id)
# List saved NPCs
saved_npcs = client.npc.list_saved()
# Verify we get NPC objects
assert isinstance(saved_npcs, list)
assert len(saved_npcs) >= 3
# Find our saved NPCs
our_npcs = [npc for npc in saved_npcs if npc.npc_id in saved_npc_ids]
assert len(our_npcs) == 3
# Test that each NPC can chat
for npc in our_npcs:
# Verify it's an NPC object
assert isinstance(npc, NPC)
assert hasattr(npc, "chat")
assert hasattr(npc, "completions")
assert npc.client is not None
# Test chat.completions()
response = npc.chat.completions(
[{"role": "user", "content": "Hello! What's your name?"}]
)
assert isinstance(response, ChatCompletion)
assert response.choices[0].message.content
assert len(response.choices[0].message.content) > 0
# Test completions() alias
response2 = npc.completions(
[{"role": "user", "content": "What technology do you use?"}]
)
assert isinstance(response2, ChatCompletion)
assert response2.choices[0].message.content
# Test streaming
stream = npc.chat.completions(
[{"role": "user", "content": "Count to three"}], stream=True
)
chunks = list(stream)
assert len(chunks) > 0
# Test parameters
test_npc = our_npcs[0]
response = test_npc.chat.completions(
[{"role": "user", "content": "Say hello"}], temperature=0.5, max_tokens=20
)
assert isinstance(response, ChatCompletion)
# Clean up - delete saved NPCs
for npc_id in saved_npc_ids:
client.npc.delete(npc_id)
finally:
client.close()
@pytest.mark.asyncio
@pytest.mark.integration
async def test_list_saved_empty_returns_empty_list():
"""Test that list_saved returns empty list when no saved NPCs"""
client = AsyncClient("http://localhost:8081")
try:
# Create new user with no saved NPCs
await client.auth.register(
"test_empty_list", "password123", "test_empty@example.com"
)
# List saved NPCs (should be empty)
saved_npcs = await client.npc.list_saved()
assert isinstance(saved_npcs, list)
assert len(saved_npcs) == 0
finally:
await client.close()
if __name__ == "__main__":
# Run async tests
asyncio.run(test_list_saved_returns_npcs_with_chat_async())
asyncio.run(test_list_saved_empty_returns_empty_list())
# Run sync test
test_list_saved_returns_npcs_with_chat_sync()
print("✅ All list_saved integration tests passed!")