Google api oauth 序言

Google api oauth prolog

我正在尝试连接到 google oauth。我已经使用 javascript 连接到 google 并获得代码,然后我明白我需要将此代码交换为令牌,详情如下:https://developers.google.com/identity/protocols/OAuth2WebServer

我的密码是:

 :- use_module(library(http/http_dispatch)).
 :- use_module(library(http/http_error)).
 :- use_module(library(http/html_write)).
 :- use_module(library(http/http_session)).
 :- use_module(library(http/js_write)).
 :- use_module(library(http/http_files)).
 :- use_module(library(http/json)).
 :- use_module(library(http/http_open)).
 :- use_module(library(http/http_json)).
 :- use_module(library(http/http_parameters)).
 :- use_module(library(http/http_client)).
 :- use_module(library(http/http_ssl_plugin)).

post_to_google(Reply,Code,Client_Id,Client_Secret):-
      Grant_type=authorization_code,
      http_post(
         'http://requestb.in/10qo0si1',
         %'https://www.googleapis.com/oauth2/v3/token',
         form([
          code=Code,
          client_id=Client_Id,
          client_secret=Client_Secret,
          redirect_uri='http://localhost:5000/',
          grant_type=Grant_type
         ]),
         Reply,
         []
      ).

如果我查询post_to_google(R,123,id,secret). 这会向请求 bin 发送一个请求,这样我就可以在 (http://requestb.in/10qo0si1?inspect) 检查它,然后我得到一个响应 'ok'.

如果我注释掉请求 bin 并替换为 google 地址,我会得到 false。我期望像 { "error": "invalid_request" } 这样的东西,或者如果使用正确的凭据查询像:

{
  "access_token":"1/fFAGRNJru1FTz70BzhT3Zg",
  "expires_in":3920,
  "token_type":"Bearer"
} 

我是否必须做一些不同的事情,因为它是 https 还是我在其他地方犯了错误?由于不匹配协议,在 address/4 中跟踪它似乎失败了?

好的,这一步终于搞定了。如果有人感兴趣:

使用 status_code(_ErrorCode) 似乎解决了 streampair 的问题,我需要设置 redirect_uri='postmessage' 才能使请求正常工作。 我还使用 http_open 而不是 http_post。

:- use_module(library(http/thread_httpd)).
:- use_module(library(http/http_dispatch)).
:- use_module(library(http/http_error)).
:- use_module(library(http/html_write)).
:- use_module(library(http/http_session)).
:- use_module(library(http/js_write)).
:- use_module(library(http/http_files)).
:- use_module(library(http/json)).
:- use_module(library(http/http_open)).
:- use_module(library(http/http_json)).
:- use_module(library(http/http_parameters)).
:- use_module(library(http/http_client)).
:- use_module(library(http/http_ssl_plugin)).

:- use_module('../prolog/google_client').

http:location(files, '/f', []).

:- http_handler('/', home_page, []).
:- http_handler('/gconnect', gconnect, []).

:- http_handler(files(.), http_reply_from_files('test_files', []), [prefix]).

:- dynamic
    my_code/1.
server :-
    server(5000).

server(Port) :-
        http_server(http_dispatch, [port(Port)]),
    format("Server should be on port 5000 to work with google settings- is it?").

read_client_secrets(MyWeb,Client_Id,Client_Secret) :-
    open('client_secrets.json',read,Stream),
    json_read_dict(Stream,Dict),
    _{web:MyWeb} :< Dict,
    _{
        auth_provider_x509_cert_url:Auth_url,
        auth_uri:Auth_uri,
        client_email:Client_email,
        client_id:Client_Id,
        client_secret:Client_Secret,
        client_x509_cert_url:Client_cert_url,
        javascript_origins:Javascript_origins,
        redirect_uris: Redirect_uris,
        token_uri:Token_Uri
    } :<MyWeb,
    close(Stream).



post_to_google(Profile,Code,CID,CS):-

    ListofData=[
               code=Code,
               client_id=CID,
               client_secret=CS,
               redirect_uri='postmessage',
               grant_type=authorization_code

              ],
        http_open('https://www.googleapis.com/oauth2/v3/token', In,
                  [ status_code(_ErrorCode),
            method(post),post(form(ListofData))
                  ]),
    call_cleanup(json_read_dict(In, Profile),
             close(In)).


home_page(Request) :-
    reply_html_page(
       [title('Oauth Test'),
       script([type='text/javascript',
            src='//ajax.googleapis.com/ajax/libs/jquery/1.8.2/jquery.min.js'],[]),
       script([type='text/javascript',
            src='//apis.google.com/js/platform.js?onload=start'],[]),
       \call_back_script
       ],
        [h1('hello'),
        p('test'),
        \google_loginButton
        ]).

gconnect(Request):-
    %I need to get the code from the request
    http_parameters(Request,[code(Code,[default(default)])]),
    read_client_secrets(_MyWeb,Client_Id,Client_Secret),
    post_to_google(Reply,Code,Client_Id,Client_Secret),
    reply_json(Reply).


call_back_script -->
    js_script({|javascript||
              console.log("script runs");
              function signInCallback(authResult) {
                        console.log("got to call back");
                        if (authResult['code']) {
                         console.log("has code");
                         console.log(authResult['code']);
             $('#signInButton').attr('style','display: none');

             $.post("/gconnect",
               {code:authResult['code']},
               function(data,status){
                //console.log("Data: " + data.reply + "\nStatus: " + status);
                console.log("Access Token: " + data.access_token + "\nExpires in : " + data.expires_in + "\nToken_type : " + data.token_type +  "\nStatus: " + status);
               });
             /*
             $.ajax({
                   type: 'POST',
                   url: '/gconnect',
                   processData:false,
                   //contentType: 'application/x-www-form-urlencoded; charset=UTF-8',
                   contentType: 'application/octet-stream; charset=utf-8',
                   data: {code:authResult['code']},
                   success: function(result){
                        console.log("success");
                        console.log(result);
                    }
               });
                          */

            }
              }

              |}).


google_loginButton -->
    html([div([id="signInButton"],[
          span([
             class="g-signin",
             data-scope="openid email",
             data-clientid="124024716168-p5lvtlj5jinp9u912s3f7v3a5cuvj2g8.apps.googleusercontent.com",
             data-redirecturi="postmessage",
             data-accesstype="offline",
             data-cookiepolicy="single_host_origin",
             data-callback="signInCallback",
             data-approvalprompt="force"],[])
          ])]).