Password Policy in ASP.NET Profile (Membership) - c#

In change password page, we have this code, So if we want to change Password Policy into "StrongPolicy", have we a way or is it by default?
Also can we change it to weak policy ?
I read MSDN but couldn't find it.
Membership mu ;
mu=Membership.GetUser(txtUserName.Text);
mu.UnlockUser();
var newPass= mu.ResetPassword();
mu.ChangePassword(newPass,TxtPassword.Text);

If you are using MVC 5 (possibly MVC4, havent checked).
Theres a nice easy way of changing this without changing the config. In your solution explorer, go to
'App_Start' > IdentityConfig
Here you will see a passwordvalidator, changing these settings will allow you to alter the complexity of passwords required for your site:
manager.PasswordValidator = new PasswordValidator
{
RequiredLength = 6,
RequireNonLetterOrDigit = true,
RequireDigit = true,
RequireLowercase = true,
RequireUppercase = true,
};

By default the memebership provider in .net restricts you to have password of length 7(atleast) and of which one character must be alpha-numeric.
Although there many ways by which you can change that. You can check Changing password policy setting in membership provider.
Using minimum length and non-alphanumeric character
<membership ...>
<providers>
<add minRequiredPasswordLength=10 minRequiredNonalphanumericCharacters=2 .../>
</providers>
</membership>
Using regular expression
<membership ...>
<providers>
<add passwordStrengthRegularExpression=
"^(?=.*\d)(?=.*[a-z])(?=.*[A-Z]).{8,10}$" .../>
</providers>
</membership>
The above code is from the same site.

By default ASP.NET Membership enforces strong passwords. If you want to make it weaker, by changing the configuration settings in Web.config
<membership>
<providers>
<add passwordStrengthRegularExpression= "" .../>
<add minRequiredPasswordLength=... minRequiredNonalphanumericCharacters=2 .../>
</providers>
</membership>
MSDN
By default, the ASP.NET membership providers enforce strong passwords.
For example, the SqlMembershipProvider and the
ActiveDirectoryMembership providers ensure that passwords are at least
seven characters in length with at least one non-alphanumeric
character. Ensure that your membership provider configuration enforces
passwords of at least this strength. To configure the precise password
complexity rules enforced by your provider, you can set the following
additional attributes:
More information :
http://msdn.microsoft.com/en-us/library/ff649487.aspx

Related

Roles.GetRolesForUser() & Roles.GetAllRoles() returns empty

