Add OAuth models, plugin DB migrations, api_auth
[mediagoblin.git] / mediagoblin / plugins / oauth / views.py
1 # GNU MediaGoblin -- federated, autonomous media hosting
2 # Copyright (C) 2011, 2012 MediaGoblin contributors. See AUTHORS.
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 import logging
18 import json
19
20 from webob import exc, Response
21 from urllib import urlencode
22 from uuid import uuid4
23 from datetime import datetime
24 from functools import wraps
25
26 from mediagoblin.tools import pluginapi
27 from mediagoblin.tools.response import render_to_response
28 from mediagoblin.decorators import require_active_login
29 from mediagoblin.messages import add_message, SUCCESS, ERROR
30 from mediagoblin.tools.translate import pass_to_ugettext as _
31 from mediagoblin.plugins.oauth.models import OAuthCode, OAuthToken
32
33 _log = logging.getLogger(__name__)
34
35
36 @require_active_login
37 def authorize(request):
38 # TODO: Check if allowed
39
40 # Client is allowed by the user
41 if True or already_authorized:
42 # Generate a code
43 # Save the code, the client will later use it to obtain an access token
44 # Redirect the user agent to the redirect_uri with the code
45
46 if not 'redirect_uri' in request.GET:
47 add_message(request, ERROR, _('No redirect_uri found'))
48
49 code = OAuthCode()
50 code.code = unicode(uuid4())
51 code.user = request.user
52 code.save()
53
54 redirect_uri = ''.join([
55 request.GET.get('redirect_uri'),
56 '?',
57 urlencode({'code': code.code})])
58
59 _log.debug('Redirecting to {0}'.format(redirect_uri))
60
61 return exc.HTTPFound(location=redirect_uri)
62 else:
63 # Show prompt to allow client to access data
64 # - on accept: send the user agent back to the redirect_uri with the
65 # code parameter
66 # - on deny: send the user agent back to the redirect uri with error
67 # information
68 pass
69 return render_to_response(request, 'oauth/base.html', {})
70
71
72 def access_token(request):
73 if request.GET.get('code'):
74 code = OAuthCode.query.filter(OAuthCode.code == request.GET.get('code'))\
75 .first()
76
77 if code:
78 token = OAuthToken()
79 token.token = unicode(uuid4())
80 token.user = code.user
81 token.save()
82
83 access_token_data = {
84 'access_token': token.token,
85 'token_type': 'what_do_i_use_this_for', # TODO
86 'expires_in':
87 (token.expires - datetime.now()).total_seconds(),
88 'refresh_token': 'This should probably be safe'}
89 return Response(json.dumps(access_token_data))
90
91 error_data = {
92 'error': 'Incorrect code'}
93 return Response(json.dumps(error_data))
94
95
96 @pluginapi.api_auth
97 def api_test(request):
98 if not request.user:
99 return exc.HTTPForbidden()
100
101 user_data = {
102 'username': request.user.username,
103 'email': request.user.email}
104
105 return Response(json.dumps(user_data))