Web API Basic Auth inside MVC application with Auth id
So, I have an application C# MVC
using Identity
to authenticate it. Now I have a need to expose several things through Web API
for some of my clients. Instead of creating a separate app, project, deployment ... I just added API Controller
to my existing project. To keep things simple for my clients, I decided to use Basic Auth
, preferring to use SSL
connections to my API instead of my clients .
I followed this very helpful implementation guide Basic Auth
in my API:
http://www.piotrwalat.net/basic-http-authentication-in-asp-net-web-api-using-message-handlers/
The problem is their teams are taking over Auth
for the whole application ...
I need my application MVC
to continue to use Identity Auth
which it is currently using, and hopefully generate its own custom attribute (for example [APIAuthorize]
) so that it only applies to mine API Controller
.
Perhaps I can hack and try to get this to work, but since this is a security issue, I decided to ask for some help on how best to implement this. Specifically, I need to know 1) what should I do in my Global.asax
(if anything), since the above url assumes I am doing this:
protected void Application_Start()
{
GlobalConfiguration.Configuration.MessageHandlers
.Add(new BasicAuthMessageHandler(){
PrincipalProvider = new DummyPrincipalProvider()
});
//...
}
But again this will lead to authentication to the whole application ... 2) What do I need to do in my custom auth attribute to do all this without issue.
And of course, if there is a better way to do all of this (without creating a separate application or increasing the complexity of the implementation for my clients), then I'm all ears.
source to share
I am using a filter attribute to decorate the actions I wanted to expose for Simple Auth. I can't remember where I got this code from (maybe stackoverflow I just don't have a link so I can't apply for credit)
public class BasicHttpAuthorizeAttribute : AuthorizeAttribute
{
protected override bool IsAuthorized(HttpActionContext actionContext)
{
if (Thread.CurrentPrincipal.Identity.Name.Length == 0)
{
// Get the header value
AuthenticationHeaderValue auth = actionContext.Request.Headers.Authorization;
// ensure its schema is correct
if (auth != null && string.Compare(auth.Scheme, "Basic", StringComparison.OrdinalIgnoreCase) == 0)
{
// get the credientials
string credentials = UTF8Encoding.UTF8.GetString(Convert.FromBase64String(auth.Parameter));
int separatorIndex = credentials.IndexOf(':');
if (separatorIndex >= 0)
{
// get user and password
string passedUserName = credentials.Substring(0, separatorIndex);
string passedPassword = credentials.Substring(separatorIndex + 1);
SimpleAES crypto = new SimpleAES();
string userName = crypto.DecryptString(ConfigurationManager.AppSettings.Get(Constants.SIMPLEUSERNAME));
string password = crypto.DecryptString(ConfigurationManager.AppSettings.Get(Constants.SIMPLEUSERPASSWORD));
// validate
if (passedUserName == userName && passedPassword == password)
{
Thread.CurrentPrincipal = actionContext.ControllerContext.RequestContext.Principal = new GenericPrincipal(new GenericIdentity(userName, "Basic"), new string[] { });
}
}
}
}
return base.IsAuthorized(actionContext);
}
}
Then I use it like this
[BasicHttpAuthorize]
public HttpResponseMessage MyExposedSimpleAuthAction()
source to share