/// /// /// import * as Request from 'request'; import { Observable } from 'rx'; import { TakenCourse } from '../models/course'; import { Exam } from '../models/exam'; import { caller } from '../helpers/caller'; import { fetcher } from '../helpers/fetcher'; import { seeker } from '../helpers/seeker'; /** * @description * Represents an instance of Student User. */ export class User { /** * @description The administration class id. (行政班级) * @example '2012010201' */ administrationClass: string = null; /** * @description The administration college name.(行政管理院系) * @example '通信与信息工程学院' */ administrationCollege: string = null; /** * @description The campus name. (所属校区) * @example '清水河校区' */ campus: string = null; /** * @description The college name. (院系) * @example '通信与信息工程学院' */ college: string = null; /** * @description The date of enrollment. (入校时间) * @example new Date('2012-09-01') */ dateFrom: Date = null; /** * @description The date of graduation. (应毕业时间) * @example new Date('2016-07-01') */ dateTo: Date = null; /** * @description The direction of major. (专业方向) * @example null */ direction: string = null; /** * @description The type of education. (教育形式) * @example null */ educationType: string = null; /** * @description The english name. (英文名) * @example 'Qiu Tongyu' */ englishName: string = null; /** * @description The gender/sex. (性别) * @example '男' */ gender: string = null; /** * @description The actual grade of education. (所在年级) * @notice It may not be the same number in the student id. * @example 2012 */ grade: number = null; /** * @description The student/staff id. (学号/工号) * @example '2012019050031' */ id: string = null; /** * @description The status of whether in enrollment. (是否在籍) * @example true */ inEnrollment: boolean = null; /** * @description The status of whether in school. (是否在校) * @example true */ inSchool: boolean = null; /** * @description The major name. (专业) * @example '网络工程' */ major: string = null; /** * @description The chinese name. (姓名) * @example '秋桐宇' */ name: string = null; /** * @description The project name. (项目) * @example '本科' */ project: string = null; /** * @description The qualification of education. (学历层次) * @example '本科' */ qualification: string = null; /** * @description The length of years in campus. (学制) * @example 4 */ schoolingLength: number = null; /** * @description The status of enrollment. (学籍状态) * @example '在籍在校' */ status: string = null; /** * @description The type of study. (学习形式) * @example '普通全日制' */ studyType: string = null; /** * @description The genre of student. (学生类别) * @example '普通本科生' */ genre: string = null; /** * @description The status of whether the given id and password is confirmed. * @example true */ isConfirmed: boolean = null; /** * @description The password. */ private password: string = null; /** * @description The jar to save the cookies. */ jar: Request.CookieJar = null; /** * @description The constructor of the class. * @param id The student/staff id. * @param password The password. */ constructor (id: string, password: string) { this.id = id; this.password = password; this.isConfirmed = false; this.jar = Request.jar(); } /** * @description Check whether the student id and password is valid of not. * @notice If some other accident occurs (i.e. No network), the result would be null, please do check whether the error exists or not. * @param callback The callback function to be called with an error or the result of verify for users unfamiliar with Rx. It's deprecated. * @returns The Observable instance of the confirm result. */ confirm (callback?: { (error: Error, res: boolean): void; }): Observable { var observable = fetcher.confirmUser(this.id, this.password, this.jar) .do((res) => res && this.getDetail()); caller.nodifyObservable(observable, callback); return observable; } /** * @description Get the courses of the given grade and semester online only once. * @param grade The grade of courses, such as 2012, use 0 to mean all grades. * @param semester The semester of courses, such as 1, use 0 to mean all semesters. * @param callback The callback function to be called with an error or the result of courses for users unfamiliar with Rx. It's deprecated. */ getCourses (grade: number, semester: number, callback?: any): Observable { var observable = this.getCoursesCallByParam(grade, semester, false); caller.nodifyObservable(observable, callback); return observable; } /** * @description Get the courses of the given grade and semester online anytime it's updated. * @param grade The grade of courses, such as 2012, use 0 to mean all grades. * @param semester The semester of courses, such as 1, use 0 to mean all semesters. * @param callback The callback function to be called with an error or the result of courses for users unfamiliar with Rx. It's deprecated. */ getCoursesForever (grade: number, semester: number, callback?: any): Observable { var observable = this.getCoursesCallByParam(grade, semester, true); caller.nodifyObservable(observable, callback); return observable; } /** * @description Get the courses of the given grade and semester offline only once. * @param grade The grade of courses, such as 2012, use 0 to mean all grades. * @param semester The semester of courses, such as 1, use 0 to mean all semesters. * @param callback The callback function to be called with an error or the result of courses for users unfamiliar with Rx. It's deprecated. */ getCoursesInCache (grade: number, semester: number, callback?: any): Observable { var observable = seeker.getUserCourses({ grade: grade, semester: semester }); caller.nodifyObservable(observable, callback); return observable; } /** * @description Get the courses of the given grade and semester online when possible, offline if necessary only once. * @param grade The grade of courses, such as 2012, use 0 to mean all grades. * @param semester The semester of courses, such as 1, use 0 to mean all semesters. * @param callback The callback function to be called with an error or the result of courses for users unfamiliar with Rx. It's deprecated. */ getCoursesWithCache (grade: number, semester: number, callback?: any): Observable { var observable = this.getCourses(grade, semester) .catch(this.getCoursesInCache(grade, semester)); caller.nodifyObservable(observable, callback); return observable; } /** * @description Get the exams of the given grade and semester online only once. * @param grade The grade of exams, such as 2012, use 0 to mean all grades. * @param semester The semester of exams, such as 1, use 0 to mean all semesters. * @param callback The callback function to be called with an error or the result of exams for users unfamiliar with Rx. It's deprecated. */ getExams (grade: number, semester: number, callback?: any): Observable { var observable = this.getExamsCallByParam(grade, semester, false); caller.nodifyObservable(observable, callback); return observable; } /** * @description Get the exams of the given grade and semester online anytime it's updated. * @param grade The grade of exams, such as 2012, use 0 to mean all grades. * @param semester The semester of exams, such as 1, use 0 to mean all semesters. * @param callback The callback function to be called with an error or the result of exams for users unfamiliar with Rx. It's deprecated. */ getExamsForever (grade: number, semester: number, callback?: any): Observable { var observable = this.getExamsCallByParam(grade, semester, true); caller.nodifyObservable(observable, callback); return observable; } /** * @description Get the exams of the given grade and semester offline only once. * @param grade The grade of exams, such as 2012, use 0 to mean all grades. * @param semester The semester of exams, such as 1, use 0 to mean all semesters. * @param callback The callback function to be called with an error or the result of exams for users unfamiliar with Rx. It's deprecated. */ getExamsInCache (grade: number, semester: number, callback?: any): Observable { var observable = seeker.getUserExams({ grade: grade, semester: semester }); caller.nodifyObservable(observable, callback); return observable; } /** * @description Get the exams of the given grade and semester online when possible, offline if necessary only once. * @param grade The grade of exams, such as 2012, use 0 to mean all grades. * @param semester The semester of exams, such as 1, use 0 to mean all semesters. * @param callback The callback function to be called with an error or the result of exams for users unfamiliar with Rx. It's deprecated. */ getExamsWithCache (grade: number, semester: number, callback?: any): Observable { var observable = this.getExams(grade, semester) .catch(this.getExamsInCache(grade, semester)); caller.nodifyObservable(observable, callback); return observable; } /** * @description The internal method for DRY reason. */ private getCoursesCallByParam (grade: number, semester: number, forever: boolean): Observable { return this.confirm() .flatMap((res) => res? fetcher.getUserCourses({ grade: grade, semester: semester }, forever, this.jar): Observable.throw(new Error('401: The user validation failed.'))); } /** * @description The internal method to get the user details. */ private getDetail (): void { fetcher.getUserDetail(this.jar).subscribe((detail) => { if (this.id !== detail.id) { throw new Error('The user id is different of the detail one.') } this.administrationClass = detail.administrationClass; this.administrationCollege = detail.administrationCollege; this.campus = detail.campus; this.college = detail.college; this.dateFrom = detail.dateFrom; this.dateTo = detail.dateTo; this.direction = detail.direction; this.educationType = detail.educationType; this.englishName = detail.englishName; this.gender = detail.gender; this.grade = detail.grade; this.inEnrollment = detail.inEnrollment; this.inSchool = detail.inSchool; this.major = detail.major; this.project = detail.project; this.qualification = detail.qualification; this.schoolingLength = detail.schoolingLength; this.status = detail.status; this.studyType = detail.studyType; this.genre = detail.genre; }); } /** * @description The internal method for DRY reason. */ private getExamsCallByParam (grade: number, semester: number, forever: boolean): Observable { return this.confirm().flatMap((res) => res? fetcher.getUserExams({ grade: grade, semester: semester }, forever, this.jar): Observable.throw(new Error('401: The user validation failed.'))); } } /** * @description The factory of User class. */ export class UserFactory { /** * @description The method to create new user instance. * @param id The student/staff id. * @param password The password. * @returns The user instance of given id and password. (not confirmed) */ $new (id: string, password: string) { return new User(id, password); } } /** * @description The UserFactory instance for access. */ export const userFactory: UserFactory = new UserFactory();