我有一个OAuth2 java客户端尝试创建JWT,然后使用私钥(来自Google API控制台)进行签名 - 请按照这些页面https://developers.google.com/accounts/docs/OAuth2ServiceAccount进行操作。但是,Google OAuth2会一直返回“无效授权”。
以下是签署JWT的客户端代码:
package com.oauth2.google.app.url;
import java.io.FileInputStream;
import java.security.KeyStore;
import java.security.PrivateKey;
import java.security.Signature;
import java.text.MessageFormat;
import org.apache.commons.codec.binary.Base64;
public class WebToken
{
private String iss;
private String prn;
private String scope;
private String aud;
private long exp;
private long iat;
private String keystoreLoc;
private String keyAlias;
public WebToken(String iss, String prn, String scope, String aud, long exp, long iat, String keystore,
String keyAlias)
{
super();
this.iss = iss;
this.prn = prn;
this.scope = scope;
this.aud = aud;
this.exp = exp;
this.iat = iat;
this.keystoreLoc = keystore;
this.keyAlias = keyAlias;
}
/**
* Performs base64-encoding of input bytes.
*
* @param rawData * Array of bytes to be encoded.
* @return * The base64 encoded string representation of rawData.
*/
public static String encodeBase64(byte[] rawData)
{
byte[] data = Base64.encodeBase64(rawData);
return new String(data);
}
public String getToken()
throws Exception
{
String header = "{\"alg\":\"RS256\",\"typ\":\"JWT\"}";
//String header = "{\"alg\":\"RS256\"}";
String claimTemplate = "'{'\"iss\": \"{0}\", \"prn\": \"{1}\", \"scope\": \"{2}\", \"aud\": \"{3}\", \"exp\": {4}, \"iat\": {5}'}'";
StringBuffer token = new StringBuffer();
//Encode the JWT Header and add it to our string to sign
token.append(encodeBase64(header.getBytes("UTF-8")));
//Separate with a period
token.append(".");
//Create the JWT Claims Object
String[] claimArray = new String[6];
claimArray[0] = this.iss;
claimArray[1] = this.prn;
claimArray[2] = this.scope;
claimArray[3] = this.aud;
claimArray[4] = "" + this.exp;
claimArray[5] = "" + this.iat;
MessageFormat claims = new MessageFormat(claimTemplate);
String payload = claims.format(claimArray);
print(payload);
//Add the encoded claims object
token.append(encodeBase64(payload.getBytes("UTF-8")));
//Load the private key from a keystore
KeyStore keystore = KeyStore.getInstance("JKS");
keystore.load(new FileInputStream(this.keystoreLoc), "welcome1".toCharArray());
PrivateKey privateKey = (PrivateKey) keystore.getKey(keyAlias, "notasecret".toCharArray());
//Sign the JWT Header + "." + JWT Claims Object
Signature signature = Signature.getInstance("SHA256withRSA");
signature.initSign(privateKey);
signature.update(token.toString().getBytes("UTF-8"));
byte[] sig = signature.sign();
String signedPayload = encodeBase64(sig);
//Separate with a period
token.append(".");
//Add the encoded signature
token.append(signedPayload);
return token.toString();
}
public static void print(String msg)
{
System.out.println(msg);
}
public static void main(String[] args)
throws Exception
{
String iss = "17560ddd122-nggij305nchhs76pge045jg9u1f4567k@developer.gserviceaccount.com";
String prn = "test123@ggmail.com";
String scope = "https://www.googleapis.com/auth/urlshortener";
String aud = "https://accounts.google.com/o/oauth2/token";
long iat = System.currentTimeMillis()/1000 - 60;
long exp = iat + 3600;
String keystoreLoc = "D:\\keystore.jks";
String keyAlias = "privatekey";
WebToken jwt = new WebToken(iss, prn, scope, aud, exp, iat, keystoreLoc, keyAlias);
String token = jwt.getToken();
print(token);
}
}
然后使用curl获取令牌: curl -k -vSs -X POST -d“grant_type = urn%3Aietf%3Aparams%3Aoauth%3Agrant-type%3Ajwt-bearer& assertion =”https://accounts.google.com/o/oauth2/token
对于什么是错的任何想法?