source: main/waeup.sirp/trunk/src/waeup/sirp/interfaces.py @ 6814

Last change on this file since 6814 was 6754, checked in by uli, 13 years ago

Logger-related stuff.

  • Property svn:eol-style set to native
File size: 14.2 KB
Line 
1##
2## interfaces.py
3import os
4from hurry.workflow.interfaces import IWorkflow, IWorkflowInfo
5from zc.sourcefactory.basic import BasicSourceFactory
6from zope import schema
7from zope.component import getUtility
8from zope.component.interfaces import IObjectEvent
9from zope.interface import Interface, Attribute, implements
10from zope.schema.vocabulary import SimpleVocabulary, SimpleTerm
11
12default_frontpage = u'' + open(os.path.join(
13        os.path.dirname(__file__), 'frontpage.rst'), 'rb').read()
14
15class FatalCSVError(Exception):
16    """Some row could not be processed.
17    """
18    pass
19
20class DuplicationError(Exception):
21    """An exception that can be raised when duplicates are found.
22
23    When raising :exc:`DuplicationError` you can, beside the usual
24    message, specify a list of objects which are duplicates. These
25    values can be used by catching code to print something helpful or
26    similar.
27    """
28    def __init__(self, msg, entries=[]):
29        self.msg = msg
30        self.entries = entries
31
32    def __str__(self):
33        return '%r' % self.msg
34
35def SimpleWAeUPVocabulary(*terms):
36    """A well-buildt vocabulary provides terms with a value, token and
37       title for each term
38    """
39    return SimpleVocabulary([
40            SimpleTerm(value, value, title) for title, value in terms])
41
42class RoleSource(BasicSourceFactory):
43    """A source for global roles.
44    """
45    def getValues(self):
46        # late import: in interfaces we should not import local modules
47        from waeup.sirp.permissions import getWAeUPRoleNames
48        return getWAeUPRoleNames()
49
50    def getTitle(self, value):
51        # late import: in interfaces we should not import local modules
52        from waeup.sirp.permissions import getRoles
53        roles = dict(getRoles())
54        if value in roles.keys():
55            title = roles[value].title
56            if '.' in title:
57                title = title.split('.', 2)[1]
58        return title
59
60class IWAeUPObject(Interface):
61    """A WAeUP object.
62
63    This is merely a marker interface.
64    """
65
66class IUniversity(IWAeUPObject):
67    """Representation of a university.
68    """
69    name = schema.TextLine(
70        title = u'Name of University',
71        default = u'Sample University',
72        required = True,
73        )
74
75    title = schema.TextLine(
76        title = u'Title of frontpage',
77        default = u'Welcome to the Student Information and Registration ' +
78                  u'Portal of Sample University',
79        required = False,
80        )
81
82    skin = schema.Choice(
83        title = u'Skin',
84        default = u'waeuptheme-gray1.css',
85        vocabulary = 'waeup.sirp.browser.theming.ThemesVocabulary',
86        required = True,
87        )
88
89    frontpage = schema.Text(
90        title = u'Content in reST format',
91        required = False,
92        default = default_frontpage,
93        )
94
95
96class IWAeUPContainer(IWAeUPObject):
97    """A container for WAeUP objects.
98    """
99
100class IWAeUPContained(IWAeUPObject):
101    """An item contained in an IWAeUPContainer.
102    """
103
104class IStudentContainer(IWAeUPContainer):
105    """A container for StudentObjects.
106    """
107
108
109class IHostelContainer(IWAeUPContainer):
110    """A container for hostels.
111    """
112    def addHostel(hostel):
113        """Add an IHostel object.
114
115        Returns the key, under which the object was stored.
116        """
117
118class IHostel(IWAeUPObject):
119    """Representation of a hostel.
120    """
121    name = schema.TextLine(
122        title = u'Name of Hostel',
123        default = u'Nobody',
124        required = True,
125        )
126
127
128class IWAeUPExporter(Interface):
129    """An exporter for objects.
130    """
131    def export(obj, filepath=None):
132        """Export by pickling.
133
134        Returns a file-like object containing a representation of `obj`.
135
136        This is done using `pickle`. If `filepath` is ``None``, a
137        `cStringIO` object is returned, that contains the saved data.
138        """
139
140class IWAeUPXMLExporter(Interface):
141    """An XML exporter for objects.
142    """
143    def export(obj, filepath=None):
144        """Export as XML.
145
146        Returns an XML representation of `obj`.
147
148        If `filepath` is ``None``, a StringIO` object is returned,
149        that contains the transformed data.
150        """
151
152class IWAeUPXMLImporter(Interface):
153    """An XML import for objects.
154    """
155    def doImport(filepath):
156        """Create Python object from XML.
157
158        Returns a Python object.
159        """
160
161class IBatchProcessor(Interface):
162    """A batch processor that handles mass-operations.
163    """
164    name = schema.TextLine(
165        title = u'Importer name'
166        )
167
168    mode = schema.Choice(
169        title = u'Import mode',
170        values = ['create', 'update', 'remove']
171        )
172
173    def doImport(path, headerfields, mode='create', user='Unknown',
174                 logger=None):
175        """Read data from ``path`` and update connected object.
176
177        `headerfields` is a list of headerfields as read from the file
178        to import.
179
180        `mode` gives the import mode to use (``'create'``,
181        ``'update'``, or ``'remove'``.
182
183        `user` is a string describing the user performing the
184        import. Normally fetched from current principal.
185
186        `logger` is the logger to use during import.
187        """
188
189class IUserAccount(IWAeUPObject):
190    """A user account.
191    """
192    name = schema.TextLine(
193        title = u'User ID',
194        description = u'Login name of user',
195        required = True,)
196    title = schema.TextLine(
197        title = u'Name',
198        description = u'Real name of user',
199        required = False,)
200    description = schema.TextLine(
201        title = u'Description',
202        required = False,)
203    password = schema.Password(
204        title = u'Password',
205        required = True,)
206    roles = schema.List(
207        title = u'Global roles',
208        value_type = schema.Choice(source=RoleSource()))
209
210
211class IUserContainer(IWAeUPObject):
212    """A container for users (principals).
213
214    These users are used for authentication purposes.
215    """
216
217    def addUser(name, password, title=None, description=None):
218        """Add a user.
219        """
220
221    def delUser(name):
222        """Delete a user if it exists.
223        """
224
225class ILocalRolesAssignable(Interface):
226    """The local roles assignable to an object.
227    """
228    def __call__():
229        """Returns a list of dicts.
230
231        Each dict contains a ``name`` referring to the role assignable
232        for the specified object and a `title` to describe the range
233        of users to which this role can be assigned.
234        """
235
236class IDataCenter(IWAeUPObject):
237    """A data center.
238
239    TODO : declare methods, at least those needed by pages.
240    """
241    pass
242
243class IDataCenterFile(Interface):
244    """A data center file.
245    """
246
247    name = schema.TextLine(
248        title = u'Filename')
249
250    size = schema.TextLine(
251        title = u'Human readable file size')
252
253    uploaddate = schema.TextLine(
254        title = u'Human readable upload datetime')
255
256    lines = schema.Int(
257        title = u'Number of lines in file')
258
259    def getDate():
260        """Get creation timestamp from file in human readable form.
261        """
262
263    def getSize():
264        """Get human readable size of file.
265        """
266
267    def getLinesNumber():
268        """Get number of lines of file.
269        """
270
271class IDataCenterStorageMovedEvent(IObjectEvent):
272    """Emitted, when the storage of a datacenter changes.
273    """
274
275class IObjectUpgradeEvent(IObjectEvent):
276    """Can be fired, when an object shall be upgraded.
277    """
278
279class ILocalRoleSetEvent(IObjectEvent):
280    """A local role was granted/revoked for a principal on an object.
281    """
282    role_id = Attribute(
283        "The role id that was set.")
284    principal_id = Attribute(
285        "The principal id for which the role was granted/revoked.")
286    granted = Attribute(
287        "Boolean. If false, then the role was revoked.")
288
289class IQueryResultItem(Interface):
290    """An item in a search result.
291    """
292    url = schema.TextLine(
293        title = u'URL that links to the found item')
294    title = schema.TextLine(
295        title = u'Title displayed in search results.')
296    description = schema.Text(
297        title = u'Longer description of the item found.')
298
299class IWAeUPSIRPPluggable(Interface):
300    """A component that might be plugged into a WAeUP SIRP app.
301
302    Components implementing this interface are referred to as
303    'plugins'. They are normally called when a new
304    :class:`waeup.sirp.app.University` instance is created.
305
306    Plugins can setup and update parts of the central site without the
307    site object (normally a :class:`waeup.sirp.app.University` object)
308    needing to know about that parts. The site simply collects all
309    available plugins, calls them and the plugins care for their
310    respective subarea like the applicants area or the datacenter
311    area.
312
313    Currently we have no mechanism to define an order of plugins. A
314    plugin should therefore make no assumptions about the state of the
315    site or other plugins being run before and instead do appropriate
316    checks if necessary.
317
318    Updates can be triggered for instance by the respective form in
319    the site configuration. You normally do updates when the
320    underlying software changed.
321    """
322    def setup(site, name, logger):
323        """Create an instance of the plugin.
324
325        The method is meant to be called by the central app (site)
326        when it is created.
327
328        `site`:
329           The site that requests a setup.
330
331        `name`:
332           The name under which the plugin was registered (utility name).
333
334        `logger`:
335           A standard Python logger for the plugins use.
336        """
337
338    def update(site, name, logger):
339        """Method to update an already existing plugin.
340
341        This might be called by a site when something serious
342        changes. It is a poor-man replacement for Zope generations
343        (but probably more comprehensive and better understandable).
344
345        `site`:
346           The site that requests an update.
347
348        `name`:
349           The name under which the plugin was registered (utility name).
350
351        `logger`:
352           A standard Python logger for the plugins use.
353        """
354
355class IAuthPluginUtility(Interface):
356    """A component that cares for authentication setup at site creation.
357
358    Utilities providing this interface are looked up when a Pluggable
359    Authentication Utility (PAU) for any
360    :class:`waeup.sirp.app.University` instance is created and put
361    into ZODB.
362
363    The setup-code then calls the `register` method of the utility and
364    expects a modified (or unmodified) version of the PAU back.
365
366    This allows to define any authentication setup modifications by
367    submodules or third-party modules/packages.
368    """
369
370    def register(pau):
371        """Register any plugins wanted to be in the PAU.
372        """
373
374    def unregister(pau):
375        """Unregister any plugins not wanted to be in the PAU.
376        """
377
378class IObjectConverter(Interface):
379    """Object converters are available as simple adapters, adapting
380       interfaces (not regular instances).
381
382    """
383
384    def fromStringDict(self, data_dict, context, form_fields=None):
385        """Convert values in `data_dict`.
386
387        Converts data in `data_dict` into real values based on
388        `context` and `form_fields`.
389
390        `data_dict` is a mapping (dict) from field names to values
391        represented as strings.
392
393        The fields (keys) to convert can be given in optional
394        `form_fields`. If given, form_fields should be an instance of
395        :class:`zope.formlib.form.Fields`. Suitable instances are for
396        example created by :class:`grok.AutoFields`.
397
398        If no `form_fields` are given, a default is computed from the
399        associated interface.
400
401        The `context` can be an existing object (implementing the
402        associated interface) or a factory name. If it is a string, we
403        try to create an object using
404        :func:`zope.component.createObject`.
405
406        Returns a tuple ``(<FIELD_ERRORS>, <INVARIANT_ERRORS>,
407        <DATA_DICT>)`` where
408
409        ``<FIELD_ERRORS>``
410           is a list of tuples ``(<FIELD_NAME>, <ERROR>)`` for each
411           error that happened when validating the input data in
412           `data_dict`
413
414        ``<INVARIANT_ERRORS>``
415           is a list of invariant errors concerning several fields
416
417        ``<DATA_DICT>``
418           is a dict with the values from input dict converted.
419
420        If errors happen, i.e. the error lists are not empty, always
421        an empty ``<DATA_DICT>`` is returned.
422
423        If ``<DATA_DICT>` is non-empty, there were no errors.
424        """
425
426class IObjectHistory(Interface):
427
428    messages = schema.List(
429        title = u'List of messages stored',
430        required = True,
431        )
432
433    def addMessage(message):
434        """Add a message.
435        """
436
437class IWAeUPWorkflowInfo(IWorkflowInfo):
438    """A :class:`hurry.workflow.workflow.WorkflowInfo` with additional
439       methods for convenience.
440    """
441    def getManualTransitions():
442        """Get allowed manual transitions.
443
444        Get a sorted list of tuples containing the `transition_id` and
445        `title` of each allowed transition.
446        """
447
448class ISiteLoggers(Interface):
449
450    loggers = Attribute("A list or generator of registered WAeUPLoggers")
451
452    def register(name, filename=None, site=None, **options):
453        """Register a logger `name` which logs to `filename`.
454
455        If `filename` is not given, logfile will be `name` with
456        ``.log`` as filename extension.
457        """
458
459    def unregister(name):
460        """Unregister a once registered logger.
461        """
462
463class ILogger(Interface):
464    """A logger cares for setup, update and restarting of a Python logger.
465    """
466
467    logger = Attribute("""A :class:`logging.Logger` instance""")
468
469
470    def __init__(name, filename=None, site=None, **options):
471        """Create a WAeUP logger instance.
472        """
473
474    def setup():
475        """Create a Python :class:`logging.Logger` instance.
476
477        The created logger is based on the params given by constructor.
478        """
479
480    def update(**options):
481        """Update the logger.
482
483        Updates the logger respecting modified `options` and changed
484        paths.
485        """
486
487class ILoggerCollector(Interface):
488
489    def getLoggers(site):
490        """Return all loggers registered for `site`.
491        """
492
493    def registerLogger(site, logging_component):
494        """Register a logging component residing in `site`.
495        """
496
497    def unregisterLogger(site, logging_component):
498        """Unregister a logger.
499        """
Note: See TracBrowser for help on using the repository browser.