软件更新原理
自动更新的时候,客户端软件提交更新请求给固定的网址,然后网址返回最新版本的版本号。客户端
软件和自己的版本号对比,如果发现服务器的版本和自己的版本不一样,那么就请求下载升级补丁。服务
器响应请求,提供补丁下载;下载成功后,手动或自动安装一下就可以了。
安装补丁的时候,客户端的主程序一般是要关闭的,除非采用动态卸载、调入组件的技术,比如网络
游戏,就是尽量让玩家边玩游戏边更新。
如果更新的是主程序,那么就必须关闭主程序了。可是主程序关闭了之后,谁来调用安装补丁呢?为
了解决这个问题,人们把主程序和自动更新程序分开来做。当需要校验版本的时候,主程序调用自动更新
程序。自动更新程序如果发现主程序需要更新,在下载了升级补丁之后,就会要求关闭主程序。主程序关
闭之后,自动更新程序调用升级补丁进行安装,安装完成后再重新启动主程序。自动更新程序自动退出,
完成更新任务。这和你刚才关闭电脑后再插网卡的原理是一模一样的。其实生活中有很多现象可以借鉴到
软件设计中。
人们嫌这样的升级仍然太麻烦,后来出现了 B/S结构,大家像抓住了救命稻草一样的追捧至今,希望
能从这些劳动中解脱出来。B/S结构就是浏览器/服务器结构,它所有的功能,都是在浏览器里完成。程序
升级的时候,只需要在服务端升级一下就可以了,浏览器再次访问服务器的时候,得到的就是新版本。你
可以把它理解成一个纯粹的网站。是不是站长更新的时候,你打开网站就看到最新的页面?
但是 B/S结构有天生的弱点,因为它是基于网页浏览的,所以安全性是首要的难题,你能浏览的东西,
原则上别人也能浏览。而且出于安全考虑,B/S访问本地资源,比如串口,必须借助于其他技术实现。B/S
也不是万能的,必须考虑实际应用。
Winform的自动更新
winform程序相对 web程序而言,功能更强大,编程更方便,但软件更新却相当麻烦,要到客户端一台一
台地升级,面对这个实际问题,在最近的一个小项目中,本人设计了一个通过软件实现自动升级技术方案,
弥补了这一缺陷,有较好的参考价值。
一、升级的好处。
长期以来,广大程序员为到底是使用 Client/Server,还是使用 Browser/Server结构争论不休,在这些争论
当中,C/S结构的程序的可维护性差,布置困难,升级不方便,维护成本高就是一个相当重要的因素,也是
那些 B/S的支持者们将 Client/Server结构打入地狱的一个重要原因。
现在好了,我们就在最新的基于 Microsoft 的 WinForm上用WebServices来实现软件的自动升级功能。
二、升级的技术原理。
升级的原理有好几个,首先无非是将现有版本与最新版本作比较,发现最新的则提示用户是否升级。当然
也有人用其它属性比较的,例如:文件大小。 或者更新日期。
而实现的方法呢?在 VB时代,我使用的是 XmlHTTP+INet控件。用 XmlHTTP获取信息,用 INET传输升
级文件,而用一个简单的 BAT文件来实现升级。
Public Sub CheckUpdate()
On Error Resume Next
Dim b As Boolean
Dim XmlHttp As Object
Set XmlHttp = CreateObject("Microsoft.XMLHttp"
XmlHttp.Open "GET", "Http://mu.5inet.net/MuAdmin/update.xml", False
XmlHttp.Send
Dim vs As String
vs = XmlHttp.responseText
If Err.Number > 0 Then
Exit Sub
End If
Dim Xml As Object
Set Xml = CreateObject("Microsoft.XmlDom"
Xml.LoadXml vs
Dim Version As String
Dim downAddr As String
Dim FSize As Long
Dim fInfo As String
Version = Xml.DocumentElement.ChildNodes(0).Text
downAddr = Xml.DocumentElement.ChildNodes(1).Text
FSize = CLng(Xml.DocumentElement.ChildNodes(2).Text)
fInfo = Xml.DocumentElement.ChildNodes(3).Text
Set Xml = Nothing
Set XmlHttp = Nothing
Dim Major As Long
Dim Minor As Long
Dim Revision As Long
Dim C() As String
C = Split(Version, "."
Major = CLng(C(0))
Minor = CLng(C(1))
Revision = CLng(C(2))
If Major > App.Major Then
b = True
ElseIf Minor > App.Minor Then
b = True
ElseIf Revision > App.Revision Then
b = True
Else
b = False
End If
If (b) Then
Dim result As VbMsgBoxResult
result = MsgBox("发现程序新版本。当前版本为:" & App.Major & "." & App.Minor & "." & App.Revision &
",目前最新版本为:" & Version & ",是否进行更新?", vbQuestion Or vbYesNo, "自动更新"
If result = vbYes Then
Dim frm As New Update
frm.DownloadAddress = downAddr
frm.size = FSize
frm.InfoPage = fInfo
frm.Version = Version
frm.Show vbModal
End If
End If
End Sub
而 BAT文件有个特性,是可以删除自己本身。下面是 BAT文件的内容.
@echo off
echo
echo echo 欢迎使用无垠奇迹管理器升级向导。
echo 本次升级版本为:1.1.0。
echo 请按任意键开始升级无垠奇迹管理器... echo
echo
pause
del SQLSrvBrowser.Exe
ren ~update.tmp SQLSrvBrowser.Exe
echo 升级成功,按任意键重新启动应用程序。
pause
start http://mu.5inet.net/
start SQLSrvBrowser.Exe
del update.bat
三、在.Net时代的实现。
在.Net时代,我们就有了更多的选择,可以使用WebRequest,也可以使用WebServices。在这里我们将用
WebServices来实现软件的自动升级。
实现原理:在WebServices中实现一个 GetVer的WebMethod方法,其作用是获取当前的最新版本。
然后将现在版本与最新版本比较,如果有新版本,则进行升级。
步骤:
1、准备一个XML文件 (Update.xml)。
1.0.1818.42821
修正一些 Bug
-
-
-
-
作用是作为一个升级用的模板。
2、WebServices的 GetVer方法。
[WebMethod(Description="取得更新版本"]
public string GetVer()
{
XmlDocument doc = new XmlDocument();
doc.Load(Server.MapPath("update.xml");
XmlElement root = doc.DocumentElement;
return root.SelectSingleNode("version".InnerText;
}
3、WebServices的 GetUpdateData方法。
[WebMethod(Description="在线更新软件"]
[SoapHeader("sHeader"]
public System.Xml.XmlDocument GetUpdateData()
{
//验证用户是否登陆
if(sHeader==null)
return null;
if(!DataProvider.GetInstance.CheckLogin(sHeader.Username,sHeader.Password))
return null;
//取得更新的 xml模板内容
XmlDocument doc = new XmlDocument();
doc.Load(Server.MapPath("update.xml");
XmlElement root = doc.DocumentElement;
//看看有几个文件需要更新
XmlNode updateNode = root.SelectSingleNode("filelist";
string path = updateNode.Attributes["sourcepath"].Value;
int count = int.Parse(updateNode.Attributes["count"].Value);
//将 xml中的 value用实际内容替换
for(int i=0;i