2006-12-30

非凡的Altova StyleVision,同源输出HTML,PDF,RTF。

如今的XML,在文档生成方面可谓大红大紫。使用XML + XSLT可以动态生成HTML文档和表单。而XML + XSL + FO更可以动态生成PDF/RTF文档。

所谓动态生成,就是在运行,才将数据放到具有指定DTD/schema的XML文档中,使用预定义的XSL文档生成可供浏览或打印的文档。

一般来说,生成HTML和PDF的XSLT要分别定义。对于HTML和PDF表现差别较大的文档,有必要使用这种方法。

但是,对于一些格式要求较高的表单和报表,在HTML和PDF下的表现是基本一致的。这个时候就有必要用同一个样式表输出HTML和PDF。要知道,手工定义一份XSLT可是很费工夫的。

FO似乎能达到这个目标,它具备足够精细的样式定义,借助FOP等工具,可直接输出PDF等格式。可惜的是,目前的主流浏览器,如IE和firefox,并不能直接显示FO文档。必须将其转换成HTML或XHTML。然后,我没有发现任何的开源工具可以做到这一点。

Altove StyleVision,恰到好处的实现上述目标。

顾名思义,StyleVision就是用来设计样式表的,它提供一个非常友好的GUI设计界面。它使用一个私有的XML格式(SPS)来保存样式表,这个样式表可转换成生成HTML的XSLT和生成FO的XSLT。

这样,做为开发方,购买一份Altova StyleVision,用来设计样式表,然后将其生成的XSLT发布给用户,就可以实现同源输出报表了。而最终用户可以不购买Altova StyleVision

附图:两种动态文档生成方案(在图中体现为两条可选的路线):

Technorati :

2006-12-27

如何设计数据库表实现完整的RBAC(基于角色权限控制)

RBAC(基于角色的权限控制)是一个老话题了,但是这两天我试图设计一套表结构实现完整的RBAC时,发现存在很多困难。

我说的完整的RBAC,是指支持角色树形结构和角色分组。具体来说,应当包含如下权限控制需求:

  1. 父级角色可以访问甚至是修改其子级的数据,包含直接子级直到最终子级。
  2. 角色可以访问其所在组的数据。
  3. 父级角色可以访问其所有子级(从直接子级到最终子级)所在组的数据。

而具体到我的系统中,还应当有如下需求。

  1. 兼容多种数据库产品。只能用简单的表,视图,存储过程和函数等实现。
  2. 同时兼容单条数据处理和批量数据处理的需求。

且不论这些具体需求,RBAC的基本表应当如下四个:

  • roleList表,记录所有的角色和角色组。
    • roleId: PK, 角色/组的ID,全局唯一,不区分角色和组。
    • roleName:角色/组的名称。
    • roleType: R - 角色,G - 组
  • rolePermission表,记录每一个角色/组对每一个对象的权限。
    • permissionID: PK, 无特定意义。
    • role: 角色/组的ID。
    • object: 对象的ID。
    • permission: 权限标识,如读,写,删等。
  • roleRelationship表,记录角色/组之间的关系。
    • relationId: PK, 无特定意义。
    • superiorRole: 父角色/组的ID。
    • role:子角色,子组,成员角色,成员组的ID。
    • relationship: 关系标识,可在如下设置集中选取一个。
      • PG标识:P - 父子关系,G - 组/成员关系。
      • PPGG标识:在PG集上,再加三种:PP - 间接父级关系,GG - 组内组关系,CG - parentRole是组,childRole的子角色或间接子角色是其成员,或其子组(含间接子组)的成员
  • objectList表,记录所有的对象。
    • objectId: PK,对象ID,全局唯一。
    • objectName: 对象名称。
    • ... ...

分析上述表结构,不难发现,问题的关键在于从rolePermission表中读取数据时,如何限定角色/组的范围.

方案一

如果角色和组的总量不大,比如在100以内,采用PPGG标识关系,读取数据时是最快的。这个时候的SQL只需要一个输入参数?roleId:

SELECT object FROM rolePermission p left join roleRelationship r on p.role = r.role WHERE p.role = ?roleId or r.superiorRole = ?roleId. (尚未验证SQL的正确性)

但是,这个方案是以极度冗余roleRelationship表的数据为代价的,比如有100个角色,那么roleRelationship中将会有100 * 100 =10,000条记录。而在每次调整角色和R角色组的时候,就要在roleRelationship中一次增加或删除100条记录。这个开销是比较大的。

方案二

