module Teacher;
	from CourseDB import CourseDB, CourseRecord;
	export Monday, Tuesday, Wednesday, Thursday, Friday, TeacherRecord, Name, TeacherDatabase, Teacher_info, Department, Email, Phone, Office, WTUS, Teacher_class_pref, Preference_value, Class;
	
	object TeacherRecord is
		components: ti:Teacher_info and tp: Teacher_time_pref and 
			    cp: Teacher_class_pref;
		description:	(*
			This contains all the information about a teachers preferences.
				*) ; 	
	end TeacherRecord;

	object Teacher_info is
		components: n:Name and d:Department and o:Office and p:Phone and e:Email and 
			    w:WTUS and oh:Office_hours;
		description: 	(*
			Teacher_info is all the information that a teacher want to share 
			with the students.  The Name component is the teacher's real world
			name.  The Department component specifies what department in 
			the university the teacher belongs to.  The Office component contains
			information about the 	location of the teacher's office.  The Phone 
			component holds the teacher's school phone number.  The Email
			component is the teacher's email address.
				*);
	end Teacher_info;


	object Office_hours is
		components: Days and Times;
		description:	(*
			Office hours will hold the days and times that the teacher will have 
			office hours.  The Days component are all the days in the week
			starting on Monday and ending on Friday.  The Times component 
			are all the working hours in the day.
				*);
	end Office_hours;
	
	object Times is
		components: integer;
		description:	(*
			The times represented w/ an integer of when office hours are held.
				*);
	end Times;

	object TeacherDatabase is 
		components: q: TeacherRecord*;
		description:	(*
			TeacherDatabase is a collection of TeacherRecord.
				*);
	end TeacherDatabase;

	object Name is 
		components: string;
		description:	(*
			Name of the teacher.
				*);
	end Name;

	object Department is 
		components: string;
		description:	(*
			Name of Department.
				*);
	end Department;

	object Office is 
		components: string;
		description:	(*
			Office number.
				*);
	end Office;

	object Phone is 
		components: string;
		description:	(*
			Teacher's phone number.
				*);
	end Phone;

	object Email is 
		components: string;
		description:	(*
			Teacher Email address.
				*);
	end Email;

	object WTUS is 
		components: integer; 
		description:	(*
			Amount of WTUs that a teacher wants.
				*);
	end WTUS;
	
	object Teacher_time_pref is
		components: d: Days;
		description:	(*
			Teacher_time_pref are all the teacher time preferences for the 
			week.  The Days component are all the days in the week, starting 
			on Monday and ending on Friday.
				*);
	end Teacher_time_pref;

	
	object Days is
		components: M: Monday and T: Tuesday and W: Wednesday and Th: Thursday and 
			    F: Friday and S: Saturday;
		description:	(*
			Days are all the days in the week.  All the components are 
			individual days of the week.
				*);
	end Days;


	object Monday is
		components: h: Hour*;
		description:	(*
			Monday is a day in a week.  The Hours components are all the 
			working hours that teacher can work on.
				*);
	end Monday;


	object Tuesday is
		components: h: Hour*;
		description:	(*
			Tuesday is a day in a week.  The Hours components are all the 
			working hours that teacher can work on.
				*);
	end Tuesday;


	object Wednesday is
		components: h: Hour*;
		description:	(*
			Wednesday is a day in a week.  The Hours components are all the 
			working hours that teacher can work on.
				*);
	end Wednesday;


	object Thursday is
		components: h: Hour*;
		description:	(*
			Thursday is a day in a week.  The Hours components are all the 
			working hours that teacher can work on.
				*);
	end Thursday;


	object Friday is
		components: h: Hour*;
		description:	(*
			Friday is a day in a week.  The Hours components are all the 
			working hours that teacher can work on.
				*);
	end Friday;

	object Saturday is
		components: h: Hour*;
		description:	(*
			Saturday is a day in a week.  The Hours components are all the 
			working hours that teacher can work on.
				*);
	end Saturday;

	
	
	object Hour is
		components: p: Preference_value;
		description:	(*
			Hour is an hour of all of the working times of the day and their 
			corresponding preference value. The Preference_value component is 			
			a preference level that the teacher desire. 
				*);
	end Hour;



	object Preference_value is 
		components: integer;
		description:	(*
			A Value between 0-10.
				*);
	end Preference_value;



	object Teacher_class_pref is
		components: c: Class*;
		description:	(*
			Teacher_class_pref is the teacher's complete class preferences and 
			Lab gap time preferences.  The Pref_item component is one item  				
			in Teacher_class_pref
				*);
	end Teacher_class_pref;

		

	object Class is
		components: Lab_gap_time and crd:CourseRecord and p: Preference_value;
		description:	(*
			The Class is all the information of the prefernces for a class.  The 
			Lab_gap_time is how long the teacher think the lab and lecture 			
			should be apart by. The Preference_value component is the 
			preference level that the teacher desire.
				*);
	end Class;

	object Lab_gap_time is 
		components: integer;
		description:	(*
			The number of hours between lecture and lab that the teacher 
			wants.
				*);
	end Lab_gap_time;


	operation Update_Info is
		inputs: tip: Teacher_info and db: TeacherDatabase;
		outputs: db': TeacherDatabase;
		description:	(*
			Add information about a teacher, if the login operation is passed.
				*);
		precondition:
			((tip.n != nil) and (tip.d != nil) and (tip.o != nil) and (tip.p != nil) and (tip.e != nil) and 
			(tip.w != nil) and (tip.oh != nil));
		postcondition:
			forall(tr: TeacherRecord)
				(tr in db') iff 
					(tr in db) or ((tr.ti.n = tip.n) and
							(tr.ti.d = tip.d) and
							(tr.ti.o = tip.o) and
							(tr.ti.e = tip.e) and
							(tr.ti.w = tip.w) and
							(tr.ti.oh = tip.oh));
	end Update_Info;

	operation Update_time_pref is
		inputs: itp: Teacher_time_pref, db: TeacherDatabase;
		outputs: db': TeacherDatabase;
		
		precondition:
			(*
			 * The user must be already Login in order to save the preferences
			 * to the teacher's record, other wise the user will be prompt with
			 * the login window.  Values must range from 0 -10.
			*)
			forall(hour in itp.d.M.h)
				(hour.p != nil) and (hour.p >=0) and (hour.p <= 10) 
				and 
			forall(hour in itp.d.T.h)
				(hour.p != nil) and (hour.p >=0) and (hour.p <= 10)
				and 
			forall(hour in itp.d.W.h)
				(hour.p != nil) and (hour.p >=0) and (hour.p <= 10)
				and 
			forall(hour in itp.d.Th.h)
				(hour.p != nil) and (hour.p >=0) and (hour.p <= 10)
				and 
			forall(hour in itp.d.F.h)
				(hour.p != nil) and (hour.p >=0) and (hour.p <= 10)
				and 
			forall(hour in itp.d.S.h)
				(hour.p != nil) and (hour.p >=0) and (hour.p <= 10)
			; 
		postcondition:
			(*
			 * 
			*)
			forall(tr: TeacherRecord)
				(tr in db') iff 
					(tr in db) or ((tr.tp.d.M.h = itp.d.M.h) and
							(tr.tp.d.T.h = itp.d.T.h) and
							(tr.tp.d.W.h = itp.d.W.h) and
							(tr.tp.d.T.h = itp.d.Th.h) and
							(tr.tp.d.F.h = itp.d.F.h) and
							(tr.tp.d.S.h = itp.d.S.h));
		description:	(*
			Add time preferences for a particular teacher, if the login operation 
			is passed.
				*);
	end Update_time_pref;

	operation Update_class_pref is
		inputs: icp: Teacher_class_pref and db: TeacherDatabase;
		outputs: db': TeacherDatabase;
		description:	(*
			Add class preferences for a particular teacher, if the login 
			operation is passes.
				*);
		precondition:
			(* All Preference values must be between 0 -10
			*)
			forall(class in icp.c)
				(class.p != nil) and (class.p >= 0) and (class.p <=10);
		postcondition:
			forall(tr: TeacherRecord)
				(tr in db') iff 
					(tr in db) or (tr.cp.c = icp.c); 
							



	end Update_class_pref;
	
	operation Login is
		inputs: ts: Teacher_Server and us: Username and p: Password;
		outputs: pass: Pass;
		description:	(*
			Takes the username and password that the user inputted and checks 
			the inputs with the databases of usernames and passwords stored on the server.
			If successful, the "global variable" PASS for the workspace is set.   
				*);
		end Login;
	
	object Teacher_Server 
		components: us: Username and p: Password and db: TeacherDatabase;
		description:	(*	
					The Username component is the user name and the Password component is the password of the user. 
					TeacherDatabase is a database of the preferences for all the teachers.
					The server has a list of Usernames and Passwords.
				*); 	
	end Teacher_Server;
	
	object Username is 
		components: string;
		description:	(*
			The teacher username.
				*);
	end Username;
	
	object Password is string;

	object Pass is boolean ;	 
 
end Teacher;