用VB6写在线更新程序(上篇)
说起VB6,算是老朋友了,从学计算机开始就接触它了。然而,有了Delphi5之后,再也不想用它了。毕竟,在OOP流行的年代,Delphi相继推出了6和7(8、9、10、11、12就不说了,伤心!),而VB还是6.0,等到7.1出来之后,已经不是VB了,而是VB.NET,需要.NET Framework的支持,太麻烦了。
曾经有人说过,VB非常强大,几乎无所不能(当然,其实是依赖于Win32 API的运用,这点他不说也知道),甚至还说比Delphi强,这一点我是强烈反对的。先不说借助API不算是它的能力,用起来的感觉就不一样,没有指针、没有动态链表也就算了,就连最常用、的最基本的函都没实现(或者说内置),实在是难以容忍(可别再提API了,难道判断一个目录是否存在也要用API吗?封装一下也好呀。)!
最近在修改一个VB写的程序,为了增加下载更新功能,折腾好几天,还好没出现失败中止的惨剧,还是凭着好奇心坚持写出来了。实现的功能并不复杂,主要是写一个下载文件的更新程序,并修改主程序入口,让程序启动时检查更新,如果有新版本就启动更新程序进行下载。另外再写一个用于发布文件(也就是将文件拷贝到网络上)并更新配置文件的程序。当然,这只是局域网上使用的,并没有实现FTP上传功能。主要是对文件(版本信息等)的操作及XML技术的应用。这个思路我已经用了很久了,Delphi版本与C#.NET版本早就写出来了,所以,这次的工作有点像翻译。
「更新程序的编写」
更新程序首先要实现对XML配置文件的解析,得到需要更新的文件,再者就是比对这些文件的版本(或修改时间),并从网络上下载它们到本地覆盖旧文件。
首先,为了使程序更通用一些,更新程序必需的配置文件名与要更新的主程序文件名使用命令行参数传入。问题来了,对命令行参数的处理,在Delphi里是现成的,直接使用ParamStr数组即可;然而,VB6里只有一个Command变量,得到命令行的原始字符串,还需要自行拆分。
对命令行的拆分,本想直接用Split函数(这个函数不错,相对于Delphi,唯一令我赞赏的)简单拆分的,但是,得有点容错能力才行,命令中可能会出现双引号的哦。想依照Delphi的拆分方法(Delphi中几乎所有源码都可以跟踪查看的!再赞一下Delphi,呵呵)的,但Delphi中用的是PChar,一种同时具备指针和字符串特性的类型,这在VB中根本没有替代品。没办法,只有自己再创造一个算法了。所以,就有了下面这段拆分命令行参数的代码了(想了很久的,真的头都快要想爆了):
'{ 将命令行参数拆分到数组。Cable Fan 2009-08-13 } Public Function SplitCommandLine(CommandLine As String) As Variant Dim Lines() As String Dim S As String Dim i As Integer Dim j As Integer Dim Quot As Boolean Dim P As String
S = CommandLine j = -1 While S <> "" ' 是否双引号开头。 If Left(S, 1) = """" Then Quot = True S = Mid(S, 2, Len(S)) ' 剔除双引号。 Else Quot = False End If
' 查找参数结束点。 For i = 1 To Len(S) If i = Len(S) Then ' 查找到最后。 If Quot And Right(S, 1) = """" Then P = Left(S, Len(S) - 1) ' 有双引号结束。 Else P = S ' 无双引号开头与结束。 End If S = "" Quot = False Exit For ElseIf Mid(S, i + 1, 1) = " " Then ' 遇到分隔符(空格)。 If Quot Then If Mid(S, i, 1) = """" Then ' 找到结束双引号。 P = Left(S, i - 1) S = Mid(S, i + 2, Len(S)) Quot = False Exit For End If Else '不以双引号结束。 P = Left(S, i) S = Mid(S, Len(S)) Exit For End If End If Next
' 将参数添加到数组。 j = j + 1 ReDim Preserve Lines(j) Lines(j) = P Wend
SplitCommandLine = Lines End Function |
经过了简单的测试,基本上可以应付Windows下规范的命令行参数了。用法很简单,就像下面的几句即可:
Dim Lines() As String Lines = SplitCommandLine(Command) ‘ 调用命令行拆分函数。 If UBound(Lines) >= 0 Then ConfigFile = Lines(0) If UBound(Lines) >= 1 Then AppFile = Lines(1) |