只标识PG,查询时接收的输入参数为一个完整的相关角色列表?roleList。

SELECT object FROM rolePermission WHERE role in (?roleList)

在系统运行时,这个?roleList通常可以从role hierarchy cache中取到,比较方便。这个方案的主要问题有二:

1)如果?roleList过长,使用in判断性能会很差。

2)在有些情况下,如报表查询和系统外查询时,取得roleList不太方便。

方案三

只标识PG,但使用如下三个数据库函数来判断角色/组之间的关系。

  • boolean isChild(role, parentRole) - 如role为parentRole的子,返回true。
  • boolean isDescendant(role, ancestorRole) - 如role为ancestorRole的子或间接子级,返回true。
  • boolean isMember(role, group) - 如role为group的成员或子组的成员,返回true。
  • boolean descendantIsMember(role, group) - 如role的子或间接子级为group的成员,返回true。
  • boolean isBelong(role, super) - 如role为super的子,间接子,成员或间接员,或者role的子(含间接子)是super的成员或子组成员,返回true。

在查询时,也只需要接收一个?roleId:SELECT object FROM rolePemission WHERE isBelong(?roleId, role)

如何写出高性能的数据库函数是实现这个方法的关键。

上述方法仅是理论分析,我倾向于方案二。

终于想到新的方案了。

方案四,

结合方案一和方案二,在roleRelationship中,对前两级(也可以是三级或四级)角色,保存其所有的下级角色和组。这样,如果以前两级角色查询数据,就使用方案一,如果以第三级及以下的角色查询数据,就使用方案二。

仍以100个角色为例,每个角色要保存三个关系:一级主管角色,二级主管角色,直接主管角色,最多有300条数据。

每往角色组中加一个角色,也需要加入三条数据:角色本身,一级主管角色,二级主管角色。

但往角色组中加一个子组,需要加入的数据量就大一些:子组本身,子组所有角色,子组所有角色的一级主管角色和二级主管角色。如在多个子组中发现同一角色,可重复保存,但应在表中附加说明是由哪个子组导入的。这样在删除子组时就可以有选择性的删除。

但重复子组的情况就比较麻烦,还有等考虑。假充有组g01,g11,g12,g21。g01包含g11和g12,g11和g12分别包含g21。从g01中删除g11时,如何判断g21的去留?看来还是应当在维护时判断应不应当删除。

Technorati :

2006-12-26

UUID and GUID

http://tb.blog.csdn.net/TrackBack.aspx?PostId=1406125

原来GUID只是UUID的一种实现。

原来UUID虽长,做数据库主键不但不会影响性能,反而对性能有所帮助。

有时间我实际测试一下。

Technorati :

2006-12-21

Rational RequisitePro 7.0 vs PowerDesinger 12.1 Requirement Module

Today I tried Rational RequisitePro 7.0 and PowerDesinger 12.1.

Rational RequisitePro Strong points:

  1. Powerful requirement tracking.
  2. Deep integrated with MS Word.
  3. Full change log and revision
  4. Discussion list for each requirement.
  5. Integrated with MS Project.

RequisitePro Weaknesses:

  1. Poor attribute editing form. the form can not be resized. User has to go through all attributes via scroll bar.
  2. All options to each attribute are fixed. User can not customize them.
  3. Too many attributes.

PowerDesinger strong points:

  1. Easy to use.
  2. Most attributes are customizable.
  3. Friendly list page.
  4. Description box support RTF.
  5. Easy customized RTF document template.

PowerDesinger weaknesses:

  1. There are some obviously bugs. For example, if customized priority name as non-numeric name, the priority dropdown in attribute edit form can not list all priorities correctly.
  2. Can not define default option to each attributes. such as define Must Have as default priority.

Powerdesigner 12.1 sequence model has bug too: it can not list all procedures when show procedure collage.


  • This bug is a new bug in Powerdesigner 12.1. Powerdesigner 12.0 works well for procedure call in sequnce diagram.
    0003.PNG

    However, Powerdesigner 12.0 sequence diagram has another bug.
    0005.PNG

I found above powerdesinger bugs in its 30day trial version. After comparing Rational family, Together, Altoval UModel, Myeclipse UML, Microsoft Visio and some other commercial UML tools. I found Powerdesigner is the most excellent one.

  • It supports UML2 well.
  • It's data model is the best one.
  • It is the most free one. I do not need follow UML standard strictly.
  • I am able to express anything I want. No tool has more powerful expressive force than power designer
  • It's diagrams are most beautiful.
  • It is very easy to use.

