2007年4月16日星期一

WEB系统设计-SQL上要写一些什么?

1.SQL要写到什么程度?
这个系统的SQL语句不少写得比较复杂。比如:

SELECT
decode( ?, 0, '(オーダー入力)', '(オーダーキャンセル)' ) TITLE,
decode(a.FAX_HATCHU_FLG, '1', '', a.JUCHU_NO ) JUCHU_NO,
....
FROM
SUE_INC a,
SS_MASTER b,
...
WHERE
a.SS_CODE(+) = b.SS_CODE
...


甚至还有在SELECT句上含有IF/ELSE分支选择语句的(这是我第一次知道ORACLE支持这种语法)。在一个多层WEB MIS系统上,SQL写得过于复杂,是不好的设计。

带来的坏处是:
导致系统业务逻辑分散分布在SQL语句和BO(Bussiness Objects)上。违反了分层设计的初衷,阅读和理解代码变难,系统维护和升级的工作也复杂了。

举例来说,以上的功能模块,进行维护或升级工作的技术人员必须兼顾JAVA和数据库,在这两个方面都要不错才可胜任工作,要不然就需要两个技术人员。

就上面的SQL语句来说,
1.要避免使用DECODE解码语句。将常量和字典的映射写在SQL上是很笨的,首先SQL的设计者必须记一堆编码映射表不要搞错,很多系统有很大的映射参照表,SQL设计者们要经常查阅这个表。另外试想有一天常量的名称需要改变时,需要修改所有有关的SQL语句。(当然我们还有文件批量查找和替换工具可以用,不过那实在是不太优雅的招数)

2.要避免在SQL上使用外联接来查询字典表。联接查询字典表不能算是大的问题,事实上很多系统都一直这么做的,毕竟比起上述的把字典解码直接写到SQL上要进步很多了,它实现了字典数据的集中管理。但我认为,对于系统运行过程中不会改变的全局字典表(SYSTEM MASTER表,比如《邮政编码映射》,《业务分类》,《顾客分类》等字典表)来说,最好的办法是在系统初始化的时候就将其加载到全局内存中,并在JAVA层提供查询的接口。这样可以减少不少SQL句的复杂度,而且对使用频繁的字典表的访问减少到最低,数据库的负荷也减轻了。

按照分层设计的原则,理想的状态,SQL语句因该是纯粹的最简单的SELECT/UPDATE/DELETE语句,不要包含任何逻辑。存储过程和触发器应该避免使用。

但是,世上的事情总是没有那么简单。不可避免地,我们要遇到一些有关性能的问题,比如,需要对大量的记录的每一条进行一些复杂运算,然后更新这些记录。这时候,在JAVA层面上对每一条记录进行循环,做运算,然后写回数据库,效率可能无法满足要求。此时可以考虑存储过程或复杂的批量UPDATE语句。必须记住的是,在整个系统设计中,这是极端状态下的特例,不能以性能为理由来破坏分层设计的原则。(Hibernate有持久对象缓存机制,另外好像在关注批量更新的性能问题,不知现在应付这类任务性能如何。

WEB系统设计-前言

这一段在做一个系统的代码验收,一家石油零售商的WEB MIS系统,开发周期长达数年。进入这个小组1个月有余,除了编程的问题外,发现设计上存在不少的瑕疵,问题是存在的,不过现在已经进入验收阶段,只要影响不大,也就没有改的必要了。日本的Team会做代码重构吗,会,在他们被系统的问题逼到墙角的时候就会。
一直很关注Web系统设计,在技术问题上一直是吹毛求疵的我(哈),看到这些问题,不免心下痒痒,随便拿几点指摘一下系统的设计吧。

Facts About Me

Software I use:
Mac OS X, Ubuntu, Opera, Google Family, Eclipse, Java, Sure, the M$ family -- Windows and Office

Hardware I use:
IBM T41, Toshiba A20, Mac Book G4, iPod, Palm Zire, Treo,Sony Clie

If I won 1 million dollars, I would:
E..E...E.....Exicted to die, so better in times. :)

If I were a super hero I would:
Super hero, really? ...Could I have a dozen of GFs ? It may be a hard job to handle with so much, but trust me, I will try a super hero's best. :D

I wish I could:
Have a two-months vacation, one for piggy sleep, one for staying with family !