我想知道是否有人可以建议我在当前设置中如何使用PKI证书而不是客户端机密字符串来访问Java中的图形。证书将提供给我,并且将为我完成Azure应用程序中的所有设置,我只需要知道如何在Java设置中使用证书即可。
我的GraphAuthManager。我用这些信息构建了一个OAuth20Service。
package com.mycompany.graph.connect;
import java.io.IOException;
import java.net.URISyntaxException;
import java.util.Scanner;
import java.util.concurrent.ExecutionException;
import java.util.logging.Level;
import com.github.scribejava.core.builder.ServiceBuilder;
import com.github.scribejava.core.model.OAuth2AccessToken;
import com.github.scribejava.core.model.OAuth2AccessTokenErrorResponse;
import com.github.scribejava.core.oauth.OAuth20Service;
import com.microsoft.graph.core.ClientException;
import com.microsoft.graph.logger.LoggerLevel;
//this modifying the example authentication manager to my purposes
public class GraphAuthManager {
//extrnalised info like scopes,client secret,etc
private OAuth2AccessToken mAccessToken;
// this is set if we already have a refresh token
/**
* Initialization block. Runs before constructor to get a logger and start up
* the ScribeJava OAuth2 authentication service
*/
{
if (Debug.DebugLevel == LoggerLevel.DEBUG) {
DebugLogger.getInstance().writeLog(Level.INFO, "AuthenticationManager initialization block called");
try (OAuth20Service service = new ServiceBuilder(Constants.CLIENT_ID).callback(Constants.REDIRECT_URL)
.scope(Constants.SCOPES).apiKey(Constants.CLIENT_ID).apiSecret(API_SECRET).debugStream(System.out)
.debug().build(MicrosoftAzureAD20Api.instance())) {
mOAuthService = service;
} catch (java.io.IOException | IllegalArgumentException ex) {
try {
throw ex;
} catch (IOException e) {
e.printStackTrace();
}
}
} else {
try (OAuth20Service service = new ServiceBuilder(Constants.CLIENT_ID).callback(Constants.REDIRECT_URL)
.scope(Constants.SCOPES).apiKey(Constants.CLIENT_ID).apiKey(Constants.CLIENT_ID)
.apiSecret(API_SECRET).build(MicrosoftAzureAD20Api.instance())) {
mOAuthService = service;
} catch (java.io.IOException | IllegalArgumentException ex) {
try {
throw ex;
} catch (IOException e) {
e.printStackTrace();
}
}
}
}
private GraphAuthManager() throws IOException {
DebugLogger.getInstance().writeLog(Level.INFO, "AuthenticationManager constructor called");
}
public static synchronized GraphAuthManager getInstance() throws java.io.IOException, java.net.ConnectException {
return new GraphAuthManager();
}
public OAuth2AccessToken getRefreshTokenWithAuthToken(String authToken)
throws OAuth2AccessTokenErrorResponse, IOException, InterruptedException, ExecutionException {
try {
System.out.println("trying for the first time");
mAccessToken = mOAuthService.getAccessToken(authToken);
return mAccessToken;
}
catch (IOException | InterruptedException | ExecutionException e) {
// if a catch other than a response code error occurs, try it agaiin
System.out.println("trying a second time");
try {
mAccessToken = mOAuthService.getAccessToken(authToken);
return mAccessToken;
} catch (IOException | InterruptedException | ExecutionException e2) {
// TODO Auto-generated catch block
// an error occured
e2.printStackTrace();
throw e2; // this is for bubbling up the exception to the class using graphauth to do
// validations
}
}
}
public OAuth2AccessToken getAccessTokenWithRefreshToken(String refreshToken)
throws OAuth2AccessTokenErrorResponse, IOException, InterruptedException, ExecutionException {
try {
System.out.println("trying for the first time");
OAuth2AccessToken mAccessToken = mOAuthService.refreshAccessToken(refreshToken);
return mAccessToken;
} catch (IOException | InterruptedException | ExecutionException e) {
try {
System.out.println("trying for the second time");
OAuth2AccessToken mAccessToken = mOAuthService.refreshAccessToken(refreshToken);
return mAccessToken;
} catch (IOException | InterruptedException | ExecutionException e2) {
// TODO Auto-generated catch block
e2.printStackTrace();
throw e2;
}
}
}
public OAuth20Service getOAuthService() {
return mOAuthService;
}
public String getRefreshToken() {
if (mAccessToken == null) {
return "";
}
return mAccessToken.getRefreshToken();
}
public String getAccessToken() {
if (mAccessToken == null) {
return "";
}
return mAccessToken.getAccessToken();
}
}
答案 0 :(得分:0)
我快速研究了scribejava。看来它现在只能支持使用客户端机密。
要使用PKI证书代替客户端机密,您需要:
$cert=New-SelfSignedCertificate -Subject "CN=AADCert" -CertStoreLocation "Cert:\CurrentUser\My" -KeyExportPolicy Exportable -KeySpec Signature
$bin = $cert.RawData
$base64Value = [System.Convert]::ToBase64String($bin)
$bin = $cert.GetCertHash()
$base64Thumbprint = [System.Convert]::ToBase64String($bin)
$cert | Export-Certificate -FilePath D:\test.cer
$CertPassword = ConvertTo-SecureString -String “YourPassword” -Force –AsPlainText
$cert | Export-PfxCertificate -FilePath D:\test.pfx -Password $CertPassword
一个cer文件将被导出到D:\ test.cer。您可以将其上传到在Azure AD中注册的应用程序。
一个pfx文件也将被导出。它是证书的备份。它将用于获取令牌。
import com.microsoft.aad.msal4j.*;
import java.io.IOException;
import java.net.MalformedURLException;
import java.net.URI;
import java.util.HashSet;
import java.util.Set;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
public class MsalTest {
public static void main(String[] args) throws Exception {
Set<String> scopes = new HashSet<>();
scopes.add("openid");
scopes.add("User.Read");
String code = "The authorization code, AQABAAI......UQ_CIAA";
IClientCredential clientCredential = ClientCredentialFactory.create(ClassLoader.getSystemResourceAsStream("./others/test.pfx"), "YourPassword");
String clientId = "Your client id, dc17****-****-****-****-****e56da5e7";
String authority = "https://login.microsoftonline.com/+tenantid, for example: https://login.microsoftonline.com/e4c9ab4e-bd27-40d5-8459-230ba2a757fb";
URI redirectUri = new URI("redirect uri of your applicaiton in azure ad, https://localhost/");
IAuthenticationResult result = GetTokenWithCertficate(scopes, code, clientCredential, clientId, authority, redirectUri);
System.out.println(result.accessToken());
}
static IAuthenticationResult GetTokenWithCertficate(Set<String> scopes, String code, IClientCredential clientCredential, String clientId, String authority, URI redirectUri){
IAuthenticationResult result = null;
ExecutorService service = null;
try{
service = Executors.newFixedThreadPool(1);
ConfidentialClientApplication app = ConfidentialClientApplication.builder(clientId, clientCredential).authority(authority).executorService(service).build();
AuthorizationCodeParameters authorizationCodeParameters = AuthorizationCodeParameters.builder(code, redirectUri).scopes(scopes).build();
result = app.acquireToken(authorizationCodeParameters).get();
} catch (ExecutionException e) {
e.printStackTrace();
} catch (MalformedURLException e) {
e.printStackTrace();
} catch (InterruptedException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
} finally {
service.shutdown();
}
return result;
}
}