What I can not understand is: Why such a famous tool has these obviouse, derisible bugs?! It is these minor bug stopped our company buy it as formal tool!

Technorati :

2006-12-19

Project Management Programs Probation

I tried some free project management programs these days.

  1. Project Engine 2007 from download.com.
  2. Air Todo from download.com. It request JRE 6.0. My product request JRE 1.4.2. I can not executed it at all.
  3. SharePlan from download.com. When I open this program, I do not know what to do.
  4. GanttProject from sf.net. This is a wonderful product. It use XML to save file. It is able to import MS project. the gantt chart is professional.

Project Engine 2007 has lots of features and easy to create project and task. However, there are too many input fields in the task detail page. I don't know how to create and assign a task.

It does not allow directly input task's start date and end date. When you start a task, it automatically set start date; when you complete a task ,it automatically set end date.

I hope it provides following features from PSP:

1) Pause a task

2) Remember both date and time. Generally I complete many tasks in one day.

My suggests:

No. 1 GanttProject

No. 2 Project Engine 2007

Technorati :

2006-12-14

寻找合适的XML内容管理系统

http://www.mambochina.net/content/view/7_38.html 我的内容管理系统(CMS)寻找历程 -- Mambo出鞘,谁与争锋?

http://www.dedecms.com/html/cms/2005/0405/642.html 国外流行的开源CMS解决方案

http://www.chedong.com/tech/cms.html 内容管理系统(CMS)的设计和选型

Technorati :

有意思的Google Calendar

今天上网搜索了一些有关PIM和日程安排的软件,希望找到一个Outlook的替代产品。

先后简单试用了友情强档,RedBox, WinOrganizer。感觉都差强人意。友情强档这款国产软件做得非常优秀,也是最接近Outlook的,可惜在项目的说明栏中,只能输入纯文本。无法使用RTF。RedBox也是只接收纯文本。相比之下,WinOrganizer在技术上就到位得多,可以自由的输入RFT,包括表格和图形都可以输入。不过,我实在不喜欢WinOrganizer的UI风格。

天天日程安排也不支持RTF输入,但是其资料管理功能中可支持RTF。安琪个人助理的界面好难看。

Essential PIM虽然也不支持RTF,但支持多级子任务项,这点还可以。

不经意间还看到有人推荐Google Calendar。这个东东居然把Calendar搬到的Web上,真有意思。由于网络依赖和提醒功能两大原因,我是不知道这东东有没有大用。

Technorati :

2006-12-11

郁闷,高级开发员居然不喜欢写文档

今天安排几位高级开发员更新产品的设计文档。要求一要和代码完全一致,二要具体到类和公用方法。

不料有几位对两个要求都不理解,认为没有必要。

我解释说:咱们做的产品,几十号人,做了五六年的产品。如果不写好文档,别人就没法顺利的接手,到时候什么事情都得问你,这样对你的发展很不利。

有同事听了我这话更是漠然的说:"别老是和发展扯在一起。"

唉,真不知道该怎样激励他们。对自己的职业发展都漠然视之。别跟我说是老板不给机会。

Technorati :

2006-12-06

Java World,为什么你们的国际化实现那么差?

目前Java开源世界的主流力量来自英语国家,单纯的英语背景导致了许多著名的产品虽然号称支持Unicode,在国际化实现上表现极为糟糕。在此略举近期碰到的二三例。

  1. JRE中的zip类无法正确保存压缩文件的中文名。为此Ant项目不得不写了自己的zip类。
  2. Eclipse中code assistance的快捷键与经典的winnows输入法开关键冲突,同为Ctrl + Space。为此我不得不将code assistance键换为Alt + Z
  3. Java中很难创建一个全新的locale,必须得从rt.jar中选一个。
  4. Java的locale基本上不允许用户再做用户级别定制。

Technorati :

First Impress of Eclipse Scrapbook

今晚闲来无事,浏览了一下Eclipse的Helper,发现一个用于java调试的好工具,叫Scrapbook。这个单词的中文意思是剪贴薄。这个工具的功能有点像VB的立即窗口和VS.net中的命令窗口。当你输入一段简单的java表达式或代码时,它可以立即显示出结果值,或执行代码并输出结果到Console中。这个功能能够大大提高检测小段代码的效率。

Technorati :

天天的免疫接种记录

