I am working on a project where a third party provider will act as an Oauth2 based Authorization Server. An Asp.net MVC 5 based client which will send the user to the authorization server to authenticate (using login / password) and the auth server will return an access token back to the MVC client. Any further calls to resource servers (APIs) will be made using the access token.
To achieve this I am using Microsoft.Owin.Security.OpenIdConnect and the UseOpenIdConnectAuthentication extension. I am able to successfully redirect and get the access token from the auth server but the client is not creating an Authentication Cookie. Every time I try to access a secured page, I get the callback page with access token.
What am I missing here? My current code is below.
The secured controller action:
namespace MvcWebApp.Controllers
{
public class SecuredController : Controller
{
// GET: Secured
[Authorize]
public ActionResult Index()
{
return View((User as ClaimsPrincipal).Claims);
}
}
}
The Startup Class:
public class Startup
{
public void Configuration(IAppBuilder app)
{
app.SetDefaultSignInAsAuthenticationType("ClientCookie");
app.UseCookieAuthentication(new CookieAuthenticationOptions
{
AuthenticationMode = AuthenticationMode.Active,
AuthenticationType = "ClientCookie",
CookieName = CookieAuthenticationDefaults.CookiePrefix + "ClientCookie",
ExpireTimeSpan = TimeSpan.FromMinutes(5)
});
// ***************************************************************************
// Approach 1 : ResponseType = "id_token token"
// ***************************************************************************
app.UseOpenIdConnectAuthentication(new OpenIdConnectAuthenticationOptions
{
AuthenticationMode = AuthenticationMode.Active,
AuthenticationType = OpenIdConnectAuthenticationDefaults.AuthenticationType,
SignInAsAuthenticationType = app.GetDefaultSignInAsAuthenticationType(),
Authority = "https://thirdparty.com.au/oauth2",
ClientId = "_Th4GVMa0JSrJ8RKcZrzbcexk5ca",
ClientSecret = "a3GVJJbLHkrn9nJRj3IGNvk5eGQa",
RedirectUri = "http://mvcwebapp.local/",
ResponseType = "id_token token",
Scope = "openid",
Configuration = new OpenIdConnectConfiguration
{
AuthorizationEndpoint = "https://thirdparty.com.au/oauth2/authorize",
TokenEndpoint = "https://thirdparty.com.au/oauth2/token",
UserInfoEndpoint = "https://thirdparty.com.au/oauth2/userinfo",
},
Notifications = new OpenIdConnectAuthenticationNotifications
{
SecurityTokenValidated = n =>
{
var token = n.ProtocolMessage.AccessToken;
// persist access token in cookie
if (!string.IsNullOrEmpty(token))
{
n.AuthenticationTicket.Identity.AddClaim(
new Claim("access_token", token));
}
return Task.FromResult(0);
},
AuthenticationFailed = notification =>
{
if (string.Equals(notification.ProtocolMessage.Error, "access_denied", StringComparison.Ordinal))
{
notification.HandleResponse();
notification.Response.Redirect("/");
}
return Task.FromResult<object>(null);
}
}
});
// ***************************************************************************
// Approach 2 : ResponseType = "code"
// ***************************************************************************
//app.UseOpenIdConnectAuthentication(new OpenIdConnectAuthenticationOptions
//{
// AuthenticationMode = AuthenticationMode.Active,
// AuthenticationType = OpenIdConnectAuthenticationDefaults.AuthenticationType,
// SignInAsAuthenticationType = app.GetDefaultSignInAsAuthenticationType(),
// Authority = "https://thirdparty.com.au/oauth2",
// ClientId = "_Th4GVMa0JSrJ8RKcZrzbcexk5ca",
// ClientSecret = "a3GVJJbLHkrn9nJRj3IGNvk5eGQa",
// RedirectUri = "http://mvcwebapp.local/",
// ResponseType = "code",
// Scope = "openid",
// Configuration = new OpenIdConnectConfiguration
// {
// AuthorizationEndpoint = "https://thirdparty.com.au/oauth2/authorize",
// TokenEndpoint = "https://thirdparty.com.au/oauth2/token",
// UserInfoEndpoint = "https://thirdparty.com.au/oauth2/userinfo",
// },
// Notifications = new OpenIdConnectAuthenticationNotifications
// {
// AuthorizationCodeReceived = async (notification) =>
// {
// using (var client = new HttpClient())
// {
// var configuration = await notification.Options.ConfigurationManager.GetConfigurationAsync(notification.Request.CallCancelled);
// var request = new HttpRequestMessage(HttpMethod.Get, configuration.TokenEndpoint);
// request.Content = new FormUrlEncodedContent(new Dictionary<string, string>
// {
// {OpenIdConnectParameterNames.ClientId, notification.Options.ClientId},
// {OpenIdConnectParameterNames.ClientSecret, notification.Options.ClientSecret},
// {OpenIdConnectParameterNames.Code, notification.ProtocolMessage.Code},
// {OpenIdConnectParameterNames.GrantType, "authorization_code"},
// {OpenIdConnectParameterNames.ResponseType, "token"},
// {OpenIdConnectParameterNames.RedirectUri, notification.Options.RedirectUri}
// });
// var response = await client.SendAsync(request, notification.Request.CallCancelled);
// response.EnsureSuccessStatusCode();
// var payload = JObject.Parse(await response.Content.ReadAsStringAsync());
// // Add the access token to the returned ClaimsIdentity to make it easier to retrieve.
// notification.AuthenticationTicket.Identity.AddClaim(new Claim(
// type: OpenIdConnectParameterNames.AccessToken,
// value: payload.Value<string>(OpenIdConnectParameterNames.AccessToken)));
// }
// }
// }
//});
}
}