oauth 2.0 Microsoft Graph和Java针对授权代码流的多次调用
几个小时来我一直在想这个问题,现在我在兜圈子,浪费时间。我正在使用MS Graph API访问Office 365,我已经使用授权流对其进行了设置,以授权我的Java servlet。它工作正常(获取身份验证代码的URL在别处),但我只能运行一个调用。我在后续调用的异常中得到以下错误(在我的代码中,是在我尝试查看驱动器时):
OAuth2授权代码已兑换,请使用新的有效代码重试,或使用现有的刷新令牌强>
我假设这意味着我需要刷新我的令牌(很明显,我已经找到了关于这一点的注释,说明它现在在这个流程中是必要的),但我不知道如何使用GraphServiceClient来完成
下面是我的代码,在我将笔记本电脑从最近的窗口飞盘出去之前,任何帮助都将是最受欢迎的
protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
PrintWriter out = response.getWriter();
String code = request.getParameter("code");
String clientId = "***";
String clientSecret = "***";
String authorisationCode = code;
String redirectURL = "http://localhost:8080/O365Web/auth";
String tenant = "***";
AuthorizationCodeCredential authCodeCredential = new AuthorizationCodeCredentialBuilder()
.clientId(clientId)
.clientSecret(clientSecret) //required for web apps, do not set for native apps
.authorizationCode(authorisationCode)
.redirectUrl(redirectURL)
.build();
List<String> scopes = new ArrayList<String>();
scopes.add("https://graph.microsoft.com/User.Read");
scopes.add("https://graph.microsoft.com/Files.ReadWrite.All");
scopes.add("https://graph.microsoft.com/offline_access");
TokenCredentialAuthProvider tokenCredentialAuthProvider = new TokenCredentialAuthProvider(scopes, authCodeCredential);
GraphServiceClient graphClient =
GraphServiceClient
.builder()
.authenticationProvider(tokenCredentialAuthProvider)
.buildClient();
try {
final User me = graphClient.me().buildRequest().get();
out.println("Name: " + me.displayName + "");
} catch ( Exception ex ) {
out.println("Exception in first user get: " + ex.getMessage() );
ex.printStackTrace();
}
try {
DriveItemCollectionPage children = graphClient.me().drive().root().children().buildRequest().get();
while ( children != null ) {
for ( DriveItem item : children.getCurrentPage() ) {
out.println("C:" + item.name + " : " + item.id);
}
DriveItemCollectionRequestBuilder builder = children.getNextPage();
if ( builder != null ) {
out.println("Loading page...");
children = children.getNextPage().buildRequest().get();
} else {
children = null;
}
}
} catch ( Exception ex ) {
out.println("Exception in children get: " + ex.getMessage());
ex.printStackTrace();
}
try {
final User me2 = graphClient.me().buildRequest().get();
out.println(me2.displayName + "<br/>");
} catch ( Exception ex ) {
out.println("Exception in second user get: " + ex.getMessage());
ex.printStackTrace();
}
}
# 1 楼答案
我已经在我的环境中进行了测试
当我第一次运行请求时,我能够生成访问令牌
当我再次运行相同的请求时,我也得到了相同的错误:
OAuth2授权码已兑换,请使用新的有效码重试,或使用现有的刷新令牌
错误原因是AuthCodeRedential中使用的授权代码只能使用一次
如果您想发出新请求,可以生成新的授权码(获取授权码的URL在别处),并在AuthCodeRedential中使用它
这可以解决这个问题
另一种方法是使用刷新令牌
在使用URL生成授权代码时,您可以使用离线访问添加另一个作用域
现在,在使用授权代码生成访问令牌的同时,添加另一个具有脱机访问的作用域。 这将生成一个刷新令牌和访问令牌
现在,当访问令牌过期时,可以使用刷新令牌生成新的访问令牌
参考:Get access on behalf of a user - Microsoft Graph | Microsoft Docs