日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當(dāng)前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

如何制作自动更新程序?

發(fā)布時間:2023/12/20 编程问答 32 豆豆
生活随笔 收集整理的這篇文章主要介紹了 如何制作自动更新程序? 小編覺得挺不錯的,現(xiàn)在分享給大家,幫大家做個參考.

原文出自:http://blog.csdn.net/metaphysis/article/details/18866631


如何制作自動更新程序?

[版權(quán)所有 邱秋 2014 metaphysis@yeah.net, 轉(zhuǎn)載請注明出處]

最近為單位寫了一個C/S結(jié)構(gòu)的軟件,這個軟件是工作在單位的局域網(wǎng)內(nèi)的。為了減輕為程序進(jìn)行升級的工作量,需要解決程序自動更新的問題。那么如何做一個自動更新程序呢?

想了一下,更新程序需要解決以下問題:

(A)它需要知道哪些是需要更新的文件,哪些是不需要的文件;

(B)它需要知道從哪里下載更新文件;

(C) 它需要將更新的文件下載下來,并將舊的文件替換掉,將不再需要的文件刪除掉;

(D)它需要能夠在更新完畢后自動重新啟動程序以便用戶繼續(xù)使用;

問題(A)可以通過版本控制的方法來解決。具體方法是為程序所使用的文件都設(shè)定一個版本號,所有文件的版本號都記錄在一個 XML 文件中,當(dāng)升級時,檢查最新程序的版本控制文件和當(dāng)前的版本控制文件,當(dāng)版本號較大時,則表示該文件需要更新。最新的版本控制文件可以放在一個匿名 FTP 上以便程序下載下來和本地的版本控制文件進(jìn)行比對。如果一個文件不再需要了,則將該文件的版本信息從最新的版本控制文件中刪除,通過對比控制文件,就知道該文件不再需要了,可以將之刪除。由于我寫的程序除主程序外,其他組件都不會發(fā)生太多改動,所以我使用了如下的方式來表示一個文件的版本信息:

