24
23
import genshi.template
26
25
from ivle.webapp.media import media_url
27
from ivle.webapp.core import Plugin as CorePlugin
28
26
from ivle.webapp.base.views import BaseView
29
from ivle.webapp.base.plugins import ViewPlugin, OverlayPlugin
30
from ivle.webapp.errors import HTTPError, Unauthorized
27
from ivle.webapp.base.plugins import OverlayPlugin
41
38
template = 'template.html'
42
39
plugin_scripts = {}
45
41
overlay_blacklist = []
47
43
def __init__(self, req, **kwargs):
49
45
setattr(self, key, kwargs[key])
51
def filter(self, stream, ctx):
54
47
def render(self, req):
55
48
req.content_type = 'text/html' # TODO: Detect application/xhtml+xml
63
56
app_template = os.path.join(os.path.dirname(
64
57
inspect.getmodule(self).__file__), self.template)
58
req.write_html_head_foot = False
65
59
loader = genshi.template.TemplateLoader(".", auto_reload=True)
66
60
tmpl = loader.load(app_template)
67
app = self.filter(tmpl.generate(viewctx), viewctx)
61
app = tmpl.generate(viewctx)
69
63
for plugin in self.plugin_scripts:
70
64
for path in self.plugin_scripts[plugin]:
78
72
ctx = genshi.template.Context()
79
73
# XXX: Leave this here!! (Before req.styles is read)
80
ctx['overlays'] = self.render_overlays(req) if req.user else []
82
ctx['styles'] = [media_url(req, CorePlugin, 'ivle.css')]
83
ctx['styles'] += req.styles
85
ctx['scripts'] = [media_url(req, CorePlugin, path) for path in
86
('util.js', 'json2.js', 'md5.js')]
87
ctx['scripts'].append(media_url(req, '+external/jquery', 'jquery.js'))
88
ctx['scripts'] += req.scripts
74
ctx['overlays'] = self.render_overlays(req)
75
ctx['app_styles'] = req.styles
76
ctx['scripts'] = req.scripts
90
77
ctx['scripts_init'] = req.scripts_init
91
78
ctx['app_template'] = app
92
ctx['title_img'] = media_url(req, CorePlugin,
93
"images/chrome/title.png")
94
79
self.populate_headings(req, ctx)
95
80
tmpl = loader.load(os.path.join(os.path.dirname(__file__),
96
81
'ivle-headings.html'))
110
95
ctx['nick'] = req.user.nick
112
97
ctx['login'] = None
113
ctx['logged_in'] = False
114
98
ctx['publicmode'] = req.publicmode
115
if hasattr(self, 'help'):
116
ctx['help_path'] = self.help
118
99
ctx['apps_in_tabs'] = []
119
for plugin in req.config.plugin_index[ViewPlugin]:
120
if not hasattr(plugin, 'tabs'):
123
for tab in plugin.tabs:
124
# tab is a tuple: name, title, desc, icon, path
126
new_app['this_app'] = hasattr(self, 'tab') \
127
and tab[0] == self.tab
130
if tab[3] is not None:
131
new_app['has_icon'] = True
132
icon_url = media_url(req, plugin, tab[3])
133
new_app['icon_url'] = icon_url
134
if new_app['this_app']:
135
ctx['favicon'] = icon_url
137
new_app['has_icon'] = False
138
new_app['path'] = ivle.util.make_path(tab[4])
139
new_app['desc'] = tab[2]
140
new_app['name'] = tab[1]
141
new_app['weight'] = tab[5]
142
ctx['apps_in_tabs'].append(new_app)
144
ctx['apps_in_tabs'].sort(key=lambda tab: tab['weight'])
100
for urlname in ivle.conf.apps.apps_in_tabs:
102
app = ivle.conf.apps.app_url[urlname]
103
new_app['this_app'] = hasattr(self, 'appname') \
104
and urlname == self.appname
106
new_app['has_icon'] = True
107
icon_dir = ivle.conf.apps.app_icon_dir
108
icon_url = ivle.util.make_path(os.path.join(icon_dir, app.icon))
109
new_app['icon_url'] = icon_url
110
if new_app['this_app']:
111
ctx['favicon'] = icon_url
113
new_app['has_icon'] = False
114
new_app['path'] = ivle.util.make_path(urlname)
115
new_app['desc'] = app.desc
116
new_app['name'] = app.name
117
ctx['apps_in_tabs'].append(new_app)
146
119
def render_overlays(self, req):
147
120
"""Generate XML streams for the overlays.
153
if not self.allow_overlays:
156
for plugin in req.config.plugin_index[OverlayPlugin]:
126
for plugin in req.plugin_index[OverlayPlugin]:
157
127
for overclass in plugin.overlays:
158
128
if overclass in self.overlay_blacklist:
166
136
for mplugin in overlay.plugin_styles:
167
137
for path in overlay.plugin_styles[mplugin]:
168
138
req.styles.append(media_url(req, mplugin, path))
170
140
req.scripts_init += overlay.plugin_scripts_init
172
142
overlays.append(overlay.render(req))
176
def get_error_view(cls, e):
177
view_map = {HTTPError: XHTMLErrorView,
178
Unauthorized: XHTMLUnauthorizedView}
179
for exccls in inspect.getmro(type(e)):
180
if exccls in view_map:
181
return view_map[exccls]
183
class XHTMLErrorView(XHTMLView):
184
template = 'xhtmlerror.html'
186
def __init__(self, req, exception):
187
self.context = exception
189
def populate(self, req, ctx):
190
ctx['exception'] = self.context
192
class XHTMLUnauthorizedView(XHTMLErrorView):
193
template = 'xhtmlunauthorized.html'
195
def __init__(self, req, exception):
196
super(XHTMLUnauthorizedView, self).__init__(req, exception)
199
# Not logged in. Redirect to login page.
203
query_string = '?url=' + urllib.quote(req.uri, safe="/~")
204
req.throw_redirect('/+login' + query_string)