~aelkner/schooltool/schooltool.sla_august_fixes

« back to all changes in this revision

Viewing changes to src/schooltool/intervention/intervention.py

  • Committer: Justas Sadzevicius
  • Date: 2009-08-14 09:48:48 UTC
  • mfrom: (163.1.19 sla)
  • Revision ID: justas@pov.lt-20090814094848-ajt79v222ovkv9tj
Merge sla intervetion migration to the gradebook package.

Show diffs side-by-side

added added

removed removed

Lines of Context:
27
27
from zope.app.container import btree
28
28
from zope.app.security.interfaces import IUnauthenticatedPrincipal
29
29
from zope.component import queryMultiAdapter, queryUtility
 
30
from zope.component import adapter
 
31
from zope.interface import implementer
30
32
from zope.event import notify
31
33
from zope.interface import implements
32
34
from zope.lifecycleevent import ObjectModifiedEvent
38
40
from schooltool.app.app import InitBase
39
41
from schooltool.app.interfaces import ISchoolToolApplication
40
42
from schooltool.basicperson.interfaces import IBasicPerson
 
43
from schooltool.contact.interfaces import IContactable
 
44
from schooltool.contact.contact import Contact
41
45
from schooltool.course.interfaces import ISectionContainer
42
46
from schooltool.group.interfaces import IGroupContainer
43
47
from schooltool.person.interfaces import IPerson
44
48
from schooltool.schoolyear.interfaces import ISchoolYear
 
49
from schooltool.schoolyear.interfaces import ISchoolYearContainer
45
50
from schooltool.securitypolicy import crowds
46
51
from schooltool.term.interfaces import IDateManager
47
52
from schooltool.traverser.traverser import NameTraverserPlugin
67
72
def convertIdToNameWithSort(id):
68
73
    if id[-2] == ':':
69
74
        student = convertIdToPerson(id[:-2])
70
 
        demos = interfaces.IDemographics(student)
71
 
        if id[-1] == '1':
72
 
            first_name = demos.parent_first_name
73
 
            last_name = demos.parent_last_name
 
75
        for index, contact in enumerate(IContactable(student).contacts):
 
76
            if id[-1] == str(index + 1):
 
77
                first_name = contact.first_name
 
78
                last_name = contact.last_name
 
79
                break
74
80
        else:
75
 
            first_name = demos.parent2_first_name
76
 
            last_name = demos.parent2_last_name
 
81
            raise IndexError
77
82
    else:
78
83
        person = convertIdToPerson(id)
79
84
        first_name = person.first_name
96
101
def convertIdToEmail(id):
97
102
    if id[-2] == ':':
98
103
        student = convertIdToPerson(id[:-2])
99
 
        demos = interfaces.IDemographics(student)
100
 
        if id[-1] == '1':
101
 
            return student.email
 
104
        for index, contact in enumerate(IContactable(student).contacts):
 
105
            if id[-1] == str(index + 1):
 
106
                return contact.email
102
107
        else:
103
 
            return demos.email2
 
108
            raise IndexError
104
109
    else:
105
110
        return id + '@scienceleadership.org'
106
111
 
118
123
       for the purpose of sending emails, but they will be filtered
119
124
       out of any application elements that are for staff only."""
120
125
 
121
 
    demos = interfaces.IDemographics(student)
122
 
    responsible = [id for id in [demos.advisor1, demos.advisor2] if id]
 
126
    responsible = [advisor.username for advisor in student.advisors]
123
127
 
124
128
    term = queryUtility(IDateManager).current_term
125
129
    groups = IGroupContainer(ISchoolYear(term))
136
140
                    responsible.append(teacher.username)
137
141
 
138
142
    responsible.append(student.username)
139
 
    if student.email:
140
 
        responsible.append(student.username + ':1')
141
 
    if demos.email2:
142
 
        responsible.append(student.username + ':2')
 
143
    for index, contact in enumerate(IContactable(student).contacts):
 
144
        responsible.append(student.username + ':%d' % (index + 1))
143
145
 
144
146
    return responsible
145
147
 
261
263
            return None
262
264
 
263
265
 
264
 
class InterventionNarratives(btree.BTreeContainer):
265
 
    """Container of Narrative of persons."""
266
 
 
267
 
    implements(interfaces.IInterventionNarratives)
268
 
 
269
 
    @property
270
 
    def student(self):
271
 
        try:
272
 
            return self.__parent__.student
273
 
        except:
274
 
            return None
275
 
 
276
 
 
277
 
class InterventionNarrative(Persistent, Contained):
278
 
    """Narrative associated with a person.
