Domino R5中使用Lotus Script 处理XML
问题:我们的Support Team维护着不同地区各个部门的十几个Domino应用,这些应用都采用外接数据库Access DB和Oracle DB。由于某种原因,User要求连接数据库的UserID和Password可以变更,由于UserID和Password在开发时已作为Const固化在Agent 和公式@DbColumn、 @DbLookup中,所以每次变更时,不得不使用Lotus Designer逐个应用逐个Form、Agent等,一一打开变更,一不小心就漏掉了,十分麻烦。于是,我们想到一个方案:配置文件。配置文件要满足:
1)对UserID和Password的变更,只需要修改配置文件即可完成。
2)不需要Lotus Designer开发环境。
3)格式清晰,易于修改维护。
鉴于以上,我们把配置文件格式定为XML。
在Domino R5中,对XML的处理,有两种方式: (1) 采用Java来处理; (2) Lotus Script来处理。
通常采用Java Agent来处理XML文档。由于连接数据库的Agent是Lotus Script Agent,所以不得不采用Lotus Script来处理XML。
环境:Win2k、Domino R5、 Lotus Designer R5、Visual Basic 6.0
方案:我们知道Lotus Script没有直接处理XML文档的函数、方法。但是Lotus Script和Visual Basic融合的非常好,VB代码不需要做太多修改就可以在Lotus Script Agent中使用。我们知道在VB中使用MSXML处理XML文档。所以我们先在VB中使用MSXML处理XML文档,以此作为原型,再进行修改,移植到Lotus Script Agent中。
一、 定义XML文件
我们将其命名为DBConfig.xml,放在Lotus\domino\目录下。它由一个根元素<DATABASE>,DATABASE有一个以上的<APPLICATION>子元素,APPLICATION有一个属性name,并且有三个子元素,<USERID>、<PASSWORD>、<TNS>,这三个元素都没有属性。
文件 : \Lotus\domino\DBConfig.xml
内容 :
<?xml version="1.0" encoding="utf-8"?>
<!-- For Database username password etc. -->
<DATABASE>
<!-- App 1 -->
<APPLICATION name="APP1">
<USERID>UID1</USERID>
<PASSWORD>PWD1</PASSWORD>
<TNS>TNS1</TNS>
</APPLICATION>
<!-- App 2 -->
<APPLICATION name="APP2">
<USERID>UID2</USERID>
<PASSWORD>PWD2</PASSWORD>
<TNS>TNS2</TNS>
</APPLICATION>
<!-- App 3 -->
<APPLICATION name="APP3">
<USERID>UID3</USERID>
<PASSWORD>PWD3</PASSWORD>
<TNS>TNS3</TNS>
</APPLICATION>
</DATABASE>
二、 VB原型
新建一标准EXE工程,在Form1上加button : Command1;新建一标准Module(因为要用到Public Type):Module1。从菜单Project 导入Microsoft XML v3.0。
(1)Module1中加入以下代码:
Public Type XMLForDB
AppName As String
DB_UID As String
DB_PWD As String
DB_TNS As String
End Type
Public DBConfig() As XMLForDB
Sub initConfig()
Dim xml As DOMDocument
Set xml = New DOMDocument
xml.Load ("\Lotus\domino\DBConfig.xml ") ‘指定XML文件路径
Dim root As IXMLDOMElement
Set root = xml.documentElement
Dim node As IXMLDOMNode
Dim cNode As IXMLDOMNode
Dim nodeList As IXMLDOMNodeList
Set nodeList = root.getElementsByTagName("APPLICATION")
ReDim DBConfig(nodeList.length)
For i = 0 To nodeList.length - 1
Set node = nodeList.Item(i)
If (node.nodeType = 1 And node.hasChildNodes()) Then
With DBConfig(i + 1)
.AppName = UCase(node.Attributes.getNamedItem("name").Text)
.DB_UID = node.selectSingleNode("USERID").Text
.DB_PWD = node.selectSingleNode("PASSWORD").Text
.DB_TNS = node.selectSingleNode("TNS").Text
End With
End If
Next
For i = 1 To UBound(DBConfig)
With DBConfig(i)
Debug.Print .AppName
Debug.Print .DB_UID
Debug.Print .DB_PWD
Debug.Print .DB_TNS
End With
Next
End Sub
Function getDBConfig(name As String) As Variant
Call initConfig
getDBConfig = 0
For i = 1 To UBound(DBConfig)
If (UCase(DBConfig(i).AppName) = UCase(name)) Then
getDBConfig = i
Exit For
End If
Next
End Function
(2)在Command1一的Click中加入:
Private Sub Command1_Click()
Debug.Print "----------------- Test Start -------------------"
If getDBConfig("app1") then
Debug.Print "---------------- Test OK --------------------"
Else
Debug.Print "---------------- Test Error --------------------"
End if
End Sub
三、 修改VBàLotus Script
修改后Lotus Script如下 :
'-----------------------------------------------------------------------------
' File: DBCONFIG.LSS
' Copyright (c) 2001-2005
' Language : LotusScript
' Description: Global Constants for connect to Oracle DB.
' The PG use a XML file named DBConfig.xml to config DB connections for appliction.
' Useage : (1) Declaration : %include "DBconfig.lss"
' (2) Code :
' Dim AppName, uid, pwd, tns , index
' index = getDBConfig(appName)
' if index then
' 'AppName = DBConfig(index).AppName
' 'uid = DBConfig(index).DB_UID
' 'pwd = DBConfig(index).DB_PWD
' 'tns = DBConfig(v).DB_TNS
'
' uid = DB_UID
' pwd = DB_PWD
' tns = DB_TNS
' else
' msgbox (" The appName wasn't found.")
' end if
'
'-----------------------------------------------------------------------------
' Structure for keep xml APPLICATION
Public Type XMLForDB
AppName As String
DB_UID As String
DB_PWD As String
DB_TNS As String
End Type
' Keep xml file content
Public DBConfig() As XMLForDB
' DB connection
Public DB_UID As String
Public DB_PWD As String
Public DB_TNS As String
Public DB_Result As Integer
Const XMLPATH = "D:\Lotus\Domino\DBConfig.xml"
' ///////////////////////////////////////////////////////////////////////////////////////////////////////
' Author : ivy8890
' Created : 2005/04/15
' Purpose : Get xml file and parse it and keep all APPLICATION content to DBConfig arrary.
' History : <<< ID : 999 Type[Add, Update, Del] Start yyyy/mm/dd Department Purpose >>>
' XXXXXXXXXXXXXXXXXXXXXXXXXXXX
' <<< ID : 999 Type[Add, Update, Del] End yyyy/mm/dd Department>>>
'
' ///////////////////////////////////////////////////////////////////////////////////////////////////////
Sub initConfig()
On Error GoTo bottom
Dim xml
Set xml = CreateObject("Msxml2.DOMDocument")
xml.Load (XMLPATH)
Dim root
Set root = xml.documentElement
Dim node
Dim nodeList
Set nodeList = root.getElementsByTagName("APPLICATION")
Dim AppName As String
Dim uid As String
Dim pwd As String
Dim TNS As String
Redim DBConfig(nodeList.length)
For i = 1 To nodeList.length
Set node = nodeList.Item(i-1)
If (node.nodeType = 1 And node.hasChildNodes()) Then
DBConfig(i).AppName = Ucase(node.Attributes.getNamedItem("name").Text)
DBConfig(i).DB_UID = node.selectSingleNode("USERID").Text
DBConfig(i).DB_PWD = node.selectSingleNode("PASSWORD").Text
DBConfig(i ).DB_TNS = node.selectSingleNode("TNS").Text
End If
Next
bottom:
Exit Sub
End Sub
' ///////////////////////////////////////////////////////////////////////////////////////////////////////
' Author : ivy8890
' Created : 2005/04/15
' Purpose : Get specified application config information.
' Return : (1) >0 index of DBConfig
' (2) err : 0
'
' History : <<< ID : 999 Type[Add, Update, Del] Start yyyy/mm/dd Department Purpose >>>
' XXXXXXXXXXXXXXXXXXXXXXXXXXXX
' <<< ID : 999 Type[Add, Update, Del] End yyyy/mm/dd Department>>>
'
' ///////////////////////////////////////////////////////////////////////////////////////////////////////
Function getDBConfig(sname As String) As Integer
getDBConfig = 0
DB_Result = 0
On Error GoTo bottom
Call initConfig
For i = 1 To Ubound(DBConfig)
If (Ucase(DBConfig(i).AppName) = Ucase(sname)) Then
getDBConfig = i
DB_Result = i
DB_UID = DBConfig(i).DB_UID
DB_PWD = DBConfig(i).DB_PWD
DB_TNS = DBConfig(i).DB_TNS
Exit For
End If
Next
bottom:
Exit Function
End Function
四、 配置和使用
为了使多个应用使用,将以上代码保存为DBConfig.lss。*.Lss文件位置 : Server端 Lotus\domino目录下;Client端 Lotus\notes目录下。
(1)导入Lss文件
如果DBConfig.lss放在Lotus\notes目录下,使用时要用Include语句,%Include “DBConfig.lss”; 如果放在Lotus\notes\lss目录下,要用%Include “lss/DBConfig.lss”。
(2)调用getDBConfig
以字符型 Application Name 为参数调用getDBConfig(AppName),此AppName应于DBConfig.xml文件中<APPLICATION>的name属性值一致,不区分大小写。返回值为整型,如果返回值为零,表示出错或没有找到对应APPLICATION;如果返回值大于零,表示正常,返回值为其在DBConfig数组中的位置,UserID 和Password等可以用DBConfig(返回值). DB_UID和DBConfig(返回值). DB_PWD取得,也可以直接使用DB_UID和DB_PWD取得。
(3)和ScriptLib一块使用
在ScriptLib中新建DBConfig导入DBConfig.lss,在Sub Initialize中以字符型 Application Name 为参数调用getDBConfig(AppName),在Agent中使用Use语句:Use "DBConfig",在取得UserID 和Password处,先用DB_Result判断,DB_Result大于零时,正常;等于零时,出错。正常时等可以用DBConfig(DB_Result). DB_UID和DBConfig(DB_Result). DB_PWD取得,也可以直接使用DB_UID和DB_PWD取得。
注意: 如果Server端没用安装注册Microsoft XML v3.0,会出现429错误,需要安装注册Microsoft XML v3.0。 以下是安装注册过程:
1)拷贝文件msxml3.dll、msxml3a.dll、msxml3r.dll到C:\Winnt\System32目录下。
2)在MS-Dos下转到C:\Winnt\System32目录,执行命令:regsvr32 C:\WINNT\system32\msxml3.dll
五、追加、变更、删除
(1)追加
DBConfig.xml 中追加<APPLICATION>元素,Lotus Script Agent中追加调用。
(2)变更
只需对DBConfig.xml中的相应<APPLICATION>元素进行变更。
(3)删除
在Lotus Script Agent中删除调用后,对应的DBConfig.xml中可以删除也可以不删除。