307 lines
11 KiB
Python
307 lines
11 KiB
Python
"""
|
|
Test script for updating custom task statuses
|
|
Tests Requirements: 2.1, 2.2, 2.3, 5.2
|
|
"""
|
|
|
|
import requests
|
|
import json
|
|
|
|
BASE_URL = "http://localhost:8000"
|
|
|
|
def login_as_admin():
|
|
"""Login as admin user"""
|
|
response = requests.post(
|
|
f"{BASE_URL}/auth/login",
|
|
json={
|
|
"email": "admin@vfx.com",
|
|
"password": "admin123"
|
|
}
|
|
)
|
|
if response.status_code == 200:
|
|
return response.json()["access_token"]
|
|
else:
|
|
print(f"Login failed: {response.status_code}")
|
|
print(response.text)
|
|
return None
|
|
|
|
def get_all_task_statuses(token, project_id):
|
|
"""Get all task statuses for a project"""
|
|
response = requests.get(
|
|
f"{BASE_URL}/projects/{project_id}/task-statuses",
|
|
headers={"Authorization": f"Bearer {token}"}
|
|
)
|
|
if response.status_code == 200:
|
|
return response.json()
|
|
else:
|
|
print(f"Failed to get task statuses: {response.status_code}")
|
|
print(response.text)
|
|
return None
|
|
|
|
def create_custom_status(token, project_id, name, color=None):
|
|
"""Create a custom task status"""
|
|
data = {"name": name}
|
|
if color:
|
|
data["color"] = color
|
|
|
|
response = requests.post(
|
|
f"{BASE_URL}/projects/{project_id}/task-statuses",
|
|
headers={"Authorization": f"Bearer {token}"},
|
|
json=data
|
|
)
|
|
if response.status_code == 201:
|
|
return response.json()
|
|
else:
|
|
print(f"Failed to create status: {response.status_code}")
|
|
print(response.text)
|
|
return None
|
|
|
|
def update_custom_status(token, project_id, status_id, name=None, color=None, is_default=None):
|
|
"""Update a custom task status"""
|
|
data = {}
|
|
if name is not None:
|
|
data["name"] = name
|
|
if color is not None:
|
|
data["color"] = color
|
|
if is_default is not None:
|
|
data["is_default"] = is_default
|
|
|
|
response = requests.put(
|
|
f"{BASE_URL}/projects/{project_id}/task-statuses/{status_id}",
|
|
headers={"Authorization": f"Bearer {token}"},
|
|
json=data
|
|
)
|
|
if response.status_code == 200:
|
|
return response.json()
|
|
else:
|
|
print(f"Failed to update status: {response.status_code}")
|
|
print(response.text)
|
|
return None
|
|
|
|
def main():
|
|
print("=" * 80)
|
|
print("Testing Custom Task Status Update Endpoint")
|
|
print("=" * 80)
|
|
|
|
# Login
|
|
print("\n1. Logging in as admin...")
|
|
token = login_as_admin()
|
|
if not token:
|
|
print("❌ Failed to login")
|
|
return
|
|
print("✅ Login successful")
|
|
|
|
# Use project ID 1 (should exist from setup)
|
|
project_id = 1
|
|
|
|
# Get initial statuses
|
|
print(f"\n2. Getting initial task statuses for project {project_id}...")
|
|
initial_statuses = get_all_task_statuses(token, project_id)
|
|
if not initial_statuses:
|
|
print("❌ Failed to get initial statuses")
|
|
return
|
|
print(f"✅ Found {len(initial_statuses['statuses'])} custom statuses")
|
|
print(f" System statuses: {len(initial_statuses['system_statuses'])}")
|
|
|
|
# Create a test status
|
|
print("\n3. Creating a test custom status...")
|
|
create_result = create_custom_status(token, project_id, "Test Status", "#FF5733")
|
|
if not create_result:
|
|
print("❌ Failed to create test status")
|
|
return
|
|
|
|
created_status = create_result['status']
|
|
status_id = created_status['id']
|
|
print(f"✅ Created status: {created_status['name']} (ID: {status_id})")
|
|
print(f" Color: {created_status['color']}")
|
|
print(f" Order: {created_status['order']}")
|
|
print(f" Is Default: {created_status['is_default']}")
|
|
|
|
# Test 1: Update status name (Requirement 2.1)
|
|
print("\n4. Test 1: Updating status name...")
|
|
update_result = update_custom_status(token, project_id, status_id, name="Updated Test Status")
|
|
if not update_result:
|
|
print("❌ Failed to update status name")
|
|
return
|
|
|
|
updated_status = update_result['status']
|
|
if updated_status['name'] == "Updated Test Status":
|
|
print(f"✅ Status name updated successfully: {updated_status['name']}")
|
|
else:
|
|
print(f"❌ Status name not updated correctly: {updated_status['name']}")
|
|
return
|
|
|
|
# Test 2: Update status color (Requirement 2.2)
|
|
print("\n5. Test 2: Updating status color...")
|
|
update_result = update_custom_status(token, project_id, status_id, color="#00FF00")
|
|
if not update_result:
|
|
print("❌ Failed to update status color")
|
|
return
|
|
|
|
updated_status = update_result['status']
|
|
if updated_status['color'] == "#00FF00":
|
|
print(f"✅ Status color updated successfully: {updated_status['color']}")
|
|
else:
|
|
print(f"❌ Status color not updated correctly: {updated_status['color']}")
|
|
return
|
|
|
|
# Test 3: Update both name and color (Requirement 2.1, 2.2)
|
|
print("\n6. Test 3: Updating both name and color...")
|
|
update_result = update_custom_status(
|
|
token, project_id, status_id,
|
|
name="Final Test Status",
|
|
color="#0000FF"
|
|
)
|
|
if not update_result:
|
|
print("❌ Failed to update status name and color")
|
|
return
|
|
|
|
updated_status = update_result['status']
|
|
if updated_status['name'] == "Final Test Status" and updated_status['color'] == "#0000FF":
|
|
print(f"✅ Status name and color updated successfully")
|
|
print(f" Name: {updated_status['name']}")
|
|
print(f" Color: {updated_status['color']}")
|
|
else:
|
|
print(f"❌ Status not updated correctly")
|
|
return
|
|
|
|
# Test 4: Validate name uniqueness (Requirement 2.4)
|
|
print("\n7. Test 4: Testing name uniqueness validation...")
|
|
# Create another status
|
|
create_result2 = create_custom_status(token, project_id, "Another Status", "#FFFF00")
|
|
if not create_result2:
|
|
print("❌ Failed to create second test status")
|
|
return
|
|
|
|
status_id2 = create_result2['status']['id']
|
|
print(f"✅ Created second status: {create_result2['status']['name']}")
|
|
|
|
# Try to update first status with the name of the second status
|
|
print(" Attempting to update with duplicate name...")
|
|
update_result = update_custom_status(token, project_id, status_id, name="Another Status")
|
|
if update_result is None:
|
|
print("✅ Duplicate name correctly rejected")
|
|
else:
|
|
print("❌ Duplicate name was not rejected")
|
|
return
|
|
|
|
# Test 5: Try to use system status name (Requirement 2.4)
|
|
print("\n8. Test 5: Testing system status name conflict...")
|
|
update_result = update_custom_status(token, project_id, status_id, name="In Progress")
|
|
if update_result is None:
|
|
print("✅ System status name correctly rejected")
|
|
else:
|
|
print("❌ System status name was not rejected")
|
|
return
|
|
|
|
# Test 6: Set as default status (Requirement 2.3, 5.2)
|
|
print("\n9. Test 6: Setting status as default...")
|
|
update_result = update_custom_status(token, project_id, status_id, is_default=True)
|
|
if not update_result:
|
|
print("❌ Failed to set status as default")
|
|
return
|
|
|
|
updated_status = update_result['status']
|
|
all_statuses = update_result['all_statuses']
|
|
|
|
if updated_status['is_default']:
|
|
print(f"✅ Status set as default successfully")
|
|
print(f" Default status ID: {all_statuses['default_status_id']}")
|
|
|
|
# Verify only one default status exists
|
|
default_count = sum(1 for s in all_statuses['statuses'] if s['is_default'])
|
|
if default_count == 1:
|
|
print(f"✅ Only one default status exists")
|
|
else:
|
|
print(f"❌ Multiple default statuses found: {default_count}")
|
|
return
|
|
else:
|
|
print(f"❌ Status not set as default")
|
|
return
|
|
|
|
# Test 7: Set another status as default (should unset previous default)
|
|
print("\n10. Test 7: Setting another status as default (should unset previous)...")
|
|
update_result = update_custom_status(token, project_id, status_id2, is_default=True)
|
|
if not update_result:
|
|
print("❌ Failed to set second status as default")
|
|
return
|
|
|
|
all_statuses = update_result['all_statuses']
|
|
|
|
# Verify only one default status exists
|
|
default_count = sum(1 for s in all_statuses['statuses'] if s['is_default'])
|
|
if default_count == 1:
|
|
print(f"✅ Only one default status exists after changing default")
|
|
print(f" New default status ID: {all_statuses['default_status_id']}")
|
|
|
|
# Verify the first status is no longer default
|
|
first_status = next((s for s in all_statuses['statuses'] if s['id'] == status_id), None)
|
|
if first_status and not first_status['is_default']:
|
|
print(f"✅ Previous default status correctly unset")
|
|
else:
|
|
print(f"❌ Previous default status not unset")
|
|
return
|
|
else:
|
|
print(f"❌ Multiple default statuses found: {default_count}")
|
|
return
|
|
|
|
# Test 8: Unset default status
|
|
print("\n11. Test 8: Unsetting default status...")
|
|
update_result = update_custom_status(token, project_id, status_id2, is_default=False)
|
|
if not update_result:
|
|
print("❌ Failed to unset default status")
|
|
return
|
|
|
|
updated_status = update_result['status']
|
|
if not updated_status['is_default']:
|
|
print(f"✅ Default status unset successfully")
|
|
else:
|
|
print(f"❌ Default status not unset")
|
|
return
|
|
|
|
# Test 9: Update non-existent status
|
|
print("\n12. Test 9: Testing update of non-existent status...")
|
|
update_result = update_custom_status(token, project_id, "nonexistent_id", name="Test")
|
|
if update_result is None:
|
|
print("✅ Non-existent status correctly rejected")
|
|
else:
|
|
print("❌ Non-existent status was not rejected")
|
|
return
|
|
|
|
# Test 10: Verify flag_modified works (JSON column update)
|
|
print("\n13. Test 10: Verifying JSON column updates persist...")
|
|
# Get statuses again to verify changes persisted
|
|
final_statuses = get_all_task_statuses(token, project_id)
|
|
if not final_statuses:
|
|
print("❌ Failed to get final statuses")
|
|
return
|
|
|
|
# Find our updated status
|
|
final_status = next((s for s in final_statuses['statuses'] if s['id'] == status_id), None)
|
|
if final_status:
|
|
if final_status['name'] == "Final Test Status" and final_status['color'] == "#0000FF":
|
|
print(f"✅ Changes persisted correctly in database")
|
|
print(f" Name: {final_status['name']}")
|
|
print(f" Color: {final_status['color']}")
|
|
else:
|
|
print(f"❌ Changes did not persist correctly")
|
|
return
|
|
else:
|
|
print(f"❌ Updated status not found in final list")
|
|
return
|
|
|
|
print("\n" + "=" * 80)
|
|
print("✅ ALL TESTS PASSED!")
|
|
print("=" * 80)
|
|
print("\nSummary:")
|
|
print(" ✅ Status name update works (Requirement 2.1)")
|
|
print(" ✅ Status color update works (Requirement 2.2)")
|
|
print(" ✅ Default status management works (Requirement 2.3, 5.2)")
|
|
print(" ✅ Name uniqueness validation works (Requirement 2.4)")
|
|
print(" ✅ System status name conflict detection works")
|
|
print(" ✅ Only one default status at a time (Requirement 5.2)")
|
|
print(" ✅ flag_modified ensures JSON column updates persist")
|
|
print(" ✅ Non-existent status handling works")
|
|
|
|
if __name__ == "__main__":
|
|
main()
|