我使用UseJwtBearerAuthentication方法遇到困难,我使用Microsoft Azure ACS获取令牌(使用服务标识)。 JWT令牌可以很好地返回我的测试程序。在测试程序中,令牌被发送到MVC WebAPI 2.(从Azure Active Directory获取令牌时,WAAD身份验证正常工作)
public partial class Startup
{
private const string Issuer = "https://bluebeam-us-east.accesscontrol.windows.net/";
public void ConfigureAuth(IAppBuilder app)
{
string CertificateThumbprint = "99B25E3E31FCD24F669C260A743FBD508D21FE30";
var audience = ConfigurationManager.AppSettings["ida:Audience"];
app.UseErrorPage(new ErrorPageOptions()
{
ShowEnvironment = true,
ShowCookies = false,
ShowSourceCode = true,
});
app.UseWindowsAzureActiveDirectoryBearerAuthentication(
new WindowsAzureActiveDirectoryBearerAuthenticationOptions
{
Audience = audience ,
Tenant = ConfigurationManager.AppSettings["ida:Tenant"]
});
app.UseJwtBearerAuthentication(new JwtBearerAuthenticationOptions
{
AllowedAudiences = new[] { audience },
IssuerSecurityTokenProviders = new IIssuerSecurityTokenProvider[]
{
new X509CertificateSecurityTokenProvider(Issuer, X509CertificateHelper.FindByThumbprint(StoreName.My,StoreLocation.LocalMachine,CertificateThumbprint).First())
},
});
}
从ACS获取令牌的代码如下:
private async void GetJwtToken()
{
try
{
using (var client = new HttpClient())
{
client.BaseAddress = new Uri(IdP.Authority);
var content = new FormUrlEncodedContent(new Dictionary<String, String>
{
{"grant_type","client_credentials"},
{"client_id", IdP.UserName},
{"client_secret", IdP.Password},
{"scope", IdP.Resource}
});
var response = await client.PostAsync("v2/OAuth2-13", content);
response.EnsureSuccessStatusCode();
var jwtdata = await response.Content.ReadAsStringAsync();
var jwt = JsonConvert.DeserializeObject<Token>(jwtdata);
AccessToken = jwt.access_token;
TokenType = jwt.token_type;
long expire;
if (long.TryParse(jwt.expires_in, out expire))
{
ExpiresOn = DateTimeOffset.UtcNow.AddSeconds(expire);
}
Authorization = AccessToken;
}
}
catch (HttpRequestException re)
{
Response = re.Message;
}
}
请求资源的代码(WebAPI):
private async void WebApiRequestCall()
{
try
{
ConfigureSsl();
using (var client = new HttpClient())
{
client.BaseAddress = _baseAddress;
client.DefaultRequestHeaders.Accept.Clear();
client.DefaultRequestHeaders.Accept.Add(new MediaTypeWithQualityHeaderValue("application/json"));
if (!String.IsNullOrWhiteSpace(Authorization))
client.DefaultRequestHeaders.Add("Authorization", Authorization);
var response = await client.GetAsync(WebApiRequest);
response.EnsureSuccessStatusCode();
Response = await response.Content.ReadAsStringAsync();
}
}
catch (HttpRequestException e)
{
Response = e.Message;
}
}
解码后的令牌(使用谷歌令牌解码器如下所示)
Header
{
"x5t": "mbJePjH80k9mnCYKdD-9UI0h_jA",
"alg": "RS256",
"typ": "JWT"
}
Claims
{
"identityprovider": "https://bluebeam-us-east.accesscontrol.windows.net/",
"iss": "https://bluebeam-us-east.accesscontrol.windows.net/",
"http://schemas.microsoft.com/identity/claims/identityprovider": "revu",
"exp": 1406957036,
"nbf": 1406956676,
"aud": "https://bluebeam.com/Bluebeam.Licensing.WebApi/"
}
所以我有以下问题:
1)使用JwtBearerToken正确的方法来解码来自ACS的解码JWT令牌 2)Owin中是否有任何跟踪设施可以提供认证管道中的哪些内容?
我使用的是Microsoft Own 3.0-rc1。
答案 0 :(得分:3)
我的代码中似乎有一个错误,我没有设置正确的&#34; bearer header&#34;在向WebAPI发送客户端请求时为OWIN。
从ACS接收JWT令牌后,我需要正确设置授权
private async void GetJwtToken()
{
try
{
using (var client = new HttpClient())
{
client.BaseAddress = new Uri(IdP.Authority);
var content = new FormUrlEncodedContent(new Dictionary<String, String>
{
{"grant_type","client_credentials"},
{"client_id", IdP.UserName},
{"client_secret", IdP.Password},
{"scope", IdP.Resource}
});
var response = await client.PostAsync("v2/OAuth2-13", content);
response.EnsureSuccessStatusCode();
var jwtdata = await response.Content.ReadAsStringAsync();
var jwt = JsonConvert.DeserializeObject<Token>(jwtdata);
IdP.AccessToken = jwt.access_token;
IdP.TokenType = jwt.token_type;
long expire;
if (long.TryParse(jwt.expires_in, out expire))
{
IdP.ExpiresOn = DateTimeOffset.UtcNow.AddSeconds(expire);
}
// Ensure that Correct Authorization Header for Owin
Authorization = String.Format("{0} {1}", "Bearer", IdP.AccessToken);**
}
}
catch (HttpRequestException re)
{
Response = re.Message;
}
}
我们还需要支持WebAPI上的对称密钥,具体取决于ACS如何发送令牌
public void ConfigureAuth(IAppBuilder app)
{
var thumbPrint = ConfigurationManager.AppSettings["ida:Thumbprint"];
var audience = ConfigurationManager.AppSettings["ida:Audience"];
var trustedTokenPolicyKey = ConfigurationManager.AppSettings["ida:SymmetricKey"];
app.UseErrorPage(new ErrorPageOptions()
{
ShowEnvironment = true,
ShowCookies = false,
ShowSourceCode = true,
});
app.UseJwtBearerAuthentication(new JwtBearerAuthenticationOptions()
{
AllowedAudiences = new[] {audience},
IssuerSecurityTokenProviders = new IIssuerSecurityTokenProvider[]
{
new X509CertificateSecurityTokenProvider(Issuer,
X509CertificateHelper.FindByThumbprint(StoreName.My, StoreLocation.LocalMachine, thumbPrint)
.First()),
new SymmetricKeyIssuerSecurityTokenProvider(Issuer, trustedTokenPolicyKey),
},
});
app.UseWindowsAzureActiveDirectoryBearerAuthentication(
new WindowsAzureActiveDirectoryBearerAuthenticationOptions
{
Audience = audience,
Tenant = ConfigurationManager.AppSettings["ida:Tenant"]
});
}