283 lines
8.3 KiB
Python
283 lines
8.3 KiB
Python
#!/usr/bin/env python
|
|
"""
|
|
Test script to verify survey can be accessed multiple times until submission.
|
|
|
|
Tests:
|
|
1. Survey can be opened multiple times
|
|
2. Survey shows error after completion
|
|
3. Survey shows error after token expiry
|
|
"""
|
|
import os
|
|
import sys
|
|
import django
|
|
|
|
# Setup Django
|
|
os.environ.setdefault('DJANGO_SETTINGS_MODULE', 'PX360.settings')
|
|
sys.path.insert(0, os.path.dirname(os.path.abspath(__file__)))
|
|
django.setup()
|
|
|
|
from django.test import Client
|
|
from django.utils import timezone
|
|
from datetime import timedelta
|
|
from apps.surveys.models import SurveyInstance, SurveyTemplate
|
|
from apps.patients.models import Patient
|
|
from apps.hospitals.models import Hospital
|
|
import uuid
|
|
|
|
|
|
def print_header(text):
|
|
"""Print formatted header"""
|
|
print("\n" + "="*70)
|
|
print(f" {text}")
|
|
print("="*70 + "\n")
|
|
|
|
|
|
def print_success(text):
|
|
"""Print success message"""
|
|
print(f"✓ {text}")
|
|
|
|
|
|
def print_error(text):
|
|
"""Print error message"""
|
|
print(f"✗ {text}")
|
|
|
|
|
|
def test_multiple_access():
|
|
"""Test that survey can be accessed multiple times"""
|
|
print_header("TEST 1: Multiple Survey Access")
|
|
|
|
# Get or create test data
|
|
patient = Patient.objects.first()
|
|
hospital = Hospital.objects.first()
|
|
template = SurveyTemplate.objects.filter(is_active=True).first()
|
|
|
|
if not all([patient, hospital, template]):
|
|
print_error("Missing required test data (patient, hospital, or template)")
|
|
return False
|
|
|
|
# Create test survey
|
|
survey = SurveyInstance.objects.create(
|
|
survey_template=template,
|
|
patient=patient,
|
|
hospital=hospital,
|
|
status='sent',
|
|
sent_at=timezone.now(),
|
|
token_expires_at=timezone.now() + timedelta(days=2),
|
|
access_token=uuid.uuid4().hex
|
|
)
|
|
|
|
print(f"Created test survey: {survey.survey_template.name}")
|
|
print(f"Access token: {survey.access_token}")
|
|
print(f"Initial status: {survey.status}")
|
|
|
|
client = Client()
|
|
|
|
# Access survey first time
|
|
print("\n1. First access...")
|
|
response = client.get(f'/surveys/s/{survey.access_token}/')
|
|
|
|
if response.status_code == 200:
|
|
print_success(f"First access successful (200)")
|
|
else:
|
|
print_error(f"First access failed ({response.status_code})")
|
|
survey.delete()
|
|
return False
|
|
|
|
survey.refresh_from_db()
|
|
print(f" Status after first access: {survey.status}")
|
|
print(f" Open count: {survey.open_count}")
|
|
|
|
# Access survey second time (refresh)
|
|
print("\n2. Second access (refresh)...")
|
|
response = client.get(f'/surveys/s/{survey.access_token}/')
|
|
|
|
if response.status_code == 200:
|
|
print_success(f"Second access successful (200)")
|
|
else:
|
|
print_error(f"Second access failed ({response.status_code})")
|
|
survey.delete()
|
|
return False
|
|
|
|
survey.refresh_from_db()
|
|
print(f" Status after second access: {survey.status}")
|
|
print(f" Open count: {survey.open_count}")
|
|
|
|
# Access survey third time
|
|
print("\n3. Third access...")
|
|
response = client.get(f'/surveys/s/{survey.access_token}/')
|
|
|
|
if response.status_code == 200:
|
|
print_success(f"Third access successful (200)")
|
|
else:
|
|
print_error(f"Third access failed ({response.status_code})")
|
|
survey.delete()
|
|
return False
|
|
|
|
survey.refresh_from_db()
|
|
print(f" Status after third access: {survey.status}")
|
|
print(f" Open count: {survey.open_count}")
|
|
|
|
# Verify open count increased
|
|
if survey.open_count == 3:
|
|
print_success(f"Open count correctly tracked: {survey.open_count}")
|
|
else:
|
|
print_error(f"Open count incorrect: {survey.open_count} (expected 3)")
|
|
survey.delete()
|
|
return False
|
|
|
|
# Clean up
|
|
survey.delete()
|
|
print_success("Test survey cleaned up")
|
|
|
|
return True
|
|
|
|
|
|
def test_access_after_completion():
|
|
"""Test that survey cannot be accessed after completion"""
|
|
print_header("TEST 2: Access After Completion")
|
|
|
|
# Get or create test data
|
|
patient = Patient.objects.first()
|
|
hospital = Hospital.objects.first()
|
|
template = SurveyTemplate.objects.filter(is_active=True).first()
|
|
|
|
if not all([patient, hospital, template]):
|
|
print_error("Missing required test data")
|
|
return False
|
|
|
|
# Create and complete test survey
|
|
survey = SurveyInstance.objects.create(
|
|
survey_template=template,
|
|
patient=patient,
|
|
hospital=hospital,
|
|
status='completed',
|
|
sent_at=timezone.now(),
|
|
opened_at=timezone.now(),
|
|
completed_at=timezone.now(),
|
|
token_expires_at=timezone.now() + timedelta(days=2),
|
|
access_token=uuid.uuid4().hex
|
|
)
|
|
|
|
print(f"Created completed survey")
|
|
print(f"Status: {survey.status}")
|
|
|
|
client = Client()
|
|
|
|
# Try to access completed survey
|
|
print("\nAttempting to access completed survey...")
|
|
response = client.get(f'/surveys/s/{survey.access_token}/')
|
|
|
|
if response.status_code == 200:
|
|
print_error("Should not be able to access completed survey (200)")
|
|
survey.delete()
|
|
return False
|
|
elif response.status_code == 404:
|
|
print_success("Correctly rejected access to completed survey (404)")
|
|
else:
|
|
print_error(f"Unexpected status code: {response.status_code}")
|
|
survey.delete()
|
|
return False
|
|
|
|
# Clean up
|
|
survey.delete()
|
|
print_success("Test survey cleaned up")
|
|
|
|
return True
|
|
|
|
|
|
def test_access_after_expiry():
|
|
"""Test that survey cannot be accessed after token expiry"""
|
|
print_header("TEST 3: Access After Token Expiry")
|
|
|
|
# Get or create test data
|
|
patient = Patient.objects.first()
|
|
hospital = Hospital.objects.first()
|
|
template = SurveyTemplate.objects.filter(is_active=True).first()
|
|
|
|
if not all([patient, hospital, template]):
|
|
print_error("Missing required test data")
|
|
return False
|
|
|
|
# Create expired survey
|
|
now = timezone.now()
|
|
survey = SurveyInstance.objects.create(
|
|
survey_template=template,
|
|
patient=patient,
|
|
hospital=hospital,
|
|
status='sent',
|
|
sent_at=now - timedelta(days=3),
|
|
token_expires_at=now - timedelta(hours=1), # Expired 1 hour ago
|
|
access_token=uuid.uuid4().hex
|
|
)
|
|
|
|
print(f"Created expired survey")
|
|
print(f"Token expired at: {survey.token_expires_at}")
|
|
print(f"Current time: {now}")
|
|
|
|
client = Client()
|
|
|
|
# Try to access expired survey
|
|
print("\nAttempting to access expired survey...")
|
|
response = client.get(f'/surveys/s/{survey.access_token}/')
|
|
|
|
if response.status_code == 200:
|
|
print_error("Should not be able to access expired survey (200)")
|
|
survey.delete()
|
|
return False
|
|
else:
|
|
print_success(f"Correctly rejected access to expired survey ({response.status_code})")
|
|
|
|
# Clean up
|
|
survey.delete()
|
|
print_success("Test survey cleaned up")
|
|
|
|
return True
|
|
|
|
|
|
def main():
|
|
"""Run all tests"""
|
|
print_header("Survey Multiple Access Test Suite")
|
|
print("This script verifies that:")
|
|
print(" 1. Survey can be accessed multiple times until submission")
|
|
print(" 2. Survey cannot be accessed after completion")
|
|
print(" 3. Survey cannot be accessed after token expiry (2 days)")
|
|
|
|
results = []
|
|
|
|
try:
|
|
# Test 1: Multiple access
|
|
results.append(('Multiple Access', test_multiple_access()))
|
|
|
|
# Test 2: Access after completion
|
|
results.append(('Access After Completion', test_access_after_completion()))
|
|
|
|
# Test 3: Access after expiry
|
|
results.append(('Access After Expiry', test_access_after_expiry()))
|
|
|
|
except Exception as e:
|
|
print_error(f"Test failed with error: {str(e)}")
|
|
import traceback
|
|
traceback.print_exc()
|
|
|
|
# Print summary
|
|
print_header("Test Summary")
|
|
passed = sum(1 for _, result in results if result)
|
|
total = len(results)
|
|
|
|
for test_name, result in results:
|
|
status = "✓ PASS" if result else "✗ FAIL"
|
|
print(f"{status}: {test_name}")
|
|
|
|
print(f"\nTotal: {passed}/{total} tests passed")
|
|
|
|
if passed == total:
|
|
print_success("All tests passed!")
|
|
return 0
|
|
else:
|
|
print_error(f"{total - passed} test(s) failed")
|
|
return 1
|
|
|
|
|
|
if __name__ == '__main__':
|
|
sys.exit(main())
|