CP_AUTOMATION/scripts/complete_profile_to_assessment.py
2025-12-12 19:54:54 +05:30

459 lines
16 KiB
Python
Executable File

#!/usr/bin/env python3
"""
End-to-End Script: Complete Profile to Assessment Ready State
This script performs the complete student journey:
1. Login (with smart password handling)
2. Password Reset (if needed)
3. Profile Completion (to 100%)
4. Navigate to Assessments Page
Usage:
python scripts/complete_profile_to_assessment.py --cpid <CPID> --password <PASSWORD> [--profile-data <JSON_FILE>]
Example:
python scripts/complete_profile_to_assessment.py --cpid BATBAT311A --password Admin@123
python scripts/complete_profile_to_assessment.py --cpid DESDES29BB --password Admin@123 --profile-data profile_data.json
"""
import argparse
import json
import sys
import time
from pathlib import Path
# Add project root to path
project_root = Path(__file__).parent.parent
sys.path.insert(0, str(project_root))
from pages.login_page import LoginPage
from pages.mandatory_reset_page import MandatoryResetPage
from pages.profile_incomplete_page import ProfileIncompletePage
from pages.profile_editor_page import ProfileEditorPage
from pages.dashboard_page import DashboardPage
from pages.assessments_page import AssessmentsPage
from utils.driver_manager import DriverManager
from utils.password_tracker import password_tracker
from config.config import TEST_NEW_PASSWORD, BASE_URL
def load_profile_data(json_file=None):
"""
Load profile data from JSON file or return default data
Args:
json_file: Path to JSON file with profile data (optional)
Returns:
dict: Profile data dictionary
"""
default_data = {
"personal_information": {
"first_name": "Test",
"last_name": "Student",
"gender": "Male",
"dob": "2005-01-15",
"roll_number": "12345",
"nationality": "Indian"
},
"contact_information": {
"email": "test.student@example.com",
"phone": "9876543210",
"address": "123 Test Street, Test Area",
"city": "Mumbai",
"state": "Maharashtra",
"zip_code": "400001",
"native_state": "Maharashtra"
},
"parent_guardian": {
"father_name": "Father Test",
"father_age_range": "41-50",
"father_occupation": "Engineer",
"father_email": "father@example.com",
"mother_name": "Mother Test",
"mother_age_range": "30-40",
"mother_occupation": "Teacher",
"mother_email": "mother@example.com"
},
"education_details": {
"full_name": "Test Student",
"current_grade": "10",
"section": "A",
"board_stream": "CBSE"
},
"focus_areas": {
"short_term": ["01. Academics", "02. Family", "03. Health"],
"long_term": ["01. Academics", "09. Future Aspiration", "06. Personal Growth"]
},
"self_assessment": {
"strengths": ["1. Quick Learning", "3. Problem-Solving", "12. Communication"],
"improvements": ["2. Curiosity", "6. Risk Taking", "10. Leadership"]
},
"hobbies_clubs": {
"hobbies": ["01. Reading", "03. Sports", "02. Playing Musical Instruments"],
"clubs": ["1. Science Club", "3. Quiz Club", "4. Literary Club"]
},
"achievements": {
"academics": "School topper in 9th grade",
"sports": "Won district level cricket tournament",
"cultural": "Participated in school annual day",
"others": "Volunteer work at local NGO"
},
"expectations": [
"1. Self-Understanding: Gain deeper insights into their personality, strengths, and areas for growth.",
"2. Career Guidance: Clear recommendations on suitable career paths or college majors based on their interests and abilities, backed by scientific tool.",
"3. Academic Support: Help in identifying their learning styles, study habits, or cognitive strengths to improve performance."
]
}
if json_file:
json_path = Path(json_file)
if json_path.exists():
with open(json_path, 'r') as f:
custom_data = json.load(f)
# Merge custom data with defaults (custom takes precedence)
merged_data = default_data.copy()
for key, value in custom_data.items():
if isinstance(value, dict) and key in merged_data:
merged_data[key].update(value)
else:
merged_data[key] = value
return merged_data
else:
print(f"⚠️ JSON file not found: {json_file}. Using default data.")
return default_data
def complete_profile_with_data(profile_editor, profile_data):
"""
Complete profile using provided data
Args:
profile_editor: ProfileEditorPage instance
profile_data: Dictionary with profile data
"""
print("\n🚀 Starting profile completion with provided data...")
# Step 1: Personal Information
print("\n📝 Step 1/9: Personal Information")
profile_editor.navigate_to_tab(0)
time.sleep(0.5)
personal = profile_data.get("personal_information", {})
profile_editor.fill_personal_information(
first_name=personal.get("first_name"),
last_name=personal.get("last_name"),
gender=personal.get("gender"),
dob=personal.get("dob"),
roll_number=personal.get("roll_number"),
nationality=personal.get("nationality")
)
print("✅ Personal Information filled")
# Step 2: Contact Information
print("\n📝 Step 2/9: Contact Information")
profile_editor.navigate_to_tab(1)
time.sleep(0.5)
contact = profile_data.get("contact_information", {})
profile_editor.fill_contact_information(
email=contact.get("email"),
phone=contact.get("phone"),
address=contact.get("address"),
city=contact.get("city"),
state=contact.get("state"),
zip_code=contact.get("zip_code"),
native_state=contact.get("native_state")
)
print("✅ Contact Information filled")
# Step 3: Parent/Guardian
print("\n📝 Step 3/9: Parent/Guardian")
profile_editor.navigate_to_tab(2)
time.sleep(0.5)
parent = profile_data.get("parent_guardian", {})
profile_editor.fill_parent_guardian(
father_name=parent.get("father_name"),
father_age_range=parent.get("father_age_range"),
father_occupation=parent.get("father_occupation"),
father_email=parent.get("father_email"),
mother_name=parent.get("mother_name"),
mother_age_range=parent.get("mother_age_range"),
mother_occupation=parent.get("mother_occupation"),
mother_email=parent.get("mother_email")
)
print("✅ Parent/Guardian filled")
# Step 4: Education Details
print("\n📝 Step 4/9: Education Details")
profile_editor.navigate_to_tab(3)
time.sleep(0.5)
education = profile_data.get("education_details", {})
profile_editor.fill_education_details(
full_name=education.get("full_name"),
current_grade=education.get("current_grade"),
section=education.get("section"),
board_stream=education.get("board_stream")
)
print("✅ Education Details filled")
# Step 5: Focus Areas
print("\n📝 Step 5/9: Focus Areas")
profile_editor.navigate_to_tab(4)
time.sleep(0.5)
focus = profile_data.get("focus_areas", {})
profile_editor.select_focus_areas(
short_term=focus.get("short_term"),
long_term=focus.get("long_term")
)
print("✅ Focus Areas selected")
# Step 6: Self-Assessment
print("\n📝 Step 6/9: Self-Assessment")
profile_editor.navigate_to_tab(5)
time.sleep(0.5)
assessment = profile_data.get("self_assessment", {})
profile_editor.select_strengths(assessment.get("strengths", []))
profile_editor.select_improvements(assessment.get("improvements", []))
print("✅ Self-Assessment completed")
# Step 7: Hobbies & Clubs
print("\n📝 Step 7/9: Hobbies & Clubs")
profile_editor.navigate_to_tab(6)
time.sleep(0.5)
hobbies_clubs = profile_data.get("hobbies_clubs", {})
profile_editor.select_hobbies(hobbies_clubs.get("hobbies", []))
profile_editor.select_clubs(hobbies_clubs.get("clubs", []))
print("✅ Hobbies & Clubs selected")
# Step 8: Achievements
print("\n📝 Step 8/9: Achievements")
profile_editor.navigate_to_tab(7)
time.sleep(0.5)
achievements = profile_data.get("achievements", {})
profile_editor.fill_achievements(
academics=achievements.get("academics"),
sports=achievements.get("sports"),
cultural=achievements.get("cultural"),
others=achievements.get("others")
)
print("✅ Achievements filled")
# Step 9: Expectations
print("\n📝 Step 9/9: Expectations")
profile_editor.navigate_to_tab(8)
time.sleep(0.5)
expectations = profile_data.get("expectations", [])
profile_editor.select_expectations(expectations)
print("✅ Expectations selected")
# Save profile
print("\n💾 Saving profile...")
progress_before = profile_editor.get_progress_value()
print(f"📊 Progress before save: {progress_before}")
profile_editor.click_save()
time.sleep(2)
progress_after = profile_editor.get_progress_value()
print(f"📊 Progress after save: {progress_after}")
if "100%" in progress_after or progress_after == "100":
print("✅ Profile completed to 100%!")
return True
else:
print(f"⚠️ Profile not at 100% yet. Current: {progress_after}")
# Try saving again
profile_editor.click_save()
time.sleep(2)
progress_final = profile_editor.get_progress_value()
print(f"📊 Final progress: {progress_final}")
return "100%" in progress_final or progress_final == "100"
def main():
"""Main execution function"""
parser = argparse.ArgumentParser(
description="Complete student profile to 100% and navigate to assessments",
formatter_class=argparse.RawDescriptionHelpFormatter,
epilog="""
Examples:
# Basic usage with default data
python scripts/complete_profile_to_assessment.py --cpid BATBAT311A --password Admin@123
# With custom profile data
python scripts/complete_profile_to_assessment.py --cpid DESDES29BB --password Admin@123 --profile-data profile_data.json
"""
)
parser.add_argument(
"--cpid",
required=True,
help="Student CPID (e.g., BATBAT311A)"
)
parser.add_argument(
"--password",
required=True,
help="Student password (will try this first, then Admin@123 if needed)"
)
parser.add_argument(
"--profile-data",
help="Path to JSON file with custom profile data (optional)"
)
parser.add_argument(
"--headless",
action="store_true",
help="Run in headless mode (no browser window)"
)
args = parser.parse_args()
# Load profile data
profile_data = load_profile_data(args.profile_data)
# Initialize driver
driver = None
try:
print("=" * 80)
print("🚀 COMPLETE PROFILE TO ASSESSMENT - END-TO-END SCRIPT")
print("=" * 80)
print(f"\n📋 Configuration:")
print(f" CPID: {args.cpid}")
print(f" Password: {'*' * len(args.password)}")
print(f" Profile Data: {'Custom' if args.profile_data else 'Default'}")
print(f" Headless: {args.headless}")
print(f" Base URL: {BASE_URL}")
print()
# Get driver
driver = DriverManager.get_driver(headless=args.headless)
# Step 1: Login
print("\n" + "=" * 80)
print("STEP 1: LOGIN")
print("=" * 80)
login_page = LoginPage(driver)
login_page.login(identifier=args.cpid, password=args.password)
print(f"✅ Login successful for {args.cpid}")
# Step 2: Handle Password Reset (if needed)
print("\n" + "=" * 80)
print("STEP 2: PASSWORD RESET (if needed)")
print("=" * 80)
reset_page = MandatoryResetPage(driver)
if reset_page.is_modal_present():
print("🔐 Password reset modal detected - resetting password...")
current_password = password_tracker.get_password(args.cpid, args.password)
reset_page.reset_password(
current_password=current_password,
new_password=TEST_NEW_PASSWORD,
confirm_password=TEST_NEW_PASSWORD,
student_cpid=args.cpid
)
print(f"✅ Password reset to {TEST_NEW_PASSWORD}")
else:
print("✅ No password reset needed")
# Step 3: Handle Profile Incomplete Modal (if needed)
print("\n" + "=" * 80)
print("STEP 3: PROFILE INCOMPLETE MODAL (if needed)")
print("=" * 80)
profile_incomplete = ProfileIncompletePage(driver)
if profile_incomplete.is_modal_present():
progress = profile_incomplete.get_progress_value()
print(f"📊 Current profile progress: {progress}")
print("📝 Clicking 'Complete Profile Now' button...")
profile_incomplete.click_complete()
print("✅ Navigated to profile editor")
else:
print("✅ Profile incomplete modal not present")
# Step 4: Complete Profile to 100%
print("\n" + "=" * 80)
print("STEP 4: COMPLETE PROFILE TO 100%")
print("=" * 80)
profile_editor = ProfileEditorPage(driver)
profile_editor.wait_for_page_load()
initial_progress = profile_editor.get_progress_value()
print(f"📊 Initial profile progress: {initial_progress}")
if "100%" in initial_progress or initial_progress == "100":
print("✅ Profile is already 100% complete!")
else:
# Complete profile with provided data
success = complete_profile_with_data(profile_editor, profile_data)
if not success:
print("❌ Failed to complete profile to 100%")
return 1
# Step 5: Navigate to Assessments
print("\n" + "=" * 80)
print("STEP 5: NAVIGATE TO ASSESSMENTS")
print("=" * 80)
# Navigate to dashboard first
dashboard = DashboardPage(driver)
dashboard.navigate()
time.sleep(1)
# Click Assessments link
dashboard.click_assessments()
time.sleep(2)
# Verify we're on assessments page
assessments = AssessmentsPage(driver)
assessments.wait_for_page_load()
current_url = driver.current_url
if "/assessments" in current_url:
print("✅ Successfully navigated to Assessments page!")
print(f" URL: {current_url}")
else:
print(f"⚠️ Unexpected URL: {current_url}")
# Final summary
print("\n" + "=" * 80)
print("✅ SUCCESS - STUDENT IS NOW ASSESSMENT READY!")
print("=" * 80)
print(f"\n📋 Summary:")
print(f" CPID: {args.cpid}")
print(f" Profile Status: 100% Complete")
print(f" Current Page: Assessments")
print(f" URL: {driver.current_url}")
print("\n🎉 Student can now access and take assessments!")
# Keep browser open for inspection (if not headless)
if not args.headless:
print("\n⏸️ Browser will remain open for 30 seconds for inspection...")
print(" Press Ctrl+C to close immediately")
try:
time.sleep(30)
except KeyboardInterrupt:
print("\n👋 Closing browser...")
return 0
except Exception as e:
print(f"\n❌ ERROR: {e}")
import traceback
traceback.print_exc()
return 1
finally:
if driver:
driver.quit()
print("\n👋 Browser closed")
if __name__ == "__main__":
sys.exit(main())