├── .gitignore
├── examples
└── example_project
│ ├── __init__.py
│ ├── fbconnect
│ ├── __init__.py
│ ├── models.py
│ └── views.py
│ ├── manage.py
│ ├── settings.py
│ ├── templates
│ ├── myfriends.html
│ └── welcome.html
│ └── urls.py
├── readme.markdown
├── setup.py
└── src
└── fbpy
├── __init__.py
├── extras.py
├── facebook.py
└── middleware.py
/.gitignore:
--------------------------------------------------------------------------------
1 | *.pyc
2 | *.db
3 | .idea
4 | .idea/*
--------------------------------------------------------------------------------
/examples/example_project/__init__.py:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/emre/fb.py/1eae613c7dd6e2a652eee312df3a9371f91be837/examples/example_project/__init__.py
--------------------------------------------------------------------------------
/examples/example_project/fbconnect/__init__.py:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/emre/fb.py/1eae613c7dd6e2a652eee312df3a9371f91be837/examples/example_project/fbconnect/__init__.py
--------------------------------------------------------------------------------
/examples/example_project/fbconnect/models.py:
--------------------------------------------------------------------------------
1 | from django.db import models
2 |
3 | # Create your models here.
4 |
--------------------------------------------------------------------------------
/examples/example_project/fbconnect/views.py:
--------------------------------------------------------------------------------
1 | from django.http import HttpResponse, HttpResponseRedirect
2 | from django.template import RequestContext
3 | from django.shortcuts import render_to_response
4 | from django.contrib.csrf.middleware import csrf_exempt
5 |
6 | from fbpy.extras import require_facebook_login
7 |
8 | @csrf_exempt
9 | def index(request):
10 | if not request.facebook.is_authenticated():
11 | return HttpResponseRedirect(request.facebook.get_login_url())
12 | else:
13 | user_info = request.facebook.graph().get_object("me")
14 | return render_to_response("welcome.html", user_info, context_instance = RequestContext(request))
15 |
16 | @csrf_exempt
17 | def myfriends(request):
18 | if request.facebook.is_authenticated():
19 | print request.facebook.auth_token
20 | friends = request.facebook.graph().get_object("me/friends")
21 | for friend in friends["data"]:
22 | friend["avatar_url"] = request.facebook.graph().get_picture(friend["id"],"small")
23 |
24 | return render_to_response("myfriends.html", {"entries": friends["data"]}, context_instance = RequestContext(request))
25 | else:
26 | return HttpResponseRedirect(request.facebook.get_login_url())
27 |
28 | @csrf_exempt
29 | @require_facebook_login
30 | def facebook_login_required_view(request):
31 | return HttpResponse("oo hai.")
32 |
33 | @csrf_exempt
34 | def view_with_no_access(request):
35 | user_info = request.facebook.graph().get_object("emre.py")
36 | return HttpResponse(str(user_info))
37 |
38 | @csrf_exempt
39 | def extra_arguments_example(request):
40 | photos = request.facebook.graph().get_object("103688113031204/photos", {"limit": 5})
41 | return HttpResponse(str(photos))
42 |
43 |
44 |
45 |
46 |
47 |
48 |
--------------------------------------------------------------------------------
/examples/example_project/manage.py:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env python
2 | from django.core.management import execute_manager
3 | try:
4 | import settings # Assumed to be in the same directory.
5 | except ImportError:
6 | import sys
7 | sys.stderr.write("Error: Can't find the file 'settings.py' in the directory containing %r. It appears you've customized things.\nYou'll have to run django-admin.py, passing it your settings module.\n(If the file settings.py does indeed exist, it's causing an ImportError somehow.)\n" % __file__)
8 | sys.exit(1)
9 |
10 | if __name__ == "__main__":
11 | execute_manager(settings)
12 |
--------------------------------------------------------------------------------
/examples/example_project/settings.py:
--------------------------------------------------------------------------------
1 | # -*- coding: utf8 -*-
2 |
3 | import os
4 |
5 | DEBUG = True
6 | TEMPLATE_DEBUG = DEBUG
7 |
8 | ADMINS = (
9 | # ('Your Name', 'your_email@domain.com'),
10 | )
11 |
12 | MANAGERS = ADMINS
13 |
14 | DATABASES = {
15 | 'default': {
16 | 'ENGINE': 'django.db.backends.sqlite3', # Add 'postgresql_psycopg2', 'postgresql', 'mysql', 'sqlite3' or 'oracle'.
17 | 'NAME': 'ehe.db', # Or path to database file if using sqlite3.
18 | 'USER': '', # Not used with sqlite3.
19 | 'PASSWORD': '', # Not used with sqlite3.
20 | 'HOST': '', # Set to empty string for localhost. Not used with sqlite3.
21 | 'PORT': '', # Set to empty string for default. Not used with sqlite3.
22 | }
23 | }
24 |
25 | BASE_URL = 'http://localhost:8000'
26 | BASE_PATH = os.path.realpath(os.path.dirname(__file__))
27 | PROJECT_PATH = os.path.realpath(os.path.dirname(__file__))
28 | MEDIA_ROOT = os.path.join(PROJECT_PATH, 'media')
29 |
30 | # Local time zone for this installation. Choices can be found here:
31 | # http://en.wikipedia.org/wiki/List_of_tz_zones_by_name
32 | # although not all choices may be available on all operating systems.
33 | # On Unix systems, a value of None will cause Django to use the same
34 | # timezone as the operating system.
35 | # If running in a Windows environment this must be set to the same as your
36 | # system time zone.
37 | TIME_ZONE = 'America/Chicago'
38 |
39 |
40 | # Language code for this installation. All choices can be found here:
41 | # http://www.i18nguy.com/unicode/language-identifiers.html
42 | LANGUAGE_CODE = 'en-us'
43 |
44 | SITE_ID = 1
45 |
46 | # If you set this to False, Django will make some optimizations so as not
47 | # to load the internationalization machinery.
48 | USE_I18N = True
49 |
50 | # If you set this to False, Django will not format dates, numbers and
51 | # calendars according to the current locale
52 | USE_L10N = True
53 |
54 | # Absolute path to the directory that holds media.
55 | # Example: "/home/media/media.lawrence.com/"
56 | MEDIA_ROOT = ''
57 |
58 | # URL that handles the media served from MEDIA_ROOT. Make sure to use a
59 | # trailing slash if there is a path component (optional in other cases).
60 | # Examples: "http://media.lawrence.com", "http://example.com/media/"
61 | MEDIA_URL = ''
62 |
63 | # URL prefix for admin media -- CSS, JavaScript and images. Make sure to use a
64 | # trailing slash.
65 | # Examples: "http://foo.com/media/", "/media/".
66 | ADMIN_MEDIA_PREFIX = '/media/'
67 |
68 | # Make this unique, and don't share it with anybody.
69 | SECRET_KEY = 'vqg*ja58-gqmfz2d=jl8cj16h6tlk$r*x66s5gfo1czwe5m+o-'
70 |
71 | # List of callables that know how to import templates from various sources.
72 | TEMPLATE_LOADERS = (
73 | 'django.template.loaders.filesystem.Loader',
74 | 'django.template.loaders.app_directories.Loader',
75 | # 'django.template.loaders.eggs.Loader',
76 | )
77 |
78 | MIDDLEWARE_CLASSES = (
79 | 'django.middleware.common.CommonMiddleware',
80 | 'django.contrib.sessions.middleware.SessionMiddleware',
81 | 'django.middleware.csrf.CsrfViewMiddleware',
82 | 'django.contrib.auth.middleware.AuthenticationMiddleware',
83 | 'django.contrib.messages.middleware.MessageMiddleware',
84 | 'fbpy.middleware.FBPYMiddleware',
85 | )
86 |
87 | ROOT_URLCONF = 'example_project.urls'
88 |
89 | TEMPLATE_DIRS = (
90 | "%s/templates" % BASE_PATH,
91 | )
92 |
93 | INSTALLED_APPS = (
94 | 'django.contrib.auth',
95 | 'django.contrib.contenttypes',
96 | 'django.contrib.sessions',
97 | 'django.contrib.sites',
98 | 'django.contrib.messages',
99 | # Uncomment the next line to enable the admin:
100 | # 'django.contrib.admin',
101 | )
102 |
103 | FACEBOOK_CONFIG = {
104 | "redirect_uri" : "%s/fbconnect" % BASE_URL,
105 | "scope" : 'email,publish_stream,offline_access,user_hometown,user_location',
106 | "api_key" : "[fb_app_api_key]",
107 | "app_secret" : "[fb_app_secret]",
108 | "app_id" : "[fb_app_id]",
109 | }
110 |
111 |
112 |
113 |
114 |
115 |
116 |
--------------------------------------------------------------------------------
/examples/example_project/templates/myfriends.html:
--------------------------------------------------------------------------------
1 | {% for item in entries %}
2 |
3 | {% endfor %}
4 |
--------------------------------------------------------------------------------
/examples/example_project/templates/welcome.html:
--------------------------------------------------------------------------------
1 |
2 | name: {{name}}
3 | email: {{email}}
4 |
5 |
6 |
7 |
8 |
9 |
21 |
22 |
--------------------------------------------------------------------------------
/examples/example_project/urls.py:
--------------------------------------------------------------------------------
1 | from django.conf.urls.defaults import *
2 |
3 | # Uncomment the next two lines to enable the admin:
4 | # from django.contrib import admin
5 | # admin.autodiscover()
6 |
7 | from fbconnect.views import index, myfriends, facebook_login_required_view, view_with_no_access, extra_arguments_example
8 |
9 | urlpatterns = patterns('',
10 | # Example:
11 | # (r'^trailer/', include('trailer.foo.urls')),
12 |
13 | # Uncomment the admin/doc line below and add 'django.contrib.admindocs'
14 | # to INSTALLED_APPS to enable admin documentation:
15 | # (r'^admin/doc/', include('django.contrib.admindocs.urls')),
16 |
17 | # Uncomment the next line to enable the admin:
18 | # (r'^admin/', include(admin.site.urls)),
19 | url('^fbconnect/$', index, name = "index"),
20 | url('^fbconnect/myfriends$', myfriends, name = "myfriends"),
21 | url('^no_auth', view_with_no_access, name = "view_with_no_access"),
22 | url('^login_required/$', facebook_login_required_view, name = "facebook_login_required_view"),
23 | url('^extra_arguments/$', extra_arguments_example, name = "extra_arguments_example"),
24 | )
25 |
--------------------------------------------------------------------------------
/readme.markdown:
--------------------------------------------------------------------------------
1 | fb.py
2 | =================
3 |
4 | fb.py is a software development kit for Facebook. It supports both old rest api
5 | and new graph api. it uses oauth, old style signature/secretkey based api calls
6 | for old rest api are not supported at this time.
7 |
8 | you can find official documentation at facebook about api calls and methods.
9 |
10 | 1) old rest api: http://developers.facebook.com/docs/reference/rest/
11 | 2) graph api: http://graph.facebook.com
12 |
13 | dependencies
14 | =================
15 | 1) python-simplejson
16 |
17 | installation
18 | =================
19 |
20 | 1) get the archive.
21 | 2) run python setup.py install (with root priviliges)
22 |
23 | usage in Django
24 | =================
25 |
26 | 1) add these lines to your settings.py
27 |
28 | FACEBOOK_CONFIG = {
29 | "redirect_uri" : "%s/fbconnect" % BASE_URL,
30 | "scope" : 'email,publish_stream,offline_access,user_hometown,user_location',
31 | "api_key" : "[INSERT_API_KEY_HERE]",
32 | "app_secret" : "[INSERT_APPLICATION_SECRET_HERE]",
33 | "app_id" : "[INSERT_APPLICATION_ID_HERE]",
34 | }
35 |
36 | 2) add to your MIDDLEWARE_CLASSES:
37 |
38 | fbpy.middleware.FBPYMiddleware
39 |
40 |
41 | 5) after these steps, you can call FBPY instance as request.facebook. a simple view example:
42 |
43 | if not request.facebook.is_authenticated():
44 | return HttpResponseRedirect(request.facebook.get_login_url())
45 | else:
46 | user_info = request.facebook.graph().get_object("me")
47 | return render_to_response("welcome.html", user_info, context_instance = RequestContext(request))
48 |
49 |
50 | 6) read the code/wait for more documentation. fb.py is one python file with inline documentation, so browsing the code is a good idea than waiting a fully documentation.
51 |
52 | installation of "example_project"
53 | =================
54 |
55 | 1) there is a sandbox django project in example_project directory.
56 |
57 | 2) download it and edit settings.py. (FACEBOOK_CONFIG variable.)
58 |
59 | 3) run python manage.py syncdb (we need sessions!)
60 |
61 | 4) run python manage.py runserver
62 |
63 | 5) go to your web browser, and see 127.0.0.1:8000/fbconnect
64 |
65 |
66 | low level api
67 | =================
68 |
69 | 1) in order to send calls to new graph api, a simple request should be like that:
70 | reply = request.facebook.graph().get_object("me")
71 |
72 | 2) old rest api example: (taking mutual friends for a spesific profile id)
73 | reply = request.facebook.rest().get_object("friends.getMutualFriends", target_uid = profile_id)
74 |
75 | 3) happy hacking!
76 |
77 | to-do
78 | =================
79 |
80 | 1) more documentation.
81 |
82 | 2) handling cookie/session storage in FBPY.
83 |
84 | thanks
85 | =================
86 |
87 | 1) Timu Eren & Yilmaz Ugurlu - suggestions and ideas.
88 |
89 |
90 | for donations:
91 | =================
92 |
93 |
94 |
--------------------------------------------------------------------------------
/setup.py:
--------------------------------------------------------------------------------
1 | #!/usr/bin/env python
2 |
3 | from setuptools import setup
4 |
5 | setup(name='fbpy',
6 | version='0.2',
7 | description='python sdk for facebook apis',
8 | author='Emre Yilmaz',
9 | author_email='mail@emreyilmaz.me',
10 | url='http://github.com/emre/fb.py',
11 | package_dir={'': 'src'},
12 | packages = ["fbpy"]
13 | )
14 |
15 |
16 |
--------------------------------------------------------------------------------
/src/fbpy/__init__.py:
--------------------------------------------------------------------------------
1 | from facebook import *
2 |
3 | __version__ = '0.2'
4 |
--------------------------------------------------------------------------------
/src/fbpy/extras.py:
--------------------------------------------------------------------------------
1 | # -*- coding: utf8 -*-
2 |
3 | from django.http import HttpResponseRedirect
4 |
5 | def require_facebook_login(function):
6 | """
7 | login_required decorator for views.
8 | """
9 | def wrap(request, *args, **kwargs):
10 | if not request.facebook.is_authenticated():
11 | return HttpResponseRedirect(request.facebook.get_login_url())
12 | return function(request, *args, **kwargs)
13 | return wrap
14 |
--------------------------------------------------------------------------------
/src/fbpy/facebook.py:
--------------------------------------------------------------------------------
1 | # -*- coding: utf8 -*-
2 |
3 | import urllib, simplejson
4 |
5 | """
6 | fb.py is a python client library for facebook api. it supports both *old rest api*
7 | and *new graph api*.
8 |
9 | you can find official documentation at facebook:
10 | * old rest api: http://developers.facebook.com/docs/reference/rest/
11 | * graph api: http://graph.facebook.com
12 |
13 | for the installation tips and usage examples, take a look to the readme.
14 |
15 | Copyright (c) 2010 emre yilmaz
16 |
17 | Permission is hereby granted, free of charge, to any person obtaining a copy
18 | of this software and associated documentation files (the "Software"), to deal
19 | in the Software without restriction, including without limitation the rights
20 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
21 | copies of the Software, and to permit persons to whom the Software is
22 | furnished to do so, subject to the following conditions:
23 |
24 | The above copyright notice and this permission notice shall be included in
25 | all copies or substantial portions of the Software.
26 |
27 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
28 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
29 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
30 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
31 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
32 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
33 | THE SOFTWARE.
34 |
35 | """
36 |
37 |
38 |
39 | class GraphApiException(Exception):
40 | """
41 | custom exception class for graph api response errors.
42 | """
43 | def __init__(self, type, message):
44 | Exception.__init__(self, message)
45 | self.type = type
46 |
47 | class RestApiException(Exception):
48 | """
49 | custom exception class for rest api response errors.
50 | """
51 | def __init__(self, error_code, message):
52 | Exception.__init__(self, message)
53 | self.error_code = error_code
54 |
55 | class RestApi(object):
56 | """
57 | Facebook RestApi Backend For the FBPY.
58 | documentation for the official methods can be found at: http://developers.facebook.com/docs/reference/rest/
59 | """
60 |
61 | def __init__(self, token):
62 | self.auth_token = token
63 |
64 | def _handle_errors(self, api_response):
65 | """
66 | handles api-response errors
67 | """
68 | if isinstance(api_response, dict) and api_response.has_key("error_code"):
69 | raise RestApiException(api_response["error_code"], api_response["error_msg"])
70 |
71 | def get_object(self, call_method, **kargs):
72 | """
73 | @params:
74 | - call_method : method for the rest api.
75 | (http://developers.facebook.com/docs/reference/rest/)
76 | -
77 | """
78 | return self._get_request(call_method, **kargs)
79 |
80 | def _get_request(self, call_method, **kargs):
81 | """
82 | makes a HTTP (GET) request to the facebook rest api servers for given parameters.
83 | """
84 | query_string = {
85 | "access_token": self.auth_token,
86 | "format": "json"
87 | }
88 | query_string.update(kargs)
89 | f = urllib.urlopen("https://api.facebook.com/method/%s?%s" % (call_method, urllib.urlencode(query_string)))
90 | api_response = simplejson.loads(f.read())
91 | self._handle_errors(api_response)
92 |
93 | return api_response
94 |
95 |
96 | class GraphApi(object):
97 | """
98 | Facebook GraphApi Backend For the FBPY.
99 | documentation for the official methods can be found at: https://graph.facebook.com/
100 | """
101 |
102 | def __init__(self, token):
103 | self.auth_token = token
104 |
105 | @property
106 | def auth_status(self):
107 | if not self.auth_token:
108 | return False
109 |
110 | return True
111 |
112 | def get_object(self, request_path, extra_params = None):
113 | """
114 | gets the given object from facebook api.
115 | """
116 | return self._get_request(request_path, extra_params)
117 |
118 |
119 | def put_object(self, request_path, post_data):
120 | """
121 | puts the given object to the facebook api_key.
122 | """
123 | return self._put_request(request_path, post_data)
124 |
125 | def _handle_errors(self, api_response):
126 | """
127 | handles api-response errors
128 | """
129 | if isinstance(api_response, dict) and api_response.has_key("error"):
130 | raise GraphApiException(api_response["error"]["type"], api_response["error"]["message"])
131 |
132 | def _get_request(self, request_path, extra_params = None):
133 | """
134 | makes a HTTP (GET) request to the facebook graph api servers for given parameters.
135 | (just for the information getter methods.)
136 | """
137 | parameters = {}
138 |
139 | if self.auth_status:
140 | parameters.update({
141 | "access_token" : self.auth_token,
142 | })
143 |
144 | if extra_params:
145 | parameters.update(extra_params)
146 |
147 | f = urllib.urlopen("https://graph.facebook.com/%s?%s" % (request_path, urllib.urlencode(parameters)))
148 |
149 | api_response = simplejson.loads(f.read())
150 | self._handle_errors(api_response)
151 |
152 | return api_response
153 |
154 |
155 | def get_picture(self, user_alias, picture_size = None):
156 | """
157 | shortcut method to retrieve user avatars easily by selected size.
158 | possible types: small, square, large.
159 | example:
160 | - fbpy_instance.graph().get_picture(USER_ID, "small")
161 | """
162 | extra_params = {}
163 | if user_alias == 'me':
164 | result = self.get_object("me")
165 | user_alias = result["id"]
166 | if picture_size and picture_size in ["small", "square", "large"]:
167 | extra_params.update({
168 | "type": picture_size,
169 | })
170 |
171 | return "https://graph.facebook.com/%s/picture?%s" % (user_alias, urllib.urlencode(extra_params))
172 |
173 | def _put_request(self, request_path, post_data):
174 | """
175 | makes a HTTP (POST) request to the facebook graph api servers for given parameters.
176 | (just for the information setter methods.)
177 | """
178 | post_data.update({
179 | "access_token": self.auth_token,
180 | })
181 |
182 | if post_data:
183 | for key, value in post_data.iteritems():
184 | if isinstance(value, unicode): post_data[key] = value.encode("utf8")
185 | post_data = urllib.urlencode(post_data)
186 | f = urllib.urlopen("https://graph.facebook.com/%s" % request_path, post_data)
187 | api_response = simplejson.loads(f.read())
188 | self._handle_errors(api_response)
189 |
190 | return api_response
191 |
192 | def put_wall_post(self, user_alias, post_data):
193 | """
194 | helper/shortcut function for wall postings
195 | @params:
196 | - user alias (profile id or username)
197 | - post_data (dictionary)
198 | - example = {
199 | "message": "foo bar",
200 | "picture": "https://github.com/images/modules/header/logov3.png",
201 | "link" : "http://www.github.com/emre/",
202 | "name" : "github logo",
203 | "description": "buraya bakarlar description alani"
204 | }
205 | if you want to post to your running user's wall, just send user_alias parameter as "me".
206 | """
207 | return self._put_request("%s/feed" % user_alias, post_data)
208 |
209 | class FBPY(object):
210 |
211 | # config dict for usual operations
212 | CONFIG = {
213 | "scope" : None,
214 | "redirect_uri" : None,
215 | "api_key" : None,
216 | "app_id" : None,
217 | "app_secret" : None,
218 | }
219 |
220 | def __init__(self, token = None):
221 | self.auth_token = token
222 | self.graph_api_instance = None
223 | self.rest_api_instance = None
224 | self.user_id = 0
225 |
226 | def set_config(self, config):
227 | """
228 | setter for FBPY config attribute.
229 | """
230 | FBPY.CONFIG.update(config)
231 |
232 | def get_config(self):
233 | """
234 | getter for FBPY config attribute.
235 | """
236 | return FBPY.CONFIG
237 |
238 | def set_token(self, token):
239 | """
240 | setter for FBPY oauth token.
241 | """
242 | self.auth_token = token
243 |
244 | def set_uid(self, uid):
245 | """
246 | setter for autenticated user id on facebook.
247 | """
248 | self.user_id = uid
249 |
250 | def get_uid(self):
251 | """
252 | return facebook id.
253 | """
254 | return self.user_id
255 |
256 | def is_authenticated(self):
257 | """
258 | returns authenticate status.
259 | """
260 | return bool(self.auth_token)
261 |
262 | def graph(self):
263 | """
264 | returns graph api interface
265 | """
266 | if not self.graph_api_instance:
267 | self.graph_api_instance = GraphApi(self.auth_token)
268 |
269 | return self.graph_api_instance
270 |
271 | def rest(self):
272 | """
273 | returns rest api interface
274 | """
275 | if not self.rest_api_instance:
276 | self.rest_api_instance = RestApi(self.auth_token)
277 |
278 | return self.rest_api_instance
279 |
280 | @staticmethod
281 | def get_login_url(params = {}):
282 | """
283 | gets the login url to the your facebook application
284 | @params:
285 | - api_key (if exists in FBPY.CONFIG, not required)
286 | - cancel_url (if exists in FBPY.CONFIG, not required)
287 | - next (if exists in FBPY.CONFIG, not required)
288 | - req_perms (if exists in FBPY.CONFIG, not required)
289 | """
290 | query_string = {}
291 |
292 | # load default config
293 | query_string.update({
294 | "client_id" : FBPY.CONFIG.get("app_id"),
295 | "redirect_uri" : FBPY.CONFIG.get("redirect_uri"),
296 | "scope" : FBPY.CONFIG.get("scope"),
297 | })
298 |
299 | query_string.update(params)
300 |
301 | return "https://www.facebook.com/dialog/oauth?%s" % urllib.urlencode(query_string)
302 |
303 | @staticmethod
304 | def get_redirect_html(params = {}):
305 | redirect_url = FBPY.get_login_url(params)
306 | return "" % redirect_url
307 |
308 | @staticmethod
309 | def get_logout_url(params):
310 | """
311 | gets the logout url:
312 | @params:
313 | - api_key (if exists in FBPY.CONFIG, not required)
314 | - next (if exists in FBPY.CONFIG, not required)
315 | - session_key (required)
316 | """
317 | default_params = {
318 | "api_key": FBPY.CONFIG.get("api_key"),
319 | "next" : FBPY.CONFIG.get("logout_next_url"),
320 | }
321 |
322 | if not params.has_key("session_key"):
323 | raise Exception("session_key is required for get_logout_url method.")
324 |
325 | default_params.update(params)
326 | return "https://www.facebook.com/logout.php?%s" % urllib.urlencode(default_params)
327 |
328 |
329 |
330 |
331 |
332 |
--------------------------------------------------------------------------------
/src/fbpy/middleware.py:
--------------------------------------------------------------------------------
1 | # -*- coding: utf8 -*-
2 |
3 | import urllib, re, sys
4 |
5 | from fbpy import FBPY
6 | from string import split
7 |
8 | from django.conf import settings
9 |
10 | def get_token_from_facebook(code):
11 | """
12 | gets auth token for the returned code from Facebook.
13 | """
14 | query_string = {
15 | "client_id" : settings.FACEBOOK_CONFIG.get("app_id"),
16 | "redirect_uri" : settings.FACEBOOK_CONFIG.get("redirect_uri"),
17 | "client_secret" : settings.FACEBOOK_CONFIG.get("app_secret"),
18 | "code" : code,
19 | }
20 | content = urllib.urlopen("https://graph.facebook.com/oauth/access_token?%s" % urllib.urlencode(query_string)).read()
21 |
22 | return content
23 |
24 | class FBPYMiddleware(object):
25 |
26 | def process_request(self, request):
27 | facebook = getattr('request', 'facebook', None)
28 | if not facebook:
29 | request.facebook = FBPY()
30 | request.facebook.set_config(settings.FACEBOOK_CONFIG)
31 | if request.session.has_key("token_string"):
32 | token_string = split(request.session.get("token_string"), '&')[0]
33 | request.facebook.set_token(token_string)
34 |
35 | # if facebook returned back the user session, register it.
36 | if request.GET.has_key("code"):
37 | try:
38 | auth_response = get_token_from_facebook(request.GET.get("code"))
39 | token_string = re.search('access_token=([^&]*)', auth_response).group(1)
40 | request.facebook.set_token(token_string)
41 | # cache in session
42 | request.session["token_string"] = token_string
43 | except Exception, error:
44 | pass
45 |
46 | def process_response(self, request, response):
47 | """
48 | internet explorer fix for iframe typed facebook applications.
49 | """
50 | response['P3P'] = 'CP="NOI DSP COR NID ADMa OPTa OUR NOR"'
51 | return response
52 |
53 |
54 |
--------------------------------------------------------------------------------