使用 Oauth 通过 Azure 活动目录保护 WebAPI
Using Oauth to protect WebAPI with Azure active directory
我在线浏览了所有关于使用Oauth 保护Azure 活动目录中的WebAPI 的教程。但不幸的是,其中 none 个可以工作。
我使用的是 VS 2017,我的项目是 .net core。
到目前为止我尝试过的是:
public void ConfigureServices(IServiceCollection services)
{
services.AddMvc();
ervices.AddAuthentication(); // -----------> newly added
}
在"Configure"中,我添加了:
app.UseJwtBearerAuthentication(new JwtBearerOptions
{
AutomaticAuthenticate = true,
AutomaticChallenge = true,
Authority = String.Format(Configuration["AzureAd:AadInstance"], Configuration["AzureAD:Tenant"]),
Audience = Configuration["AzureAd:Audience"],
});
这是我的配置:
"AzureAd": {
"AadInstance": "https://login.microsoftonline.com/{0}",
"Tenant": "tenantname.onmicrosoft.com",
"Audience": "https://tenantname.onmicrosoft.com/webapiservice"
}
我已经在我的 AAD 上注册了这个 "webapiservice"(link 是:http://webapiservice.azurewebsites.net)。
此外,为了访问此网络 api 服务,我创建了一个网络 api 客户端 "webapiclient" 这也是一个网络 api 并且还在我的 AAD 上注册了它并请求访问 "webapiservice" 的权限。 Webapi 客户端 link 是:http://webapiclient.azurewebsites.net
HttpClient client = new HttpClient();
client.BaseAddress = new Uri("http://webapiservice.azurewebsites.net/");
//is this uri correct? should it be the link of webapi service or the one of webapi client?
HttpResponseMessage response = client.GetAsync("api/values").Result;
if (response.IsSuccessStatusCode)
{
var result = response.Content.ReadAsAsync<IEnumerable<string>>().Result;
return result;
}
else
{
return new string[] { "Something wrong" };
}
所以理论上,我应该从 webapiservice 收到正确的结果。但我总是收到 "Something wrong"。
我在这里遗漏了什么吗?
要调用受 azure ad 保护的网络 api,您应该使用承载方案在授权 header 中传递此获得的访问令牌:
client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", authResult.AccessToken);
您需要来自 Azure AD 的访问令牌。
GitHub 上有很多很好的示例应用程序,这里是一个守护程序应用程序:https://github.com/Azure-Samples/active-directory-dotnet-daemon/blob/master/TodoListDaemon/Program.cs#L96
AuthenticationResult authResult = await authContext.AcquireTokenAsync(todoListResourceId, clientCredential);
此应用为 API 获取带有其客户端 ID 和客户端密码的访问令牌。您可以在您的案例中采用类似的方法。例如,对于 Azure AD Graph API,您可以将 todoListResourceId
替换为 "https://graph.windows.net/"
,或者将 Microsoft Graph API 替换为 "https://graph.microsoft.com/"
。那是您想要令牌的 API 的标识符。
这是它在 AAD 中的工作方式。您想要访问 API,您向 AAD 请求该访问权限。在成功的响应中,您将取回一个访问令牌,您必须将其作为 header:
附加到 HTTP 调用
Authorization: Bearer accesstokengoeshere......
现在,如果您正在构建 Web 应用程序,您可能希望以不同的方式进行操作,因为您现在正在以客户端应用程序而非用户的身份访问 API。如果您想拨打委托电话,则需要使用例如授权代码流程,您向用户显示浏览器,将他们重定向到正确的地址,然后他们将被发送回您的应用程序以进行登录。
我在线浏览了所有关于使用Oauth 保护Azure 活动目录中的WebAPI 的教程。但不幸的是,其中 none 个可以工作。
我使用的是 VS 2017,我的项目是 .net core。
到目前为止我尝试过的是:
public void ConfigureServices(IServiceCollection services)
{
services.AddMvc();
ervices.AddAuthentication(); // -----------> newly added
}
在"Configure"中,我添加了:
app.UseJwtBearerAuthentication(new JwtBearerOptions
{
AutomaticAuthenticate = true,
AutomaticChallenge = true,
Authority = String.Format(Configuration["AzureAd:AadInstance"], Configuration["AzureAD:Tenant"]),
Audience = Configuration["AzureAd:Audience"],
});
这是我的配置:
"AzureAd": {
"AadInstance": "https://login.microsoftonline.com/{0}",
"Tenant": "tenantname.onmicrosoft.com",
"Audience": "https://tenantname.onmicrosoft.com/webapiservice"
}
我已经在我的 AAD 上注册了这个 "webapiservice"(link 是:http://webapiservice.azurewebsites.net)。
此外,为了访问此网络 api 服务,我创建了一个网络 api 客户端 "webapiclient" 这也是一个网络 api 并且还在我的 AAD 上注册了它并请求访问 "webapiservice" 的权限。 Webapi 客户端 link 是:http://webapiclient.azurewebsites.net
HttpClient client = new HttpClient();
client.BaseAddress = new Uri("http://webapiservice.azurewebsites.net/");
//is this uri correct? should it be the link of webapi service or the one of webapi client?
HttpResponseMessage response = client.GetAsync("api/values").Result;
if (response.IsSuccessStatusCode)
{
var result = response.Content.ReadAsAsync<IEnumerable<string>>().Result;
return result;
}
else
{
return new string[] { "Something wrong" };
}
所以理论上,我应该从 webapiservice 收到正确的结果。但我总是收到 "Something wrong"。
我在这里遗漏了什么吗?
要调用受 azure ad 保护的网络 api,您应该使用承载方案在授权 header 中传递此获得的访问令牌:
client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Bearer", authResult.AccessToken);
您需要来自 Azure AD 的访问令牌。
GitHub 上有很多很好的示例应用程序,这里是一个守护程序应用程序:https://github.com/Azure-Samples/active-directory-dotnet-daemon/blob/master/TodoListDaemon/Program.cs#L96
AuthenticationResult authResult = await authContext.AcquireTokenAsync(todoListResourceId, clientCredential);
此应用为 API 获取带有其客户端 ID 和客户端密码的访问令牌。您可以在您的案例中采用类似的方法。例如,对于 Azure AD Graph API,您可以将 todoListResourceId
替换为 "https://graph.windows.net/"
,或者将 Microsoft Graph API 替换为 "https://graph.microsoft.com/"
。那是您想要令牌的 API 的标识符。
这是它在 AAD 中的工作方式。您想要访问 API,您向 AAD 请求该访问权限。在成功的响应中,您将取回一个访问令牌,您必须将其作为 header:
附加到 HTTP 调用Authorization: Bearer accesstokengoeshere......
现在,如果您正在构建 Web 应用程序,您可能希望以不同的方式进行操作,因为您现在正在以客户端应用程序而非用户的身份访问 API。如果您想拨打委托电话,则需要使用例如授权代码流程,您向用户显示浏览器,将他们重定向到正确的地址,然后他们将被发送回您的应用程序以进行登录。