天天的免疫接种记录
已接种疫苗 针次 接种日期 评价 应种未种疫苗 针次
卡介苗 1 2004-11-22 及时 HIB_OMPC 1
糖丸 1 2005-04-05 合格 乙脑 2
糖丸 2 2005-05-12 及时
糖丸 3 2005-06-14 及时
百白破 1 2005-04-05 及时
百白破 2 2005-05-12 及时
百白破 3 2005-06-14 及时
百白破 4 2006-5-29 石泉 根据免疫接种证补登
乙脑 1 2005-08-16 及时 预约疫苗 针次 预约日期
麻疹 1 2005-07-22 及时 甲肝灭活 1 2006-11-21
麻疹 2 2006-7-20 西丽医院 根据免疫接种证补登 水痘 1 2006-12-21
乙肝 1 2004-11-21 及时 流脑 1 2007-01-21
乙肝 2 2004-12-21 及时 肺炎 1 2007-02-21
乙肝 3 2005-05-27 及时 糖丸 4 2008-11-21
风疹 1 2006-01-16 及时 麻腮风 2 2008-11-21
风疹 2 2006-7-20 西丽医院 根据免疫接种证补登 流感疫苗 4 2006-11-24
流感裂解 1 2005-11-03 合格 说明:医生说流感疫苗三岁内只打两针就行了,这一针可能不用打。
流感裂解 2 2005-12-08
流感疫苗 3 2006-10-20 鄂城 根据免疫接种证补登
麻腮风 1 2006-01-16 首次提前
麻腮二联 1 2005-07-22 及时
轮状病毒 1 2005-09-24 及时
腮腺炎 1 2006-7-20 西丽医院
HIB 1 2006-1-16 南头 根据免疫接种证补登
HIB 2 2006-09-21 鄂城 根据免疫接种证补登

Technorati :

2006-12-05

Outlook 2003的一些设置技巧



Outlook 2003中文版中,设置邮件回复为英文的"re",而不是中文的"回复"
工具->选项->邮件格式->国际选项

office 2003中去掉烦人的加载项工具栏
安装Acrobat 后,所有的Office工具都会多出单独的一行PDF工具栏,很烦人。
在注册表中找到相应的Addin,把LoadBehavior键值改为9就可以去掉它了。
LoadBehavior 指示加载行为的整数:0(无)、3(启动)、9(按需装载)或 16(只在下次启动时装载)

所有Office 2003软件注的addin注册在:HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Office

如:

HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Office\Access\Addins\PDFMaker.OfficeAddin

HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Office\Excel\Addins\PDFMaker.OfficeAddin

一些Outlook网址

http://www.outlookcode.com/d/launchform.htm
http://www.outlookcode.com/d/forms/formlauncher.htm
http://support.microsoft.com/?kbid=249199
http://www.outlookcode.com/d/code/getfolder.htm

Office Outlook会自动读取Outlook Express的地址本,读取位置如下:
D:\Documents and Settings\Administrator\Application Data\Microsoft\Address Book\Administrator.wab

Technorati :

让Windows 2000/XP系统自动登陆

一、设置缺省的用户名

在"运行"对话框中输入"regedt32.exe",打开注册表编辑器。选择窗口菜单项中的"HKEY_LOCAL_MACHINE"窗口,在左边的目录树中找到"SOFTWARE\Microsoft\WindowsNT\CurrentVersion\Winlogon"子项,单击后在右边窗口中找到"DefaultUserName"条目,双击后更改为你希望系统自动登录时使用的用户名称(前提是这个用户必须存在)。

二、设置缺省的用户口令

同样在右边的窗口中找到"DefaultPassword"条目,双击更改为DefaultUserName中的用户使用的口令(如果"DefaultPassword"条目不存在,就需要选择"编辑→添加值"创建该条目)。

设置完成缺省用户口令后,就可以设置自动登录了。在"SOFTWARE\Microsoft\WindowsNT\CurrentVersion\Winlogon"子项中,找到"AutoAdminLogon"条目,双击更改该值为1时,系统使用缺省的用户名和密码自动登录;该值为0时,需要用户手工登录


Technorati :

命令行中使用VSS (转贴)

最近工作需要将三四百个DLL文件汇入到VSS数据库中,并且一个个打上Label号,label号取的DLL的版本号(就是选中,点击鼠标邮件,属性里面可以看到的版本号),初步算了一下,这样几百个文件,一个Check out/Check in,再找到Label号,打上Label号,少说也要花上一两天的时间,这样实在是太慢了。下午希望能够通过在DotNet中编程来操作VSS数据库,于是查帮助文档,没有看到相关资料,倒是看到说VSS有命令行可以使用。于是网上搜了一下,也没看到几篇介绍VSS命令行的文章,还是看帮助文档吧,看了一个下午,一个晚上。再结合C#或者C/C++的使用,基本上以后可以实现自动Check Out/Check In并且自动打Label号了。简单总结了一下,下面是VSS的一些常用命令和操作:

