-
Notifications
You must be signed in to change notification settings - Fork 4
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Improve Page Loading & Profile Structure (#6)
* Add modular breakdown of page loading * Added object approach to profile info * Remove unused variables
- Loading branch information
1 parent
54e5c66
commit 33759f6
Showing
14 changed files
with
541 additions
and
227 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Empty file.
This file was deleted.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,70 @@ | ||
import datetime | ||
from typing import Optional | ||
|
||
import requests_html | ||
from bs4 import BeautifulSoup | ||
|
||
from pesuacademy import pages | ||
|
||
|
||
class PageHandler: | ||
def __init__(self, session: requests_html.HTMLSession): | ||
self.__session = session | ||
self._semester_ids = dict() | ||
self.course_page_handler = pages.CoursesPageHandler() | ||
self.attendance_page_handler = pages.AttendancePageHandler() | ||
self.profile_page_handler = pages.ProfilePageHandler() | ||
|
||
def set_semester_id_to_number_mapping(self, csrf_token: str): | ||
try: | ||
url = "https://www.pesuacademy.com/Academy/a/studentProfilePESU/getStudentSemestersPESU" | ||
query = {"_": str(int(datetime.datetime.now().timestamp() * 1000))} | ||
headers = { | ||
"accept": "*/*", | ||
"accept-language": "en-IN,en-US;q=0.9,en-GB;q=0.8,en;q=0.7", | ||
"content-type": "application/x-www-form-urlencoded", | ||
"referer": "https://www.pesuacademy.com/Academy/s/studentProfilePESU", | ||
"sec-ch-ua": '"Google Chrome";v="123", "Not:A-Brand";v="8", "Chromium";v="123"', | ||
"sec-ch-ua-mobile": "?0", | ||
"sec-ch-ua-platform": "Windows", | ||
"sec-fetch-dest": "empty", | ||
"sec-fetch-mode": "cors", | ||
"sec-fetch-site": "same-origin", | ||
"user-agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/123.0.0.0 Safari/537.36", | ||
"x-csrf-token": csrf_token, | ||
"x-requested-with": "XMLHttpRequest" | ||
} | ||
response = self.__session.get(url, allow_redirects=False, params=query, headers=headers) | ||
if response.status_code != 200: | ||
raise ConnectionError("Unable to fetch course data.") | ||
except Exception: | ||
raise ConnectionError("Unable to fetch course data.") | ||
|
||
option_tags = response.json() | ||
option_tags = BeautifulSoup(option_tags, "lxml") | ||
option_tags = option_tags.find_all("option") | ||
semester_string_ids = list(map(lambda x: x.attrs["value"], option_tags)) | ||
# TODO: Handle CIE semesters (sometimes the tag is <option value="972">CIE - Level2 (Odd Sem)</option> | ||
semester_numbers = list(map(lambda x: int(x.text.split("Sem-")[1]), option_tags)) | ||
semesters = dict(zip(semester_numbers, semester_string_ids)) | ||
self._semester_ids = semesters | ||
|
||
def get_semester_ids_from_semester_number(self, semester: Optional[int] = None) -> dict: | ||
""" | ||
Get the semester ids from the semester number. If semester is not provided, all semester ids are returned. | ||
:param semester: The semester number. | ||
:return: The semester ids mapping. | ||
""" | ||
assert semester is None or 1 <= semester <= 8, "Semester number should be between 1 and 8." | ||
return self._semester_ids if semester is None else {semester: self._semester_ids[semester]} | ||
|
||
def get_profile(self): | ||
return self.profile_page_handler.get_page(self.__session) | ||
|
||
def get_courses(self, semester: Optional[int] = None): | ||
semester_ids = self.get_semester_ids_from_semester_number(semester) | ||
return self.course_page_handler.get_page(self.__session, semester_ids) | ||
|
||
def get_attendance(self, semester: Optional[int] = None): | ||
semester_ids = self.get_semester_ids_from_semester_number(semester) | ||
return self.attendance_page_handler.get_page(self.__session, semester_ids) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,2 +1,11 @@ | ||
from .course import Course, Attendance | ||
from .profile import Profile | ||
from .profile import ( | ||
Profile, | ||
ClassAndSectionInfo, | ||
PersonalDetails, | ||
OtherInformation, | ||
ParentDetails, | ||
ParentInformation, | ||
AddressDetails, | ||
QualifyingExamination | ||
) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,8 +1,146 @@ | ||
# TODO: Add a list of fields and assign them only. Do not allow any other fields to be added. | ||
# TODO: Make separate profile for KYCAS and Profile | ||
import datetime | ||
from typing import Optional | ||
|
||
|
||
class ClassAndSectionInfo: | ||
def __init__( | ||
self, | ||
prn: str, | ||
srn: str, | ||
name: str, | ||
semester: str, | ||
section: str, | ||
department: str, | ||
branch: str, | ||
institute: str, | ||
cycle: Optional[str] = None | ||
): | ||
self.prn = prn | ||
self.srn = srn | ||
self.name = name | ||
self.semester = semester | ||
self.section = section | ||
self.cycle = cycle | ||
self.department = department | ||
self.branch = branch | ||
self.institute = institute | ||
|
||
def __str__(self): | ||
return f"{self.__dict__}" | ||
|
||
|
||
class PersonalDetails: | ||
def __init__( | ||
self, | ||
name: str, | ||
prn: str, | ||
srn: str, | ||
branch: str, | ||
semester: str, | ||
section: str, | ||
program: Optional[str] = None, | ||
email: Optional[str] = None, | ||
mobile: Optional[str] = None, | ||
aadhar: Optional[str] = None, | ||
name_as_in_aadhar: Optional[str] = None | ||
): | ||
self.name = name | ||
self.prn = prn | ||
self.srn = srn | ||
self.program = program | ||
self.branch = branch | ||
self.semester = semester | ||
self.section = section | ||
self.email = email | ||
self.mobile = mobile | ||
self.aadhar = aadhar | ||
self.name_as_in_aadhar = name_as_in_aadhar | ||
|
||
def __str__(self): | ||
return f"{self.__dict__}" | ||
|
||
|
||
class OtherInformation: | ||
def __init__(self, sslc: float, puc: float, dob: datetime.date, blood_group: str): | ||
self.sslc = sslc | ||
self.puc = puc | ||
self.dob = dob | ||
self.blood_group = blood_group | ||
|
||
def __str__(self): | ||
return f"{self.__dict__}" | ||
|
||
|
||
class QualifyingExamination: | ||
def __init__(self, exam: str, rank: int, score: float): | ||
self.exam = exam | ||
self.rank = rank | ||
self.score = score | ||
|
||
def __str__(self): | ||
return f"{self.__dict__}" | ||
|
||
|
||
class ParentInformation: | ||
def __init__( | ||
self, | ||
name: str, | ||
mobile: str, | ||
email: str, | ||
occupation: str, | ||
qualification: str, | ||
designation: str, | ||
employer: str | ||
): | ||
self.name = name | ||
self.mobile = mobile | ||
self.email = email | ||
self.occupation = occupation | ||
self.qualification = qualification | ||
self.designation = designation | ||
self.employer = employer | ||
|
||
|
||
class ParentDetails: | ||
def __init__( | ||
self, | ||
mother: ParentInformation, | ||
father: ParentInformation | ||
): | ||
self.mother = mother | ||
self.father = father | ||
|
||
def __str__(self): | ||
return f"{self.__dict__}" | ||
|
||
|
||
def __str__(self): | ||
return f"{self.__dict__}" | ||
|
||
|
||
class AddressDetails: | ||
def __init__(self, present: str, permanent: str): | ||
self.present = present | ||
self.permanent = permanent | ||
|
||
def __str__(self): | ||
return f"{self.__dict__}" | ||
|
||
|
||
class Profile: | ||
def __init__(self, **kwargs): | ||
self.__dict__.update(kwargs) | ||
def __init__( | ||
self, | ||
personal_details: PersonalDetails, | ||
other_information: OtherInformation, | ||
qualifying_examination: QualifyingExamination, | ||
parent_details: ParentDetails, | ||
address_details: AddressDetails | ||
): | ||
self.personal_details = personal_details | ||
self.other_information = other_information | ||
self.qualifying_examination = qualifying_examination | ||
self.parent_details = parent_details | ||
self.address_details = address_details | ||
|
||
def __str__(self): | ||
return f"{self.__dict__}" |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1 +1,3 @@ | ||
from .profile import get_profile_page | ||
from .attendance import AttendancePageHandler | ||
from .courses import CoursesPageHandler | ||
from .profile import ProfilePageHandler |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Oops, something went wrong.