MrSwitch / hello.js

A Javascript RESTFUL API library for connecting with OAuth2 services, such as Google+ API, Facebook Graph and Windows Live Connect
https://adodson.com/hello.js/
MIT License
4.63k stars 548 forks source link

Tumblr POST-ing #135

Closed btosic closed 9 years ago

btosic commented 9 years ago

Hello,

I'm trying to POST a message to Tumblr so I have set up a 'xhr' parameter to use proxy server:

hello.init({
    'tumblr' : {
        // Set default window height
        login : function(p){
            p.options.window_width = 600;
            p.options.window_height = 510;
        },      

        // Ensure that you define an oauth_proxy
        oauth : {
            version : "1.0a",
            auth    : "https://www.tumblr.com/oauth/authorize",
            request : 'https://www.tumblr.com/oauth/request_token',
            token   : 'https://www.tumblr.com/oauth/access_token'
        },

        base    : "https://api.tumblr.com/v2/",

        get : {
            me      : 'user/info'
        },

        post : {
            "me/like" : function(p, callback){
                p.data = JSON.stringify(p.data);
                callback('user/like');
            }
        },

        wrap : {
            me : function(o){
                if(o&&o.response&&o.response.user){
                    o = o.response.user;
                }
                return o;
            }
        },

        xhr : function(p,qs){
            if(p.method !== 'get'){
                p.headers['Content-Type'] = 'application/json';
                p.proxy = true;
                return true;
            }
            return false;
        }
    }
});

I tested this setup with 'me/like' verb and I'm sending this message:

body = {
          id: 123, // number type
          reblog_key: "456" // string type 
        };

Message is based on Tumblr API: https://www.tumblr.com/docs/en/api/v2#m-up-like

When this is sent, Tumblr returns this message:

{
"meta": {
    "status":400,
    "msg":"Bad Request"
    },
"response": {
    "message":"missing  'id' or 'reblog_key' arguments"
}
} 

My guess is that proxy server maybe ignores or converts number values in JSON ('id' argument has to be number)?

MrSwitch commented 9 years ago

I couldn't see anything in the docs about setting p.headers['Content-Type'] = 'application/json'; or JSON.stringify(p.data);

Also: no need to define p.proxy = true, that's implied by oauth.version : "1.0a"

btosic commented 9 years ago

Thanks for the reply. I have removed JSON.stringify and updated my xhr method to following:

xhr : function(p,qs){
    if(p.method !== 'get'){
        return true;
    }
    return false;
}

The request is now posted as multipart/form-data. Error message regarding parameters is no longer returned, but not I get 'Not Authorized':

{"meta": {
    "status":401,
    "msg":"Not Authorized"
    },
    "response":[]
}

Here is the request and response:

Request

POST /proxy?path=https%3A%2F%2Fapi.tumblr.com%2Fv2%2Fuser%2Flike&access_token=lp0CNCYWJ1KAZiJuEjAyjpasMPABVSfuLfIITEGtNHjbzWpSnP%3Am2iD4moDHpNSMB99nKswy3LIkAhUwqFq78OEeGhaiirA3hFFXa%40ppoJ62sVunHWNpc6JeMX1YSTpYt49iCKFVD38WPrsAfaIU4b9Z&then=proxy&method=post&suppress_response_codes=true HTTP/1.1
Host: auth-server.herokuapp.com
Connection: keep-alive
Content-Length: 250
Origin: http://localhost:8080
User-Agent: Mozilla/5.0 (Macintosh; Intel Mac OS X 10_9_5) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/38.0.2125.111 Safari/537.36
Content-Type: multipart/form-data; boundary=----WebKitFormBoundaryTYlQ23187ZwdVikw
Accept: */*
Referer: http://localhost:8080/index.html
Accept-Encoding: gzip,deflate
Accept-Language: en-US,en;q=0.8,hr;q=0.6,nl;q=0.4,fr;q=0.2

------WebKitFormBoundaryTYlQ23187ZwdVikw
Content-Disposition: form-data; name="id"

101510996286
------WebKitFormBoundaryTYlQ23187ZwdVikw
Content-Disposition: form-data; name="reblog_key"

619YK20j
------WebKitFormBoundaryTYlQ23187ZwdVikw--

Response

HTTP/1.1 200 OK
Connection: keep-alive
Server: nginx
Date: Sun, 02 Nov 2014 10:40:25 GMT
Content-Type: application/json; charset=utf-8
Set-Cookie: tmgioct=54560a19e5f2300467891840; expires=Wed, 30-Oct-2024 10:40:25 GMT; path=/; httponly
P3p: CP="ALL ADM DEV PSAi COM OUR OTRo STP IND ONL"
Access-Control-Allow-Methods: OPTIONS, TRACE, GET, HEAD, POST, PUT
Access-Control-Allow-Origin: *
Transfer-Encoding: chunked
Via: 1.1 vegur

{"meta":{"status":401,"msg":"Not Authorized"},"response":[]}

API docs say that for /user/like resource OAuth is used. Do you know if I need to configure anything else in order to have the proxy perform the authentication? GET requests work fine (getting posts for example), but they require only API key for access, while this uses OAuth. Thanks in advance.

MrSwitch commented 9 years ago

Ah blocker ...

The API supports the OAuth 1.0a Protocol, accepting parameters via the Authorization header,...

The node-oauth-shim needs a code change to sign the requests via the Authorization header.

If you want to give it a shot i'd be happy to merge it ASAP. Otherwise i'll give it a stab in the week.

btosic commented 9 years ago

Hm, I'm not proficient in node.js. If you plan to work on it next week, I'd rather wait. Thanks!

MrSwitch commented 9 years ago

Np, its pretty horrible code otherwise i'd encourage you to give it a shot. On 3 Nov 2014 04:16, "Bojan Tosic" notifications@github.com wrote:

Hm, I'm not proficient in node.js. If you plan to work on it next week, I'd rather wait. Thanks!

— Reply to this email directly or view it on GitHub https://github.com/MrSwitch/hello.js/issues/135#issuecomment-61414723.

MrSwitch commented 9 years ago

Doesn't need a //auth-server change afterall, just move those parameters into the querystring. See 38d5019

i.e. for a request like below (change the reblog_key)

hello('tumblr').api('me/like', 'post', {id:101517936806, reblog_key:"fE3PKrpi"}).then(function(o){console.log(o.meta);});

Forms a request

POST https://api.tumblr.com/v2/user/like?id=101517936806&reblog_key=fE3PKrpi

Response

{"meta":{"status":200,"msg":"OK"},"response":[]}
btosic commented 9 years ago

Thank you, this works for me now.