Merge remote branch 'remotes/gandaro/324-bad-media-types'
[mediagoblin.git] / mediagoblin / decorators.py
1 # GNU MediaGoblin -- federated, autonomous media hosting
2 # Copyright (C) 2011 Free Software Foundation, Inc
3 #
4 # This program is free software: you can redistribute it and/or modify
5 # it under the terms of the GNU Affero General Public License as published by
6 # the Free Software Foundation, either version 3 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 Affero General Public License for more details.
13 #
14 # You should have received a copy of the GNU Affero General Public License
15 # along with this program. If not, see <http://www.gnu.org/licenses/>.
16
17
18 from bson.errors import InvalidId
19 from webob import exc
20
21 from mediagoblin.util import redirect
22 from mediagoblin.db.util import ObjectId
23
24
25 def _make_safe(decorator, original):
26 """
27 Copy the function data from the old function to the decorator.
28 """
29 decorator.__name__ = original.__name__
30 decorator.__dict__ = original.__dict__
31 decorator.__doc__ = original.__doc__
32 return decorator
33
34
35 def require_active_login(controller):
36 """
37 Require an active login from the user.
38 """
39 def new_controller_func(request, *args, **kwargs):
40 if request.user and \
41 request.user.get('status') == u'needs_email_verification':
42 return redirect(request,
43 'mediagoblin.auth.verify_email_notice')
44 elif not request.user or request.user.get('status') != u'active':
45 return exc.HTTPFound(
46 location="%s?next=%s" % (
47 request.urlgen("mediagoblin.auth.login"),
48 request.path_info))
49
50 return controller(request, *args, **kwargs)
51
52 return _make_safe(new_controller_func, controller)
53
54
55 def uses_pagination(controller):
56 """
57 Check request GET 'page' key for wrong values
58 """
59 def wrapper(request, *args, **kwargs):
60 try:
61 page = int(request.GET.get('page', 1))
62 if page < 0:
63 return exc.HTTPNotFound()
64 except ValueError:
65 return exc.HTTPNotFound()
66
67 return controller(request, page=page, *args, **kwargs)
68
69 return _make_safe(wrapper, controller)
70
71
72 def get_user_media_entry(controller):
73 """
74 Pass in a MediaEntry based off of a url component
75 """
76 def wrapper(request, *args, **kwargs):
77 user = request.db.User.find_one(
78 {'username': request.matchdict['user']})
79
80 if not user:
81 return exc.HTTPNotFound()
82
83 media = request.db.MediaEntry.find_one(
84 {'slug': request.matchdict['media'],
85 'state': 'processed',
86 'uploader': user['_id']})
87
88 # no media via slug? Grab it via ObjectId
89 if not media:
90 try:
91 media = request.db.MediaEntry.find_one(
92 {'_id': ObjectId(request.matchdict['media']),
93 'state': 'processed',
94 'uploader': user['_id']})
95 except InvalidId:
96 return exc.HTTPNotFound()
97
98 # Still no media? Okay, 404.
99 if not media:
100 return exc.HTTPNotFound()
101
102 return controller(request, media=media, *args, **kwargs)
103
104 return _make_safe(wrapper, controller)
105
106 def get_media_entry_by_id(controller):
107 """
108 Pass in a MediaEntry based off of a url component
109 """
110 def wrapper(request, *args, **kwargs):
111 try:
112 media = request.db.MediaEntry.find_one(
113 {'_id': ObjectId(request.matchdict['media']),
114 'state': 'processed'})
115 except InvalidId:
116 return exc.HTTPNotFound()
117
118 # Still no media? Okay, 404.
119 if not media:
120 return exc.HTTPNotFound()
121
122 return controller(request, media=media, *args, **kwargs)
123
124 return _make_safe(wrapper, controller)