OAuth {"error":"invalid_client"} 授权类型 "client credential" - C# ASP.Net Web API
OAuth {"error":"invalid_client"} grant type "client credential" - C# ASP.Net Web API
我在尝试使用 postman 或 curl 从我的本地端点请求令牌时不断收到无效的客户端。它只是一个启用了 WebAPI 的 ASP.NET MVC 项目(创建项目时的复选框)。我有一个 class MyAuthorizationServerProvider.cs,它有以下代码
using System;
using System.Configuration;
using System.Security.Claims;
using System.Threading.Tasks;
using Microsoft.Owin.Security.OAuth;
namespace OAuth2App.Provider
{
public class OAuthProvider : OAuthAuthorizationServerProvider
{
public override async Task ValidateClientAuthentication(OAuthValidateClientAuthenticationContext context)
{
string clientId;
string clientSecret;
Guid clientIdGuid;
if (!context.TryGetBasicCredentials(out clientId, out clientSecret))
{
context.TryGetFormCredentials(out clientId, out clientSecret);
}
if (null == context.ClientId || null == clientSecret || !Guid.TryParse(clientId, out clientIdGuid))
{
context.SetError("invalid_credentials", "A valid client_Id and client_Secret must be provided.");
context.Rejected();
return;
}
//validate aginstdb or config: GetClient(clientIdGuid, clientSecret);
bool isValidClient = ConfigurationManager.AppSettings["ClientId"] == clientId && ConfigurationManager.AppSettings["ClientSecret"] == clientSecret;
if (!isValidClient)
{
context.SetError("invalid_credentials", "A valid client_Id and client_Secret must be provided.");
context.Rejected();
return;
}
await Task.Run(() => context.Validated(clientId));
}
public override async Task GrantClientCredentials(OAuthGrantClientCredentialsContext context)
{
Guid clientId;
Guid.TryParse(context.ClientId, out clientId);
//validate aginstdb or config: GetByClientId(clientId);
bool client = ConfigurationManager.AppSettings["ClientId"] == clientId.ToString().ToUpper();
if (!client)
{
context.SetError("invalid_grant", "Invaild client.");
context.Rejected();
return;
}
var claimsIdentity = new ClaimsIdentity(context.Options.AuthenticationType);
claimsIdentity.AddClaim(new Claim("LoggedOn", DateTime.Now.ToString()));
await Task.Run(() => context.Validated(claimsIdentity));
}
public override Task TokenEndpoint(OAuthTokenEndpointContext context)
{
if (context.TokenIssued)
{
context.Properties.ExpiresUtc = DateTimeOffset.UtcNow.AddSeconds(3600);
}
return Task.FromResult<object>(null);
}
}
}
我有另一个 OWIN 启动 class 如下
using Microsoft.Owin;
using Microsoft.Owin.Security.OAuth;
using OAuth2App.Provider;
using Owin;
using System;
[assembly: OwinStartup(typeof(OAuth2App.Startup))]
namespace OAuth2App
{
public class Startup
{
public void Configuration(IAppBuilder app)
{
ConfigureAuth(app);
}
public void ConfigureAuth(IAppBuilder app)
{
var oAuthOptions = new OAuthAuthorizationServerOptions {
AllowInsecureHttp = true, // need set to false in PROD
TokenEndpointPath = new PathString("/oauth2/token"),
AccessTokenExpireTimeSpan = TimeSpan.FromMinutes(60), //token expiration time
Provider = new OAuthProvider(),
};
app.UseOAuthAuthorizationServer(oAuthOptions);
app.UseOAuthBearerAuthentication(new OAuthBearerAuthenticationOptions());
}
}
}
我的 web.config 应用设置部分如下
<appSettings>
<add key="webpages:Version" value="3.0.0.0" />
<add key="webpages:Enabled" value="false" />
<add key="ClientValidationEnabled" value="true" />
<add key="clientId" value="XXXXXXXXXXXXXXXXXXXXXX" />
<add key="clientSecret" value="XXXXXXXXXXXXXXXXXXXXXXXXX" />
<add key="UnobtrusiveJavaScriptEnabled" value="true" />
</appSettings>
当我尝试发出 post 请求时,下面是我在 postman 中得到的内容。调试时,我看到上下文对象的 clientID 字段始终为空。有人可以指出我错了什么吗?
public override async Task ValidateClientAuthentication(OAuthValidateClientAuthenticationContext context)
已编辑
(我错过了你退而求其次的部分 TryGetFormCredentials
)
您似乎需要将表单数据发送为 application/x-www-form-urlencoded
。见 RFC
问题出在下面的代码上,存在错误。我基本上将其更改为 if 语句并删除了 context.rejected
bool isValidClient = ConfigurationManager.AppSettings["ClientId"] == clientId && ConfigurationManager.AppSettings["ClientSecret"] == clientSecret;
if (!isValidClient)
{
context.SetError("invalid_credentials", "A valid client_Id and client_Secret must be provided.");
context.Rejected();
return;
}
// 改为
If(ConfigurationManager.AppSettings["ClientId"] == clientId && ConfigurationManager.AppSettings["ClientSecret"] == clientSecret)
{
context.SetError("invalid_credentials", "A valid client_Id and client_Secret must be provided.");
}
我在尝试使用 postman 或 curl 从我的本地端点请求令牌时不断收到无效的客户端。它只是一个启用了 WebAPI 的 ASP.NET MVC 项目(创建项目时的复选框)。我有一个 class MyAuthorizationServerProvider.cs,它有以下代码
using System;
using System.Configuration;
using System.Security.Claims;
using System.Threading.Tasks;
using Microsoft.Owin.Security.OAuth;
namespace OAuth2App.Provider
{
public class OAuthProvider : OAuthAuthorizationServerProvider
{
public override async Task ValidateClientAuthentication(OAuthValidateClientAuthenticationContext context)
{
string clientId;
string clientSecret;
Guid clientIdGuid;
if (!context.TryGetBasicCredentials(out clientId, out clientSecret))
{
context.TryGetFormCredentials(out clientId, out clientSecret);
}
if (null == context.ClientId || null == clientSecret || !Guid.TryParse(clientId, out clientIdGuid))
{
context.SetError("invalid_credentials", "A valid client_Id and client_Secret must be provided.");
context.Rejected();
return;
}
//validate aginstdb or config: GetClient(clientIdGuid, clientSecret);
bool isValidClient = ConfigurationManager.AppSettings["ClientId"] == clientId && ConfigurationManager.AppSettings["ClientSecret"] == clientSecret;
if (!isValidClient)
{
context.SetError("invalid_credentials", "A valid client_Id and client_Secret must be provided.");
context.Rejected();
return;
}
await Task.Run(() => context.Validated(clientId));
}
public override async Task GrantClientCredentials(OAuthGrantClientCredentialsContext context)
{
Guid clientId;
Guid.TryParse(context.ClientId, out clientId);
//validate aginstdb or config: GetByClientId(clientId);
bool client = ConfigurationManager.AppSettings["ClientId"] == clientId.ToString().ToUpper();
if (!client)
{
context.SetError("invalid_grant", "Invaild client.");
context.Rejected();
return;
}
var claimsIdentity = new ClaimsIdentity(context.Options.AuthenticationType);
claimsIdentity.AddClaim(new Claim("LoggedOn", DateTime.Now.ToString()));
await Task.Run(() => context.Validated(claimsIdentity));
}
public override Task TokenEndpoint(OAuthTokenEndpointContext context)
{
if (context.TokenIssued)
{
context.Properties.ExpiresUtc = DateTimeOffset.UtcNow.AddSeconds(3600);
}
return Task.FromResult<object>(null);
}
}
}
我有另一个 OWIN 启动 class 如下
using Microsoft.Owin;
using Microsoft.Owin.Security.OAuth;
using OAuth2App.Provider;
using Owin;
using System;
[assembly: OwinStartup(typeof(OAuth2App.Startup))]
namespace OAuth2App
{
public class Startup
{
public void Configuration(IAppBuilder app)
{
ConfigureAuth(app);
}
public void ConfigureAuth(IAppBuilder app)
{
var oAuthOptions = new OAuthAuthorizationServerOptions {
AllowInsecureHttp = true, // need set to false in PROD
TokenEndpointPath = new PathString("/oauth2/token"),
AccessTokenExpireTimeSpan = TimeSpan.FromMinutes(60), //token expiration time
Provider = new OAuthProvider(),
};
app.UseOAuthAuthorizationServer(oAuthOptions);
app.UseOAuthBearerAuthentication(new OAuthBearerAuthenticationOptions());
}
}
}
我的 web.config 应用设置部分如下
<appSettings>
<add key="webpages:Version" value="3.0.0.0" />
<add key="webpages:Enabled" value="false" />
<add key="ClientValidationEnabled" value="true" />
<add key="clientId" value="XXXXXXXXXXXXXXXXXXXXXX" />
<add key="clientSecret" value="XXXXXXXXXXXXXXXXXXXXXXXXX" />
<add key="UnobtrusiveJavaScriptEnabled" value="true" />
</appSettings>
当我尝试发出 post 请求时,下面是我在 postman 中得到的内容。调试时,我看到上下文对象的 clientID 字段始终为空。有人可以指出我错了什么吗?
public override async Task ValidateClientAuthentication(OAuthValidateClientAuthenticationContext context)
已编辑
(我错过了你退而求其次的部分 TryGetFormCredentials
)
您似乎需要将表单数据发送为 application/x-www-form-urlencoded
。见 RFC
问题出在下面的代码上,存在错误。我基本上将其更改为 if 语句并删除了 context.rejected
bool isValidClient = ConfigurationManager.AppSettings["ClientId"] == clientId && ConfigurationManager.AppSettings["ClientSecret"] == clientSecret;
if (!isValidClient)
{
context.SetError("invalid_credentials", "A valid client_Id and client_Secret must be provided.");
context.Rejected();
return;
}
// 改为
If(ConfigurationManager.AppSettings["ClientId"] == clientId && ConfigurationManager.AppSettings["ClientSecret"] == clientSecret)
{
context.SetError("invalid_credentials", "A valid client_Id and client_Secret must be provided.");
}