source: main/waeup.aaue/trunk/src/waeup/aaue/applicants/browser.py @ 15950

Last change on this file since 15950 was 15950, checked in by Henrik Bettermann, 5 years ago

Add Fedex payment application.

  • Property svn:keywords set to Id
File size: 28.1 KB
Line 
1## $Id: browser.py 15950 2020-01-24 08:36:46Z henrik $
2##
3## Copyright (C) 2011 Uli Fouquet & Henrik Bettermann
4## This program is free software; you can redistribute it and/or modify
5## it under the terms of the GNU General Public License as published by
6## the Free Software Foundation; either version 2 of the License, or
7## (at your option) any later version.
8##
9## This program is distributed in the hope that it will be useful,
10## but WITHOUT ANY WARRANTY; without even the implied warranty of
11## MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12## GNU General Public License for more details.
13##
14## You should have received a copy of the GNU General Public License
15## along with this program; if not, write to the Free Software
16## Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
17##
18"""UI components for basic applicants and related components.
19"""
20import grok
21import os
22from zope.component import getUtility, getAdapter
23from zope.i18n import translate
24from hurry.workflow.interfaces import IWorkflowState
25from waeup.kofa.interfaces import (
26    IExtFileStore, IFileStoreNameChooser, IKofaUtils)
27from zope.formlib.textwidgets import BytesDisplayWidget
28from waeup.kofa.utils.helpers import string_from_bytes, file_size
29from waeup.kofa.applicants.browser import (
30    ApplicantCheckStatusPage, ApplicantBaseDisplayFormPage,
31    AdditionalFile)
32from waeup.kofa.applicants.workflow import STARTED, PAID
33from waeup.kofa.applicants.viewlets import PDFActionButton
34from waeup.kofa.applicants.interfaces import IApplicantRegisterUpdate
35from waeup.kofa.browser.layout import UtilityView
36from waeup.kofa.students.interfaces import IStudentsUtils
37from waeup.kofa.interfaces import IPDF
38from waeup.kofa.browser.viewlets import ManageActionButton
39from waeup.aaue.interfaces import MessageFactory as _
40from kofacustom.nigeria.applicants.browser import (
41    NigeriaApplicantDisplayFormPage,
42    NigeriaApplicantManageFormPage,
43    NigeriaApplicantEditFormPage,
44    NigeriaPDFApplicationSlip,
45    NigeriaApplicantRegistrationPage,
46    NigeriaExportPDFPaymentSlipPage,
47    )
48from kofacustom.nigeria.applicants.interfaces import OMIT_DISPLAY_FIELDS
49from waeup.aaue.applicants.interfaces import (
50    ICustomUGApplicant,
51    ICustomUGApplicantEdit,
52    ITranscriptApplicant,
53    ICertificateRequest,
54    ICustomApplicant,
55    IVerificationRequest,
56    ISendByEmailRequest,
57    IFedexRequest
58    )
59
60UG_OMIT_FIELDS = (
61      'hq_type', 'hq_fname', 'hq_matric_no',
62      'hq_degree', 'hq_school', 'hq_session', 'hq_disc',
63      'hq_type2', 'hq_fname2', 'hq_matric_no2',
64      'hq_degree2', 'hq_school2', 'hq_session2', 'hq_disc2',
65      'hq_type3', 'hq_fname3', 'hq_matric_no3',
66      'hq_degree3', 'hq_school3', 'hq_session3', 'hq_disc3',
67      'nysc_year',
68      'nysc_location',
69      'nysc_lga',
70      'employer',
71      'emp_position',
72      'emp_start',
73      'emp_end',
74      'emp_reason',
75      'employer2',
76      'emp2_position',
77      'emp2_start',
78      'emp2_end',
79      'emp2_reason',
80      'former_matric',
81      )
82UG_OMIT_DISPLAY_FIELDS = OMIT_DISPLAY_FIELDS + (
83    'jamb_subjects_list', 'master_sheet_number') + UG_OMIT_FIELDS
84UG_OMIT_PDF_FIELDS = UG_OMIT_DISPLAY_FIELDS + UG_OMIT_FIELDS + (
85      'alr_fname', 'alr_no', 'alr_date',
86      'alr_results', 'notice')
87UG_OMIT_MANAGE_FIELDS = (
88    'special_application','jamb_subjects_list',) + UG_OMIT_FIELDS
89UG_OMIT_EDIT_FIELDS = UG_OMIT_MANAGE_FIELDS + OMIT_DISPLAY_FIELDS + (
90    'student_id',
91    'notice',
92    'jamb_age',
93    'jamb_subjects',
94    'jamb_score',
95    'jamb_reg_number',
96    'aggregate',
97    'master_sheet_number',
98    'screening_venue',
99    'screening_score',
100    'screening_date'
101    )
102
103UDE_OMIT_FIELDS = (
104      'nysc_year',
105      'nysc_location',
106      'nysc_lga',
107      'employer',
108      'emp_position',
109      'emp_start',
110      'emp_end',
111      'emp_reason',
112      'employer2',
113      'emp2_position',
114      'emp2_start',
115      'emp2_end',
116      'emp2_reason',
117      'former_matric',
118      )
119UDE_OMIT_DISPLAY_FIELDS = OMIT_DISPLAY_FIELDS + (
120    'jamb_subjects_list', 'master_sheet_number') + UDE_OMIT_FIELDS
121UDE_OMIT_PDF_FIELDS = UDE_OMIT_DISPLAY_FIELDS + UDE_OMIT_FIELDS + (
122      #'alr_fname', 'alr_no', 'alr_date', 'alr_results',
123      'hq_type2', 'hq_fname2', 'hq_matric_no2',
124      'hq_degree2', 'hq_school2', 'hq_session2', 'hq_disc2',
125      'hq_type3', 'hq_fname3', 'hq_matric_no3',
126      'hq_degree3', 'hq_school3', 'hq_session3', 'hq_disc3',
127      'notice')
128UDE_OMIT_MANAGE_FIELDS = (
129    'special_application','jamb_subjects_list',) + UDE_OMIT_FIELDS
130UDE_OMIT_EDIT_FIELDS = UDE_OMIT_MANAGE_FIELDS + OMIT_DISPLAY_FIELDS + (
131    'student_id',
132    'notice',
133    'jamb_age',
134    'jamb_subjects',
135    'jamb_score',
136    'jamb_reg_number',
137    'aggregate',
138    'master_sheet_number',
139    'screening_venue',
140    'screening_score',
141    'screening_date'
142    )
143
144#UG_OMIT_PDF_FIELDS = tuple([
145#    element for element in UG_OMIT_PDF_FIELDS if not element == 'phone'])
146
147#UG_OMIT_PDF_FIELDS += (
148#      'reg_number','alr_fname', 'alr_no', 'alr_date',
149#      'alr_results', 'notice'
150#      )
151
152PG_OMIT_FIELDS = (
153    'fst_sit_fname',
154    'fst_sit_no',
155    'fst_sit_date',
156    'fst_sit_type',
157    'fst_sit_results',
158    'scd_sit_fname',
159    'scd_sit_no',
160    'scd_sit_date',
161    'scd_sit_type',
162    'scd_sit_results',
163    #'programme_type',
164    'jamb_age',
165    'jamb_subjects',
166    'jamb_score',
167    'jamb_reg_number',
168    'aggregate'
169    )
170PG_OMIT_DISPLAY_FIELDS = OMIT_DISPLAY_FIELDS + (
171    'jamb_subjects_list',) + PG_OMIT_FIELDS
172PG_OMIT_PDF_FIELDS = PG_OMIT_DISPLAY_FIELDS + PG_OMIT_FIELDS + (
173      'reg_number','alr_fname', 'alr_no', 'alr_date',
174      'alr_results', 'notice',
175      'nysc_year',
176      'nysc_location',
177      'nysc_lga',
178      'former_matric',
179      )
180PG_OMIT_MANAGE_FIELDS = (
181    'special_application','jamb_subjects_list',) + PG_OMIT_FIELDS
182PG_OMIT_EDIT_FIELDS = PG_OMIT_MANAGE_FIELDS + OMIT_DISPLAY_FIELDS + (
183    'student_id',
184    'notice',
185    )
186
187PTEE_OMIT_FIELDS = (
188    'jamb_age',
189    'jamb_subjects',
190    'jamb_score',
191    'jamb_reg_number',
192    'aggregate'
193    )
194PTEE_OMIT_DISPLAY_FIELDS = OMIT_DISPLAY_FIELDS + (
195    'jamb_subjects_list',) + PTEE_OMIT_FIELDS
196PTEE_OMIT_PDF_FIELDS = PTEE_OMIT_DISPLAY_FIELDS + PTEE_OMIT_FIELDS + (
197      'reg_number','alr_fname', 'alr_no', 'alr_date',
198      'alr_results', 'notice',
199      'nysc_year',
200      'nysc_location',
201      'nysc_lga',
202      'employer',
203      'emp_position',
204      'emp_start',
205      'emp_end',
206      'emp_reason',
207      'employer2',
208      'emp2_position',
209      'emp2_start',
210      'emp2_end',
211      'emp2_reason',
212      'former_matric',
213    )
214PTEE_OMIT_MANAGE_FIELDS = (
215    'special_application','jamb_subjects_list',) + PTEE_OMIT_FIELDS
216PTEE_OMIT_EDIT_FIELDS = PTEE_OMIT_MANAGE_FIELDS + OMIT_DISPLAY_FIELDS + (
217    'student_id',
218    'notice',
219    )
220
221UPDATE_OMIT_FIELDS = (
222    'firstname',
223    'middlename',
224    'lastname',
225    'sex',
226    'lga',
227    'course1',
228    )
229
230MAX_FILE_UPLOAD_SIZE = 1024 * 500
231
232class CustomApplicantDisplayFormPage(NigeriaApplicantDisplayFormPage):
233    """A display view for applicant data.
234    """
235
236    @property
237    def form_fields(self):
238        if self.target is not None and self.target == 'trans':
239            form_fields = grok.AutoFields(ITranscriptApplicant).omit(
240                'locked', 'suspended')
241            form_fields['dispatch_address'].custom_widget = BytesDisplayWidget
242            form_fields['perm_address'].custom_widget = BytesDisplayWidget
243            return form_fields
244        if self.target is not None and self.target == 'ver':
245            form_fields = grok.AutoFields(IVerificationRequest).omit(
246                'locked', 'suspended')
247            form_fields['body_address'].custom_widget = BytesDisplayWidget
248            return form_fields
249        if self.target is not None and self.target == 'fedex':
250            form_fields = grok.AutoFields(IFedexRequest).omit(
251                'locked', 'suspended')
252            form_fields['dispatch_address'].custom_widget = BytesDisplayWidget
253            return form_fields
254        if self.target is not None and self.target == 'send':
255            form_fields = grok.AutoFields(ISendByEmailRequest).omit(
256                'locked', 'suspended')
257            form_fields['body_address'].custom_widget = BytesDisplayWidget
258            return form_fields
259        if self.target is not None and self.target == 'cert':
260            form_fields = grok.AutoFields(ICertificateRequest).omit(
261                'locked', 'suspended')
262            #form_fields['dispatch_address'].custom_widget = BytesDisplayWidget
263            #form_fields['perm_address'].custom_widget = BytesDisplayWidget
264            return form_fields
265        # AAUE is using the same interface for all regular applications.
266        form_fields = grok.AutoFields(ICustomUGApplicant)
267        if self.target is not None and self.target.startswith('pg'):
268            for field in PG_OMIT_DISPLAY_FIELDS:
269                form_fields = form_fields.omit(field)
270        elif self.target is not None and self.target in ('ptee','dsh',):
271            for field in PTEE_OMIT_DISPLAY_FIELDS:
272                form_fields = form_fields.omit(field)
273        elif self.target is not None and self.target in ('bridge', 'ude',):
274            for field in UDE_OMIT_DISPLAY_FIELDS:
275                form_fields = form_fields.omit(field)
276        else:
277            for field in UG_OMIT_DISPLAY_FIELDS:
278                form_fields = form_fields.omit(field)
279        form_fields['perm_address'].custom_widget = BytesDisplayWidget
280        form_fields['notice'].custom_widget = BytesDisplayWidget
281        if not getattr(self.context, 'student_id'):
282            form_fields = form_fields.omit('student_id')
283        if not getattr(self.context, 'screening_score'):
284            form_fields = form_fields.omit('screening_score')
285        if not getattr(self.context, 'screening_venue') or \
286            self.context.state not in ('submitted', 'admitted', 'created'):
287            form_fields = form_fields.omit('screening_venue')
288        if not getattr(self.context, 'screening_date') or \
289            self.context.state not in ('submitted', 'admitted', 'created'):
290            form_fields = form_fields.omit('screening_date')
291        return form_fields
292
293    def getCourseAdmitted(self):
294        """Return link, title and code in html format to the certificate
295           admitted.
296        """
297        if self.layout.isApplicant():
298            return ''
299        course_admitted = self.context.course_admitted
300        if getattr(course_admitted, '__parent__',None):
301            url = self.url(course_admitted)
302            title = course_admitted.title
303            code = course_admitted.code
304            return '<a href="%s">%s - %s</a>' %(url,code,title)
305        return ''
306
307class CustomPDFActionButton(PDFActionButton):
308
309    @property
310    def target_url(self):
311        if self.context.state in ('initialized', 'started', 'paid'):
312            # or self.context.special or self.view.target in ('trans', 'cert'):
313            return
314        return self.view.url(self.view.context, self.target)
315
316
317class CustomPDFApplicationSlip(NigeriaPDFApplicationSlip):
318
319    column_two_fields = ('applicant_id', 'reg_number',
320        'firstname', 'middlename', 'lastname', 'sex', 'date_of_birth')
321    #two_columns_design_fields = [
322    #    'fst_sit_fname', 'fst_sit_no', 'fst_sit_date',
323    #    'fst_sit_type', 'fst_sit_results',
324    #    'scd_sit_fname', 'scd_sit_no', 'scd_sit_date',
325    #    'scd_sit_type', 'scd_sit_results']
326
327    def _getCourseAdmittedLink(self, view):
328        return None
329
330    def _getDeptAndFaculty(self):
331        return [None, None]
332
333    @property
334    def note(self):
335        note = getattr(self.context.__parent__, 'application_slip_notice', None)
336        if note:
337            return '<br /><br />' + note
338        if self.target is not None and self.target in (
339            'trans', 'cert', 'ver', 'send'):
340            return
341        if self.context.sex == 'm':
342            pronoun = 'he'
343        else:
344            pronoun = 'she'
345        return '''
346The applicant has acknowledged that, if discovered at any time that %s does not possess
347any of the qualifications which %s claims %s has obtained, %s will be expelled from the
348University not be re-admitted for the same or any other programme, even if %s has
349upgraded previous qualifications or possess additional qualifications.
350
351''' % (
352    pronoun, pronoun, pronoun, pronoun, pronoun)
353
354    @property
355    def form_fields(self):
356        # AAUE is using the same interface for all regular applications.
357        form_fields = grok.AutoFields(ICustomUGApplicant)
358        if self.target is not None and self.target.startswith('pg'):
359            for field in PG_OMIT_PDF_FIELDS:
360                form_fields = form_fields.omit(field)
361        elif self.target is not None and self.target in ('ptee', 'dsh',):
362            for field in PTEE_OMIT_PDF_FIELDS:
363                form_fields = form_fields.omit(field)
364        elif self.target is not None and self.target in ('bridge', 'ude',):
365            for field in UDE_OMIT_PDF_FIELDS:
366                form_fields = form_fields.omit(field)
367        elif self.target is not None and self.target == 'trans':
368            form_fields = grok.AutoFields(ITranscriptApplicant).omit(
369                'locked', 'suspended')
370        elif self.target is not None and self.target == 'ver':
371            form_fields = grok.AutoFields(IVerificationRequest).omit(
372                'locked', 'suspended')
373        elif self.target is not None and self.target == 'send':
374            form_fields = grok.AutoFields(ISendByEmailRequest).omit(
375                'locked', 'suspended')
376        elif self.target is not None and self.target == 'cert':
377            form_fields = grok.AutoFields(ICertificateRequest).omit(
378                'locked', 'suspended')
379        else:
380            for field in UG_OMIT_PDF_FIELDS:
381                form_fields = form_fields.omit(field)
382        if not getattr(self.context, 'student_id'):
383            form_fields = form_fields.omit('student_id')
384        if not getattr(self.context, 'screening_score'):
385            form_fields = form_fields.omit('screening_score')
386        if not getattr(self.context, 'screening_venue'):
387            form_fields = form_fields.omit('screening_venue')
388        if not getattr(self.context, 'screening_date'):
389            form_fields = form_fields.omit('screening_date')
390        return form_fields
391
392class CustomApplicantManageFormPage(NigeriaApplicantManageFormPage):
393    """A full edit view for applicant data.
394    """
395
396    def display_fileupload(self, filename):
397        if filename[1] == 'stateresult.pdf':
398            if self.target in ('trans', 'cert'):
399                return True
400        if filename[1] == 'verificationdoc.pdf':
401            if self.target in ('ver', 'send'):
402                return True
403        return False
404
405    @property
406    def form_fields(self):
407        if self.target is not None and self.target == 'trans':
408            form_fields = grok.AutoFields(ITranscriptApplicant)
409            form_fields['applicant_id'].for_display = True
410            return form_fields
411        if self.target is not None and self.target == 'cert':
412            form_fields = grok.AutoFields(ICertificateRequest)
413            form_fields['applicant_id'].for_display = True
414            return form_fields
415        if self.target is not None and self.target == 'ver':
416            form_fields = grok.AutoFields(IVerificationRequest)
417            form_fields['applicant_id'].for_display = True
418            return form_fields
419        if self.target is not None and self.target == 'send':
420            form_fields = grok.AutoFields(ISendByEmailRequest)
421            form_fields['applicant_id'].for_display = True
422            return form_fields
423        if self.target is not None and self.target == 'fedex':
424            form_fields = grok.AutoFields(IFedexRequest)
425            form_fields['applicant_id'].for_display = True
426            return form_fields
427        # AAUE is using the same interface for all regular applications.
428        form_fields = grok.AutoFields(ICustomUGApplicant)
429        if self.target is not None and self.target.startswith('pg'):
430            for field in PG_OMIT_MANAGE_FIELDS:
431                form_fields = form_fields.omit(field)
432        elif self.target is not None and self.target in ('ptee', 'dsh',):
433            for field in PTEE_OMIT_MANAGE_FIELDS:
434                form_fields = form_fields.omit(field)
435        elif self.target is not None and self.target in ('bridge', 'ude',):
436            for field in UDE_OMIT_MANAGE_FIELDS:
437                form_fields = form_fields.omit(field)
438        else:
439            for field in UG_OMIT_MANAGE_FIELDS:
440                form_fields = form_fields.omit(field)
441        form_fields['student_id'].for_display = True
442        form_fields['applicant_id'].for_display = True
443        return form_fields
444
445class CustomApplicantEditFormPage(NigeriaApplicantEditFormPage):
446    """An applicant-centered edit view for applicant data.
447    """
448
449    def display_fileupload(self, filename):
450        if filename[1] == 'stateresult.pdf':
451            if self.target in ('trans', 'cert'):
452                return True
453        if filename[1] == 'verificationdoc.pdf':
454            if self.target in ('ver', 'send'):
455                return True
456        return False
457
458    def unremovable(self, ticket):
459        return True
460
461    def dataNotComplete(self, data):
462        store = getUtility(IExtFileStore)
463        # Temporarily enable passport upload also for cert and trans
464        # applications.
465        if self.context.__parent__.with_picture:
466            if not store.getFileByContext(self.context, attr=u'passport.jpg'):
467                return _('No passport picture uploaded.')
468            if not self.target[:4] in ('cert', 'tran') and \
469                not self.request.form.get('confirm_passport', False):
470                return _('Passport picture confirmation box not ticked.')
471        if self.target in ('trans', 'cert') and \
472            not store.getFileByContext(self.context, attr=u'stateresult.pdf'):
473            return _('No statement of result pdf file uploaded.')
474        if self.target in ('ver',) and \
475            not store.getFileByContext(self.context, attr=u'verificationdoc.pdf'):
476            return _('No pdf file uploaded.')
477
478        return False
479
480    # AAUE applicants never see the 'Remove Selected Tickets' button.
481    @property
482    def display_actions(self):
483        # If the form is unlocked, applicants are allowed to save the form
484        # and remove unused tickets.
485        actions = [[_('Save')], []]
486        # Only in state started they can also add tickets.
487        if self.context.state == STARTED:
488            actions = [[_('Save')],
489                [_('Add online payment ticket')]]
490        # In state paid, they can submit the data and further add tickets
491        # if the application is special.
492        elif self.context.special and self.context.state == PAID:
493            actions = [[_('Save'), _('Finally Submit')],
494                [_('Add online payment ticket')]]
495        elif self.context.state == PAID:
496            actions = [[_('Save'), _('Finally Submit')], []]
497        return actions
498
499    @property
500    def form_fields(self):
501        if self.target is not None and self.target == 'trans':
502            form_fields = grok.AutoFields(ITranscriptApplicant).omit(
503                'locked', 'suspended')
504            form_fields['applicant_id'].for_display = True
505            form_fields['reg_number'].for_display = True
506            form_fields['place_of_birth'].field.required = True
507            form_fields['date_of_birth'].field.required = True
508            form_fields['nationality'].field.required = True
509            form_fields['email'].field.required = True
510            form_fields['phone'].field.required = True
511            form_fields['perm_address'].field.required = True
512            form_fields['dispatch_address'].field.required = True
513            form_fields['entry_mode'].field.required = True
514            form_fields['entry_session'].field.required = True
515            form_fields['end_session'].field.required = True
516            form_fields['course_studied'].field.required = True
517            return form_fields
518        if self.target is not None and self.target == 'cert':
519            form_fields = grok.AutoFields(ICertificateRequest).omit(
520                'locked', 'suspended')
521            form_fields['applicant_id'].for_display = True
522            form_fields['reg_number'].for_display = True
523            form_fields['place_of_birth'].field.required = True
524            form_fields['date_of_birth'].field.required = True
525            form_fields['nationality'].field.required = True
526            form_fields['email'].field.required = True
527            form_fields['phone'].field.required = True
528            form_fields['entry_session'].field.required = True
529            form_fields['end_session'].field.required = True
530            form_fields['course_studied'].field.required = True
531            form_fields['certificate_type'].field.required = True
532            # Additional omissions
533            if self.context.__parent__.code == 'cert5':
534                for field in ('firstname', 'middlename', 'lastname'):
535                    form_fields[field].for_display = True
536            return form_fields
537        if self.target is not None and self.target == 'ver':
538            form_fields = grok.AutoFields(IVerificationRequest).omit(
539                'locked', 'suspended')
540            form_fields['applicant_id'].for_display = True
541            return form_fields
542        if self.target is not None and self.target == 'send':
543            form_fields = grok.AutoFields(ISendByEmailRequest).omit(
544                'locked', 'suspended')
545            form_fields['applicant_id'].for_display = True
546            return form_fields
547        if self.target is not None and self.target == 'fedex':
548            form_fields = grok.AutoFields(IFedexRequest).omit(
549                'locked', 'suspended')
550            form_fields['applicant_id'].for_display = True
551            return form_fields
552        # AAUE is using the same interface for all regular applications.
553        form_fields = grok.AutoFields(ICustomUGApplicantEdit)
554        if self.target is not None and self.target.startswith('pg'):
555            for field in PG_OMIT_EDIT_FIELDS:
556                form_fields = form_fields.omit(field)
557        elif self.target is not None and self.target in ('ptee','dsh',):
558            for field in PTEE_OMIT_EDIT_FIELDS:
559                form_fields = form_fields.omit(field)
560        elif self.target is not None and self.target in ('bridge', 'ude',):
561            for field in UDE_OMIT_EDIT_FIELDS:
562                form_fields = form_fields.omit(field)
563        else:
564            for field in UG_OMIT_EDIT_FIELDS:
565                form_fields = form_fields.omit(field)
566        # Additional omissions
567        if self.target is not None and self.target in ('ude', 'utme'):
568            for field in UPDATE_OMIT_FIELDS:
569                form_fields[field].for_display = True
570        form_fields['applicant_id'].for_display = True
571        form_fields['reg_number'].for_display = True
572        return form_fields
573
574    def update(self):
575        if self.context.locked or (
576            self.context.__parent__.expired and
577            self.context.__parent__.strict_deadline):
578            self.emit_lock_message()
579            return
580        if getattr(
581            self.context.course1, 'code', 'nocourse') == self.request.form.get(
582            'form.course2', None):
583            self.flash(_('2nd choice course must differ from 1st choice course.'),
584                       type='danger')
585            self.redirect(self.url(self.context))
586            return
587        if getattr(
588            self.context.course1, 'code', 'nocourse') == self.request.form.get(
589            'form.course3', None):
590            self.flash(_('3rd choice course must differ from 1st choice course.'),
591                       type='danger')
592            self.redirect(self.url(self.context))
593            return
594        super(CustomApplicantEditFormPage, self).update()
595        return
596
597class CustomApplicantRegistrationPage(NigeriaApplicantRegistrationPage):
598    """Captcha'd registration page for applicants.
599    """
600
601    @property
602    def form_fields(self):
603        form_fields = None
604        if self.context.mode == 'update':
605            form_fields = grok.AutoFields(IApplicantRegisterUpdate).select(
606                'lastname','reg_number','email')
607            target = getattr(self.context, 'prefix', None)
608            if target in ('trans', 'cert'):
609                form_fields.get('reg_number').field.title = u'Matriculation Number'
610        else: #if self.context.mode == 'create':
611            form_fields = grok.AutoFields(ICustomUGApplicantEdit).select(
612                'firstname', 'middlename', 'lastname', 'email', 'phone')
613        return form_fields
614
615    def _redirect(self, email, password, applicant_id):
616        # Forward email and credentials to landing page.
617        self.redirect(self.url(self.context, 'registration_complete',
618            data = dict(email=email, password=password,
619            applicant_id=applicant_id)))
620        return
621
622    @property
623    def _postfix(self):
624        """Alumni records have to be imported into several containers.
625        Therefore a string must be added to their registration number
626        to make it unique.
627        """
628        if self.context.prefix in ('trans', 'cert'):
629            return self.context.code
630        return ''
631
632class CustomExportPDFPaymentSlipPage(NigeriaExportPDFPaymentSlipPage):
633
634    @property
635    def payment_slip_download_warning(self):
636        return ''
637
638class CustomApplicantCheckStatusPage(ApplicantCheckStatusPage):
639    """Captcha'd status checking page for applicants.
640    """
641    grok.template('applicantcheckstatus')
642
643class ScreeningInvitationActionButton(ManageActionButton):
644    grok.order(8) # This button should always be the last one.
645    grok.context(ICustomApplicant)
646    grok.view(CustomApplicantDisplayFormPage)
647    grok.require('waeup.viewApplication')
648    icon = 'actionicon_pdf.png'
649    text = _('Download screening invitation letter')
650    target = 'screening_invitation.pdf'
651
652    @property
653    def target_url(self):
654        if not self.context.screening_date or not self.context.state in (
655            'submitted', 'admitted', 'created'):
656            return ''
657        return self.view.url(self.view.context, self.target)
658
659class ExportScreeningInvitationLetter(UtilityView, grok.View):
660    """Deliver a slip with only screening data.
661    This form page is available only in AAUE.
662    """
663    grok.context(ICustomApplicant)
664    grok.name('screening_invitation.pdf')
665    grok.require('waeup.viewApplication')
666    prefix = 'form'
667
668    label = u'Screening Invitation Letter'
669
670    form_fields = []
671
672    @property
673    def note(self):
674        if self.context.screening_date:
675            year = self.context.__parent__.year
676            session = '%s/%s' % (year, year + 1)
677            sdate = self.context.screening_date
678            stime = ''
679            if '@' in self.context.screening_date:
680                sdate = self.context.screening_date.split('@')[0].strip()
681                stime = self.context.screening_date.split('@')[1].strip()
682            return """
683<br /><br /><br /><br /><font size='12'>
684Dear %s,
685<br /><br />
686You are invited to the Ambrose Alli University %s Admissions Screening Exercise.
687<br /><br />
688<strong>Date: %s
689<br /><br />
690Time: %s
691<br /><br />
692Venue: %s
693</strong>
694<br /><br />
695Please bring this letter of invitation and the downloaded application form along with you on your screening date.
696<br /><br />
697You are expected to be available 30 minutes before the commencement of your Screening.
698</font>
699
700""" % (
701       self.context.display_fullname,
702       session,
703       sdate,
704       stime,
705       self.context.screening_venue)
706        return
707
708    @property
709    def title(self):
710        return None
711
712    def update(self):
713        if not self.context.screening_date or not self.context.state in (
714            'submitted', 'admitted', 'created'):
715            self.flash(_('Forbidden'), type="warning")
716            self.redirect(self.url(self.context))
717
718    def render(self):
719        applicantview = ApplicantBaseDisplayFormPage(self.context, self.request)
720        students_utils = getUtility(IStudentsUtils)
721        return students_utils.renderPDF(self,'screening_data.pdf',
722            self.context, applicantview, note=self.note)
723
724class StateResult(AdditionalFile):
725    """Renders the pdf form extension for applicants.
726    """
727    grok.name('stateresult.pdf')
728
729class VerificationDoc(AdditionalFile):
730    """Renders the pdf form extension for applicants.
731    """
732    grok.name('verificationdoc.pdf')
Note: See TracBrowser for help on using the repository browser.