WEB开发网
开发学院数据库Sybase 西安市电信局“九七工程”系统集成技巧 阅读

西安市电信局“九七工程”系统集成技巧

 2006-04-10 23:07:08 来源:WEB开发网   
核心提示:邮电部的"九七工程"是一个大型数据库综合应用系统,其全称是"电信业务计算机综合应用系统",西安市电信局“九七工程”系统集成技巧,整个系统囊括了当今先进的计算机、数据库及网络技术,西安市电信局"九七工程"客户端的开发环境为英文Windows95配合中文之星2.5

邮电部的"九七工程"是一个大型数据库综合应用系统,其全称是"电信业务计算机综合应用系统",整个系统囊括了当今先进的计算机、数据库及网络技术。西安市电信局"九七工程"客户端的开发环境为英文Windows95配合中文之星2.5,使用Sybase大型数据库系统及其开发工具PowerBuilder5.0。一期工程整个系统网络连接二百余台计算机,应用端程序代码几十万行。在对这样一个大型系统进行集成的过程中,使用了多种技巧,对Windows95环境进行设置,对应用程序加以改进,在实践中获得了一套行之有效的措施,用来对付整个系统应用过程中的各类问题。之所以称为"技巧"而不是"技术",是因为所使用的各种方法,有的可能只是一个设置的改动,有的只是四五行源代码的集合。但就是这些设置和代码,在整个系统的应用中起了十分重要的作用。下面分三个方面来介绍这些设置和代码。

设置客户端计算机为"九七"专用系统

基于对系统安全和设备管理的考虑,我们希望运行"九七工程"系统的计算机成为一个专用计算机,也就是说当计算机启动时自动加载应用程序,退出应用程序后自动关闭计算机。为此我们对系统进行了一系列设置:

1、更改系统启动画面 启动画面使用一个320*400大小的256色BMP图象文件,文件名为logo.sys,并将其放置在C盘的根目录下,这样在以后Win95每次启动时就可以使用自己制作的画面作为启动画面了。如果还希望改动关机画面,用类似的方法修改windows目录下的logos.sys和logow.sys文件就可以了。
  2、 计算机启动时直接进入"九七系统"的应用界面   "九七系统"有一个封面程序Shell1.exe,通过这个封面进行数据库的连接,输入工号和口令,进行用户身份验证,并根据用户工号的编码特征运行相应的应用程序。在用户打开计算机电源的时候,我们就希望能够使计算机直接启动这个封面程序。对这个问题,在Win95中的实现一般有两种方法,简单的一种是在Start菜单的Program\Startup中加入封面程序;另一个稍微麻烦,是在系统注册表的HKEY_LOCAL_MACHINE \SOFTWARE \Microsoft \Windows \CurrentVersion \Run下加入封面程序。这两个方法是最通用的,但考虑到系统本身的特点,却是不可行的。"九七系统"是一个专用系统,不仅基于系统安全和设备管理的考虑,我们希望运行"九七工程"系统的计算机成为一个专用计算机,而且由于"九七系统"计算机的最终用户大多没有经过Windows95使用的培训,如果呈现在用户面前的东西太多,必然会对系统的安全构成潜在的威胁。因此,在实际的应用中,我们采用的是修改Windows目录下的System.ini文件的方法。在System.ini文件中有一个关于Windows95外壳程序的设置,在缺省情况下,外壳程序为Explorer.exe,即Shell=Explorer.exe,我们将其改为Shell=c:\apply\shell1.exe(封面程序统一放置在c:\apply目录下),这样,当Win95启动时会直接进入我们自己的封面程序,同时用户还看不到包括"开始"、桌面、我的电脑、网络邻居和回收站等所有的东西,真正将计算机做成了"九七系统"专用。
  3、 汉字系统的加载   为了使计算机成为"九七系统"专用,我们对System.ini文件进行了改动,结果是牺牲掉了汉字系统。我们的应用程序在开发时使用的是英文Windows95和中文之星2.5,在对System.ini文件进行改动之后,桌面和"开始"都不见了踪影,中文之星自然也就启动不了了。而且比较麻烦的一点是中文之星的自动启动并不是包含在Windows的Startup中,也不是包含在注册表的run下面,而且我们网络上的二百多台微机是分了好几批进行软件安装的,使用的中文系统虽然大部分是中文之星2.5,但仍有相当一部分使用的是中文之星2.0,他们的安装目录名并不相同,这就为从我们的封面程序直接启动中文之星带来了不便。但我们对Windows95的启动过程进行了较为细致的分析,最终发现中文之星的自动启动是在Win.ini文件中设置的,因此,我们可以通过读取Win.ini 这个文件来直接获得中文之星执行文件的文件名和绝对路径,当然,有了路径和文件名之后只须用PowerBuilder 在程序适当的地方加一句run( CstarPath )的语句,不论中文之星的版本号是多少,也不用专门设定路径就可以顺利启动中文系统。   
  4、 实现程序自动关机   完成了以上几项设置后,计算机就象是一个专用系统了。但是,当我们把自己的封面程序设置成为Win95的外壳程序后,Start菜单不见了踪影,ShutDown自然无处可寻,计算机的安全关闭成了随之而来的问题。通过对Windows API的研究我们知道,一个应用程序可以通过调用标准函数ExitWindowsEx()完成计算机的自动关闭。这个函数有两个参数,前一个用来确定计算机关闭的方式,例如EWX_LOGOFF关闭所有应用程序并以其它用户身份登录,EWX_POWEROFF退出Windows后关闭计算机电源(要求计算机支持软件关闭电源),EWX_SHUTDOWN退出Windows后停留在"You can shutdown your computer safely"的地方,EWX_REBOOT重新启动计算机;后一个参数保留。当程序调用这个函数后,它向所有的进程发送CTRL_SHUTDOWN_EVENT或 CTRL_LOGOFF_EVENT消息,要求所有进程立即结束运行准备退出Windows95系统。可以使用两种方法调用这个函数,一是在Visual C++中编写程序调用这个函数,编译成为EXE文件后在PowerBuilder中用run()命令调用运行。用VC编程调用这个函数完成自动关机的功能十分方便,另外只要将VC编译出的EXE文件改名或删除,自动关机功能就不能实现,算是为维护人员修改计算机设置提供了方便,这是使用这种方法实现自动关机的好处。另一种调用关机函数的方法是在PowerBuilder中直接定义后使用。在PowerBuilder中的Global External Function中定义Function boolean ExitWindowsEx( uint uFlags, ulong dwReserved ) library "user32.dll"后,就可以在PowerBuilder的程序当中直接调用这个关机函数完成自动关机的任务。这种方法的好处也是显而易见的,它看起来比前一种方法更紧凑。   实现程序自动关机后虽然有许多好处,但同时给维护人员的维护工作带来了不便,我们的解决方法是如果在进行自动关机的过程中按住Shift键不放,则只关闭自己的应用程序而不是整个Windows系统都退出。具体实现是在封面程序的Close事件中加入下面的语句: if KeyDown( KeyShift! ) = 0 then ExitWindows( 1, 0 ) end if   方法很简单,但确实行之有效。另外,我们还可以更进一步在关闭封面程序的同时启动资源管理器,方便维护人员工作。
  5、拨号上网计算机的设置   对于"九七系统"这样一个城域网来说,网线是不可能布通整个西安市的每个角落的,特别是对于一些地处郊县的远程点,最经济的方法就是拨号上网。当然,由于运行环境的不同,为我们的系统界面提出了新的要求--每次进入系统后能够自动拨号入网。   对于这个问题,我们首先想到的方法是模仿前面中文之星的启动方法,找到拨号网络的应用程序后由程序自动调用。但事实是怎么样呢?拨号网络的应用是隐含在Exporer.exe当中的,如果在命令行的状态下键入EXPLORER.EXE::{20D04FE0-3AEA-1069-A2D8-08002B30309D}\::{992CFFA0-F557-101A-88EC-00DD010CCC48},系统就可以启动打开拨号网络的窗口。不过这距离我们需要的还有一步距离,那就是双击拨号网络中的特定图标,真正开始拨号上网注册连接的过程。其实,在进入系统时能够自动化拨号上网,Win95已经考虑到了这个问题。在Control Panel中的Internet 下,有一个connect的书夹,选择Auto connect to internet,同时选择自己需要的拨号设置后,就可以在每次进入系统的过程中首先自动拨号连接数据库了。当然,在进行拨号设置时还可以根据需要要求保护用户名和口令,这样拨号连接入网就实现了全自动,而且还保证了与其他使用网线的计算机的界面的统一性。

