Yelp API,OAuth和Angular和JSONP仅可使用一次 [英] Yelp API, OAuth and Angular with JSONP only works once

查看:92
本文介绍了Yelp API,OAuth和Angular和JSONP仅可使用一次的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

所以这个问题被问到几次,但我相信我终于把问题到底归结了.我正在将Yelp API与Angular一起使用,这需要OAuth 1.0a进行访问.像大多数人一样,我使用的是以下代码:

So this question has been asked several times, but I believe I've finally boiled down exactly what goes wrong here. I'm using the Yelp API with Angular, which requires OAuth 1.0a to access. Like most people doing this type of implementation, I'm using the following code:

.factory('YelpApi', ['$http',
      function ($http) {
        var randomString = function (length, chars) {
          var result = '';
          for (var i = length; i > 0; --i) {
            result += chars[Math.round(Math.random() * (chars.length - 1))];
          }
          return result;
        };

        var retrieveYelp = function (name, callback) {
          var method =  'GET';
          var url =     'http://api.yelp.com/v2/search';
          var params = {
            callback:                 'angular.callbacks._0',
            ll:                       /* hidden */,
            radius_filter:            '3219',
            oauth_consumer_key:       /* hidden */, // consumer key
            oauth_token:              /* hidden */, //Token
            oauth_signature_method:   'HMAC-SHA1',
            oauth_timestamp:          new Date().getTime(),
            oauth_nonce:              randomString(32, '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ'),
            term:                     name || 'food', 
            actionlinks:              true
          }; // end params
          var consumerSecret =        /* hidden */; //Consumer Secret
          var tokenSecret =           /* hidden */; //Token Secret
          var signature = 
            oauthSignature.generate(
              method, 
              url, 
              params, 
              consumerSecret, 
              tokenSecret, 
              { encodeSignature: false }
            ); 
            // end signature
          params['oauth_signature'] = signature;
          console.log('inside yelpapi factory');
          console.log('Term searched for: ' + params.term);
          $http.jsonp(url, { params : params })
            .then(callback, function(err) {
              console.log('An error occured: ', err);
            });
            console.log("inside end of yelpapi factory");
        }; // end retrieveYelp

        return {
          retrieveYelp: retrieveYelp      
        };

      } // end function

    ]) // end factory

使用'angular.callbacks._0'作为回调使它第一次使用是因为它强制它使用第一个回调,但是会中断后续请求. 您实际上应该使用 JSON_CALLBACK正确地增加回调,但这会破坏一切. Yelp生成的错误是无效签名".我认为这是由于Angular在之后已经编码之后才替换JSON_CALLBACK引起的,从而导致预期的签名不同于实际的签名.我正在使用签名生成器.

Using 'angular.callbacks._0' as the callback makes it work the first time as it forces it to use the first callback, however breaks subsequent requests. You are actually supposed to use JSON_CALLBACK to properly increment callbacks, however that breaks everything. The error generated by Yelp is "invalid signature". I believe this is caused by Angular not replacing JSON_CALLBACK until after it's already encoded, thus causing the expected signature to be different than the actual one. I'm using this signature generator.

如何解决这个问题,确保Angular在确保正确生成签名的同时适当增加回调?

推荐答案

我找到了解决问题的丑陋方法.在下面的文章中,描述了如何创建自己的拦截器以增加jsonp回调参数(angular.callbacks._0,angular.callbacks._1等)

I kind of find an ugly way to solve the problem. In following post, there is a description of how to create your own interceptor to increment the jsonp callback parameter (angular.callbacks._0, angular.callbacks._1, etc.)

如何自定义设置angularjs jsonp回调名称?

在我的情况下,此解决方案不起作用.对于yelp和必须在其中创建oauth签名的查询,应在执行jsonp请求之前将param回调分别包含在签名中,然后应将其递增.

One to one this solution didn't work in my case. With yelp and queries where you have to create a oauth signature, the param callback should be included in the signature respectively should then be already incremented before doing the jsonp request.

所以在我的服务中,在执行签名之前和在执行jsonp请求之前,我只是调用计数器以生成新的增量.

So what I did, in my service, before doing the signature and before doing the jsonp request, I just call the counter to generate the new increment.

在您的情况下,我建议您更改代码,如下所示:

In your case, I would then suggest to change your code like following:

var retrieveYelp = function (name, callback) {

// GENERATE increment and use it in the params
var callbackId = angular.callbacks.counter.toString(36);

      var method =  'GET';
      var url =     'http://api.yelp.com/v2/search';
      var params = {
        callback:                 'angular.callbacks._' + callbackId,
        ll:                       /* hidden */,
        radius_filter:            '3219',
        oauth_consumer_key:       /* hidden */, // consumer key
        oauth_token:              /* hidden */, //Token
        oauth_signature_method:   'HMAC-SHA1',
        oauth_timestamp:          new Date().getTime(),
        oauth_nonce:              randomString(32, '0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ'),
        term:                     name || 'food', 
        actionlinks:              true
      };

我同意,我发现该解决方案不是超级骗子,但至少到那时它是可行的,而且似乎没有副作用.

I found that solution not super duper, I'm agree, but well then at least it works and doesn't seems to have side effects.

这篇关于Yelp API,OAuth和Angular和JSONP仅可使用一次的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