首    页 建模架构 设计模式 培训咨询 jdon框架 论坛

用户注册系统的Refactoring(重整)过程(1)

板桥里人 http://www.jdon.com 2002/06/15

Refactoring就是在不改变代码外观功能基础上,对代码设计质量的提高,在这里我们不讨论Refactoring的理论,而是就实例"用户注册系统"讨论如何使用设计模式进行重整。

关于设计模式和重整的理论可以见:Refactoring To Patterns 在其中,用什么设计模式代替什么进行了理论总结,相信对你读这篇文章有所帮助。

用户注册系统的需求分析
用户注册系统一般应用于访问网站 的用户注册,按照其功能分以下几种:

1.增加 删除用户资料
2.忘记密码后可查询密码
3.密码修改
4.密码验证

其中变化最大的是用户资料的列项,不同网站可能要求用户填写的资料明细不太一样,比如:专门面向律师行业的网站有的可能要求用户填写律师的案例,而面向一般公司网站则要求用户填写自己所属行业,等等。

如果将这系统中的不变的东西“固化”下来,提供对变化的适应能力,是我们重整的目标。

用户注册系统第一稿
很显然,第一步我们需要数据库的设计:

####用户资料数据库
CREATE TABLE profile (
  userid varchar(20) NOT NULL, #用户id
  username varchar(50) NOT NULL, #用户姓名
  email varchar(50), #Email地址

  gender tinyint(4) NOT NULL, #性别
  occupation tinyint(4), #职业

  location varchar(200), #住址
  city varchar(20), #城市
  country tinyint(4), #国家

  zipcode varchar(50), #邮政编码
  homephone varchar(50), #家庭电话或联系电话

  cardnumber varchar(20), #身份证号码
  birthday date DEFAULT '0000-00-00', #出生日期

  regip varchar(20), #注册时的IP 公安局追查用
  regdate datetime DEFAULT '0000-00-00 00:00:00' NOT NULL, #注册日期
  PRIMARY KEY (userid),
  UNIQUE email (email),
  UNIQUE userid (userid)
);


###本数据库是密码验证用
CREATE TABLE password (
  userid varchar(20) DEFAULT '' NOT NULL, #用户id
  password varchar(16) DEFAULT '' NOT NULL, #密码 使用PASSWORD()加密后的
  PRIMARY KEY (userid),
  KEY password (password)
);


###本数据库是用来提供用户查询密码用的
CREATE TABLE passwordassit (
  userid varchar(20) DEFAULT '' NOT NULL, #用户id
  oldpassword varchar(16) DEFAULT '' NOT NULL, #密码 未加密的
  passwdtype tinyint(4), #密码提示问题
  passwdanswer varchar(100), #密码回答
  PRIMARY KEY (userid),
  KEY passwdtype (passwdtype)
);

如上所示,我们根据需求,理所当然设计上面三个数据库。当然没有太多经验用户可能就设计一个数据库,那为什么将Password和profile分开,是为了密码验证用,我们在整个系统的其他部分都要加上密码验证功能,以便只有注册用户才能使用该系统,所以频繁的密码验证,对数据库访问量很大,所以将password和userid单独成一个表,当然速度快,且符合单一对象完成单一功能的面向对象设计思路。

在程序设计方面,我们首先提供用户一个注册表单,用于输入注册信息,这是个Jsp程序.

Jsp中使用Usebean 和setProperty 和数据Javabean直接映射。

具体程序可在本站“资料”中下载。这是一个最简单的Jsp/Javebean系统。

Jsp程序:
1. signup.jsp 用户注册 新增 修改
2. password.jsp 修改密码
3. forgetpassword.jsp 用于提示忘记密码的用户
4. signin.jsp 密码验证

相关的数据操作Javabean:
1. Profile.java 操作数据库profile
2. Password.java 操作password数据库
3. Signin.java 操作password 和passwordassist数据库
4. BeansConstants.java 存放系统配置信息
5. Mysql.java mysql数据库驱动程序
6. SendMail.java Email驱动程序 向用户信箱发送密码。

我们主要看看password.java这个程序:

public class Password {


  protected int userid = 0;

  protected String newpassword = "";
  protected String newpassword2 = "";
  protected String email = "";

  
  public void setUserid(int userid) { this.userid = userid; }
  public void setNewpassword(String newpassword) {
     this.newpassword = newpassword; }
  public void setNewpassword2(String newpassword2) {
     this.newpassword2 = newpassword2; }

