I'm using In-Build template for Login and Registration in Web Api.
It uses Token based Authentication .
But what I want is to login a user I want use Basic authentication, after web api will return a token then now I want to use that to to call api methods.
right now I request for login like this
var resp = $http({
url: "/TOKEN",
method: "POST",
data: $.param({ grant_type: 'password', username: userlogin.username, password: userlogin.password }),
headers: { 'Content-Type': 'application/x-www-form-urlencoded' },
});
and It return me a token, which I send it with next request to call authorize methods.
But I wand to send username and password : separated like basic authentication
HttpClient client = new HttpClient();
string authInfo = "admin" + ":" + "123456";
authInfo = Convert.ToBase64String(Encoding.Default.GetBytes(authInfo));
client.DefaultRequestHeaders.Authorization = new AuthenticationHeaderValue("Basic", authInfo);
client.BaseAddress = new Uri("http://localhost:63173/TOKEN");
And server side I will decode it back to get username and password to validate user and will return authentication token.
var encoding = Encoding.GetEncoding("iso-8859-1");
credentials = encoding.GetString(Convert.FromBase64String(credentials));
int separator = credentials.IndexOf(':');
string name = credentials.Substring(0, separator);
string password = credentials.Substring(separator + 1);
But I don't know where to modify the existing code.
The only workaround I can think of is writing a simple Owin middleware that remaps the credentials found in the Authorization header to form fields, executed at the beginning of the Owin pipeline.
Something similar to this:
public class Startup
{
public void Configuration(IAppBuilder app)
{
app.Use(async (ctx, n) =>
{
if (ctx.Request.Path == new PathString("/path/to/token")) //the same path you specified in the "TokenEndpointPath" property of "OAuthAuthorizationServerOptions"
{
var authHeader = ctx.Request.Headers["Authorization"];
if (!string.IsNullOrWhiteSpace(authHeader) && authHeader.StartsWith("Basic "))
{
//parse here authHeader
var name = GetUsernameFromHeader(authHeader);
var password = GetPasswordFromHeader(authHeader);
//change the above lines with your parsing methods
var form = new Dictionary<string, string[]>()
{
{ "grant_type", new [] {"password" }},
{ "username", new []{ name }},
{ "password", new [] { password}}
};
ctx.Set<IFormCollection>("Microsoft.Owin.Form#collection", new FormCollection(form));
}
}
await n.Invoke();
});
//app.UseWebApi...
//other middlewares
}
}
I warn you that this approach just writes those values to the Owin context and will work as long as the underlying OAuthAuthorizationServerMiddleware
implementation doesn't change.