mirror of
https://github.com/pacnpal/thrillwiki_django_no_react.git
synced 2025-12-20 10:31:09 -05:00
- Implement tests for RideLocation and CompanyHeadquarters models to verify functionality and data integrity. - Create a manual trigger test script for trending content calculation endpoint, including authentication and unauthorized access tests. - Develop a manufacturer sync test to ensure ride manufacturers are correctly associated with ride models. - Add tests for ParkLocation model, including coordinate setting and distance calculations between parks. - Implement a RoadTripService test suite covering geocoding, route calculation, park discovery, and error handling. - Create a unified map service test script to validate map functionality, API endpoints, and performance metrics.
409 lines
17 KiB
Bash
Executable File
409 lines
17 KiB
Bash
Executable File
#!/bin/bash
|
|
|
|
# ThrillWiki Hybrid Filtering Endpoints Test Script
|
|
# Tests the newly synchronized Parks and Rides hybrid filtering endpoints
|
|
#
|
|
# Usage: ./test_hybrid_endpoints.sh [BASE_URL]
|
|
# Default BASE_URL: http://localhost:8000
|
|
|
|
set -e
|
|
|
|
# Configuration
|
|
BASE_URL="${1:-http://localhost:8000}"
|
|
VERBOSE=true
|
|
|
|
# Colors for output
|
|
RED='\033[0;31m'
|
|
GREEN='\033[0;32m'
|
|
BLUE='\033[0;34m'
|
|
YELLOW='\033[1;33m'
|
|
PURPLE='\033[0;35m'
|
|
CYAN='\033[0;36m'
|
|
NC='\033[0m' # No Color
|
|
|
|
# Helper functions
|
|
print_header() {
|
|
local title="$1"
|
|
local level="${2:-1}"
|
|
|
|
case $level in
|
|
1) echo -e "\n${BLUE}================================================================================${NC}"
|
|
echo -e "${BLUE}$title${NC}"
|
|
echo -e "${BLUE}================================================================================${NC}" ;;
|
|
2) echo -e "\n${CYAN}--------------------------------------------------------------------------------${NC}"
|
|
echo -e "${CYAN}$title${NC}"
|
|
echo -e "${CYAN}--------------------------------------------------------------------------------${NC}" ;;
|
|
3) echo -e "\n${YELLOW}$title${NC}"
|
|
echo -e "${YELLOW}$(echo "$title" | sed 's/./~/g')${NC}" ;;
|
|
esac
|
|
}
|
|
|
|
print_endpoint() {
|
|
local method="$1"
|
|
local url="$2"
|
|
echo -e "\n${PURPLE}🔗 ENDPOINT:${NC} ${GREEN}$method${NC} $url"
|
|
}
|
|
|
|
print_description() {
|
|
local desc="$1"
|
|
echo -e "${CYAN}📋 DESCRIPTION:${NC} $desc"
|
|
}
|
|
|
|
make_request() {
|
|
local method="$1"
|
|
local url="$2"
|
|
local description="$3"
|
|
|
|
print_endpoint "$method" "$url"
|
|
print_description "$description"
|
|
|
|
echo -e "\n${YELLOW}📤 REQUEST:${NC}"
|
|
echo "curl -X $method \\"
|
|
echo " -H 'Accept: application/json' \\"
|
|
echo " -H 'Content-Type: application/json' \\"
|
|
echo " '$url'"
|
|
|
|
echo -e "\n${YELLOW}📥 RESPONSE:${NC}"
|
|
|
|
# Make the actual request
|
|
response=$(curl -s -w "\n%{http_code}" -X "$method" \
|
|
-H "Accept: application/json" \
|
|
-H "Content-Type: application/json" \
|
|
"$url")
|
|
|
|
# Extract status code and body
|
|
status_code=$(echo "$response" | tail -n1)
|
|
body=$(echo "$response" | sed '$d')
|
|
|
|
# Print status
|
|
if [[ "$status_code" -ge 200 && "$status_code" -lt 300 ]]; then
|
|
echo -e "${GREEN}✅ SUCCESS: HTTP $status_code${NC}"
|
|
else
|
|
echo -e "${RED}❌ ERROR: HTTP $status_code${NC}"
|
|
fi
|
|
|
|
# Pretty print JSON response
|
|
if command -v jq >/dev/null 2>&1; then
|
|
echo "$body" | jq '.'
|
|
else
|
|
echo "$body"
|
|
fi
|
|
|
|
# Extract and display key metrics
|
|
if command -v jq >/dev/null 2>&1 && [[ "$status_code" -ge 200 && "$status_code" -lt 300 ]]; then
|
|
echo -e "\n${CYAN}📊 RESPONSE SUMMARY:${NC}"
|
|
|
|
# Total count
|
|
total_count=$(echo "$body" | jq -r '.total_count // empty')
|
|
if [[ -n "$total_count" ]]; then
|
|
echo -e " • Total Count: ${GREEN}$total_count${NC}"
|
|
fi
|
|
|
|
# Strategy
|
|
strategy=$(echo "$body" | jq -r '.strategy // empty')
|
|
if [[ -n "$strategy" ]]; then
|
|
if [[ "$strategy" == "client_side" ]]; then
|
|
echo -e " • Strategy: ${GREEN}🖥️ $strategy${NC}"
|
|
else
|
|
echo -e " • Strategy: ${BLUE}🌐 $strategy${NC}"
|
|
fi
|
|
fi
|
|
|
|
# Has more
|
|
has_more=$(echo "$body" | jq -r '.has_more // empty')
|
|
if [[ -n "$has_more" ]]; then
|
|
if [[ "$has_more" == "true" ]]; then
|
|
echo -e " • Has More: ${YELLOW}➡️ $has_more${NC}"
|
|
else
|
|
echo -e " • Has More: ${GREEN}🏁 $has_more${NC}"
|
|
fi
|
|
fi
|
|
|
|
# Next offset
|
|
next_offset=$(echo "$body" | jq -r '.next_offset // empty')
|
|
if [[ -n "$next_offset" && "$next_offset" != "null" ]]; then
|
|
echo -e " • Next Offset: ${CYAN}$next_offset${NC}"
|
|
fi
|
|
|
|
# Data counts
|
|
parks_count=$(echo "$body" | jq -r '.parks | length // empty' 2>/dev/null)
|
|
if [[ -n "$parks_count" ]]; then
|
|
echo -e " • Parks Returned: ${GREEN}$parks_count${NC}"
|
|
fi
|
|
|
|
rides_count=$(echo "$body" | jq -r '.rides | length // empty' 2>/dev/null)
|
|
if [[ -n "$rides_count" ]]; then
|
|
echo -e " • Rides Returned: ${GREEN}$rides_count${NC}"
|
|
fi
|
|
|
|
# Filter metadata summary
|
|
if echo "$body" | jq -e '.filter_metadata' >/dev/null 2>&1; then
|
|
echo -e " • Filter Metadata: ${GREEN}✅ Available${NC}"
|
|
|
|
# Count categorical options
|
|
countries=$(echo "$body" | jq -r '.filter_metadata.categorical.countries | length // 0' 2>/dev/null)
|
|
states=$(echo "$body" | jq -r '.filter_metadata.categorical.states | length // 0' 2>/dev/null)
|
|
categories=$(echo "$body" | jq -r '.filter_metadata.categorical.categories | length // 0' 2>/dev/null)
|
|
|
|
if [[ "$countries" -gt 0 ]]; then
|
|
echo -e " - Countries: ${CYAN}$countries${NC}"
|
|
fi
|
|
if [[ "$states" -gt 0 ]]; then
|
|
echo -e " - States: ${CYAN}$states${NC}"
|
|
fi
|
|
if [[ "$categories" -gt 0 ]]; then
|
|
echo -e " - Categories: ${CYAN}$categories${NC}"
|
|
fi
|
|
fi
|
|
fi
|
|
|
|
echo -e "\n${PURPLE}$(printf '%.0s-' {1..80})${NC}"
|
|
}
|
|
|
|
# Main test execution
|
|
main() {
|
|
print_header "THRILLWIKI HYBRID FILTERING ENDPOINTS TEST SUITE" 1
|
|
echo -e "Testing endpoints at: ${GREEN}$BASE_URL${NC}"
|
|
echo -e "Timestamp: ${CYAN}$(date)${NC}"
|
|
|
|
# Check if server is running
|
|
echo -e "\n${YELLOW}🔍 Checking server availability...${NC}"
|
|
if ! curl -s --connect-timeout 5 "$BASE_URL" >/dev/null; then
|
|
echo -e "${RED}❌ Server not available at $BASE_URL${NC}"
|
|
echo -e "${YELLOW}💡 Make sure to start the Django server first:${NC}"
|
|
echo -e " cd backend && uv run manage.py runserver_plus"
|
|
exit 1
|
|
fi
|
|
echo -e "${GREEN}✅ Server is running${NC}"
|
|
|
|
# ========================================================================
|
|
# PARKS HYBRID FILTERING TESTS
|
|
# ========================================================================
|
|
|
|
print_header "PARKS HYBRID FILTERING TESTS" 1
|
|
|
|
# Test 1: Basic Parks Hybrid Filtering
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/parks/hybrid/" \
|
|
"Basic hybrid filtering with no parameters - demonstrates automatic strategy selection"
|
|
|
|
# Test 2: Parks with Search Filter
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/parks/hybrid/?search=disney" \
|
|
"Search for parks containing 'disney' - tests full-text search functionality"
|
|
|
|
# Test 3: Parks with Status Filter
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/parks/hybrid/?status=OPERATING,CLOSED_TEMP" \
|
|
"Filter parks by multiple statuses - tests comma-separated list parameters"
|
|
|
|
# Test 4: Parks with Geographic Filters
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/parks/hybrid/?country=United%20States&state=Florida,California" \
|
|
"Filter parks by country and multiple states - tests geographic filtering"
|
|
|
|
# Test 5: Parks with Numeric Range Filters
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/parks/hybrid/?opening_year_min=1990&opening_year_max=2020&rating_min=4.0" \
|
|
"Filter parks by opening year range and minimum rating - tests numeric range filtering"
|
|
|
|
# Test 6: Parks with Size and Ride Count Filters
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/parks/hybrid/?size_min=100&ride_count_min=10&coaster_count_min=5" \
|
|
"Filter parks by minimum size, ride count, and coaster count - tests park statistics filtering"
|
|
|
|
# Test 7: Parks with Operator Filter
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/parks/hybrid/?operator=disney,universal" \
|
|
"Filter parks by operator slugs - tests company relationship filtering"
|
|
|
|
# Test 8: Parks Progressive Loading (with offset)
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/parks/hybrid/?offset=50" \
|
|
"Progressive loading starting at offset 50 - tests server-side pagination"
|
|
|
|
# Test 9: Parks Filter Metadata
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/parks/hybrid/filter-metadata/" \
|
|
"Get comprehensive filter metadata for parks - provides all available filter options and ranges"
|
|
|
|
# Test 10: Parks Scoped Filter Metadata
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/parks/hybrid/filter-metadata/?scoped=true&country=United%20States" \
|
|
"Get filter metadata scoped to US parks - demonstrates dynamic metadata based on current filters"
|
|
|
|
# ========================================================================
|
|
# RIDES HYBRID FILTERING TESTS
|
|
# ========================================================================
|
|
|
|
print_header "RIDES HYBRID FILTERING TESTS" 1
|
|
|
|
# Test 1: Basic Rides Hybrid Filtering
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/rides/hybrid/" \
|
|
"Basic hybrid filtering with no parameters - demonstrates automatic strategy selection for rides"
|
|
|
|
# Test 2: Rides with Search Filter
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/rides/hybrid/?search=coaster" \
|
|
"Search for rides containing 'coaster' - tests full-text search across ride names and descriptions"
|
|
|
|
# Test 3: Rides with Category Filter
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/rides/hybrid/?category=RC,DR" \
|
|
"Filter rides by categories (Roller Coaster, Dark Ride) - tests ride category filtering"
|
|
|
|
# Test 4: Rides with Status and Park Filters
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/rides/hybrid/?status=OPERATING&park_slug=cedar-point" \
|
|
"Filter operating rides at Cedar Point - tests status and park-specific filtering"
|
|
|
|
# Test 5: Rides with Manufacturer and Designer Filters
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/rides/hybrid/?manufacturer=bolliger-mabillard&designer=bolliger-mabillard" \
|
|
"Filter rides by B&M as manufacturer and designer - tests company relationship filtering"
|
|
|
|
# Test 6: Rides with Roller Coaster Specific Filters
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/rides/hybrid/?roller_coaster_type=INVERTED,FLYING&track_material=STEEL&has_inversions=true" \
|
|
"Filter inverted/flying steel coasters with inversions - tests roller coaster specific attributes"
|
|
|
|
# Test 7: Rides with Height and Speed Filters
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/rides/hybrid/?height_ft_min=200&speed_mph_min=70&inversions_min=4" \
|
|
"Filter tall, fast coasters with multiple inversions - tests numeric performance filtering"
|
|
|
|
# Test 8: Rides with Rating and Capacity Filters
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/rides/hybrid/?rating_min=4.5&capacity_min=1000&opening_year_min=2000" \
|
|
"Filter highly-rated, high-capacity modern rides - tests quality and operational metrics"
|
|
|
|
# Test 9: Rides with Height Requirement Filters
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/rides/hybrid/?height_requirement_min=48&height_requirement_max=54" \
|
|
"Filter rides by height requirements (48-54 inches) - tests accessibility filtering"
|
|
|
|
# Test 10: Rides Progressive Loading
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/rides/hybrid/?offset=25&category=RC" \
|
|
"Progressive loading of roller coasters starting at offset 25 - tests server-side pagination with filters"
|
|
|
|
# Test 11: Rides Filter Metadata
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/rides/hybrid/filter-metadata/" \
|
|
"Get comprehensive filter metadata for rides - provides all available filter options and ranges"
|
|
|
|
# Test 12: Rides Scoped Filter Metadata
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/rides/hybrid/filter-metadata/?scoped=true&category=RC" \
|
|
"Get filter metadata scoped to roller coasters - demonstrates dynamic metadata for specific categories"
|
|
|
|
# ========================================================================
|
|
# COMPLEX COMBINATION TESTS
|
|
# ========================================================================
|
|
|
|
print_header "COMPLEX COMBINATION TESTS" 1
|
|
|
|
# Test 1: Parks with All Filter Types
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/parks/hybrid/?search=theme&status=OPERATING&country=United%20States&opening_year_min=1980&rating_min=4.0&size_min=50&ride_count_min=20" \
|
|
"Complex parks query combining search, status, geographic, temporal, rating, and size filters"
|
|
|
|
# Test 2: Rides with All Filter Types
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/rides/hybrid/?search=steel&category=RC&status=OPERATING&roller_coaster_type=SITDOWN&track_material=STEEL&height_ft_min=100&speed_mph_min=50&rating_min=4.0&has_inversions=false" \
|
|
"Complex rides query combining search, category, status, coaster type, materials, performance, and rating filters"
|
|
|
|
# ========================================================================
|
|
# EDGE CASE TESTS
|
|
# ========================================================================
|
|
|
|
print_header "EDGE CASE TESTS" 1
|
|
|
|
# Test 1: Empty Results
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/parks/hybrid/?search=nonexistentpark12345" \
|
|
"Search for non-existent park - tests empty result handling"
|
|
|
|
# Test 2: Invalid Parameters
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/rides/hybrid/?height_ft_min=invalid&rating_min=15" \
|
|
"Invalid numeric parameters - tests parameter validation and error handling"
|
|
|
|
# Test 3: Large Offset
|
|
make_request "GET" \
|
|
"$BASE_URL/api/v1/parks/hybrid/?offset=99999" \
|
|
"Very large offset value - tests pagination boundary handling"
|
|
|
|
# ========================================================================
|
|
# PERFORMANCE COMPARISON TESTS
|
|
# ========================================================================
|
|
|
|
print_header "PERFORMANCE COMPARISON TESTS" 1
|
|
|
|
echo -e "\n${CYAN}📊 Testing response times for different strategies...${NC}"
|
|
|
|
# Time the requests
|
|
echo -e "\n${YELLOW}⏱️ Timing Parks Hybrid Endpoint:${NC}"
|
|
time curl -s -o /dev/null "$BASE_URL/api/v1/parks/hybrid/"
|
|
|
|
echo -e "\n${YELLOW}⏱️ Timing Rides Hybrid Endpoint:${NC}"
|
|
time curl -s -o /dev/null "$BASE_URL/api/v1/rides/hybrid/"
|
|
|
|
echo -e "\n${YELLOW}⏱️ Timing Parks Filter Metadata:${NC}"
|
|
time curl -s -o /dev/null "$BASE_URL/api/v1/parks/hybrid/filter-metadata/"
|
|
|
|
echo -e "\n${YELLOW}⏱️ Timing Rides Filter Metadata:${NC}"
|
|
time curl -s -o /dev/null "$BASE_URL/api/v1/rides/hybrid/filter-metadata/"
|
|
|
|
# ========================================================================
|
|
# SUMMARY
|
|
# ========================================================================
|
|
|
|
print_header "TEST SUITE SUMMARY" 1
|
|
|
|
echo -e "${GREEN}✅ Test suite completed successfully!${NC}"
|
|
echo -e "\n${CYAN}📋 ENDPOINTS TESTED:${NC}"
|
|
echo -e " • Parks Hybrid Filtering: ${GREEN}/api/v1/parks/hybrid/${NC}"
|
|
echo -e " • Parks Filter Metadata: ${GREEN}/api/v1/parks/hybrid/filter-metadata/${NC}"
|
|
echo -e " • Rides Hybrid Filtering: ${GREEN}/api/v1/rides/hybrid/${NC}"
|
|
echo -e " • Rides Filter Metadata: ${GREEN}/api/v1/rides/hybrid/filter-metadata/${NC}"
|
|
|
|
echo -e "\n${CYAN}🔍 KEY FEATURES DEMONSTRATED:${NC}"
|
|
echo -e " • Automatic strategy selection (client-side vs server-side)"
|
|
echo -e " • Progressive loading for large datasets"
|
|
echo -e " • Comprehensive filter options (17+ parameters per domain)"
|
|
echo -e " • Dynamic filter metadata generation"
|
|
echo -e " • Consistent response formats across domains"
|
|
echo -e " • Full-text search capabilities"
|
|
echo -e " • Numeric range filtering"
|
|
echo -e " • Multi-value parameter support"
|
|
echo -e " • Geographic and temporal filtering"
|
|
echo -e " • Roller coaster specific filtering"
|
|
echo -e " • Error handling and validation"
|
|
|
|
echo -e "\n${YELLOW}💡 NEXT STEPS:${NC}"
|
|
echo -e " • Integrate these endpoints into your frontend application"
|
|
echo -e " • Use filter metadata to build dynamic filter interfaces"
|
|
echo -e " • Implement progressive loading for better user experience"
|
|
echo -e " • Monitor performance and adjust thresholds as needed"
|
|
|
|
echo -e "\n${PURPLE}🎉 Happy filtering! 🎢${NC}"
|
|
}
|
|
|
|
# Check dependencies
|
|
check_dependencies() {
|
|
if ! command -v curl >/dev/null 2>&1; then
|
|
echo -e "${RED}❌ curl is required but not installed${NC}"
|
|
exit 1
|
|
fi
|
|
|
|
if ! command -v jq >/dev/null 2>&1; then
|
|
echo -e "${YELLOW}⚠️ jq not found - JSON responses will not be pretty-printed${NC}"
|
|
fi
|
|
}
|
|
|
|
# Script execution
|
|
check_dependencies
|
|
main "$@"
|