1.setup environment variable: //指向ss.exe所在的路径
path=%path%;C:\Program Files\Microsoft Visual Studio\VSS\win32

2.指向VSS数据库的所在目录
set SSDIR=\\gqa-eric-lv\VSS\
set SSDIR=\\Guruvss\erp$\

3.登陆VSS:
ss CP -Yeric,eric123 -I- -s\\gqa-eric-lv\vss

4.获取任一目录的任一文件到本机(下例将$/ASP.Net/DataGridTest/index.aspx文件get到D:\tmp目录)
ss get -GLD:\tmp $/ASP.Net/DataGridTest/index.aspx
(ss get, -GLpath Copies a file to the specified folder, not to the current or working folder. )

5.分屏显示目录ASP.Net中的所有文件和文件夹(包括子文件):
ss dir $/ASP.Net -R|more (另外,有-I -V 两个参数,作用未知)

6.set Current Project:
ss cp $/SQL-sample

7.vss命令行是大小写不敏感的;命令行中的命令不需要全名,同sql一样,只要是可以识别的名字及可,如Dir就是directory的缩写;
(遵守UNC通用命名规则,Universal Naming Convention)

8.一些通用的命令行选项:
-C 为指定项(可以是多项)做注释 (Dir例外)
-O 重定向命令
-V 操作某项的指定版本
-R Perform a command recursively.
-S Turn SmartMode on or off for the command.
-G Change the way the Get command works on any file retrieved to the local drive.
-W 指明本机副本是否只读(使用此参数,表示writable)
-N 在长短文件名两种模式间切换
-I 任何环境下都不提示输入
-Y 指定用户名和密码
-?, -H 两个参数的作用都是获得在线的帮助

9.命令中有空格时,用双引号括起整个选项,如用ss CP "-Yeric Lv",eric123 而不用ss CP -Y"eric lv",eric123,

10.启动图形界面:ssexp -s\\gqa-eric-lv\vss

11.ss命令中,/表示VSS的当前目录,$/表示根目录,常用操作命令如下:
ss Add TEST.C "My long filename.H" ,把TEST.C和"My long filename.H"两个文件添加到当前项目;
ss Add -R *,把当前目录的所有文件及文件夹(包括子文件夹、文件)添加到当前项目;
ss ADD -D- *.DLL,添加当前目录的所有DLL文件到当前项目,但不保留VSS上的历史文件(以节省空间);
ss Checkout TEST.C TEST.H Checkout当前项目中的两个文件
ss Checkout $/TESTDATA/TEST.C Checkout指定项目中的文件
ss Checkout -R $/TESTDATA 循环Check项目$/TESTDATA
ss Comment TEST.C -V5 改变TEST.C的版本号为5的版本注释
ss Comment TEST.C 改变TEST.C的最新版本的注释
ss Comment $/TESTDATA 改变项目$/TESTDATA的注释
ss Create $/WORD VSS的根目录下,创建项目WORD
ss Create WORD VSS的当前目录下,创建项目WORD
ss Cp $/WORD 设置$/WORD为Current Project
ss Cp .. 跳转到当前项目的父项目
ss Delete $/PRJ/TEST.C 删除文件TEST.C (delete命令删除的文件,可以用直接add命令回复,如Add test.C)
ss Delete $/PRJ 删除项目 (不可以有两个同名的文件被delete,因为没有真正删除)
ss -S Delete *.* 删除所有文件,-S表示删除VSS上的文件之后,删除本机文件
ss Destroy $/PRJ/TEST.C 持久删除文件(不可恢复)
ss Destroy $/PRJ 持久删除项目

12.其他的更改操作有:label,merge,move,password,purge,recover,rename,rollback,share,undocheckout,workfold,branch等命令,这些命令会改变VSS数据库的内容或者环境。

13.VSS命令行中的比较/查找/显示等不改变数据库和环境的命令: diff,dir,FileType,Get,help,history,links,paths,project,properties,status,view,whoami

14.显示最近的Version,Label信息:SS properties

15.显示Checkout的文件:SS Status

Technorati : ,

Technorati :