确保系统正常运行

为了保证系统的正常运行,我们进行了如下的设置:

1、保证应用程序窗口在封面程序之上

封面程序和具体的应用程序一旦都运行之后,两者之间的关系对操作系统来说是平等的,任何其一都有可能在另一窗口之上,从而遮挡住另一程序。一般来说应用程序运行在后,其窗口也就在上,但也可能由于某些操作,使封面程序的窗口位于应用程序之上,这样就使得操作者可能误以为应用程序已经关闭。解决的方法是将封面程序总保持在其他应用程序之下。Win95窗口的排列顺序使用的是称之为Z序的排列方式,当窗口的句柄位于Z序最下面时,窗口也位于其他所有窗口之下。具体的实现方法是:在Global External Function中定义两个Windows API函数:

Function boolean FindWindow(string class,string title)library "user32.dll"Function boolean SetWindowPos(uint hWnd, uint hWndInsertAfter, int x, int y,int cx,int cy, uFlags) library "user32.dll" 在Global Function 中定义函数 boolean set2bottom(string winName), 代码为: string NULL uint Handle SetNULL(NULL) Handle=FindWindow(NULL, winName) if Handle=0 then return false end if SetWindowPos(Handle,1,-1,-1,-1,-1,3)

这样,只要在适当的时候调用set2bottom函数,用封面窗口的名称作为字符串参数,就可以将封面程序的窗口设置为在其他窗口的下面。但还有一个问题需要考虑的是,这个函数无法让窗口总保持在其他窗口之下,不过可以通过变通地在封面程序中设定定时时钟,每过一段时间譬如5秒就调用一次这个函数,这样从另一种途径实现了窗口总保持在其他窗口之下。   

就这个问题,还有一个类似的解决方法,那就是将应用程序设置为总保持在其他窗口之下,这样做和前一种方法是等效的。具体实现也是类似的,只是SetWindowPos函数的参数为SetWindowPos(Handle,-1,-1,-1,-1,-1,3)   

2、保证系统正常运行

应用程序有时打开的太多,结果会造成死机。为了保证系统的正常运行,我们定义了下面的函数:

Function uint FindWindowA(String class, String title) library "user32.dll" Function boolean SetWindowPos(uint hWnd, uint hWinInsertAfter, int X, int Y, int cx, int cy, uint uFlags) library "user32.dll" Function boolean ShowWindow(uint hWnd, int nCmdShow) library "user32.dll" Function uint GetLastActivePopup(uint hWnd) library "user32.dll" Function uint BringWindowToTop(uint hWnd) library "user32.dll" Function boolean set2top(string winName) library "extFunc.dll" uint FirstWnd,FirstchildhWnd,handle string NULL SetNULL(NULL) FirsthWnd=FindWindowA(NULL,winName) if FirstWnd<>0 then FirstChildWnd=GetLastActivePopup(FirstWnd) handle=FindWindowA(NULL,"") if handle<>0 then SetWindowPos(handle,1,-1,-1,-1,-1,3) end if BringWindowToTop(FirsthWnd) if FirsthWnd<>FirstChildhWnd then BringWindowToTop(FirstChildhWnd) end if ShowWindow(FirsthWnd,3) return true end if return false  

