source: WAeUP_SRP/base/Widgets.py @ 2643

Last change on this file since 2643 was 2632, checked in by joachim, 17 years ago

add student_levels, fix for #397,cleanup removeUnusedDocIds

  • Property svn:keywords set to Id
File size: 77.7 KB
Line 
1#-*- mode: python; mode: fold -*-
2# $Id: Widgets.py 2632 2007-11-12 17:23:46Z joachim $
3from cgi import escape
4from types import *
5import Globals
6from Globals import InitializeClass
7from ZPublisher.HTTPRequest import FileUpload
8from OFS.Image import cookId, File, Image
9##from Products.CPSSchemas.Widget import CPSWidgetType
10from Products.CMFCore.utils import getToolByName
11from Products.CPSSchemas.BasicWidgets import CPSBooleanWidget, CPSWidget, CPSStringWidget, CPSEmailWidget,CPSImageWidget
12from Products.CPSSchemas.BasicWidgets import CPSFileWidget
13from Products.CPSSchemas.BasicWidgets import renderHtmlTag,CPSSelectWidget, CPSStringWidget
14from Products.CPSSchemas.ExtendedWidgets import CPSDateTimeWidget
15from Products.CPSSchemas.Widget import widgetRegistry
16from Products.CPSUtil.file import PersistableFileUpload
17from Products.CPSUtil.id import generateFileName
18##from Products.CPSSchemas.WidgetTypesTool import WidgetTypeRegistry
19from DateTime.DateTime import DateTime
20from AccessControl import getSecurityManager
21from Products.WAeUP_SRP.Students import getStudentByRegNo
22from Products.WAeUP_SRP.Academics import makeCertificateCode
23#from Products.ExtFile.ExtFile import ExtFile
24import logging,os,re
25import operator
26p_home = Globals.package_home(globals())
27i_home = Globals.INSTANCE_HOME
28
29#from zLOG import LOG, DEBUG
30
31class CPSSelectWidgetForRecord(CPSSelectWidget): ###(
32    """Select widget. with record names"""
33    meta_type = 'Select Widget for Records'
34
35    field_types = ('CPS String Field',)
36    field_inits = ({'is_searchabletext': 1,},)
37
38    _properties = CPSSelectWidget._properties + (
39        {'id': 'record_id', 'type': 'string', 'mode': 'w',
40         'label': 'Record Id', 'is_required' : 1},
41        )
42
43    def render(self, mode, datastructure, **kw):
44        """Render in mode from datastructure."""
45        value = datastructure[self.getWidgetId()]
46        vocabulary = self._getVocabulary(datastructure)
47        portal = getToolByName(self, 'portal_url').getPortalObject()
48        cpsmcat = portal.translation_service
49        if mode == 'view':
50            if self.translated:
51                return escape(cpsmcat(vocabulary.getMsgid(value, value)).encode('ISO-8859-15', 'ignore'))
52            else:
53                return escape(vocabulary.get(value, value))
54        elif mode == 'edit':
55            html_widget_id = self.getHtmlWidgetId()
56            res = renderHtmlTag('select',
57                                name='%s.%s:records' % (self.record_id,html_widget_id),
58                                id=html_widget_id)
59            in_selection = 0
60            for k, v in vocabulary.items():
61                if self.translated:
62                    kw = {'value': k,
63                          'contents': cpsmcat(vocabulary.getMsgid(k, k)).encode('ISO-8859-15', 'ignore')
64                          }
65                else:
66                    kw = {'value': k, 'contents': v}
67                if value == k:
68                    kw['selected'] = 'selected'
69                    in_selection = 1
70                res += renderHtmlTag('option', **kw)
71            if value and not in_selection:
72                kw = {'value': value, 'contents': 'invalid: '+ str(value),
73                      'selected': 'selected'}
74                res += renderHtmlTag('option', **kw)
75            res += '</select>'
76            return res
77        raise RuntimeError('unknown mode %s' % mode)
78
79InitializeClass(CPSSelectWidgetForRecord)
80
81widgetRegistry.register(CPSSelectWidgetForRecord)
82
83###)
84
85class CPSStringWidgetForRecord(CPSStringWidget): ###(
86    """String widget."""
87    meta_type = 'String Widget For Record'
88
89    field_types = ('CPS String Field',)
90    field_inits = ({'is_searchabletext': 1,},)
91    _properties = CPSStringWidget._properties + (
92        {'id': 'record_id', 'type': 'string', 'mode': 'w',
93         'label': 'Record Id', 'is_required' : 1},
94        )
95
96    def render(self, mode, datastructure, **kw):
97        """Render in mode from datastructure."""
98        value = datastructure[self.getWidgetId()]
99        if mode == 'view':
100            return escape(value)
101        elif mode == 'edit':
102            # XXX TODO should use an other name than kw !
103            # XXX change this everywhere
104            html_widget_id = self.getHtmlWidgetId()
105            kw = {'type': 'text',
106                  'id'  : html_widget_id,
107                  'name': '%s.%s:records' % (self.record_id,html_widget_id),
108                  'value': escape(value),
109                  'size': self.display_width,
110                  }
111            if self.size_max:
112                kw['maxlength'] = self.size_max
113            return renderHtmlTag('input', **kw)
114        raise RuntimeError('unknown mode %s' % mode)
115
116InitializeClass(CPSStringWidgetForRecord)
117
118widgetRegistry.register(CPSStringWidgetForRecord)
119
120###)
121
122class CertificateCourseIdWidget(CPSStringWidget): ###(
123    """ CertificateCourseId Widget"""
124    meta_type = "CertificateCourseId Widget"
125
126    def validate(self, datastructure, **kw):
127        """Validate datastructure and update datamodel."""
128
129        valid = CPSStringWidget.validate(self, datastructure, **kw)
130        if not valid:
131            return 0
132        else:
133            widget_id = self.getWidgetId()
134            value = datastructure[widget_id].upper()
135            err = 0
136            c_ids = [c.id for c in self.portal_catalog({'meta_type': "Course"})]
137            if hasattr(self.aq_parent,value):
138                err = 'Course already exists'
139            elif value not in c_ids:
140                err = 'Course does not exist'
141            if err:
142                datastructure.setError(widget_id, err)
143            else:
144                datamodel = datastructure.getDataModel()
145                datamodel[self.fields[0]] = value
146
147            return not err
148
149InitializeClass(CertificateCourseIdWidget)
150
151widgetRegistry.register(CertificateCourseIdWidget)
152###)
153
154class CourseIdWidget(CPSStringWidget): ###(
155    """ CourseId Widget"""
156    meta_type = "CourseId Widget"
157
158    def validate(self, datastructure, **kw):
159        """Validate datastructure and update datamodel."""
160
161        valid = CPSStringWidget.validate(self, datastructure, **kw)
162        if not valid:
163            return 0
164        else:
165            widget_id = self.getWidgetId()
166            value = datastructure[widget_id].upper()
167            err = 0
168            res = self.courses_catalog(code = value)
169            if len(res) > 0:
170                err = 'Course already exists'
171            if err:
172                datastructure.setError(widget_id, err)
173            else:
174                datamodel = datastructure.getDataModel()
175                datamodel[self.fields[0]] = value
176
177            return not err
178
179InitializeClass(CourseIdWidget)
180
181widgetRegistry.register(CourseIdWidget)
182
183
184###)
185
186class WAeUPStudyModeWidget(CPSSelectWidget): ###(
187    """WAeUP StudyMode Widget."""
188    meta_type = 'WAeUP StudyMode Widget'
189    vocabulary = 'entry_modes'
190
191    def _getStudyModes(self):
192        voc = getattr(self.portal_vocabularies,self.vocabulary)
193        d = {}
194        for k,v in voc.items():
195            d[k] = v
196        return d
197
198    def validate(self, datastructure, **kw):
199        """Validate datastructure and update datamodel."""
200        widget_id = self.getWidgetId()
201        value = datastructure[widget_id]
202        try:
203            v = str(value)
204        except ValueError:
205            datastructure.setError(widget_id, "'%s' not a valid session key" % value)
206            return 0
207        studymodes = self._getStudyModes()
208        if not value:
209            v = value = 'ume_ft'
210        #import pdb;pdb.set_trace()
211        if not studymodes.has_key(value):
212            datastructure.setError(widget_id, "'%s' not a valid session key" % v)
213            return 0
214        if self.is_required and not len(v):
215            datastructure.setError(widget_id, "session key required")
216            return 0
217
218        datamodel = datastructure.getDataModel()
219        datamodel[self.fields[0]] = v
220        return 1
221
222    def render(self, mode, datastructure, **kw):
223        """Render in mode from datastructure."""
224        value = datastructure[self.getWidgetId()]
225        studymodes = self._getStudyModes()
226        if mode == 'view':
227            return escape(studymodes.get(value, value))
228        elif mode == 'edit':
229            html_widget_id = self.getHtmlWidgetId()
230            res = renderHtmlTag('select', name=html_widget_id, id=html_widget_id)
231            in_selection = 0
232            vocabulary_items = studymodes.items()
233            if self.sorted:
234                vocabulary_items.sort(key=operator.itemgetter(1))
235            for k, v in vocabulary_items:
236                kw = {'value': k, 'contents': v}
237                if value == k:
238                    kw['selected'] = 'selected'
239                    in_selection = 1
240                res += renderHtmlTag('option', **kw)
241            if value and not in_selection:
242                kw = {'value': value, 'contents': 'invalid: '+ str(value),
243                      'selected': 'selected'}
244                res += renderHtmlTag('option', **kw)
245            res += '</select>'
246            return res
247        raise RuntimeError('unknown mode %s' % mode)
248
249InitializeClass(WAeUPStudyModeWidget)
250
251widgetRegistry.register(WAeUPStudyModeWidget)
252
253###)
254
255class WAeUPSessionWidget(CPSSelectWidget): ###(
256    """WAeUP Session Widget."""
257    meta_type = 'WAeUP Session Widget'
258
259    def _getSessions(self):
260        current_year = DateTime().year()
261        d = {'-1': 'N/A'}
262        for y in range(current_year - 9,current_year + 1):
263            d['%s' % str(y)[-2:]] = '%4d/%4d' % (y,y+1)
264        return d
265
266    def validate(self, datastructure, **kw):
267        """Validate datastructure and update datamodel."""
268        widget_id = self.getWidgetId()
269        value = datastructure[widget_id]
270        try:
271            v = str(value)
272        except ValueError:
273            datastructure.setError(widget_id, "'%s' not a valid session key" % value)
274            return 0
275
276        if len(v) == 1:
277            v = value = '0%c' % v
278        elif len(v) == 9:
279            v = value[2:4]
280        elif not value:
281            v = value = self.getSessionId()[0]
282        #import pdb;pdb.set_trace()
283        sessions = self._getSessions()
284        if not sessions.has_key(v):
285            datastructure.setError(widget_id, "'%s' not a valid session key" % v)
286            return 0
287        if self.is_required and not len(v):
288            datastructure.setError(widget_id, "session key required")
289            return 0
290
291        datamodel = datastructure.getDataModel()
292        datamodel[self.fields[0]] = v
293        return 1
294
295    def render(self, mode, datastructure, **kw):
296        """Render in mode from datastructure."""
297        value = datastructure[self.getWidgetId()]
298        sessions = self._getSessions()
299        if mode == 'view':
300            return escape(sessions.get(value, value))
301        elif mode == 'edit':
302            html_widget_id = self.getHtmlWidgetId()
303            res = renderHtmlTag('select', name=html_widget_id, id=html_widget_id)
304            in_selection = 0
305            vocabulary_items = sessions.items()
306            if self.sorted:
307                vocabulary_items.sort(key=operator.itemgetter(0))
308            for k, v in vocabulary_items:
309                kw = {'value': k, 'contents': v}
310                if value == k:
311                    kw['selected'] = 'selected'
312                    in_selection = 1
313                res += renderHtmlTag('option', **kw)
314            if value and not in_selection:
315                kw = {'value': value, 'contents': 'invalid: '+ str(value),
316                      'selected': 'selected'}
317                res += renderHtmlTag('option', **kw)
318            res += '</select>'
319            return res
320        raise RuntimeError('unknown mode %s' % mode)
321
322InitializeClass(WAeUPSessionWidget)
323
324widgetRegistry.register(WAeUPSessionWidget)
325
326###)
327
328class WAeUPLevelWidget(CPSSelectWidget): ###(
329    """WAeUP Level Widget."""
330    meta_type = 'WAeUP Level Widget'
331
332    def _getLevels(self):
333        d = {'':'N/A','000':'Pre-Studies'}
334        for y in range(100,800,100):
335            d['%s' % str(y)] = 'Year %1d (%3d Level)' % (y/100,y)
336        return d
337
338    def validate(self, datastructure, **kw):
339        """Validate datastructure and update datamodel."""
340        widget_id = self.getWidgetId()
341        value = datastructure[widget_id]
342        try:
343            v = str(value)
344        except ValueError:
345            datastructure.setError(widget_id, "'%s' not a valid level key" % value)
346            return 0
347
348        if not value:
349            v = value = '100'
350        #import pdb;pdb.set_trace()
351        levels = self._getLevels()
352        if not levels.has_key(value):
353            datastructure.setError(widget_id, "'%s' not a valid level" % v)
354            return 0
355        if self.is_required and not len(v):
356            datastructure.setError(widget_id, "level key required")
357            return 0
358
359        datamodel = datastructure.getDataModel()
360        datamodel[self.fields[0]] = v
361        return 1
362
363    def render(self, mode, datastructure, **kw):
364        """Render in mode from datastructure."""
365        value = datastructure[self.getWidgetId()]
366        levels = self._getLevels()
367        if mode == 'view':
368            return escape(levels.get(value, value))
369        elif mode == 'edit':
370            html_widget_id = self.getHtmlWidgetId()
371            res = renderHtmlTag('select', name=html_widget_id, id=html_widget_id)
372            in_selection = 0
373            vocabulary_items = levels.items()
374            if self.sorted:
375                vocabulary_items.sort(key=operator.itemgetter(0))
376            for k, v in vocabulary_items:
377                kw = {'value': k, 'contents': v}
378                if value == k:
379                    kw['selected'] = 'selected'
380                    in_selection = 1
381                res += renderHtmlTag('option', **kw)
382            if value and not in_selection:
383                kw = {'value': value, 'contents': 'invalid: '+ str(value),
384                      'selected': 'selected'}
385                res += renderHtmlTag('option', **kw)
386            res += '</select>'
387            return res
388        raise RuntimeError('unknown mode %s' % mode)
389
390InitializeClass(WAeUPLevelWidget)
391
392widgetRegistry.register(WAeUPLevelWidget)
393
394###)
395
396class WAeUPVerdictWidget(CPSSelectWidget): ###(
397    """WAeUP Verdict Widget."""
398    meta_type = 'WAeUP Verdict Widget'
399
400    # XXX make a menu for the vocabulary.
401    vocabulary = 'verdicts'
402
403    # Associating the widget label with an input area to improve the widget
404    # accessibility.
405    has_input_area = True
406
407    def _getVerdicts(self,datastructure):
408        voc = getattr(self.portal_vocabularies,self.vocabulary)
409        d = {}
410        for k,v in voc.items():
411            d[k] = v
412        return d
413
414    def validate(self, datastructure, **kw):
415        """Validate datastructure and update datamodel."""
416        widget_id = self.getWidgetId()
417        value = datastructure[widget_id]
418        try:
419            v = str(value)
420        except ValueError:
421            datastructure.setError(widget_id, "'%s' not a valid verdict key" % value)
422            return 0
423        #import pdb;pdb.set_trace()
424        verdicts = self._getVerdicts(datastructure)
425        if not value:
426            v = value = verdicts['N/A']
427        if not verdicts.has_key(value):
428            datastructure.setError(widget_id, "'%s' not a valid verdict key" % v)
429            return 0
430        if self.is_required and not len(v):
431            datastructure.setError(widget_id, "verdict required")
432            return 0
433
434        datamodel = datastructure.getDataModel()
435        datamodel[self.fields[0]] = v
436        return 1
437
438    def render(self, mode, datastructure, **kw):
439        """Render in mode from datastructure."""
440        value = datastructure[self.getWidgetId()]
441        verdicts = self._getVerdicts(datastructure)
442        if mode == 'view':
443            return escape(verdicts.get(value, value))
444        elif mode == 'edit':
445            html_widget_id = self.getHtmlWidgetId()
446            res = renderHtmlTag('select', name=html_widget_id, id=html_widget_id)
447            in_selection = 0
448            vocabulary_items = verdicts.items()
449            if self.sorted:
450                vocabulary_items.sort(key=operator.itemgetter(1))
451            for k, v in vocabulary_items:
452                kw = {'value': k, 'contents': v}
453                if value == k:
454                    kw['selected'] = 'selected'
455                    in_selection = 1
456                res += renderHtmlTag('option', **kw)
457            if value and not in_selection:
458                kw = {'value': value, 'contents': 'invalid: '+ str(value),
459                      'selected': 'selected'}
460                res += renderHtmlTag('option', **kw)
461            res += '</select>'
462            return res
463        raise RuntimeError('unknown mode %s' % mode)
464
465InitializeClass(WAeUPVerdictWidget)
466
467widgetRegistry.register(WAeUPVerdictWidget)
468
469###)
470
471class WAeUPLGAWidget(CPSSelectWidget): ###(
472    """WAeUP LGA Widget."""
473    meta_type = 'WAeUP LGA Widget'
474    _properties = CPSSelectWidget._properties + (
475        {'id': 'state_field', 'type': 'string', 'mode': 'w',
476         'label': 'Name of the state field'},
477         {'id': 'lga_field', 'type': 'string', 'mode': 'w',
478         'label': 'Name of the lga field (without state)'},
479         )
480    state_field = "state"
481    lga_field = "lga"
482
483    # XXX make a menu for the vocabulary.
484    vocabulary = 'local_gov_areas'
485
486    # Associating the widget label with an input area to improve the widget
487    # accessibility.
488    has_input_area = True
489
490    def _getLGAs(self):
491        voc = getattr(self.portal_vocabularies,self.vocabulary)
492        if getattr(self,'_v_states',None) is not None and\
493           getattr(self,'_v_lgas',None) is not None and\
494           getattr(self,'_v_d',None) is not None:
495            return (_v_d,_v_states,_v_lgas)
496        states = []
497        lgas  = []
498        d = {}
499        for k,v in voc.items():
500            parts = v.split(' / ')
501            if len(parts) == 1:
502                state = parts[0].lower()
503                lga = ""
504            elif len(parts) == 2:
505                state = parts[0].lower()
506                lga = "_".join(re.split('\W+',parts[1].lower()))
507            else:
508                continue
509            if state not in states:
510                states.append(state)
511            if lga not in lgas:
512                lgas.append(lga)
513            d[k] = v
514        self._v_d = d
515        self._v_state = state
516        self._v_lga = lga
517        return (d,states,lgas)
518
519    def validate(self, datastructure, **kw):
520        """Validate datastructure and update datamodel."""
521        widget_id = self.getWidgetId()
522        value = datastructure[widget_id]
523        #import pdb;pdb.set_trace()
524        try:
525            v = str(value)
526        except ValueError:
527            datastructure.setError(widget_id, "'%s' not a valid lga key" % value)
528            return 0
529        v = v.lower()
530        combined,states,lgas = self._getLGAs()
531        datamodel = datastructure.getDataModel()
532        if not self.state_field and not self.lga_field:
533            if len(v) == 0 and self.is_required:
534                datastructure.setError(widget_id, "%s required" % widget_id)
535                return 0
536            elif v not in combined.keys():
537                datastructure.setError(widget_id, "'%s' not a valid lga key" % v)
538                return 0
539            datamodel[self.fields[0]] = v
540        else:
541            state = datastructure.get(self.state_field,"").lower()
542            lga = datastructure.get(self.lga_field,"").lower()
543            if widget_id == self.state_field:
544                if state not in states:
545                    datastructure.setError(widget_id, "'%s' not a valid state" % v)
546                    return 0
547            elif widget_id == self.lga_field:
548                if lga not in lgas:
549                    datastructure.setError(widget_id, "'%s' not a valid lga" % v)
550                    return 0
551            if len(state) == 0 or len(lga) == 0:
552                datastructure.setError(widget_id, "state AND lga must be given")
553                return 0
554            datamodel[self.fields[0]] =   state + "_" + lga
555        return 1
556
557    def render(self, mode, datastructure, **kw):
558        """Render in mode from datastructure."""
559        w_id = self
560        value = datastructure[self.getWidgetId()]
561        lgas,x,y = self._getLGAs(datastructure)
562        if mode == 'view':
563            return escape(lgas.get(value, value))
564        elif mode == 'edit':
565            html_widget_id = self.getHtmlWidgetId()
566            res = renderHtmlTag('select', name=html_widget_id, id=html_widget_id)
567            in_selection = 0
568            vocabulary_items = lgas.items()
569            # if self.sorted:
570            #     vocabulary_items.sort(key=operator.itemgetter(1))
571            for k, v in vocabulary_items:
572                kw = {'value': k, 'contents': v}
573                if value == k:
574                    kw['selected'] = 'selected'
575                    in_selection = 1
576                res += renderHtmlTag('option', **kw)
577            if value and not in_selection:
578                kw = {'value': value, 'contents': 'invalid: '+ str(value),
579                      'selected': 'selected'}
580                res += renderHtmlTag('option', **kw)
581            res += '</select>'
582            return res
583        raise RuntimeError('unknown mode %s' % mode)
584
585InitializeClass(WAeUPLGAWidget)
586
587widgetRegistry.register(WAeUPLGAWidget)
588
589###)
590
591class WAeUPReservedRoomsWidget(CPSStringWidget): ###(
592    """ WAeUPReservedRooms Widget"""
593    meta_type = "WAeUPReservedRooms Widget"
594
595    def validate(self, datastructure, **kw):
596        """Validate datastructure and update datamodel."""
597        import re
598        valid = CPSStringWidget.validate(self, datastructure, **kw)
599        if not valid:
600            return 0
601        else:
602            widget_id = self.getWidgetId()
603            value = datastructure[widget_id]
604            err = 0
605            try:
606                reserved = [(r.split('/')[0],int(r.split('/')[1])) for r in re.split(',|\.| ',value)
607                                     if r]
608            except (ValueError,IndexError),msg:
609                err = str(msg)
610            if err:
611                datastructure.setError(widget_id, err)
612            else:
613                datamodel = datastructure.getDataModel()
614                datamodel[self.fields[0]] = value
615            return not err
616
617InitializeClass(WAeUPReservedRoomsWidget)
618
619widgetRegistry.register(WAeUPReservedRoomsWidget)
620###)
621
622class WAeUPIdWidget(CPSStringWidget): ###(
623    """ WAeUPId Widget"""
624    meta_type = "WAeUPId Widget"
625
626    def validate(self, datastructure, **kw):
627        """Validate datastructure and update datamodel."""
628        mode = kw.get('mode','create')
629        valid = CPSStringWidget.validate(self, datastructure, **kw)
630        id_pat_str = r"\S"
631        inv_id_pat = re.compile(r"^%s$" % id_pat_str)
632        if not valid:
633            return 0
634        else:
635            portal_type_query = {'query':['Faculty',
636                                          'Department',
637                                          'Course',
638                                          'Certificate',
639                                          'CertificateCourse',]}
640            widget_id = self.getWidgetId()
641            value = datastructure[widget_id]  #.upper()  is not necessary here because it's also done in waeup_document_create_do
642            err = 0
643            mapping = {}
644            if len(value.split()) > 1:
645                err = 'Invalid Id, Id contains space(s).'
646            elif mode == "create" and\
647                          self.portal_catalog(portal_type=portal_type_query,id=value):
648                brain = self.portal_catalog(portal_type=portal_type_query,id=value)[0]
649                err = 'An ${portal_type} object with the Id ${id} already exists at ${path}.'
650                mapping = {'portal_type': brain.portal_type,
651                           'id': value,
652                           'path': brain.getPath(),
653                           }
654            if err:
655                datastructure.setError(widget_id, err, mapping)
656            else:
657                datamodel = datastructure.getDataModel()
658                datamodel[self.fields[0]] = value
659
660            return not err
661
662InitializeClass(WAeUPIdWidget)
663
664widgetRegistry.register(WAeUPIdWidget)
665
666
667###)
668
669class StudyCourseWidget(CPSStringWidget): ###(
670    """ StudyCourse Widget"""
671    meta_type = "StudyCourse Widget"
672
673    def validate(self, datastructure, **kw):
674        """Validate datastructure and update datamodel."""
675        #from Products.zdb import set_trace
676        #set_trace()
677##        valid = CPSStringWidget.validate(self, datastructure, **kw)
678##        if not valid:
679##            return 0
680        widget_id = self.getWidgetId()
681        value = makeCertificateCode(datastructure[widget_id]).upper()
682        id_pat_str = r"\S"
683        inv_id_pat = re.compile(r"^%s$" % id_pat_str)
684        err = 0
685        if len(value.split()) > 1:
686            err = 'Invalid Id, Id contains space(s).'
687        elif not self.portal_catalog(portal_type='Certificate',id=value):
688            err = 'No such certificate'
689        if err:
690            datastructure.setError(widget_id, err)
691        else:
692            datamodel = datastructure.getDataModel()
693            datamodel[self.fields[0]] = value
694        return not err
695
696InitializeClass(StudyCourseWidget)
697
698widgetRegistry.register(StudyCourseWidget)
699###)
700
701class JambRegNoWidget(CPSStringWidget): ###(
702    """ JambRegNo Widget"""
703    meta_type = "JambRegNo Widget"
704    _properties = CPSStringWidget._properties + (
705        {'id': 'catalog', 'type': 'string', 'mode': 'w',
706         'label': 'Catalog to search'},
707         {'id': 'reference', 'type': 'string', 'mode': 'w',
708         'label': 'Reference Field'},
709         )
710    #catalog = "portal_pumeresults" #the catalog to search for jamb_reg_no
711    reference = ""
712    digits = 8
713    digits_str = "N"*digits
714    letters = 2
715    letters_str = "L"*letters
716    def validate(self, datastructure, **kw):
717        """Validate datastructure and update datamodel."""
718        valid = CPSStringWidget.validate(self, datastructure, **kw)
719        reg_no_catalog = getattr(self,self.catalog)
720        widget_id = self.getWidgetId()
721        value = datastructure[widget_id].upper()
722        err = 0
723        #import pdb;pdb.set_trace()
724        if kw.has_key('mode'):
725            mode = kw['mode']
726        else:
727            mode = "edit"
728        if not valid:
729            err = 'Invalid registration number'
730        elif self.reference == '':
731            #s = getStudentByRegNo(self,value)
732            pume = reg_no_catalog(jamb_reg_no = value)
733            if len(pume) < 1:
734                err = 'No student record with this registration number'
735            else:
736                datastructure['pume'] = pume[0]
737        elif mode == 'add':
738            pass
739        elif self.reference != '' and self.catalog == "applicants_catalog":
740            res = reg_no_catalog.searchResults({"%s" % self.reference: value})
741            if len(res) != 1:
742                err = 'No record with this registration number'
743            else:
744                datastructure['record'] = res[0]
745        else:
746            record = datastructure[self.reference]
747            #jamb_reg_no = getattr(record,widget_id)
748            jamb_reg_no = record.Entryregno
749            if jamb_reg_no != value:
750                err = 'Registration number does not match.'
751        if err:
752            datastructure.setError(widget_id, err)
753        else:
754            datamodel = datastructure.getDataModel()
755            datamodel[self.fields[0]] = value
756        return not err
757
758InitializeClass(JambRegNoWidget)
759
760widgetRegistry.register(JambRegNoWidget)
761###)
762
763class SecretWidget(CPSStringWidget): ###(
764    """ Secret Widget"""
765    meta_type = "Secret Widget"
766    _properties = CPSStringWidget._properties + (
767        {'id': 'reference', 'type': 'string', 'mode': 'w',
768         'label': 'Reference Record'},
769         {'id': 'check_fields', 'type': 'tokens', 'mode': 'w',
770         'label': 'Fields to check'},
771         )
772    reference = "student"
773    matric_no_catalog = 'returning_import'
774    check_fields = ("Firstname", "Middlename","Lastname")
775    def validate(self, datastructure, **kw):
776        """Validate datastructure and update datamodel."""
777        logger = logging.getLogger('Widgets.SecretWidget.validate')
778        valid = CPSStringWidget.validate(self, datastructure, **kw)
779        widget_id = self.getWidgetId()
780        value = datastructure[widget_id].upper()
781        err = 0
782        record = datastructure.get(self.reference,None)
783        #import pdb;pdb.set_trace()
784        if not valid or len(value) < 2:
785            err = 'Invalid string'
786        elif not record or datastructure.errors:
787            err = 0
788        else:
789            found = False
790            cvs = []
791            for field in self.check_fields:
792                cv = getattr(record,field).upper()
793                if len(cv.split()) > 1:
794                    for splited in cv.split():
795                        cvs.append(splited.strip())
796                else:
797                    cvs.append(cv)
798            for cv in cvs:
799                if cv  == value.upper():
800                    found = True
801                    break
802            matric_no = record.matric_no
803            name = " ".join(cvs)
804            if not found:
805                logger.info('%(matric_no)s did not find %(value)s in %(name)s' % vars())
806                err = 'No name does match.'
807            else:
808                logger.info('%(matric_no)s found %(value)s in %(name)s' % vars())
809        if err:
810            datastructure.setError(widget_id, err)
811        else:
812            datamodel = datastructure.getDataModel()
813            datamodel[self.fields[0]] = value
814        return not err
815
816InitializeClass(SecretWidget)
817
818widgetRegistry.register(SecretWidget)
819###)
820
821class WAeUPSexWidget(CPSBooleanWidget): ###(
822    """WAeUP sex widget."""
823    meta_type = 'WAeUP Sex Widget'
824
825    def validate(self, datastructure, **kw):
826        """Validate datastructure and update datamodel."""
827        value = datastructure[self.getWidgetId()]
828
829        if self.render_format not in self.render_formats:
830            self.render_format = 'select'
831
832        female = value in ('F','f','Female','female',"True",True)
833        male = value in ('M','m','Male','male','False',False)
834        if not female and not male:
835            datastructure.setError(self.getWidgetId(),
836                                   "invalid sex %s" % value)
837            return 0
838        elif female:
839            v = True
840        else:
841            v = False
842        datamodel = datastructure.getDataModel()
843        datamodel[self.fields[0]] = v
844        return 1
845
846InitializeClass(WAeUPSexWidget)
847
848widgetRegistry.register(WAeUPSexWidget)
849
850###)
851
852class MatricNoWidget(CPSStringWidget): ###(
853    """ MatricNo Widget"""
854    meta_type = "MatricNo Widget"
855
856    _properties = CPSStringWidget._properties + (
857        {'id': 'matric_no_catalog', 'type': 'string', 'mode': 'w',
858         'label': 'Catalog to search for MatricNo'},
859        { 'id': 'results_catalog', 'type': 'string', 'mode': 'w',
860         'label': 'Results Catalog'},
861         )
862    matric_no_catalog = "" #the catalog to search for matric_no
863    results_catalog = "results_import" #results catalog
864
865    def validate(self, datastructure, **kw):
866        """Validate datastructure and update datamodel."""
867        #import pdb;pdb.set_trace()
868        valid = CPSStringWidget.validate(self, datastructure, **kw)
869        logger = logging.getLogger('Widgets.MatricNoWidget.validate')
870        returning = getattr(self,self.matric_no_catalog)
871        results = getattr(self,self.results_catalog,None)
872        err = 0
873        widget_id = self.getWidgetId()
874        value = datastructure[widget_id]
875        if not valid or not value:
876            err = 'Invalid string'
877            logger.info('Invalid matric_no string %s' % value)
878        else:
879            value = value.upper()
880            datastructure['student'] = None
881            while not err:
882                res = returning(matric_no = value)
883                if len(res) < 1:
884                    logger.info('matric_no %s not found' % value)
885                    err = 'No student with this matriculation number.'
886                    break
887                datastructure['student'] = res[0]
888                if results is not None:
889                    res = results(matric_no = value)
890                    if len(res) < 1:
891                        err = 'No results for this matriculation number'
892                        continue
893                    datastructure['results'] = res
894                break
895        if err:
896            datastructure.setError(widget_id, err)
897        else:
898            datamodel = datastructure.getDataModel()
899            datamodel[self.fields[0]] = value
900        return not err
901
902InitializeClass(MatricNoWidget)
903
904widgetRegistry.register(MatricNoWidget)
905###)
906
907class StudentIdWidget(CPSStringWidget): ###(
908    """ StudentId Widget"""
909    meta_type = "StudentId Widget"
910    def validate(self, datastructure, **kw):
911        """Validate datastructure and update datamodel."""
912        valid = CPSStringWidget.validate(self, datastructure, **kw)
913        logger = logging.getLogger('Widgets.StudentIdWidget.validate')
914        #import pdb;pdb.set_trace()
915        s_cat = self.students_catalog
916        err = 0
917        widget_id = self.getWidgetId()
918        value = datastructure[widget_id]
919        if not valid or not value:
920            err = 'Invalid Id string'
921            logger.info('Invalid id string %s' % value)
922            datastructure['student'] = None
923        else:
924            value = value.upper()
925            res = s_cat(id = value)
926            if not res:
927                logger.info('Student id %s not found' % value)
928                err = 'No student with this Id'
929                datastructure['student'] = None
930            else:
931                datastructure['student'] = res[0]
932        if err:
933            datastructure.setError(widget_id, err)
934        else:
935            datamodel = datastructure.getDataModel()
936            datamodel[self.fields[0]] = value
937        return not err
938
939InitializeClass(StudentIdWidget)
940
941widgetRegistry.register(StudentIdWidget)
942###)
943
944class WAeUPMultilineResultsWidget(CPSStringWidget): ###(
945    """ WAeUPMultilineResults Widget"""
946    meta_type = "WAeUp Multiline Results Widget"
947    _properties = CPSWidget._properties + (
948        {'id': 'nr_of_lines', 'type': 'int', 'mode': 'w',
949         'label': 'Nr of Lines'},
950         )
951    nr_of_lines = 5
952    def prepare(self, datastructure, **kw): ###(
953        """Prepare datastructure from datamodel."""
954        datamodel = datastructure.getDataModel()
955        #import pdb;pdb.set_trace()
956        widget_id = self.getWidgetId()
957        v = datamodel[self.fields[0]]
958        if type(v) is ListType and v:
959            nr_results = len(v)
960        else:
961            v = []
962            nr_results = 0
963        count = 1
964        for s,g in v:
965            wid = "%s%02d"% (widget_id,count)
966            datastructure[wid+'_s'] = s
967            datastructure[wid+'_g'] = g
968            count += 1
969        if nr_results < self.nr_of_lines:
970            for line in range(nr_results,self.nr_of_lines):
971                v.append(('',''))
972                wid = "%s%02d"% (widget_id,line)
973                datastructure[wid+'_s'] = ''
974                datastructure[wid+'_g'] = ''
975        datastructure[widget_id] = v
976        datastructure[widget_id+'_s'] = ''
977        datastructure[widget_id+'_g'] = ''
978    ###)
979
980    def validate(self, datastructure, **kw): ###(
981        """Validate datastructure and update datamodel."""
982        #import pdb;pdb.set_trace()
983        widget_id = self.getWidgetId()
984        err = 0
985        lines = []
986        for line in range(1,30):
987            wid = "%s%02d"% (widget_id,line)
988            if not datastructure.has_key(wid+'_s'):
989                break
990            lines.append((datastructure[wid+'_s'].strip(),
991                         datastructure[wid+'_g'].strip()))
992
993        s = datastructure[widget_id+'_s'].strip()
994        g = datastructure[widget_id+'_g'].strip()
995        if s and g:
996            lines.append((s,g))
997        active = []
998        for s,g in lines:
999            if g != "":
1000                active.append((s,g))
1001        if err:
1002            datastructure.setError(widget_id, err)
1003        else:
1004            datamodel = datastructure.getDataModel()
1005            datamodel[self.fields[0]] = active
1006        return not err
1007    ###)
1008
1009    def render(self, mode, datastructure, **kw): ###(
1010        """Render in mode from datastructure."""
1011        render_method = 'widget_waeup_multiline_result_render'
1012        meth = getattr(self, render_method, None)
1013        if meth is None:
1014            raise RuntimeError("Unknown Render Method %s for widget type %s"
1015                               % (render_method, self.getId()))
1016        #import pdb;pdb.set_trace()
1017        datamodel = datastructure.getDataModel()
1018        widget_id = self.getWidgetId()
1019        lines = datamodel[self.fields[0]]
1020        if len(lines) < self.nr_of_lines:
1021            for line in range(len(lines),self.nr_of_lines + 1):
1022                lines.append(('',''))
1023        datastructure[widget_id] = lines
1024        datastructure[widget_id+'_s'] = ''
1025        datastructure[widget_id+'_g'] = ''
1026##        count = 1
1027##        for s,g in v:
1028##            wid = "%s%02d"% (widget_id,count)
1029##            count += 1
1030        return meth(mode=mode,
1031                    datastructure=datastructure,
1032                    )
1033    ###)
1034
1035
1036InitializeClass(WAeUPMultilineResultsWidget)
1037widgetRegistry.register(WAeUPMultilineResultsWidget)
1038###)
1039
1040class WAeUPResultsWidget(CPSStringWidget): ###(
1041    """ WAeUPResults Widget"""
1042    meta_type = "WAeUp Results Widget"
1043
1044    def prepare(self, datastructure, **kw): ###(
1045        """Prepare datastructure from datamodel."""
1046        datamodel = datastructure.getDataModel()
1047        v = datamodel[self.fields[0]]
1048        #import pdb;pdb.set_trace()
1049        widget_id = self.getWidgetId()
1050        datastructure[widget_id] = v
1051        datastructure[widget_id+'_s'] = ''
1052        datastructure[widget_id+'_g'] = ''
1053    ###)
1054
1055    def validate(self, datastructure, **kw): ###(
1056        """Validate datastructure and update datamodel."""
1057        #import pdb;pdb.set_trace()
1058        widget_id = self.getWidgetId()
1059        v = datastructure[widget_id]
1060        err = 0
1061        s = datastructure[widget_id+'_s'].strip()
1062        g = datastructure[widget_id+'_g'].strip()
1063        while 1:
1064            if not s and g:
1065                err = "No subject grade for subject"
1066                break
1067            i = 0
1068            done = False
1069            for sv,gv in v:
1070                if sv == s:
1071                    done = True
1072                    if not g:
1073                        v.pop(i)
1074                        break
1075                    v[i] = (s,g)
1076                    break
1077                i += 1
1078            if done:
1079                break
1080            if s and g:
1081                v.append((s,g))
1082            break
1083        if err:
1084            datastructure.setError(widget_id, err)
1085        else:
1086            datamodel = datastructure.getDataModel()
1087            datamodel[self.fields[0]] = v
1088            datastructure[widget_id+'_s'] = s
1089            datastructure[widget_id+'_g'] = g
1090        return not err
1091    ###)
1092
1093    def render(self, mode, datastructure, **kw): ###(
1094        """Render in mode from datastructure."""
1095        render_method = 'widget_waeup_result_render'
1096        meth = getattr(self, render_method, None)
1097        if meth is None:
1098            raise RuntimeError("Unknown Render Method %s for widget type %s"
1099                               % (render_method, self.getId()))
1100        #import pdb;pdb.set_trace()
1101        datamodel = datastructure.getDataModel()
1102        widget_id = self.getWidgetId()
1103        datastructure[widget_id+'_s'] = ''
1104        datastructure[widget_id+'_g'] = ''
1105        return meth(mode=mode,
1106                    datastructure=datastructure,
1107                    )
1108    ###)
1109
1110
1111InitializeClass(WAeUPResultsWidget)
1112widgetRegistry.register(WAeUPResultsWidget)
1113###)
1114
1115class ScratchCardPin: ###(
1116    """the ScratchCardPin"""
1117    def __init__(self,prefix,batch_no,number):
1118        if not batch_no and not number:
1119            s = prefix
1120            if len(s) > 3:
1121                prefix,batch_no,number = s[:3],s[3:-10],s[-10:]
1122            else:
1123                prefix,batch_no,number = s,'',''
1124        self.p = prefix
1125        self.b = batch_no
1126        self.n = number
1127
1128    def __str__(self):
1129        return "%s-%s-%s" % (self.p,self.b,self.n)
1130
1131    def __repr__(self):
1132        return "%s%s%s" % (self.p,self.b,self.n)
1133###)
1134
1135class ScratchcardPinWidget(CPSStringWidget): ###(
1136    """ ScratchcardPin Widget"""
1137    meta_type = "Scratchcard Pin Widget"
1138    _properties = CPSWidget._properties + (
1139        {'id': 'prefix', 'type': 'string', 'mode': 'w',
1140         'label': 'Prefix'},
1141         {'id': 'reference', 'type': 'string', 'mode': 'w',
1142         'label': 'Reference Field'},
1143         {'id': 'reuse_pin', 'type': 'boolean', 'mode': 'w',
1144         'label': 'Reuse Application Pin'},
1145        )
1146    prefix = ''
1147    reference = ''
1148    reuse_pin = False
1149
1150    def prepare(self, datastructure, **kw): ###(
1151        """Prepare datastructure from datamodel."""
1152        datamodel = datastructure.getDataModel()
1153        v = datamodel[self.fields[0]]
1154        widget_id = self.getWidgetId()
1155        if v and type(v) is StringType:
1156            try:
1157                p,b,n = v.split('-')
1158                v = ScratchCardPin(p,b,n)
1159            except ValueError:
1160                v = ScratchCardPin(v,'','')
1161        if v:
1162            p = '%s' % v.p
1163            b = '%s' % v.b
1164            n = '%s' % v.n
1165        else:
1166            p = self.prefix
1167            if p.startswith('@'):
1168                p = getattr(self,self.prefix[1:])()
1169            b = n = ''
1170            v = ScratchCardPin(p,b,n)
1171        datastructure[widget_id] = v
1172        datastructure[widget_id+'_p'] = p
1173        datastructure[widget_id+'_b'] = b
1174        datastructure[widget_id+'_n'] = n
1175    ###)
1176
1177    def validate(self, datastructure, **kw): ###(
1178        """Validate datastructure and update datamodel."""
1179        s_logger = logging.getLogger('Widgets.ScratchcardPinWidget.validate')
1180        widget_id = self.getWidgetId()
1181        v = datastructure[widget_id]
1182        #import pdb;pdb.set_trace()
1183        err = 0
1184        mapping = {}
1185        prefix= self.prefix
1186        if prefix.startswith('@'):
1187            prefix= getattr(self,self.prefix[1:])()
1188        b = datastructure[widget_id+'_b'].strip()
1189        n = datastructure[widget_id+'_n'].strip()
1190        pins = self.portal_pins
1191        pin = "%(prefix)s%(b)s%(n)s" % vars()
1192        pin_str = "%(prefix)s-%(b)s-%(n)s" % vars()
1193        do = 1
1194        s_id = str(self.portal_membership.getAuthenticatedMember())
1195        if self.isStaff():
1196            do = 0
1197            err ='You are not a Student. PIN neither checked nor used.'
1198            s_logger.info('%s tried to use scratch card %s' % (s_id,pin_str))
1199        elif len(b) > 1 and b.find('-') > -1:
1200            do = 0
1201            err = 'PIN must not contain "-".'
1202            s_logger.info('%s entered invalid PIN  containing "-"' % (s_id))
1203        elif n.find('-') > -1:
1204            do = 0
1205            err = 'PIN must not contain "-".'
1206            s_logger.info('%s entered invalid PIN  containing "-"' % (s_id))
1207        elif len(n) != 10:
1208            do = 0
1209            err = 'Invalid PIN length'
1210            s_logger.info('%s entered invalid PIN with length %d' % (s_id,len(n)))
1211        elif self.reference == "":
1212            ref = s_id
1213        else:
1214            ref = datastructure[self.reference]
1215            if datastructure.errors:
1216                do = 0
1217                datastructure.setError(widget_id, 'PIN neither checked nor used.')
1218                s_logger.info('%s/%s entered wrong data together with PIN %s' % (s_id,ref,pin_str))
1219            elif prefix == 'APP' and not self.reuse_pin:
1220                res =  self.applicants_catalog(reg_no = ref)
1221                if res and res[0].pin == pin_str:
1222                    do = 0
1223                    err = 'Application PINs cannot be reused.'
1224                    s_logger.info('%s entered same PIN as for screening application %s' % (s_id,pin_str))
1225
1226        while do:
1227            ok = pins.searchAndSetRecord(pin,ref,prefix)
1228            if ok < -2 or ok > 2:
1229                err = 'Unknown error, please report!'
1230                s_logger.info('%s/%s caused unknown error with PIN %s' % (s_id,ref,pin_str))
1231                break
1232            elif ok == -2:
1233                err = 'Service already is activated but with a different PIN.'
1234                s_logger.info('%s/%s repeatedly activated service but with different PIN %s' % (s_id,ref,pin_str))
1235                break
1236            elif ok == -1:
1237                err = 'Invalid PIN'
1238                s_logger.info('%s/%s entered invalid PIN %s' % (s_id,ref,pin_str))
1239                break
1240            if ok == 0:
1241                err = 'PIN already used'
1242                s_logger.info('%s/%s entered used PIN %s' % (s_id,ref,pin_str))
1243                break
1244            if ok >= 1:
1245                #import pdb;pdb.set_trace()
1246                if self.isStudent():
1247                    if self.reference == "jamb_reg_no":
1248                        err = "You are already logged in."
1249                        s_logger.info('%s/%s checked admission with PIN %s though logged in' % (s_id,ref,pin_str))
1250                        break
1251                    if ok == 1:
1252                        s_logger.info('%s/%s successfully used PIN %s' % (s_id,ref,pin_str))
1253                    else:
1254                        s_logger.info('%s/%s repeatedly used PIN %s' % (s_id,ref,pin_str))
1255                    break
1256                else:
1257                    student = getStudentByRegNo(self,ref)
1258                    s_logger.info('%s/%s successfully used PIN %s' % (s_id,ref,pin_str))
1259                if student is None:
1260                    err = "Student record not found."
1261                    s_logger.info('%s not found in admission list' % (ref))
1262                    break
1263                s_id = student.getId()
1264                if ok == 2:
1265                    if self.reference == "jamb_reg_no":
1266                        if hasattr(self.portal_directories.students,s_id):
1267                            err = "Please login with your Student Id ${id} and 10-digit PIN."
1268                            mapping = {'id': s_id}
1269                            s_logger.info('%s/%s repeatedly checked admission with PIN %s' % (s_id,ref,pin_str))
1270                            break
1271                        else:
1272                            s_logger.info('%s/%s (non-member) repeatedly checked admission with PIN %s' % (s_id,ref,pin_str))
1273                    else:
1274                        err = "Unknown error"
1275                        s_logger.info('%s/%s repeatedly activated service with PIN %s' % (s_id,ref,pin_str))
1276                        break
1277                try:
1278                    student.getContent().makeStudentMember(s_id,password=pin[4:])
1279                    s_logger.info('%s/%s has been created using PIN %s' % (s_id,ref,pin_str))
1280                except:
1281                    err = "Please login with your Student Id ${id} and 10-digit PIN."
1282                    mapping = {'id': s_id}
1283                    s_logger.info('%s/%s could not be made a member with PIN %s' % (s_id,ref,pin_str))
1284                    break
1285            break
1286        if err:
1287            datastructure.setError(widget_id, err,mapping)
1288        else:
1289            datamodel = datastructure.getDataModel()
1290            datamodel[self.fields[0]] = ScratchCardPin(prefix,b,n)
1291            datastructure[widget_id] = ScratchCardPin(prefix,b,n)
1292            datastructure[widget_id+'_p'] = prefix
1293            datastructure[widget_id+'_b'] = b
1294            datastructure[widget_id+'_n'] = n
1295            datastructure['s_id'] = s_id
1296        return not err
1297
1298###)
1299
1300    def render(self, mode, datastructure, **kw): ###(
1301        """Render in mode from datastructure."""
1302        render_method = 'widget_scratch_card_pin_render'
1303        meth = getattr(self, render_method, None)
1304        if meth is None:
1305            raise RuntimeError("Unknown Render Method %s for widget type %s"
1306                               % (render_method, self.getId()))
1307
1308        # XXX AT: datastructure has to be set again here, in case we're in edit
1309        # or create mode, because a default value has to be provided.
1310        #import pdb;pdb.set_trace()
1311        datamodel = datastructure.getDataModel()
1312        v = datamodel[self.fields[0]]
1313        if v and type(v) is StringType:
1314            try:
1315                p,b,n = v.split('-')
1316                v = ScratchCardPin(p,b,n)
1317            except ValueError:
1318                v = ScratchCardPin(self.prefix,'XXX',v)
1319                pass
1320        if v:
1321            prefix= '%s' % v.p
1322            b = '%s' % v.b
1323            n = '%s' % v.n
1324        else:
1325            prefix= self.prefix
1326            if prefix.startswith('@'):
1327                prefix= getattr(self,self.prefix[1:])()
1328            b = n = ''
1329            v = ScratchCardPin(prefix,b,n)
1330        widget_id = self.getWidgetId()
1331        datastructure[widget_id] = v
1332        datastructure[widget_id+'_p'] = prefix
1333        datastructure[widget_id+'_b'] = b
1334        datastructure[widget_id+'_n'] = n
1335        return meth(mode=mode,
1336                    datastructure=datastructure,
1337                    )
1338    ###)
1339
1340InitializeClass(ScratchcardPinWidget)
1341widgetRegistry.register(ScratchcardPinWidget)
1342###)
1343
1344class PumePinWidget(ScratchcardPinWidget): ###(
1345    """ Pume Pin Widget"""
1346    meta_type = "Pume Pin Widget"
1347    catalog = "applicants_catalog"
1348    reference = ''
1349
1350    def prepare(self, datastructure, **kw): ###(
1351        """Prepare datastructure from datamodel."""
1352        datamodel = datastructure.getDataModel()
1353        #import pdb;pdb.set_trace()
1354        v = datamodel[self.fields[0]]
1355        widget_id = self.getWidgetId()
1356        if v and type(v) is StringType:
1357            try:
1358                p,b,n = v.split('-')
1359                v = ScratchCardPin(p,b,n)
1360            except ValueError:
1361                v = ScratchCardPin(v,'','')
1362        if v:
1363            p = '%s' % v.p
1364            b = '%s' % v.b
1365            n = '%s' % v.n
1366        else:
1367            p = self.prefix
1368            if p.startswith('@'):
1369                p = getattr(self,self.prefix[1:])()
1370            b = n = ''
1371            v = ScratchCardPin(p,b,n)
1372        datastructure[widget_id] = v
1373        datastructure[widget_id+'_p'] = p
1374        datastructure[widget_id+'_b'] = b
1375        datastructure[widget_id+'_n'] = n
1376    ###)
1377
1378    def validate(self, datastructure, **kw): ###(
1379        """Validate datastructure and update datamodel."""
1380        #import pdb;pdb.set_trace()
1381        s_logger = logging.getLogger('Widgets.ScratchcardPinWidget.validate')
1382        widget_id = self.getWidgetId()
1383        v = datastructure[widget_id]
1384        err = 0
1385        mapping = {}
1386        prefix= self.prefix
1387        if prefix.startswith('@'):
1388            prefix= getattr(self,self.prefix[1:])()
1389        b = datastructure[widget_id+'_b'].strip()
1390        n = datastructure[widget_id+'_n'].strip()
1391        pins = self.portal_pins
1392        pin = "%(prefix)s%(b)s%(n)s" % vars()
1393        pin_str = "%(prefix)s-%(b)s-%(n)s" % vars()
1394        member_id = str(self.portal_membership.getAuthenticatedMember())
1395        do = 1
1396        if self.isStaff():
1397            do = 0
1398            err ='You are logged in, please log out. PIN neither checked nor used.'
1399            s_logger.info('%s tried to use scratch card %s' % (member_id,pin_str))
1400        elif self.isStudent():
1401            do = 0
1402            ref = datastructure[self.reference]
1403            err ='You are logged in, please log out. PIN neither checked nor used.'
1404            s_logger.info('%s/%s applied for screening test with PIN %s' % (member_id,ref,pin_str))
1405        elif len(b) > 1 and b.find('-') > -1:
1406            do = 0
1407            err = 'PIN must not contain "-"'
1408            s_logger.info('%s entered invalid PIN  containing "-"' % (member_id))
1409        elif n.find('-') > -1:
1410            do = 0
1411            err = 'PIN must not contain "-"'
1412            s_logger.info('%s entered invalid PIN  containing "-"' % (member_id))
1413        elif len(n) != 10:
1414            do = 0
1415            err = 'Invalid PIN length'
1416            s_logger.info('%s entered invalid PIN with length %d' % (member_id,len(n)))
1417        elif self.reference == "":
1418            ref = n
1419        else:
1420            ref = datastructure[self.reference]
1421            if datastructure.errors:
1422                do = 0
1423                datastructure.setError(widget_id, 'PIN neither checked nor used.')
1424                s_logger.info('%s/%s entered wrong data together with PIN %s' % (member_id,ref,pin_str))
1425        while do:
1426            ok = pins.searchAndSetRecord(pin,ref,prefix)
1427            if ok < -2 or ok > 2:
1428                err = 'Unknown error, please report!'
1429                s_logger.info('%s/%s caused unknown error with PIN %s' % (member_id,ref,pin_str))
1430                break
1431            elif ok == -2:
1432                err = 'Service is already activated but with a different PIN.'
1433                s_logger.info('%s/%s repeatedly activated service but with different PIN %s' % (member_id,ref,pin_str))
1434                break
1435            elif ok == -1:
1436                err = 'Invalid PIN'
1437                s_logger.info('%s/%s entered invalid PIN %s' % (member_id,ref,pin_str))
1438                break
1439            if ok == 0:
1440                err = 'PIN already used'
1441                s_logger.info('%s/%s entered used PIN %s' % (member_id,ref,pin_str))
1442                break
1443            if ok >= 1:
1444                #screening_type = self.REQUEST.form.get('screening_type','unknown')
1445                #screening_type = datastructure['screening_type']
1446                if self.REQUEST.traverse_subpath:
1447                    screening_type_request = self.REQUEST.traverse_subpath[0]
1448                else:
1449                    screening_type_request = 'manage'
1450
1451                if datastructure.has_key('record'):
1452                    applicant = datastructure['record']
1453                    if applicant.screening_type != screening_type_request\
1454                          and screening_type_request != 'manage':
1455                        err = "You are using the wrong access form!"
1456                        s_logger.info('%s tried to use %s application form but has applied for %s' % (ref,screening_type_request,applicant.screening_type))
1457                        break
1458                    if not applicant.pin:
1459                        s_logger.info('%s successfully used PIN %s' % (ref,pin_str))
1460                        d = {}
1461                        d['reg_no'] = applicant.reg_no
1462                        d['pin'] = pin_str
1463                        #d['screening_type'] = screening_type
1464                        #d['status'] = 'entered'
1465                        getattr(self,self.catalog).modifyRecord(**d)
1466                    elif applicant.pin != pin_str:
1467                        s_logger.info('%s/%s tried to enter application record with different PIN %s' % (member_id,ref,pin_str))
1468                    elif applicant.pin == pin_str:
1469                        s_logger.info('%s/%s repeatedly entered application record with PIN %s' % (member_id,ref,pin_str))
1470                else:
1471                    datastructure['reg_no'] = ref
1472                    res = self.applicants_catalog(reg_no = ref)
1473                    if not res:
1474                        s_logger.info('%s successfully used PIN %s' % (ref,pin_str))
1475                        d = {}
1476                        d['reg_no'] = ref
1477                        d['pin'] = pin_str
1478                        d['status'] = 'entered'
1479                        d['screening_type'] = screening_type_request
1480                        self.applicants_catalog.addRecord(**d)
1481                    else:
1482                        s_logger.info('%s/%s repeatedly entered application record with PIN %s' % (ref,ref,pin_str))
1483            break
1484        if err:
1485            datastructure.setError(widget_id, err,mapping)
1486        else:
1487            datamodel = datastructure.getDataModel()
1488            datamodel[self.fields[0]] = ScratchCardPin(prefix,b,n)
1489            datastructure[widget_id] = ScratchCardPin(prefix,b,n)
1490            datastructure[widget_id+'_p'] = prefix
1491            datastructure[widget_id+'_b'] = b
1492            datastructure[widget_id+'_n'] = n
1493        return not err
1494    ###)
1495
1496    def render(self, mode, datastructure, **kw): ###(
1497        """Render in mode from datastructure."""
1498        render_method = 'widget_scratch_card_pin_render'
1499        meth = getattr(self, render_method, None)
1500        if meth is None:
1501            raise RuntimeError("Unknown Render Method %s for widget type %s"
1502                               % (render_method, self.getId()))
1503
1504        # XXX AT: datastructure has to be set again here, in case we're in edit
1505        # or create mode, because a default value has to be provided.
1506        #import pdb;pdb.set_trace()
1507        datamodel = datastructure.getDataModel()
1508        v = datamodel[self.fields[0]]
1509        #import pdb;pdb.set_trace()
1510        if v and type(v) is StringType:
1511            try:
1512                p,b,n = v.split('-')
1513                v = ScratchCardPin(p,b,n)
1514            except ValueError:
1515                v = ScratchCardPin(self.prefix,'XXX',v)
1516                pass
1517        if v:
1518            prefix= '%s' % v.p
1519            b = '%s' % v.b
1520            n = '%s' % v.n
1521        else:
1522            prefix= self.prefix
1523            if prefix.startswith('@'):
1524                prefix= getattr(self,self.prefix[1:])()
1525            b = n = ''
1526            v = ScratchCardPin(prefix,b,n)
1527        widget_id = self.getWidgetId()
1528        datastructure[widget_id] = v
1529        datastructure[widget_id+'_p'] = prefix
1530        datastructure[widget_id+'_b'] = b
1531        datastructure[widget_id+'_n'] = n
1532        return meth(mode=mode,
1533                    datastructure=datastructure,
1534                    )
1535    ###)
1536
1537InitializeClass(PumePinWidget)
1538widgetRegistry.register(PumePinWidget)
1539###)
1540
1541class WAeUPImageWidget(CPSImageWidget): ###(
1542    """Photo widget."""
1543    meta_type = 'WAeUP Image Widget'
1544
1545    def render(self, mode, datastructure, **kw):
1546        render_method = 'widget_waeup_image_render'
1547        meth = getattr(self, render_method, None)
1548        if meth is None:
1549            raise RuntimeError("Unknown Render Method %s for widget type %s"
1550                               % (render_method, self.getId()))
1551        img_info = self.getImageInfo(datastructure)
1552        return meth(mode=mode, datastructure=datastructure, **img_info)
1553
1554InitializeClass(WAeUPImageWidget)
1555
1556widgetRegistry.register(WAeUPImageWidget)
1557###)
1558
1559class ApplicationImageWidget(CPSImageWidget): ###(
1560    """Image widget with filesystem storage."""
1561    meta_type = 'Application Image Widget'
1562    _properties = CPSImageWidget._properties +\
1563    (
1564     {'id': 'path', 'type': 'string', 'mode': 'w',
1565      'label': 'Relative Path'},
1566     {'id': 'id_field', 'type': 'string', 'mode': 'w',
1567      'label': 'Field to build the id'},
1568    )
1569    path = "images"
1570    storage_path = "%s/import/%s" % (i_home,path)
1571    id_field = "reg_no"
1572
1573    def getImageInfo(self, datastructure): ###(
1574        """Get the file info from the datastructure."""
1575        widget_id = self.getWidgetId()
1576        if  datastructure.has_key(widget_id):
1577            fileupload = datastructure[widget_id]
1578            dm = datastructure.getDataModel()
1579            field_id = self.fields[0]
1580            screening_type = datastructure.get('screening_type')
1581            current_filename = "%s_%s.jpg" % (datastructure[self.id_field],
1582                                            field_id,)
1583            base_path = os.path.join(screening_type,current_filename)
1584            content_url = os.path.join('viewimage',self.path,base_path)
1585            file_path = os.path.join(self.storage_path,base_path)
1586            #import pdb; pdb.set_trace()
1587        else:
1588            file_path = "XXX"
1589        # read the file from the filesystem
1590        if not os.path.exists(file_path):
1591            height = -1
1592            width = -1
1593            empty_file = True
1594            session_file = False
1595            current_filename = ''
1596            content_url = ''
1597            size = 0
1598            mimetype = ''
1599            last_modified = ''
1600            height = ''
1601            width = ''
1602
1603        else:
1604            image = open(file_path)
1605            from OFS.Image import getImageInfo as getImageInfoOFS
1606            image.seek(0)
1607            data = image.read(2000)
1608            size = len(data)
1609            empty_file = size == 0
1610            session_file = False
1611            last_modified = ''
1612            image.close()
1613            mimetype, width, height = getImageInfoOFS(data)
1614
1615            if width < 0:
1616                width = None
1617            if height < 0:
1618                height = None
1619
1620            if (self.allow_resize
1621                and height is not None
1622                and width  is not None):
1623                z_w = z_h = 1
1624                h = int(self.display_height)
1625                w = int(self.display_width)
1626                if w and h:
1627                    if w < width:
1628                        z_w = w / float(width)
1629                    if h < height:
1630                        z_h = h / float(height)
1631                    zoom = min(z_w, z_h)
1632                    width = int(zoom * width)
1633                    height = int(zoom * height)
1634                #import pdb;pdb.set_trace()
1635        image_info = {
1636            'empty_file': empty_file,
1637            'session_file': session_file,
1638            'current_filename': current_filename,
1639            'size': size,
1640            'last_modified': last_modified,
1641            'content_url': content_url,
1642            'mimetype': mimetype,
1643            }
1644        title = image_info['current_filename']
1645        alt = title or ''
1646        #height = int(self.display_height)
1647        #width = int(self.display_width)
1648        if height is None or width is None:
1649            tag = renderHtmlTag('img', src=image_info['content_url'],
1650                                alt=alt, title=title)
1651        else:
1652            tag = renderHtmlTag('img', src=image_info['content_url'],
1653                                width=str(width), height=str(height),
1654                                alt=alt, title=title)
1655
1656        image_info['height'] = height
1657        image_info['width'] = width
1658        image_info['image_tag'] = tag
1659        return image_info
1660    ###)
1661
1662    def checkFileName(self, filename, mimetype):
1663        return '', {}
1664        if mimetype and mimetype.startswith('image'):
1665            return '', {}
1666        return 'cpsschemas_err_image', {}
1667
1668    def prepare(self, datastructure, **kw): ###(
1669        """Prepare datastructure from datamodel."""
1670        datamodel = datastructure.getDataModel()
1671        widget_id = self.getWidgetId()
1672        file_name = datamodel[self.fields[0]]
1673        #import pdb; pdb.set_trace()
1674        if self.allow_resize:
1675            datastructure[self.getWidgetId() + '_resize'] = ''
1676        screening_type = datamodel.get('screening_type',None)
1677        if not screening_type:
1678            screening_type = self.REQUEST.form.get('screening_type','pume')
1679        datastructure["screening_type"] = screening_type
1680        datastructure[widget_id] = file_name
1681        datastructure[widget_id + '_choice'] = 'change'
1682        title = 'Passport Foto'
1683        datastructure[widget_id + '_filename'] = title
1684    ###)
1685
1686    def validate(self, datastructure, **kw): ###(
1687        """Update datamodel from user data in datastructure.
1688        """
1689        logger = logging.getLogger('Widgets.ApplicationImageWidget.validate')
1690        datamodel = datastructure.getDataModel()
1691        field_id = self.fields[0]
1692        widget_id = self.getWidgetId()
1693        store = False
1694        fileupload = None
1695        mimetype = None
1696        old_file = datamodel[field_id]
1697        # if old_file is not None:
1698        #     old_filename = old_file.title
1699        # else:
1700        #     old_filename = ''
1701        choice = datastructure[widget_id+'_choice']
1702        fileupload = datastructure[widget_id]
1703        is_upload = isinstance(fileupload, FileUpload)
1704        #import pdb; pdb.set_trace()
1705        if not is_upload and not datamodel[field_id]:
1706            if self.is_required:
1707                return self.validateError('Picture upload required', {},
1708                                          datastructure)
1709        if choice == 'delete':
1710            if self.is_required:
1711                return self.validateError('cpsschemas_err_required', {},
1712                                          datastructure)
1713            datamodel[field_id] = None
1714        elif choice == 'keep':
1715            fileupload = datastructure[widget_id]
1716            if isinstance(fileupload, PersistableFileUpload):
1717                # Keeping something from the session means we
1718                # actually want to store it.
1719                store = True
1720            # else:
1721            #     # Nothing to change, don't pollute datastructure
1722            #     # with something costly already stored, which therefore
1723            #     # doesn't need to be kept in the session.
1724            #     self.unprepare(datastructure)
1725        elif choice == 'change' and is_upload:
1726            if not fileupload:
1727                return self.validateError('cpsschemas_err_file_empty', {},
1728                                          datastructure)
1729            if not isinstance(fileupload, FileUpload):
1730                return self.validateError('cpsschemas_err_file', {},
1731                                          datastructure)
1732            fileupload.seek(0, 2) # end of file
1733            size = fileupload.tell()
1734            if not size:
1735                return self.validateError('cpsschemas_err_file_empty', {},
1736                                          datastructure)
1737            if self.size_max and size > self.size_max:
1738                max_size_str = self.getHumanReadableSize(self.size_max)
1739                err = 'This file is too big, the allowed max size is ${max_size}'
1740                logger.info('%s tried to upload picture with size %dk' %(datastructure['reg_no'],int(size)/1000) )
1741                err_mapping = {'max_size': max_size_str}
1742                return self.validateError(err, err_mapping, datastructure)
1743            store = True
1744
1745
1746        # Find filename
1747        if is_upload and store:
1748            ext ='jpg'
1749            screening_type = datastructure.get('screening_type')
1750            filename = "%s_%s.%s" % (datastructure[self.id_field],
1751                                     self.getWidgetId(),
1752                                     ext)
1753            datamodel[field_id] = filename
1754            registry = getToolByName(self, 'mimetypes_registry')
1755            mimetype = registry.lookupExtension(filename.lower())
1756            if mimetype is not None:
1757                mimetype = str(mimetype) # normalize
1758            file = self.makeFile(filename, fileupload, datastructure)
1759            # Fixup mimetype
1760            if mimetype and file.content_type != mimetype:
1761                file.content_type = mimetype
1762            # Store the file in the filesystem
1763            #import pdb;pdb.set_trace()
1764            base_path = os.path.join(self.storage_path, screening_type)
1765            if not os.path.exists(base_path):
1766                os.mkdir(base_path)
1767            full_path = os.path.join(base_path, filename)
1768            pict = open(full_path,"w")
1769            fileupload.seek(0)
1770            pict.write(fileupload.read())
1771            pict.close()
1772
1773
1774        return True
1775
1776###)
1777
1778    def render(self, mode, datastructure, **kw): ###(
1779        render_method = 'widget_passport_render'
1780        meth = getattr(self, render_method, None)
1781        if meth is None:
1782            raise RuntimeError("Unknown Render Method %s for widget type %s"
1783                               % (render_method, self.getId()))
1784        img_info = self.getImageInfo(datastructure)
1785        return meth(mode=mode, datastructure=datastructure, **img_info)
1786    ###)
1787
1788InitializeClass(ApplicationImageWidget)
1789
1790widgetRegistry.register(ApplicationImageWidget)
1791###)
1792
1793class FileImageWidget(CPSImageWidget): ###(
1794    """Image widget with filesystem storage."""
1795    meta_type = 'File Image Widget'
1796    _properties = CPSImageWidget._properties +\
1797    (
1798     {'id': 'path', 'type': 'string', 'mode': 'w',
1799      'label': 'Relative Path'},
1800     {'id': 'id_field', 'type': 'string', 'mode': 'w',
1801      'label': 'Field to build the id'},
1802     {'id': 'show_image', 'type': 'boolean', 'mode': 'w',
1803      'label': 'Show Image'},
1804    )
1805    path = "images"
1806    storage_path = "%s/%s" % (i_home,path)
1807    id_field = ""
1808    show_image = False
1809
1810    def getStorageImageInfo(self,field_id):
1811        info = {}
1812        if self.id_field == "":
1813            student_id = self.getStudentId()
1814        else:
1815            student_id = datastructure[self.id_field]
1816        student_path = os.path.join(self.storage_path,
1817                                    student_id)
1818        image_name = ''
1819        content_url = ''
1820        current_filename = ''
1821        if os.path.exists(student_path):
1822            for name in os.listdir(student_path):
1823                if name.startswith(field_id):
1824                    image_name = name
1825                    break
1826        if image_name:
1827            info['image_name'] = image_name
1828            info['content_url'] = os.path.join(self.portal_url(),
1829                                   "viewimage",
1830                                   self.path,
1831                                   student_id,
1832                                   image_name,
1833                                   )
1834            info['current_filename'] = os.path.join(student_id,
1835                                                    image_name)
1836            info['file_path'] = os.path.join(self.storage_path,
1837                                             info['current_filename'])
1838        return info
1839
1840    def getImageInfo(self, datastructure): ###(
1841        """Get the file info from the datastructure."""
1842        widget_id = self.getWidgetId()
1843        if  datastructure.has_key(widget_id):
1844            fileupload = datastructure[widget_id]
1845            dm = datastructure.getDataModel()
1846            field_id = self.fields[0]
1847            info = self.getStorageImageInfo(field_id)
1848        else:
1849            file_path = "XXX"
1850            title = ""
1851        # read the file from the filesystem
1852        #import pdb; pdb.set_trace()
1853        #if not os.path.exists(file_path):
1854        if not info:
1855            title = ""
1856            height = -1
1857            width = -1
1858            empty_file = True
1859            session_file = False
1860            current_filename = ''
1861            content_url = ''
1862            size = 0
1863            mimetype = ''
1864            last_modified = ''
1865            height = ''
1866            width = ''
1867        else:
1868            title = info['image_name']
1869            current_filename = info['current_filename']
1870            content_url = info['content_url']
1871            image = open(info['file_path'])
1872            from OFS.Image import getImageInfo as getImageInfoOFS
1873            image.seek(0)
1874            data = image.read(2000)
1875            size = len(data)
1876            empty_file = size == 0
1877            session_file = False
1878            last_modified = ''
1879            image.close()
1880            mimetype, width, height = getImageInfoOFS(data)
1881            registry = getToolByName(self, 'mimetypes_registry')
1882            mimetype = (registry.lookupExtension(current_filename.lower()) or
1883                        registry.lookupExtension('file.bin'))
1884            if width < 0:
1885                width = None
1886            if height < 0:
1887                height = None
1888
1889            if (self.allow_resize
1890                and height is not None
1891                and width  is not None):
1892                z_w = z_h = 1
1893                h = int(self.display_height)
1894                w = int(self.display_width)
1895                if w and h:
1896                    if w < width:
1897                        z_w = w / float(width)
1898                    if h < height:
1899                        z_h = h / float(height)
1900                    zoom = min(z_w, z_h)
1901                    width = int(zoom * width)
1902                    height = int(zoom * height)
1903                #import pdb;pdb.set_trace()
1904        image_info = {
1905            'empty_file': empty_file,
1906            'session_file': session_file,
1907            'current_filename': title,
1908            'size': size,
1909            'last_modified': last_modified,
1910            'content_url': content_url,
1911            'mimetype': mimetype,
1912            }
1913        alt = title or ''
1914        #height = int(self.display_height)
1915        #width = int(self.display_width)
1916        if height is None or width is None:
1917            tag = renderHtmlTag('img', src=image_info['content_url'],
1918                                alt=alt, title=title)
1919        else:
1920            tag = renderHtmlTag('img', src=image_info['content_url'],
1921                                width=str(width), height=str(height),
1922                                alt=alt, title=title)
1923
1924        image_info['height'] = height
1925        image_info['width'] = width
1926        image_info['image_tag'] = tag
1927        image_info['show_image'] = self.show_image
1928        return image_info
1929    ###)
1930
1931    # def checkFileName(self, filename, mimetype):
1932    #     return '', {}
1933    #     if mimetype and mimetype.startswith('image'):
1934    #         return '', {}
1935    #     return 'cpsschemas_err_image', {}
1936
1937    def prepare(self, datastructure, **kw): ###(
1938        """Prepare datastructure from datamodel."""
1939        datamodel = datastructure.getDataModel()
1940        widget_id = self.getWidgetId()
1941        file_name = datamodel[self.fields[0]]
1942        if self.id_field == "":
1943            student_id = self.getStudentId()
1944        else:
1945            student_id = datastructure[self.id_field]
1946        if student_id is not None:
1947            student_path = os.path.join(self.storage_path,student_id)
1948            if not os.path.exists(student_path):
1949                self.waeup_tool.moveImagesToFS(student_id)
1950        if self.allow_resize:
1951            datastructure[self.getWidgetId() + '_resize'] = ''
1952        datastructure[widget_id] = file_name
1953        datastructure[widget_id + '_choice'] = 'change'
1954        title = 'Passport Foto'
1955        datastructure[widget_id + '_filename'] = title
1956    ###)
1957
1958    def validate(self, datastructure, **kw): ###(
1959        """Update datamodel from user data in datastructure.
1960        """
1961        logger = logging.getLogger('Widgets.FileImageWidget.validate')
1962        datamodel = datastructure.getDataModel()
1963        field_id = self.fields[0]
1964        widget_id = self.getWidgetId()
1965        store = False
1966        fileupload = None
1967        mimetype = None
1968        old_file = datamodel[field_id]
1969        choice = datastructure[widget_id+'_choice']
1970        fileupload = datastructure[widget_id]
1971        is_upload = isinstance(fileupload, FileUpload)
1972        #import pdb; pdb.set_trace()
1973        if not is_upload and not datamodel[field_id]:
1974            if self.is_required:
1975                return self.validateError('Picture upload required', {},
1976                                          datastructure)
1977        if self.id_field == "":
1978            student_id = self.getStudentId()
1979        else:
1980            student_id = datastructure[self.id_field]
1981        if choice == 'delete':
1982            if self.is_required:
1983                return self.validateError('cpsschemas_err_required', {},
1984                                          datastructure)
1985            info= self.getStorageImageInfo(field_id)
1986            # Remove the file in the filesystem
1987            if info:
1988                os.remove(info['file_path'])
1989            datamodel[field_id] = None
1990        elif choice == 'keep':
1991            fileupload = datastructure[widget_id]
1992            if isinstance(fileupload, PersistableFileUpload):
1993                # Keeping something from the session means we
1994                # actually want to store it.
1995                store = True
1996            # else:
1997            #     # Nothing to change, don't pollute datastructure
1998            #     # with something costly already stored, which therefore
1999            #     # doesn't need to be kept in the session.
2000            #     self.unprepare(datastructure)
2001        elif choice == 'change' and is_upload:
2002            if not fileupload:
2003                return self.validateError('cpsschemas_err_file_empty', {},
2004                                          datastructure)
2005            if not isinstance(fileupload, FileUpload):
2006                return self.validateError('cpsschemas_err_file', {},
2007                                          datastructure)
2008            fileupload.seek(0, 2) # end of file
2009            size = fileupload.tell()
2010            if not size:
2011                return self.validateError('cpsschemas_err_file_empty', {},
2012                                          datastructure)
2013            if self.size_max and size > self.size_max:
2014                max_size_str = self.getHumanReadableSize(self.size_max)
2015                err = 'This file is too big, the allowed max size is ${max_size}'
2016                member_id = str(self.portal_membership.getAuthenticatedMember())
2017                logger.info('%s tried to upload picture with size %dk' %(member_id,int(size)/1000) )
2018                err_mapping = {'max_size': max_size_str}
2019                return self.validateError(err, err_mapping, datastructure)
2020            store = True
2021
2022
2023        # Find filename
2024        if is_upload and store:
2025            filename = cookId('', '', fileupload)[0].strip()
2026            base,ext = os.path.splitext(filename)
2027            filename = "%s_%s%s" % (field_id,
2028                                    student_id,
2029                                    ext)
2030            datamodel[field_id] = filename
2031            registry = getToolByName(self, 'mimetypes_registry')
2032            mimetype = registry.lookupExtension(filename.lower())
2033            if mimetype is not None:
2034                mimetype = str(mimetype) # normalize
2035            file = self.makeFile(filename, fileupload, datastructure)
2036            # Fixup mimetype
2037            if mimetype and file.content_type != mimetype:
2038                file.content_type = mimetype
2039            # Store the file in the filesystem
2040            student_path = os.path.join(self.storage_path,student_id)
2041            if not os.path.exists(student_path):
2042                os.mkdir(student_path)
2043            full_path = os.path.join(student_path, filename)
2044            pict = open(full_path,"w")
2045            #fileupload.seek(0)
2046            #import pdb; pdb.set_trace()
2047            pict.write(str(file.data))
2048            pict.close()
2049        return True
2050    ###)
2051
2052    def render(self, mode, datastructure, **kw): ###(
2053        render_method = 'widget_image_render'
2054        meth = getattr(self, render_method, None)
2055        #import pdb;pdb.set_trace()
2056        if meth is None:
2057            raise RuntimeError("Unknown Render Method %s for widget type %s"
2058                               % (render_method, self.getId()))
2059        img_info = self.getImageInfo(datastructure)
2060        return meth(mode=mode, datastructure=datastructure, **img_info)
2061    ###)
2062
2063InitializeClass(FileImageWidget)
2064
2065widgetRegistry.register(FileImageWidget)
2066###)
2067
2068###########
2069
Note: See TracBrowser for help on using the repository browser.