279
 
    """
280
 
    implements(interfaces.IInterventionNarrative)
281
 
 
282
 
    def __init__(self, sectionId, grade='', assessments='', comments=""):
283
 
        self.__name__ = sectionId
284
 
        self.grade = grade
285
 
        self.assessments = assessments
286
 
        self.comments = comments
287
 
 
288
 
    @property
289
 
    def student(self):
290
 
        try:
291
 
            return self.__parent__.student
292
 
        except:
293
 
            return None
294
 
 
295
 
    @property
296
 
    def section(self):
297
 
        term = queryUtility(IDateManager).current_term
298
 
        if term is None:
299
 
            return None
300
 
        sections = ISectionContainer(term)
301
 
        if self.__name__ in sections:
302
 
            return sections[self.__name__]
303
 
        else:
304
 
            return None
305
 
 
306
 
 
307
266
class InterventionInit(InitBase):
308
267
    """Create the InterventionRoot object."""
309
268
 
311
270
        self.app[u'schooltool.interventions'] = InterventionRoot()
312
271
 
313
272
 
 
273
@adapter(ISchoolYear)
 
274
@implementer(interfaces.IInterventionSchoolYear)
 
275
def getSchoolYearInterventionSchoolYear(schoolyear):
 
276
    return getInterventionSchoolYear(schoolyear.__name__)
 
277
 
 
278
 
 
279
@adapter(ISchoolToolApplication)
 
280
@implementer(interfaces.IInterventionSchoolYear)
 
281
def getSchoolToolApplicationInterventionSchoolYear(app):
 
282
    return getInterventionSchoolYear()
 
283
 
 
284
 
 
285
@adapter(interfaces.IInterventionSchoolYear)
 
286
@implementer(ISchoolYear)
 
287
def getInterventionSchoolYearSchoolYear(schoolyear):
 
288
    app = ISchoolToolApplication(None)
 
289
    return ISchoolYearContainer(app)[schoolyear.__name__]
 
290
 
 
291
 
314
292
def getInterventionSchoolYear(schoolYearId=None):
315
293
    """Get InterventionSchoolYear object for the given school yearr.
316
294
       If school year not specified, use current school year."""
318
296
    app = ISchoolToolApplication(None)
319
297
    interventionRoot = app[u'schooltool.interventions']
320
298
    if not schoolYearId:
321
 
        now = date.today()
322
 
        if now.month < 8:
323
 
            schoolYearId = '%s-%s' % (now.year - 1, now.year)
324
 
        else:
325
 
            schoolYearId = '%s-%s' % (now.year, now.year + 1)
 
299
        term = queryUtility(IDateManager).current_term
 
300
        schoolyear = ISchoolYear(term)
 
301
        schoolYearId = schoolyear.__name__
326
302
    try:
327
303
        interventionSchoolYear = interventionRoot[schoolYearId]
328
304
    except KeyError:
345
321
        interventionSchoolYear[studentId] = interventionStudent
346
322
        interventionStudent[u'messages'] = InterventionMessages()
347
323
        interventionStudent[u'goals'] = InterventionGoals()
348
 
        interventionStudent[u'narratives'] = InterventionNarratives()
349
324
    return interventionStudent
350
325
 
351
326
 
366
341
        return n
367
342
 
368
343
 
369
 
class InterventionNarrativeNameChooser(NameChooser):
370
 
    """A name chooser that returns the narrative's section id."""
371
 
 
372
 
    implements(INameChooser)
373
 
 
374
 
    def chooseName(self, name, obj):
375
 
        """See INameChooser."""
376
 
        n = obj.__name__
377
 
        self.checkName(n, obj)
378
 
        return n
379
 
 
380
 
 
381
344
class  InterventionStudentTraverserPlugin(NameTraverserPlugin):
382
345
    """Allows traversal to a student's intervention object.
383
346
 
392
355
        return interventionStudent
393
356
 
394
357
 
395
 
class SectionNarrativesProxy(object):
396
 
    """Proxy used for traversing to a section's narratives."""
397
 
 
398
 
    def __init__(self, section):
399
 
        self.section = section
400
 
 
401
 
 
402
 
class SectionNarrativesTraverserPlugin(NameTraverserPlugin):
403
 
    """Allows traversal from a section object to a SectionNarrativesProxy
404
 
    object, which in turn will be used to traverse to the narratives
405
 
    container for a given student.
406
 
 
407
 
    i.e. if you go to localhost/sections/somesec/narratives this traverser
408
 
    will get called instead of standard traverser.
409
 
    """
410
 
 
411
 
    traversalName = "narratives"
412
 
    def _traverse(self, request, name):
413
 
        proxyNarratives = SectionNarrativesProxy(self.context)
414
 
        return location.LocationProxy(proxyNarratives, self.context,
415
 
                                      self.traversalName)
416
 
 
417
 
class SectionNarrativesTraverser(object):
418
 
    """Allows traversal to a student's narratives container from the
419
 
    section narratives proxy.
420
 
 
421
 
    i.e. if you go to localhost/sections/somesec/narratives/someone this
422
 
    traverser will get called instead of standard traverser.  It also wraps the
423
 
    narrative in a location proxy so the url looks like what is above.
424
 
 
425
 
    The whole reason for having this traversal adaptation is to allow
426
 
    the narative add view to know what section the narrative is for.
427
 
    """
428
 
    implements(IPublishTraverse)
429
 
 
430
 
    def __init__(self, context, request):
431
 
        self.context = context
432
 
        self.request = request
433
 
 
434
 
    def publishTraverse(self, request, name):
435
 
        interventionStudent = getInterventionStudent(name)
436
 
        narratives = interventionStudent['narratives']
437
 
        narratives = location.LocationProxy(narratives, self.context, name)
438
 
        return narratives
439
 
 
440
 
 
441
358
class SectionMessagesProxy(object):
442
359
    """Proxy used for traversing to a section's student messages."""
443
360
 
482
399
        messages = interventionStudent['messages']
483
400
        messages = location.LocationProxy(messages, self.context, name)
484
401
        return messages
 
402