java - 如何使用 gmail api 获取访问 token

标签 java google-api gmail-api

我在this document之后得到了授权码.但是当我试图获取访问 token 时,我总是会出错。谁能帮帮我?

public String AccessToken()
{
    String accessToken = "";
    StringBuilder strBuild = new StringBuilder();

    String authURL = "https://accounts.google.com/o/oauth2/token?";
    String code = "4/SVisuz_x*********************";
    String client_id = "******************e.apps.googleusercontent.com";
    String client_secret = "*******************";
    String redirect_uri = "urn:ietf:wg:oauth:2.0:oob";
    String grant_type="authorization_code";
    strBuild.append("code=").append(code)
            .append("&client_id=").append(client_id)
            .append("&client_secret=").append(client_secret)
            .append("&redirect_uri=").append(redirect_uri)
            .append("&grant_type=").append(grant_type);
    System.out.println(strBuild.toString());
    try{
        URL obj = new URL(authURL);
        HttpURLConnection con = (HttpURLConnection) obj.openConnection();
        con.setDoOutput(true);
        con.setRequestMethod("POST");

        con.setRequestProperty("Content-Type", "application/x-www-form-urlencoded");
        con.setRequestProperty("Host", "www.googleapis.com");

        //BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(con.getOutputStream()));
        //bw.write(strBuild.toString());
        //bw.close();

        DataOutputStream wr = new DataOutputStream(con.getOutputStream());
        wr.writeBytes(strBuild.toString());
        wr.flush();
        wr.close();

        //OutputStreamWriter out = new OutputStreamWriter(con.getOutputStream());
        System.out.println(con.getResponseCode());
        System.out.println(con.getResponseMessage());             

    } catch (Exception e)
    {
        System.out.println("Error.");
    }
    return "";
}

当我运行这段代码时,输​​出是: 400 错误请求

最佳答案

How to get access token using gmail api?

回答:根据your following tutorial ,您正在使用 OAuth 2.0。因此,有一个使用 OAuth 2.0 访问 Google API 的基本模式。它遵循 4 个步骤:

  1. 从 Google Developers Console 获取 OAuth 2.0 凭据。
  2. 从 Google 授权服务器获取访问 token 。
  3. 将访问 token 发送到 API。
  4. 如有必要,刷新访问 token 。

详情可引用教程-Using OAuth 2.0 to Access Google APIs

你必须访问Google Developers Console获取 OAuth 2.0 凭据,例如 Google 和您的应用程序都知道的 client IDclient secret


根本原因分析:

问题 1:

研究了你的代码,发现了一些不足。如果你的代码运行顺利,那么代码总是给出一个空字符串。因为您的 AccessToken() 方法总是返回 return "";

问题 2:

 catch (Exception e)
    {
        System.out.println("Error.");
    }

您的 try catch block 将成为异常 block 。因为,您似乎没有正确完成代码。您错过了 encoding 以及使用准备访问 token 的 JSONObject。所以它给出的输出为

Error.

解决方案:

我知道你的代码与这个 tutorial 相似

因为您的代码需要更多更改才能解决您的问题。所以我建议您使用 LinkedHashMapArrayList。这些将提供更简单的解决方案。所以我给你 2 个示例代码,让你的生活更轻松。您可以选择其中任何一个。您需要将 refresh_token、client id、client secret 和 grant type 更改为您的。

private String getAccessToken()
{
    try
    {
        Map<String,Object> params = new LinkedHashMap<>();
        params.put("grant_type","refresh_token");
        params.put("client_id",[YOUR CLIENT ID]);
        params.put("client_secret",[YOUR CLIENT SECRET]);
        params.put("refresh_token",[YOUR REFRESH TOKEN]);

        StringBuilder postData = new StringBuilder();
        for(Map.Entry<String,Object> param : params.entrySet())
        {
            if(postData.length() != 0)
            {
                postData.append('&');
            }
            postData.append(URLEncoder.encode(param.getKey(),"UTF-8"));
            postData.append('=');
            postData.append(URLEncoder.encode(String.valueOf(param.getValue()),"UTF-8"));
        }
        byte[] postDataBytes = postData.toString().getBytes("UTF-8");

        URL url = new URL("https://accounts.google.com/o/oauth2/token");
        HttpURLConnection con = (HttpURLConnection)url.openConnection();
        con.setDoOutput(true);
        con.setUseCaches(false);
        con.setRequestMethod("POST");
        con.getOutputStream().write(postDataBytes);

        BufferedReader  reader = new BufferedReader(new InputStreamReader(con.getInputStream()));
        StringBuffer buffer = new StringBuffer();
        for (String line = reader.readLine(); line != null; line = reader.readLine())
        {
            buffer.append(line);
        }

        JSONObject json = new JSONObject(buffer.toString());
        String accessToken = json.getString("access_token");
        return accessToken;
    }
    catch (Exception ex)
    {
        ex.printStackTrace(); 
    }
    return null;
}

