Python 尝试使用Tornado Web创建dropbox

Python 尝试使用Tornado Web创建dropbox,python,oauth,dropbox,tornado,Python,Oauth,Dropbox,Tornado,这是我的mixin文件: import base64 import binascii import hashlib import hmac import logging import time import urllib import urlparse import uuid import tornado.web import tornado.auth from tornado import httpclient from tornado import escape from tornado.h

这是我的mixin文件:

import base64
import binascii
import hashlib
import hmac
import logging
import time
import urllib
import urlparse
import uuid
import tornado.web
import tornado.auth
from tornado import httpclient
from tornado import escape
from tornado.httputil import url_concat
from tornado.util import bytes_type, b

class DropboxMixin(tornado.auth.OAuthMixin):
    """ Dropbox  OAuth authentication.
    """
    _OAUTH_REQUEST_TOKEN_URL = "https://api.dropbox.com/1/oauth/request_token"
    _OAUTH_ACCESS_TOKEN_URL = "https://api.dropbox.com/1/oauth/access_token"
    _OAUTH_AUTHORIZE_URL = "https://www.dropbox.com/1/oauth/authorize"

    def authorize_redirect(self, callback_uri=None, extra_params=None,
                           http_client=None):
        """Redirects the user to obtain OAuth authorization for this service.

        Twitter and FriendFeed both require that you register a Callback
        URL with your application. You should call this method to log the
        user in, and then call get_authenticated_user() in the handler
        you registered as your Callback URL to complete the authorization
        process.

        This method sets a cookie called _oauth_request_token which is
        subsequently used (and cleared) in get_authenticated_user for
        security purposes.
        """
        if callback_uri and getattr(self, "_OAUTH_NO_CALLBACKS", False):
            raise Exception("This service does not support oauth_callback")
        if http_client is None:
            http_client = httpclient.AsyncHTTPClient()
        http_client.fetch(
                          self._oauth_request_token_url(),
                          self.async_callback(
                                self._on_request_token, self._OAUTH_AUTHORIZE_URL,
                                callback_uri))

    def get_authenticated_user(self, callback, http_client=None):
        """Gets the OAuth authorized user and access token on callback.

        This method should be called from the handler for your registered
        OAuth Callback URL to complete the registration process. We call
        callback with the authenticated user, which in addition to standard
        attributes like 'name' includes the 'access_key' attribute, which
        contains the OAuth access you can use to make authorized requests
        to this service on behalf of the user.

        """
        request_key = escape.utf8(self.get_argument("oauth_token"))
        oauth_verifier = self.get_argument("oauth_verifier", None)
        request_cookie = self.get_cookie("_oauth_request_token")
        if not request_cookie:
            logging.warning("Missing OAuth request token cookie")
            callback(None)
            return
        self.clear_cookie("_oauth_request_token")
        cookie_key, cookie_secret = [base64.b64decode(escape.utf8(i)) for i in request_cookie.split("|")]
        if cookie_key != request_key:
            logging.info((cookie_key, request_key, request_cookie))
            logging.warning("Request token does not match cookie")
            callback(None)
            return
        token = dict(key=cookie_key, secret=cookie_secret)
        if oauth_verifier:
            token["verifier"] = oauth_verifier
        if http_client is None:
            http_client = httpclient.AsyncHTTPClient()
        http_client.fetch(self._oauth_access_token_url(token),
                          self.async_callback(self._on_access_token, callback))

    def dropbox_request(self, path, callback, access_token=None,
                        post_args=None, **args):
        # Add the OAuth resource request signature if we have credentials
        url = "http://api.dropbox.com/1" + path
如果有人在意,url应该是“+路径”

我的看法

class DropboxIndex(BaseHandler, DropboxMixin):
    @tornado.web.asynchronous
    def get(self):
        if self.get_argument("oauth_token", None):
            self.get_authenticated_user(self.async_callback(self._on_dbox_auth))
            return
        self.authorize_redirect()

    def _on_dbox_auth(self, token):
        from pprint import pprint
        pprint(token)
        self.redirect("/app/dropbox")
我的URL模式

patterns = [
    (r"/", Index),
    (r"/help/?", Help),
    # User authentication
    (r"/user/login/?", Login),
    (r"/user/logout/?", LogoutHandler),
    (r"/user/edit/?", IdentityIndex),
    (r"/user/register/?", Register),
    (r"/user/twitter/auth/?", TwitterLogin),
    #(r"/user/google/auth/?", GoogleLogin),
    (r"/user/facebook/auth/?", FacebookLogin),
    (r"/app/dropbox/?", DropboxIndex),
    (r"/app/dropbox/account/?", DropboxAccount),
    (r"/social/?", SocialIndex),
    (r"/api/tweets/?", apiSocialTweets),
    (r"/media/(.*)", tornado.web.StaticFileHandler, {"path" : static_serve}), 
]

除了使用oauth_令牌返回我的回调uri之外,一切都正常。我在查询中看到了oauth_令牌,并可以使用dropbox授权我的应用程序。我只是无法获得oauth_令牌并可使用。

好吧,这是一段需要花费大量时间的代码,如果我的回答没有多大帮助,请原谅-

Urllib/Urllib2与处理异步请求非常不兼容。如果必须使用Urllib,您可以跟进问题了解原因和解决方案

我建议您在代码中使用httplib,如果这有帮助或者您想知道更多,请发表评论

谢谢 苏珊特

patterns = [
    (r"/", Index),
    (r"/help/?", Help),
    # User authentication
    (r"/user/login/?", Login),
    (r"/user/logout/?", LogoutHandler),
    (r"/user/edit/?", IdentityIndex),
    (r"/user/register/?", Register),
    (r"/user/twitter/auth/?", TwitterLogin),
    #(r"/user/google/auth/?", GoogleLogin),
    (r"/user/facebook/auth/?", FacebookLogin),
    (r"/app/dropbox/?", DropboxIndex),
    (r"/app/dropbox/account/?", DropboxAccount),
    (r"/social/?", SocialIndex),
    (r"/api/tweets/?", apiSocialTweets),
    (r"/media/(.*)", tornado.web.StaticFileHandler, {"path" : static_serve}), 
]