珠海学网站开发,手机网站域名查询,网络产品营销策划方案,景区网站建设的重要性asp 2.0自带了许多方法#xff0c;很多东西都给我们封装好了#xff0c;但是这样就导致了我们自定义的空间越来越小。忙碌了两个星期#xff0c;一直想重写System.Web.Security.SqlMembershipProvider#xff0c;但是没有找到方法#xff0c;昨天在asp.net这个晚上上找到了…asp 2.0自带了许多方法很多东西都给我们封装好了但是这样就导致了我们自定义的空间越来越小。忙碌了两个星期一直想重写System.Web.Security.SqlMembershipProvider但是没有找到方法昨天在asp.net这个晚上上找到了解决方法真是很兴奋。 打下可以参考一下http://forums.asp.net/p/1042049/1458049.aspx#1458049我的大部分内容是按照里面的方法来写的。然后将中途遇到的问题做一部分解释。 步骤一首先下载一个ProviderToolkitSamples下载链接如下 http://msdn.microsoft.com/en-us/library/aa478948.aspx。 因为我们要重写SqlMembershipProvider好多要用到很多.net 2.0底层的方法这些方法是首先的就是我们不能直接使用比如我们要在类的前面定义using System.Web.SR就会报错错误如下System.Web.SR is inaccessible due to its protection level。既然我们要重写SqlMembershipProvider那么我们就要提供这个类中所使用的所有方法。 步骤二安装ProviderToolkitSamples在C:\Program Files\ASP.NET Provider Toolkit SQL Samples目录下找到下面的四个类分别是 SecUtil.csSqlConnectionHelper.csSQLMembershipProvider.csSR.cs。将他们拷贝打网站项目的app_code文件夹下面。 因为原来已经有了.vb的程序集我们这个时候如果将.cs文件放在同一个文件夹下会编译错误解决方法参考我前面的那一片博文App_Code目录中存放不同语言的类文件导致错误的解决方案。 还有就是将SQLMembershipProvider.cs改名为MySQLMembershipProvider.cs并且在类定义做如下修改 view plaincopy to clipboardprint? public class MySQLMembershipProvider : System.Web.Security.MembershipProvider { / } public class MySQLMembershipProvider : System.Web.Security.MembershipProvider{/} 步骤三重新定义一个比较方便的命名空间然后对web.config做一些修改我的修改如下 view plaincopy to clipboardprint?add nameMySQLMembershipProvider typeMyProviders.MySQLMembershipProvider connectionStringNameSiteSqlServer enablePasswordRetrievalfalse enablePasswordResettrue requiresQuestionAndAnswerfalse minRequiredPasswordLength3 minRequiredNonalphanumericCharacters0 requiresUniqueEmailfalse passwordFormatHashed applicationNameDotNetNuke description使用MVPHacksMembershipProvider/ add nameMySQLMembershipProvider typeMyProviders.MySQLMembershipProvider connectionStringNameSiteSqlServer enablePasswordRetrievalfalse enablePasswordResettrue requiresQuestionAndAnswerfalse minRequiredPasswordLength3 minRequiredNonalphanumericCharacters0 requiresUniqueEmailfalse passwordFormatHashed applicationNameDotNetNuke description使用MVPHacksMembershipProvider/ 从上面可以看出的命名空间是MyProvidersMyProviders是来自MySQLMembershipProvider.cs文件中的 view plaincopy to clipboardprint?namespace MyProviders { /// } namespace MyProviders {///} 接着更改membership defaultProvider如下 view plaincopy to clipboardprint?membership defaultProviderMySQLMembershipProvider userIsOnlineTimeWindow15 membership defaultProviderMySQLMembershipProvider userIsOnlineTimeWindow15 步骤四对MySQLMembershipProvider进行自定义修改。这里首先说一下 我们从前面的 public class MySQLMembershipProvider : System.Web.Security.MembershipProvider{} 就可以看出我们自定义的MySQLMembershipProvider 继承了System.Web.Security.MembershipProvider而不是System.Web.Security.SqlMembershipProvider。但是我们的代码确实SqlMembershipProvider这样就给了我们完全的自定义空间想想就让人兴奋。 我这次项目的目标是将已有项目的加密方式改成16位的MD5加密方式一次我在MySQLMembershipProvider类里面添加了一个求md5的方法代码如下 view plaincopy to clipboardprint?//注自加求md5密码的静态方法 public static string GetMd5(string str)//求MD5 { return System.Web.Security.FormsAuthentication.HashPasswordForStoringInConfigFile(str, MD5).ToLower().Substring(8,16); } //注自加求md5密码的静态方法 public static string GetMd5(string str)//求MD5 { return System.Web.Security.FormsAuthentication.HashPasswordForStoringInConfigFile(str, MD5).ToLower().Substring(8,16); } 我们知道md5加密时单向的这和SqlMembershipProvider中的Hashed加密方式类似所以我想到的是直接将Hashed改写为md5类型这样其他原封不动修改工作量大大减少。 下面来讨论加密方式我们在源代码中可以找到 view plaincopy to clipboardprint?string salt GenerateSalt(); string pass EncodePassword(password, (int)_PasswordFormat, salt); string salt GenerateSalt(); string pass EncodePassword(password, (int)_PasswordFormat, salt); 这表明加密方式是由EncodePassword(string pass, int passwordFormat, string salt)方法来控制的下面是我修改后的代码 view plaincopy to clipboardprint?internal string EncodePassword(string pass, int passwordFormat, string salt) { if (passwordFormat 0) // MembershipPasswordFormat.Clear return pass; byte[] bIn Encoding.Unicode.GetBytes(pass); byte[] bSalt Convert.FromBase64String(salt); byte[] bAll new byte[bSalt.Length bIn.Length]; byte[] bRet null; Buffer.BlockCopy(bSalt, 0, bAll, 0, bSalt.Length); Buffer.BlockCopy(bIn, 0, bAll, bSalt.Length, bIn.Length); if (passwordFormat 1) { // MembershipPasswordFormat.Hashed HashAlgorithm s HashAlgorithm.Create( Membership.HashAlgorithmType ); bRet s.ComputeHash(bAll); //手动添加 return GetMd5(pass); } else { bRet EncryptPassword( bAll ); } return Convert.ToBase64String(bRet); } internal string EncodePassword(string pass, int passwordFormat, string salt) { if (passwordFormat 0) // MembershipPasswordFormat.Clear return pass; byte[] bIn Encoding.Unicode.GetBytes(pass); byte[] bSalt Convert.FromBase64String(salt); byte[] bAll new byte[bSalt.Length bIn.Length]; byte[] bRet null; Buffer.BlockCopy(bSalt, 0, bAll, 0, bSalt.Length); Buffer.BlockCopy(bIn, 0, bAll, bSalt.Length, bIn.Length); if (passwordFormat 1) { // MembershipPasswordFormat.Hashed HashAlgorithm s HashAlgorithm.Create( Membership.HashAlgorithmType ); bRet s.ComputeHash(bAll); //手动添加 return GetMd5(pass); } else { bRet EncryptPassword( bAll ); } return Convert.ToBase64String(bRet); } 这样只要我们在配置web.config的时候使用Hashed加密方式得到的就是MD5的密码。 步骤五下面我们要做的就是如何修改系统中原有账户的密码。 首先我们在DNN中注册一个用户假设我们注册账号和密码都是testmd5那么这个时候我们去数据库中查看会发现有一个密码为 3a25306bb46a03d6的账户这个就是我们新建的testmd5密码的16位md5密码。 我们通过下面的脚本来更改host的密码让其密码也成为testmd5.view plaincopy to clipboardprint?/* -- Database Utility --------------------------------------------------------------------------- Description : Reset a Password in a DotNetNuke database Author : Tony Tullemans Date Created : 18.04.2007 Note/s : Before you run this script you must know the UserName and Password of another registered DNN user in the database you wish to affect. ----------------------------------------------------------------------------------------------- */ DECLARE databaseName VARCHAR(128) SELECT databaseName DB_NAME() PRINT RESET PASSWORD IN DATABASE : databaseName PRINT ----------------------------- REPLICATE(-, DATALENGTH(databaseName )); DECLARE knownUserName NVARCHAR(128) DECLARE lostUserName NVARCHAR(128) DECLARE lostUserId NVARCHAR(128) DECLARE knownPassword NVARCHAR(128) DECLARE knownSalt NVARCHAR(128) SET knownUserName host SET lostUserName testmd5 SELECT knownPassword Password, knownSalt PasswordSalt FROM aspnet_Membership INNER JOIN aspnet_users ON aspnet_Membership.UserId aspnet_users.UserId where UserName knownUserName; PRINT PRINT Known Password for knownUserName is : knownPassword PRINT Known Password Salt for knownUserName is : knownSalt SELECT lostUserId aspnet_Membership.UserId FROM aspnet_Membership INNER JOIN aspnet_users ON aspnet_Membership.UserId aspnet_users.UserId WHERE UserName lostUserName; PRINT PRINT UserID for lostUserName is : lostUserId PRINT IF (DATALENGTH(lostUserName) 0 OR lostUserName IS NULL) PRINT Invalid Lost User Name lostUserName ELSE BEGIN IF (DATALENGTH(knownUserName) 0 OR knownUserName IS NULL) PRINT Invalid Lost User Name lostUserName ELSE BEGIN IF (DATALENGTH(knownPassword) 0 OR knownPassword IS NULL) PRINT Invalid Known Password knownPassword ELSE BEGIN IF (DATALENGTH(knownSalt) 0 OR knownSalt IS NULL) PRINT Invalid Known Salt knownSalt ELSE BEGIN PRINT PRINT BEFORE SELECT left(UserName, 12) as UserName, aspnet_Membership.UserId, left(Email, 20) as Email, Password, PasswordSalt FROM aspnet_Membership INNER JOIN aspnet_users ON aspnet_Membership.UserId aspnet_users.UserId WHERE UserName IN ( knownUserName, lostUserName ); PRINT PRINT Changing Password for User Id : lostUserId to knownPassword PRINT UPDATE aspnet_Membership SET Password knownPassword, PasswordSalt knownSalt -- SELECT UserId, Password, PasswordSalt -- FROM aspnet_Membership WHERE UserId lostUserId; PRINT PRINT AFTER SELECT left(UserName, 12) as UserName, aspnet_Membership.UserId, left(Email, 20) as Email, Password, PasswordSalt FROM aspnet_Membership INNER JOIN aspnet_users ON aspnet_Membership.UserId aspnet_users.UserId WHERE UserName IN ( knownUserName, lostUserName ); END END END END GO PRINT PRINT * * * END OF SCRIPT * * * PRINT GO /* -- Database Utility --------------------------------------------------------------------------- Description : Reset a Password in a DotNetNuke database Author : Tony Tullemans Date Created : 18.04.2007 Note/s : Before you run this script you must know the UserName and Password of another registered DNN user in the database you wish to affect. ----------------------------------------------------------------------------------------------- */ DECLARE databaseName VARCHAR(128)SELECT databaseName DB_NAME() PRINT RESET PASSWORD IN DATABASE : databaseNamePRINT ----------------------------- REPLICATE(-, DATALENGTH(databaseName )); DECLARE knownUserName NVARCHAR(128)DECLARE lostUserName NVARCHAR(128)DECLARE lostUserId NVARCHAR(128)DECLARE knownPassword NVARCHAR(128)DECLARE knownSalt NVARCHAR(128) SET knownUserName hostSET lostUserName testmd5 SELECT knownPassword Password, knownSalt PasswordSaltFROM aspnet_MembershipINNER JOIN aspnet_usersON aspnet_Membership.UserId aspnet_users.UserIdwhere UserName knownUserName; PRINT PRINT Known Password for knownUserName is : knownPasswordPRINT Known Password Salt for knownUserName is : knownSalt SELECT lostUserId aspnet_Membership.UserIdFROM aspnet_MembershipINNER JOIN aspnet_usersON aspnet_Membership.UserId aspnet_users.UserIdWHERE UserName lostUserName; PRINT PRINT UserID for lostUserName is : lostUserIdPRINT IF (DATALENGTH(lostUserName) 0 OR lostUserName IS NULL)PRINT Invalid Lost User Name lostUserNameELSE BEGINIF (DATALENGTH(knownUserName) 0 OR knownUserName IS NULL)PRINT Invalid Lost User Name lostUserNameELSE BEGINIF (DATALENGTH(knownPassword) 0 OR knownPassword IS NULL)PRINT Invalid Known Password knownPasswordELSE BEGINIF (DATALENGTH(knownSalt) 0 OR knownSalt IS NULL)PRINT Invalid Known Salt knownSaltELSE BEGINPRINT PRINT BEFORESELECT left(UserName, 12) as UserName, aspnet_Membership.UserId, left(Email, 20) as Email, Password, PasswordSaltFROM aspnet_Membership INNER JOIN aspnet_users ON aspnet_Membership.UserId aspnet_users.UserIdWHERE UserName IN ( knownUserName, lostUserName );PRINT PRINT Changing Password for User Id : lostUserId to knownPassword PRINT UPDATE aspnet_MembershipSET Password knownPassword,PasswordSalt knownSalt-- SELECT UserId, Password, PasswordSalt-- FROM aspnet_MembershipWHERE UserId lostUserId;PRINT PRINT AFTERSELECT left(UserName, 12) as UserName, aspnet_Membership.UserId, left(Email, 20) as Email, Password, PasswordSaltFROM aspnet_Membership INNER JOIN aspnet_users ON aspnet_Membership.UserId aspnet_users.UserIdWHERE UserName IN ( knownUserName, lostUserName );ENDENDENDENDGO PRINT PRINT * * * END OF SCRIPT * * *PRINT GO 上面的脚本在网上挺流行的大家可能都能找到。 最后还有一步把数据库中passwordformat改成1因为原来hashed默认的就是1.现在用md5替换hashed那么就应该是1. 结语奋战两个星期终于解决问题其实问题并不难很早以前就有人有同样的问题而且早已被解决难的如何找到解决问题的方法如何找到资源。在这中间我发现好多都是英文资料中文资料少之又少。这时候终于体现了英语的作用了。 致谢johnM2Land从不闲聊牛哥 本文来自CSDN博客转载请标明出处http://blog.csdn.net/xw13106209/archive/2010/01/05/5133690.aspx