~azzar1/unity/add-show-desktop-key

1099.1.59 by William Grant
Provide a media file framework in ivle.webapp.media.
1
# IVLE - Informatics Virtual Learning Environment
2
# Copyright (C) 2009 The University of Melbourne
3
#
4
# This program is free software; you can redistribute it and/or modify
5
# it under the terms of the GNU General Public License as published by
6
# the Free Software Foundation; either version 2 of the License, or
7
# (at your option) any later version.
8
#
9
# This program is distributed in the hope that it will be useful,
10
# but WITHOUT ANY WARRANTY; without even the implied warranty of
11
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12
# GNU General Public License for more details.
13
#
14
# You should have received a copy of the GNU General Public License
15
# along with this program; if not, write to the Free Software
16
# Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA  02110-1301  USA
17
18
# Author: William Grant
19
20
'''Media file support for the framework.'''
21
22
import os
23
import inspect
24
import mimetypes
25
26
import ivle.conf
27
from ivle.webapp.base.views import BaseView
1099.1.72 by Nick Chadwick
Dispatch now generates an index for each plugin type, allowing plugins to
28
from ivle.webapp.base.plugins import ViewPlugin
1099.1.59 by William Grant
Provide a media file framework in ivle.webapp.media.
29
from ivle.webapp.errors import NotFound
30
31
def media_url(req, plugin, path):
1099.1.74 by Nick Chadwick
Added overlay system and console overlay. Note that the console overlay
32
    '''Generates a URL to a media file.
33
    
34
    Plugin can be a string, in which case it is put into the path literally,
35
    or a plugin object, in which case its name is looked up.'''
36
    if not isinstance(plugin, basestring):
37
        plugin = req.reverse_plugins[plugin]
38
        
39
    return os.path.join(ivle.conf.root_dir, '+media', plugin, path)
1099.1.59 by William Grant
Provide a media file framework in ivle.webapp.media.
40
41
class MediaFileView(BaseView):
42
    '''A view for media files.
43
44
    This serves static files from directories registered by plugins.
45
46
    Plugins wishing to export media should declare a 'media' attribute,
47
    pointing to the directory to serve (relative to the module's directory).
48
    The contents of that directory will then be available under
49
    /+media/python.path.to.module.
50
    '''
51
    def __init__(self, req, ns, path):
52
        self.ns = ns
53
        self.path = path
54
55
    def _make_filename(self, req):
56
        try:
57
            plugin = req.plugins[self.ns]
58
        except KeyError:
59
            raise NotFound()
60
61
        try:
62
            mediadir = plugin.media
63
        except AttributeError:
64
            raise NotFound()
65
66
        plugindir = os.path.dirname(inspect.getmodule(plugin).__file__)
67
68
        return os.path.join(plugindir, mediadir, self.path)
69
70
    def render(self, req):
71
        # If it begins with ".." or separator, it's illegal. Die.
72
        if self.path.startswith("..") or self.path.startswith('/'):
73
            raise Forbidden()
74
75
        filename = self._make_filename(req)
76
77
        # Find an appropriate MIME type.
78
        (type, _) = mimetypes.guess_type(filename)
79
        if type is None:
80
            type = 'application/octet-stream'
81
82
        # Get out if it is unreadable or a directory.
83
        if not os.access(filename, os.F_OK):
1099.1.62 by William Grant
Remove a bit of debugging cruft from ivle.webapp.media.
84
            raise NotFound()
1099.1.59 by William Grant
Provide a media file framework in ivle.webapp.media.
85
        if not os.access(filename, os.R_OK) or os.path.isdir(filename):
86
            raise Forbidden()
87
88
        req.content_type = type
89
        req.sendfile(filename)
90
1099.1.72 by Nick Chadwick
Dispatch now generates an index for each plugin type, allowing plugins to
91
class Plugin(ViewPlugin):
1099.1.59 by William Grant
Provide a media file framework in ivle.webapp.media.
92
    urls = [
93
        ('+media/:ns/*path', MediaFileView),
94
    ]