petshop1

    技术2022-05-11  107

    我的主要突破口是账户管理这一部分,主要是账户的注册,登陆等,里面就涉及到了数据库操作。整个petshop自身还分成若干个项目显示层的是Web项目,业务逻辑层的是BLL项目,接口层是IDAL,还有相应的DALFactory来动态的决定具体绑定哪一个数据库,数据库的类型有两个,一种是Oracle,还有SQL Server,他们里面的Account都是动态的继承自IDAL里面的IAccount接口,比较这样使逻辑层和数据库层隔离,可以对多个数据库支持,如果修改逻辑,只需要对逻辑层里面的接口编码就可以了。我以后应该只会做一些应用,具体的绑定到某一个特定的数据库上,但是工厂模式还是需要好好理解一下的。       我从显示层Web层入手,看到了这样的一些方面,首先就是分层的概念,如果需要注册一个用户,从逻辑上分成三部分,账户的基本部分,包括用户名密码和Email,然后是用户的详细信息部分,制作成为了一个控件包括地址等信息,很有意思有真实姓名,所在国家城市之类的,发现这个东西居然不是联动的,前些日子做了一个动态选学生,根据院系专业年级类别五级联动的例子,可以整合在一起。这个控件在Controls这个目录下叫做AddressUI.ascx,封装了相应的ui和代码,值得提一下的就是这个类对应的get,set一段代码.  

    using PetShop.Model;using PetShop.BLL;using System.Web.UI;using System.Web.UI.WebControls;

    namespace PetShop.Web.Controls { public abstract class AddressUI : System.Web.UI.UserControl {  protected System.Web.UI.WebControls.TextBox txtFirstName;  protected System.Web.UI.WebControls.TextBox txtLastName;  protected System.Web.UI.WebControls.TextBox txtAddress1;  protected System.Web.UI.WebControls.TextBox txtAddress2;  protected System.Web.UI.WebControls.TextBox txtCity;  protected System.Web.UI.WebControls.TextBox txtZip;  protected System.Web.UI.WebControls.TextBox txtPhone;  protected System.Web.UI.WebControls.DropDownList listState;  protected System.Web.UI.WebControls.RequiredFieldValidator valFirstName;  protected System.Web.UI.WebControls.RequiredFieldValidator valLastName;  protected System.Web.UI.WebControls.RequiredFieldValidator valAddress1;  protected System.Web.UI.WebControls.RequiredFieldValidator valCity;  protected System.Web.UI.WebControls.RequiredFieldValidator valZip;  protected System.Web.UI.WebControls.RequiredFieldValidator valPhone;  protected System.Web.UI.WebControls.DropDownList listCountry;

      private void InitializeComponent() {    }

      // Page property to set or get the address  public AddressInfo Address {   get {    // Make sure we clean the input    string firstName = WebComponents.CleanString.InputText(txtFirstName.Text, 50);    string lastName = WebComponents.CleanString.InputText(txtLastName.Text, 50);    string address1 = WebComponents.CleanString.InputText(txtAddress1.Text, 50);    string address2 = WebComponents.CleanString.InputText(txtAddress2.Text, 50);    string city = WebComponents.CleanString.InputText(txtCity.Text, 50);    string state = WebComponents.CleanString.InputText(listState.SelectedItem.Text, 2);    string zip = WebComponents.CleanString.InputText(txtZip.Text, 10);    string country = WebComponents.CleanString.InputText(listCountry.SelectedItem.Text, 50);    string phone = WebComponents.CleanString.InputText(txtPhone.Text, 10);    return new AddressInfo(firstName, lastName, address1, address2, city, state, zip, country, phone);   }   set {    txtFirstName.Text = value.FirstName;    txtLastName.Text = value.LastName;    txtAddress1.Text = value.Address1;    txtAddress2.Text = value.Address2;    txtCity.Text = value.City;    txtZip.Text = value.Zip;    txtPhone.Text = value.Phone;    listState.SelectedItem.Value = value.State;    listCountry.SelectedItem.Value = value.Country;      }  } }}

     

    这里面有一段代码:

     

    using System;using System.Text;

    namespace PetShop.Web.WebComponents{ /// <summary> /// A sample class to clean the input into web pages  /// </summary> public sealed class CleanString {

      public static string InputText(string inputString, int maxLength) {

          StringBuilder retVal = new StringBuilder();

       // check incoming parameters for null or blank string   if ((inputString != null) && (inputString != String.Empty)) {    inputString = inputString.Trim();

        //chop the string incase the client-side max length    //fields are bypassed to prevent buffer over-runs    if (inputString.Length > maxLength)     inputString = inputString.Substring(0, maxLength);

        //convert some harmful symbols incase the regular    //expression validators are changed    for (int i = 0; i < inputString.Length; i++) {     switch (inputString[i]) {      case '"':       retVal.Append(""");       break;      case '<':       retVal.Append("<");       break;      case '>':       retVal.Append(">");       break;      default:       retVal.Append(inputString[i]);       break;     }    }

        // Replace single quotes with white space    retVal.Replace("'", " ");   }

       return retVal.ToString();     } }}

    这段东西主要作用就是对于一些html的特殊字符进行转义,也比较简单,但是可以直接把输入进行转义,比如你输入“自来 也”,那么这段东西在存储的时候就储存成了“自来 也”,这样显示的时候和存储在数据库的时候,就一直了,我觉得还比较有用,对于一些懂html知识的人来讲是个屏蔽,比如他的用户名输入为<font color="red">nyy</font>那么这个时候,就自动显示为红色了,这个方法可以进行控制,原样输出,很好。

    profile里面记录一些用户的习惯,作为一个新的控件来装载,存储着显示语言,默认宠物的category,这样的东西。然后就是写数据库,我只看对于sql server而言的,比较简单:

     

      public void Insert(AccountInfo acc) {   SqlParameter[] signOnParms = GetSignOnParameters();   SqlParameter[] accountParms = GetAccountParameters();   SqlParameter[] profileParms = GetProfileParameters();

       signOnParms[0].Value = acc.UserId;   signOnParms[1].Value = acc.Password;

       SetAccountParameters(accountParms, acc);   SetProfileParameters(profileParms, acc);          using (SqlConnection conn = new SqlConnection(SQLHelper.CONN_STRING_NON_DTC)) {    conn.Open();    using (SqlTransaction trans = conn.BeginTransaction()) {     try {      SQLHelper.ExecuteNonQuery(trans, CommandType.Text, SQL_INSERT_SIGNON, signOnParms);      SQLHelper.ExecuteNonQuery(trans, CommandType.Text, SQL_INSERT_ACCOUNT, accountParms);      SQLHelper.ExecuteNonQuery(trans, CommandType.Text, SQL_INSERT_PROFILE, profileParms);      trans.Commit();          }catch {      trans.Rollback();      throw;     }    }   }  }

    传进来的参数是一个Entity类的东西,里面存着我们需要的注册需要的属性,第一步就是把相应的parameter赋好,然后开始try,以后自己用的时候注意它的try catch的写法,需要对SqlTransaction 进行相应的commit和rollback,在SQLHelper.ExecuteNonQuery就是对SQLCommand的再次封装,存储了,他的语句就是普通的insert into ,并没有调用存储过程,我想也是因为insert没有必要作存储过程,没有太大的数据量,select就不行了。很晚了,还没吃饭,下一步就是找到登陆时是怎么做的,怎么操作Session的

    最后,我们来看一下,登陆是怎么做的。

       public bool ProcessLogin(string userId, string password){    // Use the account business logic layer to login    Account account = new Account();    AccountInfo myAccountInfo = account.SignIn(userId, password);    //If login is successful then store the state in session and redirect    if (myAccountInfo != null) {     HttpContext.Current.Session[ACCOUNT_KEY] = myAccountInfo;          // Determine where to redirect the user back too     // If they came in from the home page, take them to a similar page     if (FormsAuthentication.GetRedirectUrl(userId, false).EndsWith(URL_DEFAULT)) {      FormsAuthentication.SetAuthCookie(userId, false);      HttpContext.Current.Response.Redirect(URL_ACCOUNTSIGNIN, true);     }else{      // Take the customer back to where the came from      FormsAuthentication.SetAuthCookie(userId, false);      HttpContext.Current.Response.Redirect(FormsAuthentication.GetRedirectUrl(userId, false), true);     }     return true;        }else {     // Login has failed so return false     return false;    }   } 存储在session里面,很通用的做法。我应该动手了。

    最新回复(0)