Recently I asked a question about how to use ajax calls to
authenticate user in asp.net mvc, and I got my answer.
But then is decided to use 'Roles' property of 'GenericPrincipal' class
so I changed my code as follow to contain 'Roles':
HttpContext.User = new System.Security.Principal.
GenericPrincipal(new System.Security.Principal.GenericIdentity(login.LoginName),
userRole);
In my site.master view, I check to see which kind of roles users
belongs to and I show appropriate menu, but when I watch
'HttpContext.Current.User.Identity' values during debugging,
I see m_roles=string[0] and 'IsInRole("Admin")' returns false.
How could it be fixed?
Try setting the current thread principle:
System.Threading.Thread.CurrentPrincipal = principal;
as is shown here:
http://social.msdn.microsoft.com/forums/en-US/Vsexpressvcs/thread/5f9735a9-096b-47af-963d-e95130cad6b4
Related
I have to port a website which has a TFA authentication via sms/email to asp.net 6. The client doesn’t want to use an authenticator app. The application has some specialities such as the language of the user in the URL path as the first component.
In this post I searched a way to introduce the language part and was, although in a very ugly manner, successful.
However I'm also quite unhappy to use the default UI in general for this application, since I have to manually deactivate all the things that are not required but are included in the library. It feels extremely untidy to have such a huge framework of pages active for so little of required functionality. The only things I need are
Login with a username and password
Optionally checking a tfa email/sms code if the user has configured its account for this.
The configuration of the user's profile is done in another application and should not be included in this application (hence all the default identity ui stuff has to be deactivated).
I tried to create the authentication logic manually via controller actions and not installing the default ui at all. For the login with username and password, this was fairly easy.
However, setting up the TFA part seems quite tedious and dangerous (from a security perspective). I have not found any documentation what resources have to be registered and how to setup the authentication system.
Is searching out all the required dependencies and creating the code from the Microsoft source code of default identity UI the only way?
Or is there a template solution to accomplish the desired goal?
Since there seems no such information available, I gathered the necessary code from the ms source code. Maybe it helps someone:
Registration
Copied out of the ms source code, here the required registrations:
builder.Services.AddIdentityCore<MyUserType>().AddDefaultTokenProviders();
builder.Services.TryAddScoped<ITwoFactorSecurityStampValidator, TwoFactorSecurityStampValidator<MyUserType>>();
builder.Services.TryAddScoped<ISecurityStampValidator, SecurityStampValidator<MyUserType>>();
builder.Services.AddAuthentication(options => {
options.DefaultAuthenticateScheme = IdentityConstants.ApplicationScheme;
options.DefaultChallengeScheme = IdentityConstants.ApplicationScheme;
// options.DefaultSignInScheme = IdentityConstants.ExternalScheme;
})
.AddCookie(IdentityConstants.ApplicationScheme, o =>
{
o.LoginPath = [your login path];
o.LogoutPath = [your logout path];
})
//.AddCookie(IdentityConstants.ExternalScheme, o =>
//{
// o.Cookie.Name = IdentityConstants.ExternalScheme;
// o.ExpireTimeSpan = TimeSpan.FromMinutes(5);
//})
.AddCookie(IdentityConstants.TwoFactorRememberMeScheme, o =>
{
o.Cookie.Name = IdentityConstants.TwoFactorRememberMeScheme;
o.Events = new CookieAuthenticationEvents
{
OnValidatePrincipal = SecurityStampValidator.ValidateAsync<ITwoFactorSecurityStampValidator>
};
})
.AddCookie(IdentityConstants.TwoFactorUserIdScheme, o =>
{
o.Cookie.Name = IdentityConstants.TwoFactorUserIdScheme;
o.ExpireTimeSpan = TimeSpan.FromMinutes(5);
});
The registration for the external authentication is commented out, maybe someone wants to use that also, therefore i have not directly removed it from the code. The login path can be set accordingly to your login-action. See my other post about how to extend the login url to introduce language and other path components.
Controller-code
The controller's action code and views can then derived from the original default identity ui code. The AddDefaultTokenProviders call is required to have the email token provider registered.
Result
In this way, the default ui and all its abundant functionality is no more in the project and one can selectively decide, what parts to integrate.
I am trying to access session data from inside a view.
Use Case: I'm storing status messages in the session that will be displayed at the top of the page. Currently I implemented this by using a DisplayMessages() function that sets some ViewData[....] properties and calling it at the beginning of every controller action.
Goal: I want to only set the status message once without needing additional code in the controller to display the messages on the next page load.
So I'm trying to access the messages that are stored in the session directly from the view.
So far I have tried the following:
Dependency Injection of an IHttpContextAccessor (doesn't seem to work anymore with ASP .NET Core MVC 1.0.0
Creating a static class to access the session, including the change from next() to next.invoke() suggested in the comment
This didn't work. I could access the HttpContext and Session.IsAvailable was true, but there was no data in the session.
The following should work in the view: Context.Session.TryGetValue
If you are using the SessionExtensions then Context.Session.GetString will work.
Injecting IHttpContextAccessor does work, but starting with ASP.NET Core 1.0.0 RC2, the IHttpContextAcessor is not registered by default, because it has significant performance overhead per request. See this GitHub announcement for more information.
Tratcher posted:
IHttpContextAccessor can be used to access the HttpContext for the current thread. However, maintaining this state has non-trivial performance costs so it has been removed from the default set of services.
Developers that depend on it can add it back as needed:
services.AddSingleton<IHttpContextAccessor, HttpContextAccessor>();
But in your use case, I would suggest using a ViewComponent, which is a reusable piece of View with logic, that do not depend on a controller.
The documentation can be found here.
In your Views you would simply embed it with
#await Component.InvokeAsync("PriorityList", new { maxPriority = 2, isDone = false })
or
#Component.Invoke("PriorityList", new { maxPriority = 2, isDone = false })
for synchronous calls.
Still using a very old (and slightly customized) version of BlogEngine.NET on a Windows XP (!) server so I'm a bit afraid to upgrade.
In the past, I have written a couple of extensions in order to grant or prevent access to static pages and/or posts based upon the users / roles and / or the post categories. For instance, I can prevent access to the blog from unauthenticated users, I can grant access to a subset of the blog (post categories) to users having the 'Readers' role, etc.
I noticed that images are still accessible, either ones stored explicitly under the /App_Data/files/ folder and served by the image.axd handler, or ones associated with blog posts.
Is there an extension point available where I could add some logic to prevent access to images based on criteria such as authentication and/or users / roles ? Perhaps based upon their file extensions, or whatnot ?
I don't know about an official extension point but I think the edits you need to make are as follows.
According to this line in the web.config
<add verb="*" path="image.axd" type="BlogEngine.Core.Web.HttpHandlers.ImageHandler, BlogEngine.Core" validate="false"/>
The image.axd is handled by BlogEngine.Core.Web.HttpHandlers.ImageHandler
If you look in the BlogEngine.Core project you will find the ImageHandler.cs that defines this class. Assuming you need access to the Session you will need to IReadOnlySessionState as an implemented interface to the class.
public class ImageHandler : IHttpHandler, IReadOnlySessionState {
...
}
Once this is in place you can access the Session in the ProcessRequest Method to perform your custom checks.
public void ProcessRequest(HttpContext context) {
if(context.Session["SomeKey"] == true){
//serve image code goes here
}
}
We have an MVC ASP.NET Application. A Person can see a View, if they are in one of the Active Directory Groups. We have only one box for hosting our Database and Application(code)
Our Problem:
A person does not exist in any one of The ADGroups, but he is Administrator on the box.
For Some Reason, he is authenticated with the View.. He is not supposed to be authenticated.
Do not know why its happening.
I know this is unique problem, Does anyone had similar issue?
This is the code we are using for authenticating a user
if (LoginHelper.IsUserMemberOfRoles(LoginHelper.GetLoggedInUser(), new List<string> { GroupEnum.OurADGroupName.ToString()}))
{
//authenticated
}
else
{
//Redirect to not authorised View
}
My Understanding:
As the Person is Admin on the Box, does this override all ADGroupName Permissions.
It sounds very silly but I thing, this is one possibilty?
He surely must be an admin or in a group in Active Directory
I have an MVC3 app for which I want to implement claims support. My goal is as follows:
provide a SignIn link, which when clicked displays a popup window with username/password and Facebook/WindowsLive/Google etc. links
automatically redirect to my SignIn page when a protected controller is accessed e.g. /Order/Delete
I've set up the application and providers in AppFabricLabs.com and included the STS in my project. I've also created an implementation of IAuthorizationFilter so I can mark my controllers as [WifAuth] and successfully get the OnAuthorization method called. I've implemented the use-case where the visitor has not been authenticated like this:
private static void AuthenticateUser(AuthorizationContext context)
{
var fam = FederatedAuthentication.WSFederationAuthenticationModule;
var signIn = new SignInRequestMessage(new Uri(fam.Issuer), fam.Realm);
context.Result = new RedirectResult(signIn.WriteQueryString());
}
and successfully get AppFabricLabs page with my Identity Provider choices (haven't figured out how to customise that page). When I log in my returnUrl gets called so I land in a controller method /Home/FederationResult, however the form posted to me contains only wa and wresult fields but I need wctx to know where to send the user... I haven't been able to figure out why.
the wresult is an XML document that contains (amongst a bzillion other things) the name and e-mail address of the user logging in but sadly does not contain the url to which the user was headed.
have I failed to configure something or am I just off base? thoughts anyone?
e
Just specify a Context for the SignInRequestMessage:
signIn.Context = HttpContext.Current.Request.RawUrl;
The wctx parameter is included in every request/response and also part of the form posted finally to your site.