v0.6.0 multi-user game support with longpoll, tests and doc updated

This commit is contained in:
2025-11-05 12:08:18 -05:00
parent a3f4db96fa
commit 52868af4ea
13 changed files with 708 additions and 120 deletions

213
test/test-longpoll.sh Executable file
View File

@ -0,0 +1,213 @@
#!/bin/bash
# test-longpoll.sh - Test long-polling functionality
set -e
# Configuration
API_URL="${API_URL:-http://localhost:8080/api/v1}" # Updated to include /api/v1
VERBOSE="${VERBOSE:-false}"
# Colors for output
RED='\033[0;31m'
GREEN='\033[0;32m'
YELLOW='\033[1;33m'
NC='\033[0m' # No Color
# Helper functions
log_info() {
echo -e "${GREEN}[INFO]${NC} $1"
}
log_error() {
echo -e "${RED}[ERROR]${NC} $1"
}
log_test() {
echo -e "${YELLOW}[TEST]${NC} $1"
}
# Function to create a test game
create_game() {
local white_type=$1
local black_type=$2
response=$(curl -s -X POST "$API_URL/games" \
-H "Content-Type: application/json" \
-d "{\"white\": {\"type\": $white_type}, \"black\": {\"type\": $black_type}}")
echo "$response" | jq -r '.gameId'
}
# Test 1: Basic long-polling
test_basic_longpoll() {
log_test "Basic long-polling functionality"
# Create a human vs human game
GAME_ID=$(create_game 1 1)
log_info "Created game: $GAME_ID"
# Start background poller
log_info "Starting long-poll request (25s timeout)..."
curl -s -X GET "$API_URL/games/$GAME_ID?wait=true&moveCount=0" > /tmp/poll_result.json &
POLL_PID=$!
# Wait a moment then make a move
sleep 2
log_info "Making move e2e4..."
curl -s -X POST "$API_URL/games/$GAME_ID/moves" \
-H "Content-Type: application/json" \
-d '{"move":"e2e4"}' > /dev/null
# Wait for poller to complete
if wait $POLL_PID; then
# Check if we got the updated game state
moves=$(cat /tmp/poll_result.json | jq -r '.moves | length')
if [ "$moves" = "1" ]; then
log_info "✓ Long-poll received notification successfully"
else
log_error "✗ Long-poll did not receive correct state"
exit 1
fi
else
log_error "✗ Long-poll request failed"
exit 1
fi
# Cleanup
curl -s -X DELETE "$API_URL/games/$GAME_ID" > /dev/null
}
# Test 2: Multiple concurrent waiters
test_multiple_waiters() {
log_test "Multiple concurrent waiters"
# Create a game
GAME_ID=$(create_game 1 1)
log_info "Created game: $GAME_ID"
# Start multiple background pollers
log_info "Starting 3 concurrent long-poll requests..."
curl -s -X GET "$API_URL/games/$GAME_ID?wait=true&moveCount=0" > /tmp/poll1.json &
PID1=$!
curl -s -X GET "$API_URL/games/$GAME_ID?wait=true&moveCount=0" > /tmp/poll2.json &
PID2=$!
curl -s -X GET "$API_URL/games/$GAME_ID?wait=true&moveCount=0" > /tmp/poll3.json &
PID3=$!
# Make a move
sleep 1
log_info "Making move e2e4..."
curl -s -X POST "$API_URL/games/$GAME_ID/moves" \
-H "Content-Type: application/json" \
-d '{"move":"e2e4"}' > /dev/null
# Wait for all pollers
wait $PID1 $PID2 $PID3
# Check all received the update
success=true
for i in 1 2 3; do
moves=$(cat /tmp/poll$i.json | jq -r '.moves | length')
if [ "$moves" != "1" ]; then
log_error "✗ Poller $i did not receive update"
success=false
fi
done
if $success; then
log_info "✓ All waiters received notifications"
else
exit 1
fi
# Cleanup
curl -s -X DELETE "$API_URL/games/$GAME_ID" > /dev/null
}
# Test 3: Timeout behavior
test_timeout() {
log_test "Timeout behavior (this takes 25 seconds)"
# Create a game
GAME_ID=$(create_game 1 1)
log_info "Created game: $GAME_ID"
# Start poller without making any moves
log_info "Starting long-poll that will timeout..."
start_time=$(date +%s)
curl -s -X GET "$API_URL/games/$GAME_ID?wait=true&moveCount=0" > /tmp/timeout.json
end_time=$(date +%s)
elapsed=$((end_time - start_time))
# Check timeout was ~25 seconds
if [ "$elapsed" -ge 24 ] && [ "$elapsed" -le 26 ]; then
log_info "✓ Request timed out after ~25 seconds"
else
log_error "✗ Timeout was $elapsed seconds (expected ~25)"
exit 1
fi
# Should still get valid game state
game_id=$(cat /tmp/timeout.json | jq -r '.gameId')
if [ "$game_id" = "$GAME_ID" ]; then
log_info "✓ Timeout response contains valid game state"
else
log_error "✗ Timeout response invalid"
exit 1
fi
# Cleanup
curl -s -X DELETE "$API_URL/games/$GAME_ID" > /dev/null
}
# Test 4: Immediate response when state already changed
test_immediate_response() {
log_test "Immediate response when state already changed"
# Create game and make a move
GAME_ID=$(create_game 1 1)
log_info "Created game: $GAME_ID"
curl -s -X POST "$API_URL/games/$GAME_ID/moves" \
-H "Content-Type: application/json" \
-d '{"move":"e2e4"}' > /dev/null
# Poll with moveCount=0 (should return immediately)
log_info "Polling with outdated move count..."
start_time=$(date +%s)
response=$(curl -s -X GET "$API_URL/games/$GAME_ID?wait=true&moveCount=0")
end_time=$(date +%s)
elapsed=$((end_time - start_time))
if [ "$elapsed" -le 1 ]; then
log_info "✓ Immediate response when move count differs"
else
log_error "✗ Response took $elapsed seconds (should be immediate)"
exit 1
fi
# Cleanup
curl -s -X DELETE "$API_URL/games/$GAME_ID" > /dev/null
}
# Run tests
log_info "Starting long-poll tests against $API_URL"
echo ""
test_basic_longpoll
echo ""
test_multiple_waiters
echo ""
test_immediate_response
echo ""
if [ "${SKIP_TIMEOUT_TEST:-false}" = "false" ]; then
test_timeout
else
log_info "Skipping timeout test (set SKIP_TIMEOUT_TEST=false to run)"
fi
echo ""
log_info "All tests passed! ✓"