web.config
<roleManager enabled="true" defaultProvider="SqlRoleManager">
<providers>
<clear />
<add name="SqlRoleManager"
type="System.Web.Security.SqlRoleProvider"
connectionStringName="DefaultConnection"
/>
</providers>
</roleManager>
in asp.net mvc 5, i'm trying to detect the role of the current user so i can redirect him to a page specific to it's role but
in my controller
if (Roles.IsUserInRole(User.Identity.GetUserName(), "superadmin")
or
if (Roles.IsUserInRole(User.Identity.Name, "superadmin")
the both are not true, i'm sure that i'm logged bec User.Identity.GetUserName() is displaying my login
Trying to debug, i found that Roles.GetRolesForUser() is empty, i've checked online resources but still no solution
Further debugging shows that Roles.GetAllRoles() is also empty, but my AspNetRoles table has 5 records.
I've looked at AspNetUserRoles and i found my current User id assigned to specific role id
and i've successfully run aspnet_regsql.exe to add all features but still cannot get the Roles
i think aspnet_regsql.exe is for web forms (i'm not sure)
I'm on my phone so can't double-check, but I'm sure IsUserInRole() will accept a single argument like IsUserInRole("superadmin") to check the current user in a session. I would remove the username part because you're checking the current user and not a different named user. It's quicker and will at least check and eliminate one part of the logic.
How are you seeding the roles?

How to verify user's password against hash value in AspNetUsers table in MVC.NET?

I'm recieving two strings: the username and the password, based on which, I'm retrieving and instance of AspNetUser, which has the corresponding fields. I want to produce the corresponding Id but only if the name and pass check out. The former is simple because it's in plain text.
How can I, given the provided password, verify that the hash value is correct?
I have looked at the code in the default template for a few hours but I can't get my head around it. Based on this page, I've created my own HASHes but the one I'm getting differs from the on in the DB, so I'm guessing that I'm doing it wrong or that they are adding some magic part before hashing it.
My: E8B9C259EAB04BBB67B2D67AF5745B
DB: AFczTgO67ViTWwZNejEiTyKRg5s96x5mOmwFFBj7yRUpys/5duOw0q6I6imCm1t1hQ==
See above, can you spot the difference...? The password used is "Abc123()", in case it matters.
Am I barking up the wrong tree when I try to use MD5CryptoServiceProvider? Is there a default string that's being jacked into the source before the hash's being computed?
If there are comments regarding the best practices, I'm open to them, of course. Bear in mind, however, that the security issues being my weak point, have bothered me for a long time so this is the way I want to go to understand the concept, down to bits and bolts. If possible, that is.
I can optionally use the facility that MS provided for me but I haven't got that right yet, neither. It appears to me like a lot of code doing "something here, something there".
<system.web>
<membership defaultProvider="donkey">
<providers >
<clear/>
<add name="donkey" passwordFormat="Hashed" />
</providers>
</membership>
<authentication mode="None" />
<compilation debug="true" targetFramework="4.5.2" />
<customErrors mode="Off"></customErrors>
<httpRuntime targetFramework="4.5.2" />
</system.web>
The Membership class you're using provides the static ValidateUser method:
Verifies that the supplied user name and password are valid.
public static bool ValidateUser(
string username,
string password
)
public void Login_OnClick(object sender, EventArgs args)
{
if (Membership.ValidateUser(UsernameTextbox.Text, PasswordTextbox.Text))
FormsAuthentication.RedirectFromLoginPage(UsernameTextbox.Text, NotPublicCheckBox.Checked);
else
Msg.Text = "Login failed. Please check your user name and password and try again.";
}

Change Password Issue in AspNet MembershipProvider

I am using AspNet Membership Provider in MVC 3.
I am facing issue in change password.
I have two functionality in my project
Forgot password : ask security question and based on security answer change password.
Admin change password: a admin can change password of any user without knowing old password or security answer.
Now the issue is that for functionality # 1, i have to make changes in web config for making requiresQuestionAndAnswer="true" for change password so that i can change password only if security answer is valid.
<membership>
<providers>
<clear />
<add name="AspNetSqlMembershipProvider" type="System.Web.Security.SqlMembershipProvider" connectionStringName="ApplicationServices" enablePasswordRetrieval="false" enablePasswordReset="true" requiresQuestionAndAnswer="true" requiresUniqueEmail="false" maxInvalidPasswordAttempts="5" minRequiredPasswordLength="6" minRequiredNonalphanumericCharacters="0" passwordAttemptWindow="10" applicationName="/" />
</providers>
</membership>
and i am using below code for changing password in forgot password:
string resetPassword = res.ResetPassword(model.PasswordAnswer);
MembershipService.ChangePassword(model.Username, newPassword, model.NewPassword)
now for situation # 2, where for admin i wants facility to change password of any user without knowing old password or security answer. which is only possible (as i know) by making requiresQuestionAndAnswer="false" .
Note:I am using separate MVC AREA for admin part, so may be a another web config can do some magic.
please suggest how can i have have both the features (reset password with security answer and without security answer) together in single application.
Thanks a lot
Finally got the answer:
In web config i set the requiresQuestionAndAnswer="true" so this resolves the issue#1, now for forgot password a security answer is required.
and for issue#2 where i want the facility for admin to change password of any user without knowing old password or security answer. I have used Reflection for it to change the value of private variable _RequiresQuestionAndAnswer to false then reset the password and then again set its value to true:
var _requiresQA = Membership.Provider.GetType().GetField("_RequiresQuestionAndAnswer",
System.Reflection.BindingFlags.Instance | System.Reflection.BindingFlags.NonPublic);
//change the value in the private field
_requiresQA.SetValue(Membership.Provider, false);
//do the reset
tempPassword = user.ResetPassword();
//set it's original value
_requiresQA.SetValue(Membership.Provider, true);
I got this solution at : http://djsolid.net/blog/asp.net-membership---change-password-without-asking-the-old-with-question-and-answer

How do I go about Authorization in MVC 2?

How do I go about Authorization in MVC 2?
I want to use AD groups/roles rather than the default that is provided. That seems to be "AspNetSqlMembershipProvider".
Anyway I put :
[Authorize(Users = "username")]
public ActionResult About()
{
ViewData["Welcome"] = "Welcome About";
return View();
}
And then loading the page gives me: The connection name 'ApplicationServices' was not found in
the applications configuration or the connection string is empty.
Line 34: <providers>
Line 35: <clear />
Line 36: <add name="AspNetSqlMembershipProvider" type="System.Web.Security.SqlMembershipProvider" connectionStringName="ApplicationServices" enablePasswordRetrieval="false" enablePasswordReset="true" requiresQuestionAndAnswer="false" requiresUniqueEmail="false" maxInvalidPasswordAttempts="5" minRequiredPasswordLength="6" minRequiredNonalphanumericCharacters="0" passwordAttemptWindow="10" applicationName="/" />
Line 37: </providers>
Line 38: </membership>
I read this stackoverflow, but after creating a custom class AuthorizationAttribute extending ActionFilterAttribute ContextCache, IoC and a number of other things could not resolve, and not really sure where to go from there. I also read this stackoverflow and it suggests going about it differently, starting to get confused.
How do I go about using AD groups rather than AspNetSqlMembershipProvider in MVC app ?
Bonus question: Say I have a "Edit" button a page. Can I add logic to decide whether to render this button based on the Authorization ?
Thank you for your help.
Edit: some further information.
I do not intend to block or allow ALL access to this site.
I intend to have 3 basic user groups differentiating level of access, i.e. Super Admin, Admin,
Basic Access.
There will be no log in form, when the user hits the site we will check which group the user is a member of- then the page renders based on that.
So for example, user 'bob' in 'Basic Access' group will hit the page and buttons/actions like "Edit", "Delete" are disabled, so basically a read only group. But user 'jim' in group 'Super Admin', has all actions/buttons available to him. How could I achieve this ?
You should look into Windows Authentication
Still use the Authorize attribute on your controllers/actions, but configure your site to use Windows Authentication instead.
Bonus answer: To check authentication and authorization in code, you can use one of the following from a controller:
this.User.Identity.IsAuthenticated
this.User.Identity.Name
this.User.IsInRole("roleName")
The answers to use Windows authentication work great, with the following caveats.
First, the server must be joined to your Domain. And it has to have free AD access if there are any firewalls in place.
Second, you have to be ok with having a popup dialog for login, rather than using a form based login.
If you need AD with forms login, then there's more work involved. Can you be more specific about your needs?
well, you can restrict access to the site via webconfig.
<authentication mode="Windows" />
<authorization>
<allow roles="[YOURADSERVER]\[YOUR AD GROUP]"/>
<deny users="*"/>
</authorization>
this will block any others not listed in the given ad groups.
in IIS you will need to disable anon access and enable windows auth

The Role Manager feature has not been enabled

Got the following ProviderException :
The Role Manager feature has not been enabled.
So far so good.
Is there somewhere a method that can be called to check if the Role Manager has been enabled or not?
You can do this by reading from the boolean property at:
System.Web.Security.Roles.Enabled
This is a direct read from the enabled attribute of the roleManager element in the web.config:
<configuration>
<system.web>
<roleManager enabled="true" />
</system.web>
</configuration>
Update:
For more information, check out this MSDN sample: https://msdn.microsoft.com/en-us/library/aa354509(v=vs.110).aspx
If you got here because you're using the new ASP.NET Identity UserManager, what you're actually looking for is the RoleManager:
var roleManager = new RoleManager<IdentityRole>(new RoleStore<IdentityRole>(new ApplicationDbContext()));
roleManager will give you access to see if the role exists, create, etc, plus it is created for the UserManager
I found 2 suggestions elsewhere via Google that suggested a) making sure your db connectionstring (the one that Roles is using) is correct and that the key to it is spelled correctly, and b) that the Enabled flag on RoleManager is set to true. Hope one of those helps. It did for me.
Did you try checking Roles.Enabled? Also, you can check Roles.Providers to see how many providers are available and you can check the Roles.Provider for the default provider. If it is null then there isn't one.
I found this question due the exception mentioned in it. My Web.Config didn't have any <roleManager> tag. I realized that even if I added it (as Infotekka suggested), it ended up in a Database exception. After following the suggestions in the other answers in here, none fully solved the problem.
Since these Web.Config tags can be automatically generated, it felt wrong to solve it by manually adding them. If you are in a similar case, undo all the changes you made to Web.Config and in Visual Studio:
Press Ctrl+Q, type nuget and click on "Manage NuGet Packages";
Press Ctrl+E, type providers and in the list it should show up "Microsoft ASP.NET Universal Providers Core Libraries" and "Microsoft ASP.NET Universal Providers for LocalDB" (both created by Microsoft);
Click on the Install button in both of them and close the NuGet window;
Check your Web.config and now you should have at least one <providers> tag inside Profile, Membership, SessionState tags and also inside the new RoleManager tag, like this:
<roleManager defaultProvider="DefaultRoleProvider">
<providers>
<add name="DefaultRoleProvider" type="System.Web.Providers.DefaultRoleProvider, System.Web.Providers, Version=2.0.0.0, Culture=neutral, PublicKeyToken=NUMBER" connectionStringName="DefaultConnection" applicationName="/" />
</providers>
</roleManager>
Add enabled="true" like so:
<roleManager defaultProvider="DefaultRoleProvider" enabled="true">
Press F6 to Build and now it should be OK to proceed to a database update without having that exception:
Press Ctrl+Q, type manager, click on "Package Manager Console";
Type update-database -verbose and the Seed method will run just fine (if you haven't messed elsewhere) and create a few tables in your Database;
Press Ctrl+W+L to open the Server Explorer and you should be able to check in Data Connections > DefaultConnection > Tables the Roles and UsersInRoles tables among the newly created tables!
If you are using ASP.NET Identity UserManager you can get it like this as well:
var userManager = Request.GetOwinContext().GetUserManager<ApplicationUserManager>();
var roles = userManager.GetRoles(User.Identity.GetUserId());
If you have changed key for user from Guid to Int for example use this code:
var roles = userManager.GetRoles(User.Identity.GetUserId<int>());
<roleManager
enabled="true"
cacheRolesInCookie="false"
cookieName=".ASPXROLES"
cookieTimeout="30"
cookiePath="/"
cookieRequireSSL="false"
cookieSlidingExpiration="true"
cookieProtection="All"
defaultProvider="AspNetSqlRoleProvider"
createPersistentCookie="false"
maxCachedResults="25">
<providers>
<clear />
<add
connectionStringName="MembershipConnection"
applicationName="Mvc3"
name="AspNetSqlRoleProvider"
type="System.Web.Security.SqlRoleProvider, System.Web, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a" />
<add
applicationName="Mvc3"
name="AspNetWindowsTokenRoleProvider"
type="System.Web.Security.WindowsTokenRoleProvider, System.Web, Version=2.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a" />
</providers>
</roleManager>
Here is the code that you need to put in your Account Controller in MVC5 and later
to get the list of roles of a user:
csharp
public async Task<ActionResult> RoleAdd(string UserID)
{
return View(await
UserManager.GetRolesAsync(UserID)).OrderBy(s => s).ToList());
}
There is no need to use Roles.GetRolesForUser() and enable the Role Manager Feature.

Categories