[vb]?view plaincopy
  • <?xml?version="1.0"?encoding="utf-8"?>??
  • <AutoUpdater>??
  • ??<Updater>??
  • ????<UpdateUrl>ftp://192.168.1.24/update/</UpdateUrl>??
  • ????<MainVersion>1.1.102.0</MainVersion>??
  • ????<LastUpdateTime>2014-01-27</LastUpdateTime>??
  • ????<UpdateDescription>自動更新程序</UpdateDescription>??
  • ??</Updater>??
  • ??<UpdateFileList>??
  • ????<UpdateFile?Version="2.2.5.0"?Name="AForge.dll"?/>??
  • ????<UpdateFile?Version="2.2.5.0"?Name="AForge.Video.DirectShow.dll"?/>??
  • ????<UpdateFile?Version="2.2.5.0"?Name="AForge.Video.dll"?/>??
  • ????<UpdateFile?Version="1.0.100.0"?Name="USBCleaner.exe"?/>??
  • ????<UpdateFile?Version="1.0.100.0"?Name="USBViewer.exe"?/>??
  • ??</UpdateFileList>??
  • </AutoUpdater>??
  • UpdateUrl 告訴程序要從什么地方下載最新的版本控制文件和更新文件,這里我使用了 FTP 的方式,這樣簡單一些,我將版本控制文件和最新的程序文件都放在了 ftp://192.168.1.24/update/ 下。MainVersion 表示程序的版本,用來確定是否需要進(jìn)行升級。LastUpdateTime 表示程序最后的更新時間。UpdateDescription 表示更新程序的描述。UpdateFile 則表示程序中的每一個文件條目,Version 表示其版本,Name 表示相對于程序根目錄的文件路徑名,如果文件是在根目錄下面,則直接是文件名,如果是在子目錄下,則在前面加上相應(yīng)的子目錄。

    有了這個版本控制文件,問題(B)也解決了,因?yàn)閺闹付ǖ牡刂废螺d即可。

    問題(C)可以通過比對版本控制文件,確定需要下載的文件和不再需要的文件。然后通過 WebClient 類來下載需要的文件。

    問題(D)可以這樣解決,主程序先檢查是否有升級,如果有升級,則將舊的更新程序再復(fù)制一份,啟動復(fù)制的更新程序,并啟動它來下載更新文件,這樣的話,就可以解決更新更新程序本身的問題,因?yàn)閷⑿碌母鲁绦蛳螺d來后,可以直接覆蓋掉原始的更新程序而不會產(chǎn)生文件正在使用無法更新的問題,因?yàn)檫\(yùn)行的是舊的更新程序的副本,在全部更新完畢后,主程序中可以加一段代碼檢測是否有更新副本產(chǎn)生,只要有就將它刪除即可。

    想清楚了這些問題,就是具體代碼實(shí)現(xiàn)了,以下把版本文件解析的代碼和更新下載文件的代碼貼出來,整個更新模塊也提供了下載,供有興趣的朋友參考使用。下載鏈接:http://download.csdn.net/detail/metaphysis/6891593。

    [vb]?view plaincopy
  • XmlVersionConfigFile.vb??
  • ??
  • Imports?System.Xml??
  • Imports?System.Xml.Linq??
  • ??
  • Public?Class?XmlVersionConfigFile??
  • ??
  • ????Public?Property?UpdateUrl?As?String?=?String.Empty??
  • ????Public?Property?MainVersion?As?Version?=?Version.Parse("0.0.0.0")??
  • ????Public?Property?LastUpdateTime?As?Date?=?DateTimePicker.MinimumDateTime??
  • ????Public?Property?UpdateDescription?As?String?=?String.Empty??
  • ????Public?Property?UpdateFileList?As?Dictionary(Of?String,?Version)?=?Nothing??
  • ??
  • ????Public?Sub?New(ByVal?fileContent?As?String)??
  • ????????ParseXmlVersionFile(fileContent)??
  • ????End?Sub??
  • ??
  • ????Private?Function?ParseXmlVersionFile(ByVal?fileContent?As?String)?As?Boolean??
  • ????????Dim?xdoc?As?XDocument?=?Nothing??
  • ????????Try??
  • ????????????xdoc?=?XDocument.Parse(fileContent)??
  • ????????Catch?ex?As?Exception??
  • ????????????Return?False??
  • ????????End?Try??
  • ??
  • ????????Me.UpdateUrl?=?xdoc.Element("AutoUpdater").Element("Updater").Element("UpdateUrl").Value??
  • ????????Me.MainVersion?=?Version.Parse(xdoc.Element("AutoUpdater").Element("Updater").Element("MainVersion").Value)??
  • ????????Date.TryParse(xdoc.Element("AutoUpdater").Element("Updater").Element("LastUpdateTime").Value,?Me.LastUpdateTime)??
  • ????????Me.UpdateDescription?=?xdoc.Element("AutoUpdater").Element("Updater").Element("UpdateDescription").Value??
  • ??
  • ????????Me.UpdateFileList?=?New?Dictionary(Of?String,?Version)??
  • ????????Dim?query?=?From?UpdateFile?In?xdoc.Descendants("UpdateFile")?Select?UpdateFile??
  • ????????For?Each?fileInfo?As?XElement?In?query??
  • ????????????Me.UpdateFileList.Add(fileInfo.Attribute("Name").Value.ToLower,?Version.Parse(fileInfo.Attribute("Version").Value))??
  • ????????Next??
  • ??
  • ????????Return?True??
  • ????End?Function??
  • End?Class??
  • [vb]?view plaincopy
  • UpdatingForm.vb??
  • ??
  • Imports?System.IO??
  • ??
  • Public?Class?UpdatingForm??
  • ??
  • ????Public?Property?LocalVersionConfig?As?XmlVersionConfigFile?=?Nothing??
  • ????Public?Property?ServerVersionConfig?As?XmlVersionConfigFile?=?Nothing??
  • ??
  • ????Private?WithEvents?webClient?As?New?System.Net.WebClient??
  • ??
  • ????Private?_downloadIndex?As?Integer??
  • ????Private?_localConfigFileName?As?String?=?"version.xml"??
  • ????Private?_localXmlFilePath?As?String?=?Path.Combine(Application.StartupPath,?_localConfigFileName)??
  • ????Private?_updateUrl?As?String?=?String.Empty??
  • ????Private?_deleteFileList?As?New?List(Of?String)??
  • ??
  • ????Private?Sub?webClient_DownloadFileCompleted(ByVal?sender?As?Object,?ByVal?e?As?System.ComponentModel.AsyncCompletedEventArgs)?Handles?webClient.DownloadFileCompleted??
  • ????????Me.lvwFile.Items(_downloadIndex).ImageIndex?=?2??
  • ??
  • ????????lblSinglePercent.Text?=?"0%"??
  • ????????prbSingle.Value?=?0??
  • ??
  • ????????DownloadNextFile()??
  • ????End?Sub??
  • ??
  • ????Private?Sub?webClient_DownloadProgressChanged(ByVal?sender?As?System.Object,?ByVal?e?As?System.Net.DownloadProgressChangedEventArgs)?Handles?webClient.DownloadProgressChanged??
  • ????????Dim?currentPercent?As?String?=?e.ProgressPercentage?&?"%"??
  • ????????If?currentPercent?<>?Me.lvwFile.Items(_downloadIndex).SubItems(3).Text?Then??
  • ????????????Me.lvwFile.Items(_downloadIndex).SubItems(3).Text?=?currentPercent??
  • ????????????prbSingle.Value?=?e.ProgressPercentage??
  • ????????????lblSinglePercent.Text?=?currentPercent??
  • ????????????prbAll.Value?=?Int((_downloadIndex?+?1)?/?Me.lvwFile.Items.Count?*?100)??
  • ????????????lblAllPercent.Text?=?prbAll.Value?&?"%"??
  • ????????End?If??
  • ????End?Sub??
  • ??
  • ????Private?Sub?btnQuit_Click(ByVal?sender?As?System.Object,?ByVal?e?As?System.EventArgs)?Handles?btnQuit.Click??
  • ????????Me.Close()??
  • ????End?Sub??
  • ??
  • ????Private?Sub?DownloadNextFile()??
  • ????????If?_downloadIndex?<?(lvwFile.Items.Count?-?1)?Then??
  • ??
  • ????????????_downloadIndex?+=?1??
  • ??
  • ????????????lvwFile.Items(_downloadIndex).ImageIndex?=?1??
  • ??
  • ????????????Try??
  • ????????????????Dim?destPath?As?String?=?IO.Path.Combine(Application.StartupPath,?lvwFile.Items(_downloadIndex).SubItems(1).Text)??
  • ????????????????File.Delete(destPath)??
  • ????????????????webClient.DownloadFileAsync(New?Uri(_updateUrl?&?lvwFile.Items(_downloadIndex).SubItems(1).Text),?destPath)??
  • ????????????Catch?ex?As?Exception??
  • ????????????????Me.lvwFile.Items(_downloadIndex).ImageIndex?=?3??
  • ????????????????MsgBox("下載文件發(fā)生錯誤,更新失敗。錯誤原因:?"?&?ex.Message,?MsgBoxStyle.Critical,?"錯誤")??
  • ????????????????Me.Close()??
  • ????????????End?Try??
  • ????????Else??
  • ????????????UpdateFileCompleted()??
  • ????????End?If??
  • ????End?Sub??
  • ??
  • ????Private?Sub?UpdateFileCompleted()??
  • ????????'?更新顯示信息。??
  • ????????prbSingle.Value?=?prbSingle.Maximum??
  • ????????lblSinglePercent.Text?=?"100%"??
  • ????????lblAllPercent.Text?=?"100%"??
  • ??
  • ????????'?刪除不需要的文件。??
  • ????????For?Each?f?As?String?In?_deleteFileList??
  • ????????????Try??
  • ????????????????File.Delete(Path.Combine(Application.StartupPath,?f))??
  • ????????????Catch?ex?As?Exception??
  • ????????????????'??
  • ????????????End?Try??
  • ????????Next??
  • ??
  • ????????Me.btnQuit.Enabled?=?True??
  • ????????Process.Start(IO.Path.Combine(Application.StartupPath,?"szpt.exe"))??
  • ????????Me.Close()??
  • ????End?Sub??
  • ??
  • ????Private?Sub?LoadUpdateFile()??
  • ????????_updateUrl?=?Me.ServerVersionConfig.UpdateUrl??
  • ??
  • ????????'?查找客戶端需要更新的文件和需要刪除的文件。??
  • ????????For?Each?p?As?KeyValuePair(Of?String,?Version)?In?Me.LocalVersionConfig.UpdateFileList??
  • ????????????If?Me.ServerVersionConfig.UpdateFileList.ContainsKey(p.Key)?Then??
  • ????????????????If?Me.ServerVersionConfig.UpdateFileList(p.Key)?>?Me.LocalVersionConfig.UpdateFileList(p.Key)?Then??
  • ????????????????????Dim?item?As?ListViewItem?=?Me.lvwFile.Items.Add(String.Empty,?0)??
  • ????????????????????item.SubItems.Add(p.Key)??
  • ????????????????????item.SubItems.Add(Me.ServerVersionConfig.UpdateFileList(p.Key).ToString)??
  • ????????????????????item.SubItems.Add(String.Empty)??
  • ????????????????End?If??
  • ????????????Else??
  • ????????????????_deleteFileList.Add(p.Key)??
  • ????????????End?If??
  • ????????Next??
  • ??
  • ????????'?查找服務(wù)器端新增需要下載的文件。??
  • ????????For?Each?p?As?KeyValuePair(Of?String,?Version)?In?Me.ServerVersionConfig.UpdateFileList??
  • ????????????If?Me.LocalVersionConfig.UpdateFileList.ContainsKey(p.Key)?=?False?Then??
  • ????????????????Dim?item?As?ListViewItem?=?Me.lvwFile.Items.Add(String.Empty,?0)??
  • ????????????????item.SubItems.Add(p.Key)??
  • ????????????????item.SubItems.Add(p.Value.ToString)??
  • ????????????????item.SubItems.Add(String.Empty)??
  • ????????????End?If??
  • ????????Next??
  • ??
  • ????????'?版本控制文件為必須下載文件。??
  • ????????Dim?itemVersion?As?ListViewItem?=?Me.lvwFile.Items.Add(String.Empty,?0)??
  • ????????itemVersion.SubItems.Add("version.xml")??
  • ????????itemVersion.SubItems.Add(Me.ServerVersionConfig.MainVersion.ToString)??
  • ????????itemVersion.SubItems.Add(String.Empty)??
  • ??
  • ????????'?設(shè)置當(dāng)前下載的文件序數(shù)。??
  • ????????_downloadIndex?=?-1??
  • ????End?Sub??
  • ??
  • ????Private?Sub?UpdatingForm_Load(ByVal?sender?As?System.Object,?ByVal?e?As?System.EventArgs)?Handles?MyBase.Load??
  • ????????LoadUpdateFile()??
  • ????????DownloadNextFile()??
  • ????End?Sub??
  • ??
  • End?Class??

  • 總結(jié)

    以上是生活随笔為你收集整理的如何制作自动更新程序?的全部內(nèi)容,希望文章能夠幫你解決所遇到的問題。

    如果覺得生活随笔網(wǎng)站內(nèi)容還不錯,歡迎將生活随笔推薦給好友。