source: waeup/branches/ulif-rewrite/src/waeup/university/facultycontainer.py @ 4335

Last change on this file since 4335 was 4335, checked in by uli, 16 years ago

Add importer for certcourses.

  • Property svn:eol-style set to native
File size: 11.9 KB
Line 
1import sys
2import grok
3from zope.component import getUtility
4from zope.component.factory import Factory
5from zope.component.interfaces import Invalid, IFactory
6from zope.component import createObject
7from zope.exceptions import DuplicationError
8from zope.interface import implementedBy
9from waeup.csvfile import CSVFile
10from waeup.csvfile.interfaces import ICSVFile
11from waeup.interfaces import IFacultyContainer, IFaculty, IWAeUPCSVImporter
12from waeup.utils.importexport import CSVImporter
13from waeup.viewlets import (MainArea, LeftSidebar, Index, Add, Manage,
14                            FormWrapMixin)
15
16
17class FacultyContainer(grok.Container):
18    """See interfaces for description.
19    """
20    grok.implements(IFacultyContainer)
21    grok.require('waeup.manageUniversity')
22
23    def addFaculty(self, faculty):
24        if not IFaculty.providedBy(faculty):
25            raise TypeError('FacultyContainers contain only IFaculty instances')
26        self[faculty.code] = faculty
27        return
28
29    def clear(self):
30        keys = self.keys()
31        for key in keys:
32            del self[key]
33
34class FacultyContainerFactory(grok.GlobalUtility):
35    """A factory for faculty containers.
36    """
37    grok.implements(IFactory)
38    grok.name(u'waeup.FacultyContainer')
39    title = u"Create a new faculty container.",
40    description = u"This factory instantiates new faculty containers."
41
42    def __call__(self):
43        return FacultyContainer()
44
45    def getInterfaces(self):
46        return implementedBy(FacultyContainer)
47
48
49#
50# CSV import stuff
51#
52class IFacultyCSVFile(ICSVFile):
53    """A CSV file that contains faculty data.
54    """
55
56class FacultyCSVFile(CSVFile):
57    """An abstraction of a CSV file containing faculties.
58    """
59    grok.implements(IFacultyCSVFile)
60    grok.provides(IFacultyCSVFile)
61    required_fields = ['code', 'title', 'title_prefix']
62
63class FacultyCSVImporter(CSVImporter):
64    """Shuffle data from faculty CSV files into faculty containers.
65    """
66    # Tell, what kinds of objects we connect...
67    grok.adapts(IFacultyCSVFile, IFacultyContainer)
68    # Tell the world, that we are an importer...
69    grok.implements(IWAeUPCSVImporter)
70    grok.provides(IWAeUPCSVImporter)
71
72    datatype = u'Faculty Importer'
73
74    def doImport(self, clear_old_data=True, overwrite=True):
75        # CSVImporter instances have a `csvfile` and a `receiver`
76        # object defined which refer to the CSV file and the container.
77        for row in self.csvfile.getData():
78            new_item = createObject(u'waeup.Faculty')
79            for key, val in row.items():
80                setattr(new_item, key, val)
81            self.receiver.addFaculty(new_item)
82        return
83
84class IDepartmentCSVFile(ICSVFile):
85    """A CSV file that contains department data.
86    """
87
88class DepartmentCSVFile(CSVFile):
89    """An abstraction of a CSV file containing departments.
90    """
91    grok.implements(IDepartmentCSVFile)
92    grok.provides(IDepartmentCSVFile)
93    required_fields = ['code', 'title', 'title_prefix', 'faculty_code']
94
95class DepartmentCSVImporter(CSVImporter):
96    """Shuffle data from department CSV files into faculty containers.
97    """
98    # Tell, what kinds of objects we connect...
99    grok.adapts(IDepartmentCSVFile, IFacultyContainer)
100    # Tell the world, that we are an importer...
101    grok.implements(IWAeUPCSVImporter)
102    grok.provides(IWAeUPCSVImporter)
103
104    datatype = u'Department Importer'
105
106    def doImport(self, clear_old_data=True, overwrite=True):
107        # CSVImporter instances have a `csvfile` and a `receiver`
108        # object defined which refer to the CSV file and the container.
109        for row in self.csvfile.getData():
110            new_item = createObject(u'waeup.Department')
111            faculty_code = row['faculty_code']
112            faculty = self.receiver[faculty_code]
113            del row['faculty_code']
114            for key, val in row.items():
115                setattr(new_item, key, val)
116            faculty.addDepartment(new_item)
117        return
118
119class ICourseCSVFile(ICSVFile):
120    """A CSV file that contains course data.
121    """
122
123class CourseCSVFile(CSVFile):
124    """An abstraction of a CSV file containing courses.
125    """
126    grok.implements(ICourseCSVFile)
127    grok.provides(ICourseCSVFile)
128    required_fields = ['code', 'title', 'level', 'passmark', 'credits',
129                       'semester', 'faculty', 'department']
130
131class CourseCSVImporter(CSVImporter):
132    """Shuffle data from course CSV files into faculty containers.
133    """
134    # Tell, what kinds of objects we connect...
135    grok.adapts(ICourseCSVFile, IFacultyContainer)
136    # Tell the world, that we are an importer...
137    grok.implements(IWAeUPCSVImporter)
138    grok.provides(IWAeUPCSVImporter)
139
140    datatype = u'Course Importer'
141
142    def doImport(self, clear_old_data=True, overwrite=True):
143        # CSVImporter instances have a `csvfile` and a `receiver`
144        # object defined which refer to the CSV file and the container.
145        for row in self.csvfile.getData():
146
147            new_item = createObject(u'waeup.Course')
148           
149            faculty_code = row['faculty']
150            faculty = self.receiver[faculty_code]
151            del row['faculty']
152
153            dept_code = row['department']
154            dept = faculty[dept_code]
155            del row['department']
156
157            for key, val in row.items():
158                setattr(new_item, key, val)
159            dept.courses.addCourse(new_item)
160        return
161
162class ICertificateCSVFile(ICSVFile):
163    """A CSV file that contains certificate data.
164    """
165
166class CertificateCSVFile(CSVFile):
167    """An abstraction of a CSV file containing certificates.
168    """
169    grok.implements(ICertificateCSVFile)
170    grok.provides(ICertificateCSVFile)
171    required_fields = ['code', 'title', 'faculty_code', 'department_code',
172                       'category', 'study_mode', 'start_level', 'end_level',
173                       'm_prefix', 'max_pass', 'application_category']
174
175class CertificateCSVImporter(CSVImporter):
176    """Shuffle data from certificate CSV files into faculty containers.
177    """
178    # Tell, what kinds of objects we connect...
179    grok.adapts(ICertificateCSVFile, IFacultyContainer)
180    # Tell the world, that we are an importer...
181    grok.implements(IWAeUPCSVImporter)
182    grok.provides(IWAeUPCSVImporter)
183
184    datatype = u'Certificate Importer'
185
186    def doImport(self, clear_old_data=True, overwrite=True):
187        # CSVImporter instances have a `csvfile` and a `receiver`
188        # object defined which refer to the CSV file and the container.
189        for row in self.csvfile.getData():
190
191            new_item = createObject(u'waeup.Certificate')
192           
193            faculty_code = row['faculty_code']
194            faculty = self.receiver[faculty_code]
195            del row['faculty_code']
196
197            dept_code = row['department_code']
198            dept = faculty[dept_code]
199            del row['department_code']
200
201            for key, val in row.items():
202                setattr(new_item, key, val)
203            dept.certificates.addCertificate(new_item)
204        return
205
206class ICertificateCourseCSVFile(ICSVFile):
207    """A CSV file that contains certificate-course data.
208    """
209
210class CertificateCourseCSVFile(CSVFile):
211    """An abstraction of a CSV file containing certificate-courses.
212    """
213    grok.implements(ICertificateCourseCSVFile)
214    grok.provides(ICertificateCourseCSVFile)
215    required_fields = ['code', 'faculty_code', 'department_code',
216                       'certificate_code', 'level', 'core_or_elective']
217
218class CertificateCourseCSVImporter(CSVImporter):
219    """Shuffle data from certificate CSV files into faculty containers.
220    """
221    # Tell, what kinds of objects we connect...
222    grok.adapts(ICertificateCourseCSVFile, IFacultyContainer)
223    # Tell the world, that we are an importer...
224    grok.implements(IWAeUPCSVImporter)
225    grok.provides(IWAeUPCSVImporter)
226
227    datatype = u'Certificate Importer'
228
229    def doImport(self, clear_old_data=True, overwrite=True):
230        # CSVImporter instances have a `csvfile` and a `receiver`
231        # object defined which refer to the CSV file and the container.
232        for row in self.csvfile.getData():
233
234            new_item = createObject(u'waeup.CertificateCourse')
235            code = row['code']
236            del row['code']
237           
238            faculty_code = row['faculty_code']
239            faculty = self.receiver[faculty_code]
240            del row['faculty_code']
241
242            dept_code = row['department_code']
243            dept = faculty[dept_code]
244            del row['department_code']
245
246            course = dept.courses[code]
247
248            cert_code = row['certificate_code']
249            cert = dept.certificates[cert_code]
250            del row['certificate_code']
251
252            cert.addCourseRef(course, **row)
253        return
254
255
256
257#
258# Viewing / Layout stuff...
259#
260class Content(grok.Viewlet):
261    grok.viewletmanager(MainArea)
262    grok.context(IFacultyContainer)
263    grok.view(Index)
264
265    def getFaculties(self):
266        """Convinience method to create a sorted list of faculties.
267
268        It provides a list of dicts with entries for all data needed by
269        usual list templates.
270        """
271        result = []
272        for key, val in self.context.items():
273            result.append(dict(id=key, name=val.title))
274        return result
275
276class ManageFacultyContainer(grok.Viewlet):
277    grok.viewletmanager(MainArea)
278    grok.context(IFacultyContainer)
279    grok.view(Manage)
280    grok.template('manage')   
281
282    def update(self):
283        form = self.request.form
284        if 'CANCEL' in form.keys():
285            self.view.redirect(self.view.url(self.context))
286        if not 'DELETE' in form.keys():
287            return
288        fac_id = form['fac_id']
289        if not isinstance(fac_id, list):
290            fac_id = [fac_id]
291        deleted = []
292        for id in fac_id:
293            try:
294                del self.context[id]
295                deleted.append(id)
296            except:
297                self.view.flash('Could not delete %s: %s: %s' % (
298                        id, sys.exc_info()[0], sys.exc_info()[1]))
299        if len(deleted):
300            self.view.flash('Successfully deleted: %s' % ', '.join(deleted))
301        # We have to redirect to let flash messages appear immediately...
302        self.view.redirect(self.view.url())
303        return
304       
305class AddFacultyForm(grok.AddForm):
306    grok.context(IFacultyContainer)
307    form_fields = grok.AutoFields(IFaculty)
308    label = 'Add a faculty'
309
310    @grok.action('Add faculty')
311    def addFaculty(self, **data):
312        faculty = createObject(u'waeup.Faculty')
313        self.applyData(faculty, **data)
314        try:
315            self.context.addFaculty(faculty)
316        except DuplicationError:
317            self.status = Invalid('The name chosen already exists '
318                                  'in the database')
319            return
320        self.redirect(self.url(self.context))
321
322       
323class AddFaculty(FormWrapMixin, grok.Viewlet):
324    """A viewlet that wraps the `AddFacultyForm`.
325    """
326    grok.viewletmanager(MainArea)
327    grok.context(IFacultyContainer)
328    grok.view(Add)
329    grok.require('waeup.manageUniversity')
330
331    formview_name = 'addfacultyform' # The name of the formview we
332                                     # want to be rendered in this
333                                     # viewlet.
334
335
336class AddFacultyLink(grok.Viewlet):
337    """A link in the left sidebar displaying 'Add faculty'
338    """
339    grok.viewletmanager(LeftSidebar)
340    grok.context(IFacultyContainer)
341    grok.view(Index)
342    grok.order(5)
343    # This is so cool! This link is only displayed, when the user is
344    # allowed to use it!
345    grok.require('waeup.manageUniversity')
346   
347    def render(self):
348        return u'<div class="portlet"><a href="add">Add faculty</a></div>'
349
350class ManageFacultyLink(grok.Viewlet):
351    """A link in the left sidebar displaying 'Manage faculty'
352    """
353    grok.viewletmanager(LeftSidebar)
354    grok.context(IFacultyContainer)
355    grok.view(Index)
356    grok.order(5)
357    grok.require('waeup.manageUniversity')
358   
359    def render(self):
360        return u'<div class="portlet"><a href="manage">Manage faculties</a></div>'
Note: See TracBrowser for help on using the repository browser.