Let's say that you write your own MembershipProvider (quite common if you want to use your own object model ..)
11 public class MyMemberShipProvider : System.Web.Security.MembershipProvider
12 {
Like many other articles explain, the most important Method is ValidateUser.
What very people often "forget"to mention is that all other features are not present in your provider. For example, the MaxInvalidPasswordAttempts is a property that you can set it to any number but nothing is going to happen.
In a Nutshell : you need to implement it yourself.
What I am showning below is a quite simple version but it's proves the point.
180 public override System.Boolean ValidateUser(System.String pUsername, System.String pPassword)
181 {
182 if (pUsername.Equals("demo") && pPassword.Equals("demo"))
183 {
184 return LoginSuccess();
185 }
186 return LoginFailed();
187
188 }
LoginFailed() will basically return false but also it would do the check if another attempt should be granted or not:
211 private bool LoginFailed()
212 {
213 //WebFailureAuditEvent.Raise(WebEventCodes.AuditFormsAuthenticationFailure);
214 LoginFailuresCount++;
215 if (LoginFailuresCount >= this.MaxInvalidPasswordAttempts)
216 throw new Exception("OK, that's it. Bye Bye");
217
218 return false;
219
220 }
You need to keep track of how many login failures :197 protected int LoginFailuresCount
198 {
199 get
200 {
201 if (HttpContext.Current.Session["Failures"] == null)
202 return 0;
203 return (int)HttpContext.Current.Session["Failures"];
204 }
205 set
206 {
207 HttpContext.Current.Session["Failures"] = value;
208 }
209 }
In the commented line where I was trying to Raise the "WebFailureAuditEvent", I read somewhere that I was a good idea to raise it but could not find any reference or example. If anybody knows how to do it --> please let me know.
Note: An improvement to this model would be to support "PasswordAttemptWindow" which in this case I did not implement.
Note: New Browser == new Session so it's not really state-of-the-art security technique it's a basic