给客户端计算机传送程序和消息

1、给客户端计算机传送程序

程序的及时更新,在系统运行之初是最令人头痛的一个问题。如果程序员对程序进行任何一点的修改,都需要对每个用户的程序进行更新。举例来说,如果营业前台的程序进行了修改,那么整个西安市的近二十多个营业厅就要全部跑一遍,人工地对各个营业厅的程序进行更新。同样,如果测量台的程序修改了,全市大小几十个测量台就都需要程序维护人员亲自去对程序进行更新,对于各装机公司和各程控机房亦是如此,并且在整个系统开通的初期,程序修改及其频繁,几乎每天都需要更新程序,最高峰的时期甚至到达一天就需要对程序更新好几次。由此不难看出,这种情况下对于程序维护人员的压力是可想而知的。面对这样的困难,我们的解决之道是在Shell1.exe中加入了一个小技巧FTP Server。方法仍然类似于前面中文之星的启动,直接在程序中run("Serve.exe")。正是这个FTP Server,所有的问题迎刃而解,维护人员只需要在网管中心通过远程控制,就可以完成对程序的更新,而整个工作只需要用几分钟时间敲几下键盘,维护人员再也不用为修改程序后无法及时向下发送而头痛了。另外,如果熟练使用这个FTP Server,在网管中心就可以解决一些计算机的设置问题,从而使整个系统的各个计算机都能稳定正常地运行。譬如说,一次为了系统安全的考虑,系统管理员要求对系统用户的口令进行修改,但当时系统正在运行,全市所有的营业厅、测量台、程控机房、装机公司以及号线中心的二百多台微机都需要同时进行改动,否则就会出现大量计算机不能正确连接进入网络的问题,而完成这个任务的时间只有利用中午一个半小时的空隙时间。不难想象,如果是由维护人员亲自去各地方进行改动很难在这么短的时间内把包括位于远郊的各远程点的计算机全部更新。但正是因为有了FTP Server这项技术革新,使得维护人员足不出户就在一个半小时里完成了二百多台微机的平稳更新。由此,在"九七系统"中加入FTP Server这项技术所产生的效益可窥之一斑。

2、向用户发布最新消息

通过一些简单的工作,就可以实现向用户发布最新消息的功能,当然,消息的内容可以是多种多样的,例如"九七系统"的使用知识、使用技巧、注意事项,关于电信业务的最新消息如市话初装费优惠等都可以通过发布消息给用户提示,总之所有想告诉用户的内容都可以写。具体实现如下: 建立一个表名为TUTORIAL,结构如下: DATE datetime TITLE char 30 CONTENT varchar 200 SCOPE varchar 20 ACTIVE char 1 在主窗口的open事件中加入如下代码: string atical,content,sday,scope,active,str datetime day boolean dis=false DECLARE today CURSOR FOR SELECT DATE,TITLE,CONTENT,SCOPE FROM TUTORAL WHERE covert(char(12),DATE,3)=convert(char(12),getdate(),3) AND ACTIVE='1' ORDER BY DATE; OPEN today; FETCH today INTO :day,:article,:content,:scope; if sqlca.sqlcode=0 then dis=true end if sday=string(date(day)) str=sday+'~n~r'+content FETCH today INTO :day,:article,:content,:scope; Loop if dis=true then messagebox(article,str) end if   对于系统集成来说,用户端界面的好坏,直接影响到用户对系统的评价。以上介绍的技巧,都是针对"九七系统"中的特定问题摸索出的解决方法,但同时这些方法在其他系统集成中又不乏其普遍意义。   

Tags:西安市 电信局 九七

编辑录入:coldstar [复制链接] [打 印]
赞助商链接