  //getmypassword
  public void setEmail(String email) { this.email = email; }

  /** 改变密码
   * @param userid
   * @param newpassword
   *
   */
  public void update() throws Exception
  {
    if (newpassword == null || newpassword.equals("") || newpassword2 == null     || newpassword2.equals("") || !newpassword.equals(newpassword2))
    {
        throw new Exception("something wrong with new Password maybe not
       same!");
    }

    try {
       String sql = "update password set password=PASSWORD(?) where                      userid=? and password=PASSWORD(?)";
       String assitsql = "update passwordassit set       
       passwdtype=?,passwdanswer=?,oldpassword =? where userid=?";
       Mysql mysql = new Mysql(sql);
       mysql.setString(1, newpassword);
       mysql.setString(2, userid);
       mysql.setString(3, password);
       mysql.executeUpdate();

       mysql.prepareStatement(assitsql);
       mysql.setInt(1,passwdtype);
       mysql.setString(2,passwdanswer);
       mysql.setString(3, newpassword);
       mysql.setString(4,userid);
       mysql.executeUpdate();

       mysql.close();
       mysql = null;

    } catch (Exception ex) {
       throw new Exception("Password.update()"+ex.getMessage());
    }
  }

  /** 获得忘记的密码
  * @param email
  * @return String password
  */
  public String getMypassword() throws Exception{
 
    ......//类似上面的数据库操作

  }

}

password.jsp 和forgetpassword.jsp就是分别调用这个javabean中update()和getMypassword()方法来完成密码修改和获取密码的功能。

截至目前为止,该系统还只是一个简单思想的系统,没有太多面向对象的概念,所以它也无法面对太多的需求变化。

但是现在恰恰有一个大的需求变化了,可能来自你老板或客户。需求的变化是驱使你去refactor的一个重要原因.

一般程序员是最怕听到"变化"一词,需求变化意味着很多工作需要重新做,但是

"没有什么东西能够阻止客户在核准了specification以后再次改变需求。..如果客户愿意花钱,它天天想改变需求都可以。 "

"一个最具竞争力的企业就是最能快速相应变化的企业。适应变化是一个企业的核心竞争能力。而软件之所以能够在现今社会中占据如此重要的地位,就是它比其他人造物都更能适应变化。如果软件不能提供对变化最有力的支持,那么就没有什么其他的artifact能够做到了。"

这是一个变化的世界,如果软件不能帮助人或企业去适应变化,还有什么呢?

当然,如果你的语言工具比较落后,你的工程方法比较传统,不是很"敏捷",那么你可能一生中大部分时间在为客户或上司反复修改几年前你已经完成的工作。

另外一方面,我们又寄希望于系统分析员,希望出现一个“牛人”,把客户几年后的变化都能预计到,很显然是不现实的。

面对变化的最有力武器就是Refactoring,refactor你现有的代码,使它成为一个可以适应变化的敏捷的系统,同时要积极及时反馈需求的变化,这样就进入一个极限的良性循环。

其中,不断refactor的可能结果就是,将你的系统最终形成一个框架Framework以简化因变化带来的工作量。(因变化带来的工作量是无法逃避的,但我们可以使其在强度 和量度方面减轻)。

好,言归正传,理论的东西永远探索不尽,让我们还是回到上面提到的一个大的需求变化上:

在本案例中,用户注册系统是和其他系统是融合在一起,也就是说,只有注册用户才能操作其他系统的功能。

这时你的客户可能告诉你将来有一个潜在的大的变化:"我们原来已经有一套用户注册系统了,现在可以先用你这一套的用户注册系统,但是一旦如果时机成熟,希望切换到我们自己的注册系统"。

那么你怎么办?是不是到时一个个去修改系统中的密码验证部分,然后,再测试?显然,这样做很被动。

我们需要把预防措施做在前面,那么开始对现在这个用户注册系统refactor吧,让它能为未来变化提供接口。

 

下页

案例下载

JavaBean和JSP/JDBC操作数据库

 


更多标签...



Jdon框架演示

JiveJdon
源码下载

VIP收费区

历史热点讨论排行榜




google yahoo 新浪ViVi 365Key网摘 天极网摘 CSDN网摘 添加到百度搜藏 POCO网摘





手机 add to google add to yahoo
联系我们 | 关于我们 | 广告联系 | 网站地图 | 设为首页

沪ICP证08026060 如有意见请与我们联系 Powered by JdonFramework
_×
您有新消息