source: WAeUP_SRP/trunk/Students.py @ 435

Last change on this file since 435 was 435, checked in by joachim, 18 years ago

removed metadata and common schemas from Student*
allow Catalog search for getFolderContents
added indizes jamb_reg_no matric_no to catalog.xml

  • Property svn:keywords set to Id
File size: 22.6 KB
Line 
1#-*- mode: python; mode: fold -*-
2# $Id: Students.py 435 2006-08-28 17:05:19Z joachim $
3from Globals import InitializeClass
4from AccessControl import ClassSecurityInfo
5from AccessControl.SecurityManagement import newSecurityManager
6from zExceptions import BadRequest
7from Products.CMFCore.utils import UniqueObject, getToolByName
8from Products.CMFCore.permissions import View
9from Products.CMFCore.permissions import ModifyPortalContent
10from Products.CPSCore.CPSBase import CPSBase_adder, CPSBaseFolder
11#from Products.CPSCore.CPSBase import CPSBaseDocument as BaseDocument
12from Products.CPSDocument.CPSDocument import CPSDocument
13from Products.CPSCore.CPSBase import CPSBaseBTreeFolder as BaseBTreeFolder
14from Products.CPSCore.CPSMembershipTool import CPSUnrestrictedUser
15from Products.WAeUP_SRP.Academics import makeCertificateCode
16import logging
17import csv,re
18import Globals
19p_home = Globals.package_home(globals())
20i_home = Globals.INSTANCE_HOME
21MAX_TRANS = 1000
22
23def generateStudentId():
24    import random
25    r = random
26    return "%c%d" % (r.choice('ABCDEFGHKLMNPQRSTUVWXY'),r.randint(99999,1000000))
27
28class StudentsFolder(CPSDocument): ###(
29    """
30    WAeUP container for the various WAeUP containers data
31    """
32    meta_type = 'StudentsFolder'
33    portal_type = meta_type
34    security = ClassSecurityInfo()
35    use_catalog_for_folder_contents = True
36
37    security.declareProtected(ModifyPortalContent,"loadFullTimeStudentsFromCSV")###(
38    def loadFullTimeStudentsFromCSV(self):
39        """load Fulltime Studentdata from CSV values"""
40        #return
41        import transaction
42        tr_count = 0
43        name = 'short_full_time'
44        no_import = False
45        if not no_import:
46            no_import = open("%s/import/%s_not_imported.csv" % (i_home,name),"w")
47            no_import.write('"MatricNo","EntryRegNo","CurrentSession","StudentLevel","fullname","FirstName","MiddleName","Lastname","FormerSurname","Sex","Nationality","State","LGA","PermanentAddress","PermanentAddressCity","CampusAddress","PhoneNumber","Emailaddress","Mode","CourseMajor","Faculty","Dept"\n')
48        logger = logging.getLogger('%s_import' % name)
49        logger.info('Start loading from %s.csv' % name)
50        students_folder = self.portal_catalog({'meta_type': 'StudentsFolder'})[-1].getObject()
51        try:
52            students = csv.DictReader(open("%s/import/%s.csv" % (i_home,name),"rb"))
53        except:
54            logger.error('Error reading %s.csv' % name)
55            return
56        l = self.portal_catalog({'meta_type': "StudentClearance",})
57        matrics = []
58        for s in l:
59            matrics.append(s.getObject().getContent().matric_no)
60        print matrics
61        l = self.portal_catalog({'meta_type': "Certificate"})
62        certs = {}
63        for c in l:
64            certs[c.id] = c.getObject()
65        for student in students:
66            logger.info('processing "%(MatricNo)s","%(EntryRegNo)s","%(CurrentSession)s","%(StudentLevel)s","%(fullname)s","%(FirstName)s","%(MiddleName)s","%(Lastname)s","%(FormerSurname)s","%(Sex)s","%(Nationality)s","%(State)s","%(LGA)s","%(PermanentAddress)s","%(PermanentAddressCity)s","%(CampusAddress)s","%(PhoneNumber)s","%(Emailaddress)s","%(Mode)s","%(CourseMajor)s","%(Faculty)s","%(Dept)s"\n' % student)
67            sid = student.get('MatricNo')
68            if sid == "":
69                em = 'Empty MatricNo\n'
70                logger.info(em)
71                no_import.write(em)
72                no_import.write('"%(MatricNo)s","%(EntryRegNo)s","%(CurrentSession)s","%(StudentLevel)s","%(fullname)s","%(FirstName)s","%(MiddleName)s","%(Lastname)s","%(FormerSurname)s","%(Sex)s","%(Nationality)s","%(State)s","%(LGA)s","%(PermanentAddress)s","%(PermanentAddressCity)s","%(CampusAddress)s","%(PhoneNumber)s","%(Emailaddress)s","%(Mode)s","%(CourseMajor)s","%(Faculty)s","%(Dept)s"\n' % student)
73                continue
74            certcode = makeCertificateCode(student.get('CourseMajor'))
75            if certcode not in certs.keys():
76                em = 'Certificate with ID %s %s not found\n' % (certcode, student.get('CourseMajor'))
77                logger.info(em)
78                no_import.write(em)
79                no_import.write('"%(MatricNo)s","%(EntryRegNo)s","%(CurrentSession)s","%(StudentLevel)s","%(fullname)s","%(FirstName)s","%(MiddleName)s","%(Lastname)s","%(FormerSurname)s","%(Sex)s","%(Nationality)s","%(State)s","%(LGA)s","%(PermanentAddress)s","%(PermanentAddressCity)s","%(CampusAddress)s","%(PhoneNumber)s","%(Emailaddress)s","%(Mode)s","%(CourseMajor)s","%(Faculty)s","%(Dept)s"\n' % student)
80                continue
81            level = student.get('StudentLevel')
82            try:
83                int(level)
84            except:
85                em = 'Student with ID %(MatricNo)s StudentLevel is empty\n' % student
86                logger.info(em)
87                no_import.write(em)
88                no_import.write('"%(MatricNo)s","%(EntryRegNo)s","%(CurrentSession)s","%(StudentLevel)s","%(fullname)s","%(FirstName)s","%(MiddleName)s","%(Lastname)s","%(FormerSurname)s","%(Sex)s","%(Nationality)s","%(State)s","%(LGA)s","%(PermanentAddress)s","%(PermanentAddressCity)s","%(CampusAddress)s","%(PhoneNumber)s","%(Emailaddress)s","%(Mode)s","%(CourseMajor)s","%(Faculty)s","%(Dept)s"\n' % student)
89                continue
90            matric_no = student.get('MatricNo')
91            if matric_no not in matrics:
92                matrics.append(matric_no)
93                sid = generateStudentId()
94                #self.log('Creating Faculty %(id)s = %(Title)s' % faculty)
95                logger.info('%(tr_count)s: Creating Student with ID %(sid)s Matric_no %(matric_no)s ' % vars())
96                not_created = True
97                while not_created:
98                    try:
99                        students_folder.invokeFactory('Student', sid)
100                        not_created = False
101                    except BadRequest:
102                        sid = generateStudentId()
103                logger.info('%(tr_count)s: Creating Student with ID %(sid)s Matric_no %(matric_no)s ' % vars())
104                s = getattr(self,sid)
105                s.invokeFactory('StudentPersonal','personal')
106                sp = s.personal
107                d = {'Title': 'Personal Data'}
108                s.invokeFactory('StudentClearance','clearance')
109                sc = s.clearance
110                dc = {'Title': 'Clearance Data'}
111                dc['matric_no'] = matric_no
112                dc['jamb_reg_no'] = student.get('EntryRegNo')
113                lga = student.get('State') + ' / ' + student.get('LGA')               
114                dc['lga'] = lga
115                dc['nationality'] = student.get('Nationality')
116                dc['email'] = student.get('Emailaddress')
117                d['firstname'] = student.get('FirstName')
118                d['middlename'] = student.get('MiddleName')
119                d['lastname'] = student.get('Lastname')
120                d['former_surname'] = student.get('FormerSurname')
121                d['sex'] = student.get('Sex') == 'F'
122                d['perm_address'] = student.get('PermanentAddress')
123                d['perm_city'] = student.get('PermanentAddressCity')
124                d['campus_address'] = student.get('CampusAddress')
125                d['phone'] = student.get('PhoneNumber')
126                sp.getContent().edit(mapping=d)
127                sc.getContent().edit(mapping=dc)
128                #
129                # Study Course
130                #
131                s.invokeFactory('StudentStudyCourse','study_course')
132                sc = s.study_course
133                d = {}
134                #d['matricel_no'] = student.get('MatricNo')
135                #d['entry_reg_no'] = student.get('EntryRegNo')
136                #d['faculty'] = student.get('Faculty')
137                #d['department'] = student.get('Dept')
138                d['course_major'] = certcode
139                css = student.get('CurrentSession') or '2004-2005'
140                cs = int(css.split('-')[0]) - 2000
141                cl = int(student.get('StudentLevel'))/100
142                d['entry_session'] = "200%s" % (cs - cl)
143                sc.getContent().edit(mapping=d)
144                #
145                # Level
146                #
147                l = getattr(sc,level,None)
148                if l is None:
149                    #self.log('Creating Department %(DeptCode)s = %(Description)s' % dep)
150                    logger.info('Creating Level %(StudentLevel)s for %(fullname)s' % student)
151                    sc.invokeFactory('StudyLevel', level)
152                    l = getattr(sc, level)
153                    certificate = certs[certcode]
154                    cert_level = getattr(certificate,level,None)
155                    if cert_level is None:
156                        logger.info('Level %(level)s not in %(certcode)s' % vars())
157                    l.getContent().edit(mapping={'Title': "Level %s" % level})
158                    l.invokeFactory('Semester','first')
159                    l.invokeFactory('Semester','second')
160                    first_s = getattr(l,'first')
161                    first_s.getContent().edit(mapping={'Title': 'First Semester'})
162                    second_s = getattr(l,'second')
163                    second_s.getContent().edit(mapping={'Title': 'Second Semester'})
164            else:
165                em = 'Student with ID %(MatricNo)s %(fullname)s already exists\n' % student
166                logger.info(em)
167                no_import.write(em)
168                no_import.write('"%(MatricNo)s","%(EntryRegNo)s","%(CurrentSession)s","%(StudentLevel)s","%(fullname)s","%(FirstName)s","%(MiddleName)s","%(Lastname)s","%(FormerSurname)s","%(Sex)s","%(Nationality)s","%(State)s","%(LGA)s","%(PermanentAddress)s","%(PermanentAddressCity)s","%(CampusAddress)s","%(PhoneNumber)s","%(Emailaddress)s","%(Mode)s","%(CourseMajor)s","%(Faculty)s","%(Dept)s"\n' % student)
169            if tr_count > MAX_TRANS:
170                transaction.commit()
171                em = 'Transaction commited\n' % student
172                logger.info(em)
173                tr_count = 0
174            tr_count += 1
175        return self.REQUEST.RESPONSE.redirect("%s" % self.REQUEST.get('URL1'))
176        return self.students.academics_contents()
177    ###)
178
179    security.declareProtected(ModifyPortalContent,"loadFullTimeStudentsResultsFromCSV") ###(
180    def loadFullTimeStudentsResultsFromCSV(self):
181        """load Fulltime Studentdata from CSV values"""
182        #return
183        import transaction
184        tr_count = 0
185        name = 'short_full_time_results_2004_2005'
186        no_import = False
187        if not no_import:
188            no_import = open("%s/import/%s_not_imported.csv" % (i_home,name),"w")
189            no_import.write('"Matnumber","CosCode","Ansbook","CosStuatus","Session","Mat_Cos","Score","CarryLevel","Grade","Weight","Semster","Verdict","Level","id","GPA"\n')
190        logger = logging.getLogger('%s_import' % name)
191        logger.info('Start loading from %s.csv' % name)
192        students_folder = self.portal_catalog({'meta_type': 'StudentsFolder'})[-1].getObject()
193        try:
194            results = csv.DictReader(open("%s/import/%s.csv" % (i_home,name),"rb"))
195        except:
196            logger.error('Error reading %s.csv' % name)
197            return
198        l = self.portal_catalog({'meta_type': "Student"})
199        students = {}
200        for s in l:
201            students[s.id] = s.getObject()
202        l = self.portal_catalog({'meta_type': "Course"})
203        courses = {}
204        for c in l:
205            courses[c.id] = c.getObject()
206        for result in results:
207            sid = result.get('Matnumber')
208            if sid not in students.keys():
209                em = 'Student with ID %(Matnumber)s not found\n' % result
210                logger.info(em)
211                no_import.write(em)
212                no_import.write('"%(Matnumber)s","%(CosCode)s","%(Ansbook)s","%(CosStuatus)s","%(Session)s","%(Mat_Cos)s","%(Score)s","%(CarryLevel)s","%(Grade)s","%(Weight)s","%(Semster)s","%(Verdict)s","%(Level)s","%(id)s","%(GPA)s"\n' % result)
213                continue
214            course = result.get('CosCode')
215            if course not in courses.keys():
216                em = 'Course with ID %(CosCode)s not found\n' % result
217                logger.info(em)
218                no_import.write(em)
219                no_import.write('"%(Matnumber)s","%(CosCode)s","%(Ansbook)s","%(CosStuatus)s","%(Session)s","%(Mat_Cos)s","%(Score)s","%(CarryLevel)s","%(Grade)s","%(Weight)s","%(Semster)s","%(Verdict)s","%(Level)s","%(id)s","%(GPA)s"\n' % result)
220                continue
221            level = result.get('Level')
222            try:
223                int(level)
224            except:
225                em = 'Result for result with ID %(Matnumber)s Course %(CosCode)s Level is empty\n' % result
226                logger.info(em)
227                no_import.write(em)
228                no_import.write('"%(Matnumber)s","%(CosCode)s","%(Ansbook)s","%(CosStuatus)s","%(Session)s","%(Mat_Cos)s","%(Score)s","%(CarryLevel)s","%(Grade)s","%(Weight)s","%(Semster)s","%(Verdict)s","%(Level)s","%(id)s","%(GPA)s"\n' % result)
229                continue
230            sf = students.get(sid)
231            sc = getattr(sf,'study_course')
232            l = getattr(sc,level,None)
233            if l is None:
234                #self.log('Creating Department %(DeptCode)s = %(Description)s' % dep)
235                logger.info('Creating Level %(Level)s for %(Matnumber)s' % result)
236                sc.invokeFactory('StudyLevel', level)
237                l = getattr(sc, level)
238                l.getContent().edit(mapping={'Title': "Level %s" % level})
239                l.invokeFactory('Semester','first')
240                l.invokeFactory('Semester','second')
241                first_s = getattr(l,'first')
242                first_s.getContent().edit(mapping={'Title': 'First Semester'})
243                second_s = getattr(l,'second')
244                second_s.getContent().edit(mapping={'Title': 'Second Semester'})
245            snr = result.get('Semester')
246            semester = getattr(l,'first')
247            if snr == "2":
248                semester = getattr(l,'second')
249            logger.info('Creating CourseTicket %(CourseTicket)s in Level %(Level)s for %(Matnumber)s' % result)
250            semester.invokeFactory('CourseTicket',course)
251            ct = getattr(semester,course)
252            d = {}
253            d['ansbook'] = result.get('Ansbook')
254            d['status'] = result.get('CosStuatus')
255            d['score'] = result.get('Score')
256            d['carry_level'] = result.get('CarryLevel')
257            d['grade'] = result.get('Grade')
258            d['weight'] = result.get('Weight')
259            d['verdict'] = result.get('Verdict')
260            d['import_id'] = result.get('id')
261            gpa = result.get('GPA').replace(',','.')
262            d['gpa'] = float(gpa)
263            ct.getContent().edit(mapping = d)
264            if tr_count > MAX_TRANS:
265                transaction.commit()
266                tr_count = 0
267            tr_count += 1
268        return self.students.academics_contents()
269
270###)
271
272
273    security.declareProtected(View,"Title")
274    def Title(self):
275        """compose title"""
276        return "Student Section"
277
278InitializeClass(StudentsFolder)
279
280def addStudentsFolder(container, id, REQUEST=None, **kw):
281    """Add a Student."""
282    ob = StudentsFolder(id, **kw)
283    return CPSBase_adder(container, ob, REQUEST=REQUEST)
284###)
285
286class Student(CPSDocument): ###(
287    """
288    WAeUP Student container for the various student data
289    """
290    meta_type = 'Student'
291    portal_type = meta_type
292    security = ClassSecurityInfo()
293
294    security.declareProtected(View,"Title")
295    def Title(self):
296        """compose title"""
297        reg_nr = self.getId()[1:]
298        data = getattr(self,'personal',None)
299        if data is None:
300            data = getattr(self,'jamb',None)
301        if data:
302            content = data.getContent()
303            return "%s %s" % (content.firstname,content.lastname)
304        return self.title
305
306    def Description(self):
307        """compose description"""
308        data = getattr(self,'PERSONAL',None)
309        if data is None:
310            return "none"
311        if data:
312            content = data.getContent()
313            return "%s" % (content.description)
314        return self.description
315
316    security.declareProtected(View,"setScratchCardData")
317    def setScratchCardData(self,ident,ds):
318        """set this data """
319        dict = {'%s_sc_pin' % ident : ds.get('sc_pin'),
320                '%s_sc_id' % ident : ds.get('sc_id'),
321                '%s_sc_value' % ident : ds.get('sc_value'),
322                '%s_date' % ident : ds.get('sc_date'),
323                }
324
325        old_user = self.portal_membership.getAuthenticatedMember()
326        if self.portal_membership.isAnonymousUser():
327            tmp_user = CPSUnrestrictedUser('s%(jamb_id)s' % ds, '',
328                                       ['StudentManager'], '')
329            tmp_user = tmp_user.__of__(self.acl_users)
330            newSecurityManager(None, tmp_user)
331        #print str(dict)
332        self.edit(mapping=dict)
333        newSecurityManager(None, old_user)
334
335    security.declareProtected(View,"memberIsOwner")
336    def memberIsOwner(self):
337        """is the current user the owner"""
338        member = self.portal_membership.getAuthenticatedMember()
339        #print member, self.getId(),self.aq_parent.getId()
340        if self.aq_parent.getId() == str(member):
341            return True
342        return False
343
344    security.declareProtected(View,"accommodationIsBooked")
345    def accommodationIsBooked(self):
346        """is the accommodation booked"""
347        if self.accommodation_sc_pin != '':
348            return True
349        return False
350
351    security.declareProtected(View,"accommodationIsPayed")
352    def accommodationIsPayed(self):
353        """is the accommodation payed"""
354        if self.hostel_fee_sc_pin != '':
355            return True
356        return False
357
358    security.declareProtected(View,"isRegisteredForCurrentLevel")
359    def isRegisteredForCurrentLevel(self):
360        """is the student registered for the current level"""
361        for l in  self.aq_parent.objectValues():
362            if l.portal_type == 'StudyLevel':
363                return True
364        return False
365
366InitializeClass(Student)
367
368def addStudent(container, id, REQUEST=None, **kw):
369    """Add a Student."""
370    ob = Student(id, **kw)
371    return CPSBase_adder(container, ob, REQUEST=REQUEST)
372
373###)
374
375class StudentPersonal(CPSDocument): ###(
376    """
377    WAeUP Student container for the various student data
378    """
379    meta_type = 'StudentPersonal'
380    portal_type = meta_type
381    security = ClassSecurityInfo()
382
383    security.declareProtected(View,"Title")
384    def Title(self):
385        """compose title"""
386        content = self.getContent()
387        #return "Personal Data for %s %s" % (content.firstname,content.lastname)
388        return "Personal Data"
389
390
391InitializeClass(StudentPersonal)
392
393def addStudentPersonal(container, id, REQUEST=None, **kw):
394    """Add a Students personal data."""
395    ob = StudentPersonal(id, **kw)
396    return CPSBase_adder(container, ob, REQUEST=REQUEST)
397
398###)
399
400class StudentClearance(CPSDocument): ###(
401    """
402    WAeUP Student container for the various student data
403    """
404    meta_type = 'StudentClearance'
405    portal_type = meta_type
406    security = ClassSecurityInfo()
407
408    security.declareProtected(View,"Title")
409    def Title(self):
410        """compose title"""
411        content = self.getContent()
412        #return "Clearance Data for %s %s" % (content.firstname,content.lastname)
413        return "Clearance Data"
414
415
416InitializeClass(StudentClearance)
417
418def addStudentClearance(container, id, REQUEST=None, **kw):
419    """Add a Students personal data."""
420    ob = StudentClearance(id, **kw)
421    return CPSBase_adder(container, ob, REQUEST=REQUEST)
422
423###)
424
425class StudentStudyCourse(CPSDocument): ###(
426    """
427    WAeUP Student container for the various student data
428    """
429    meta_type = 'StudentStudyCourse'
430    portal_type = meta_type
431    security = ClassSecurityInfo()
432
433    security.declareProtected(View,"Title")
434    def Title(self):
435        """compose title"""
436        content = self.getContent()
437        return "Course Major"
438
439
440InitializeClass(StudentStudyCourse)
441
442def addStudentStudyCourse(container, id, REQUEST=None, **kw):
443    """Add a Students personal data."""
444    ob = StudentStudyCourse(id, **kw)
445    return CPSBase_adder(container, ob, REQUEST=REQUEST)
446
447###)
448
449class StudentAdmission(CPSDocument): ###(
450    """
451    WAeUP Student container for the various student data
452    """
453    meta_type = 'StudentAdmission'
454    portal_type = meta_type
455    security = ClassSecurityInfo()
456
457    security.declareProtected(View,"Title")
458    def Title(self):
459        """compose title"""
460        return "Admission Data"
461
462
463InitializeClass(StudentAdmission)
464
465def addStudentAdmission(container, id, REQUEST=None, **kw):
466    """Add a Students eligibility data."""
467    ob = StudentAdmission(id, **kw)
468    return CPSBase_adder(container, ob, REQUEST=REQUEST)
469
470###)
471
472class StudentDocuments(CPSDocument): ###(
473    """
474    WAeUP Student container for the various student data
475    """
476    meta_type = 'StudentDocuments'
477    portal_type = meta_type
478    security = ClassSecurityInfo()
479
480    security.declareProtected(View,"Title")
481    def Title(self):
482        """compose title"""
483        content = self.getContent()
484        return "Scanned Documents"
485
486
487InitializeClass(StudentDocuments)
488
489def addStudentDocuments(container, id, REQUEST=None, **kw):
490    """Add a Students documents"""
491    ob = StudentDocuments(id, **kw)
492    return CPSBase_adder(container, ob, REQUEST=REQUEST)
493
494###)
495
496class Jamb(CPSDocument): ###(
497    """
498    WAeUP Jamb containing the courses and students
499    """
500    meta_type = 'Jamb'
501    portal_type = meta_type
502    security = ClassSecurityInfo()
503
504    security.declareProtected(View,"Title")
505    def Title(self):
506        """compose title"""
507        content = self.getContent()
508        return "JAMB Data for %s %s" % (content.firstname,content.lastname)
509
510    security.declareProtected(View,"setOwnership")
511    def setOwnership(self,member_id):
512        """set ownership"""
513        pm = getattr(self,'portal_membership')
514        member = pm.getMemberById(member_id)
515        self.changeOwnership(member)
516
517InitializeClass(Jamb)
518
519def addJamb(container, id, REQUEST=None, **kw):
520    """Add a Jamb."""
521    ob = Jamb(id, **kw)
522    return CPSBase_adder(container, ob, REQUEST=REQUEST)
523
524###)
525
526class StudyLevel(CPSDocument): ###(
527    """
528    WAeUP StudyLevel containing the courses and students
529    """
530    meta_type = 'StudyLevel'
531    portal_type = meta_type
532    security = ClassSecurityInfo()
533
534InitializeClass(StudyLevel)
535
536def addStudyLevel(container, id, REQUEST=None, **kw):
537    """Add a StudyLevel."""
538    ob = StudyLevel(id, **kw)
539    return CPSBase_adder(container, ob, REQUEST=REQUEST)
540
541###)
542
543class Semester(CPSDocument): ###(
544    """
545    WAeUP Semester containing the courses and students
546    """
547    meta_type = 'Semester'
548    portal_type = meta_type
549    security = ClassSecurityInfo()
550
551InitializeClass(Semester)
552
553def addSemester(container, id, REQUEST=None, **kw):
554    """Add a Semester."""
555    ob = Semester(id, **kw)
556    return CPSBase_adder(container, ob, REQUEST=REQUEST)
557
558###)
559
Note: See TracBrowser for help on using the repository browser.