For accessing google play android developer api, you need to pass the previous refresh token to get access token

private String getAccessToken(String refreshToken){

HttpClient client = new DefaultHttpClient();
HttpPost post = new HttpPost("https://accounts.google.com/o/oauth2/token");
try 
{
    List<NameValuePair> nameValuePairs = new ArrayList<NameValuePair>(4);
    nameValuePairs.add(new BasicNameValuePair("grant_type",    "refresh_token"));
    nameValuePairs.add(new BasicNameValuePair("client_id",     GOOGLE_CLIENT_ID));
    nameValuePairs.add(new BasicNameValuePair("client_secret", GOOGLE_CLIENT_SECRET));
    nameValuePairs.add(new BasicNameValuePair("refresh_token", refreshToken));
    post.setEntity(new UrlEncodedFormEntity(nameValuePairs));

    org.apache.http.HttpResponse response = client.execute(post);
    BufferedReader reader = new BufferedReader(new InputStreamReader(response.getEntity().getContent()));
    StringBuffer buffer = new StringBuffer();
    for (String line = reader.readLine(); line != null; line = reader.readLine())
    {
        buffer.append(line);
    }

    JSONObject json = new JSONObject(buffer.toString());
    String accessToken = json.getString("access_token");

    return accessToken;

}
catch (IOException e) { e.printStackTrace(); }

return null;
}

资源链接:

希望这个示例资源链接能帮助您解决问题并获得access token


What is 400 bad request?

Ans: 表示查询无效。父 ID 缺失或请求的维度或指标组合无效。

建议的操作:您需要更改 API 查询才能使其正常工作。

For HTTP/1.1 400 Bad Request error, you can go through my another answer. It will help you to make sense about which host you need to use and which conditions you need to apply.

Why token expires? What is the limit of token?

token 可能会因以下原因之一而停止工作:

  1. 用户已撤销访问权限。
  2. token 六个月未使用。
  3. 用户更改了密码, token 包含 Gmail、Calendar、 联系人或环聊范围。
  4. 用户帐户已超过一定数量的 token 请求

当前每个客户端每个用户帐户的刷新 token 限制为 25 个。如果达到限制,创建新 token 会自动使最旧的 token 失效,而不会发出警告。此限制不适用于服务帐户。

应遵循哪些预防措施?

注意事项-1:

Some requests require an authentication step where the user logs in with their Google account. After logging in, the user is asked whether they are willing to grant the permissions that your application is requesting. This process is called user consent.

If the user grants the permission, the Google Authorization Server sends your application an access token (or an authorization code that your application can use to obtain an access token). If the user does not grant the permission, the server returns an error.

注意事项-2:

If an access token is issued for the Google+ API, it does not grant access to the Google Contacts API. You can, however, send that access token to the Google+ API multiple times for similar operations.

注意事项- 3:

An access token typically has an expiration date of 1 hour, after which you will get an error if you try to use it. Google Credential takes care of automatically "refreshing" the token, which simply means getting a new access token.

Save refresh tokens in secure long-term storage and continue to use them as long as they remain valid. Limits apply to the number of refresh tokens that are issued per client-user combination, and per user across all clients, and these limits are different. If your application requests enough refresh tokens to go over one of the limits, older refresh tokens stop working.

关于java - 如何使用 gmail api 获取访问 token ,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36214968/

相关文章:

java - 检查并添加 arraylist 中的浮点值

java - 如何在 ListView 的第一行添加新帖子?

java - Spring RestTemplate 无法解析 json 响应

.net - 是否可以使用 Gmail API (.NET) 获取 Gmail 联系人列表?

php - 提高 Gmail API 速度的方法 (PHP)

java - 使用 MetaMessage getData() 和/或 MetaMessage 值从 java 中的 MIDI 文件中提取节奏?

php - 如何使用 Google API 从多个 Google Analytics 帐户中检索数据?

ios - 谷歌驱动器 API : Insufficient Permission iOS

oauth - 随着 Google+ 被关闭,OAuth API 是否也消失了?

javascript - 如何访问gmail API?