日本好好热aⅴ|国产99视频精品免费观看|日本成人aV在线|久热香蕉国产在线

  • <cite id="ikgdy"><table id="ikgdy"></table></cite>
    1. 西西軟件下載最安全的下載網(wǎng)站、值得信賴的軟件下載站!

      首頁編程開發(fā)C#.NET → C#做的在線升級小程序

      C#做的在線升級小程序

      相關(guān)軟件相關(guān)文章發(fā)表評論 來源:西西整理時間:2013/3/3 10:00:59字體大。A-A+

      作者:西西點擊:85次評論:0次標(biāo)簽: 在線升級

      • 類型:專業(yè)工具大小:16.0M語言:中文 評分:5.4
      • 標(biāo)簽:
      立即下載

      日前收到一個小任務(wù),要做一個通用的在線升級程序。更新的內(nèi)容包括一些dll或exe或、配置文件。升級的大致流程是這樣的,從服務(wù)器獲取一個更新的配置文件,經(jīng)過核對后如有新的更新,則會從服務(wù)器下載相應(yīng)的文件更新到被升級的程序目錄下。如果被升級的程序在升級之前已經(jīng)啟動,程序則會強(qiáng)制關(guān)閉它,待到升級完成之后重新啟動相應(yīng)的程序。在升級之前程序會自動備份一次,以防升級失敗造成程序不能運行。

      首先來的是數(shù)據(jù)實體

       1     public class FileENT
       2     {
       3         public string FileFullName { get; set; }
       4 
       5         public string Src { get; set; }
       6 
       7         public string Version { get; set; }
       8 
       9         public int Size { get; set; }
      10 
      11         public UpdateOption Option { get; set; }
      12     }
      13 
      14     public enum UpdateOption
      15     {
      16         add,
      17         del
      18     }

      下面這個類時程序的一些參數(shù),包括了系統(tǒng)的配置參數(shù),為了程序能通用一點,就加了配置上去。

       1     public class AppParameter
       2     {
       3         /// <summary>
       4         /// 備份路徑
       5         /// </summary>
       6         public static string BackupPath = ConfigurationManager.ApPSettings["backupPath"];
       7 
       8         /// <summary>
       9         /// 更新的URL
      10         /// </summary>
      11         public static string ServerURL = ConfigurationManager.Appsettings["serverURL"];
      12 
      13         /// <summary>
      14         /// 本地更新文件全名
      15         /// </summary>
      16         public static string LocalUPdateConfig = ConfigurationManager.AppSettings["localUPdateConfig"];
      17 
      18         /// <summary>
      19         /// 版本號
      20         /// </summary>
      21         public static string Version = ConfigurationManager.AppSettings["version"];
      22 
      23         /// <summary>
      24         /// 更新程序路徑
      25         /// </summary>
      26         public static string LocalPath = AppDomain.CurrentDomain.BaseDirectory;
      27 
      28         /// <summary>
      29         /// 主程序路徑
      30         /// </summary>
      31         public static string MainPath = ConfigurationManager.AppSettings["mainPath"];
      32 
      33         /// <summary>
      34         /// 有否啟動主程序
      35         /// </summary>
      36         public static bool IsRunning = false;
      37 
      38         /// <summary>
      39         /// 主程序名
      40         /// </summary>
      41         public static List<string> AppNames = ConfigurationManager.AppSettings["appName"].Split(';').ToList();
      42     }

      接著就介紹程序的代碼

      程序是用窗體來實現(xiàn)的,下面三個是窗體新添加的三個字段

      1         private bool isDelete=true; //是否要刪除升級配置
      2         private bool runningLock = false;//是否正在升級
      3         private Thread thread; //升級的線程

      載入窗體時需要檢查更新,如果沒有更新就提示”暫時無更新”;如果有更新的則先進(jìn)行備份,備份失敗的話提示錯誤退出更新。

       1             if (CheckUpdate())
       2             {
       3                 if (!Backup())
       4                 {
       5                     MessageBox.Show("備份失敗!");
       6                     btnStart.Enabled = false;
       7                     isDelete = true;
       8                     return;
       9                 }
      10 
      11             }
      12             else
      13             {
      14                 MessageBox.Show("暫時無更新");
      15                 this.btnFinish.Enabled = true;
      16                 this.btnStart.Enabled = false;
      17                 isDelete = false;
      18                 this.Close();
      19             }

      在這些操作之前還要檢測被更新程序有否啟動,有則將其關(guān)閉。

       1             List<string> processNames = new List<string>();
       2             string mainPro = string.Empty;
       3             processNames.AddRange(AppParameter.AppNames);
       4             for (int i = 0; i < processNames.Count; i++)
       5             {
       6                 processNames[i] = processNames[i].Substring(processNames[i].LastIndexOf('\\')).Trim('\\').Replace(".exe", "");
       7             }
       8             mainPro = processNames.FirstOrDefault();
       9             AppParameter.IsRunning = ProcessHelper.IsRunningProcess(mainPro);
      10             if (AppParameter.IsRunning)
      11             {
      12                 MessageBox.Show("此操作需要關(guān)閉要更新的程序,請保存相關(guān)數(shù)據(jù)按確定繼續(xù)", "提示", MessageBoxButtons.OK, MessageBoxIcon.Warning);
      13                 foreach (string item in processNames)
      14                     ProcessHelper.CloseProcess(item);
      15             }

      另外上面用到的CheckUpdate( )和Backup( )方法如下

       1           /// <summary>
       2         /// 檢查更新 有則提示用戶 確認(rèn)后下載新的更新配置
       3         /// </summary>
       4         /// <returns>用戶確認(rèn)信息</returns>
       5         public static bool CheckUpdate()
       6         {
       7             bool result = false;
       8 
       9             HttpHelper.DownLoadFile(AppParameter.ServerURL, AppParameter.LocalPath + "temp_config.xml");
      10             if (!File.Exists(AppParameter.LocalUPdateConfig))
      11                 result = true;
      12             else
      13             {
      14                 long localSize = new FileInfo(AppParameter.LocalUPdateConfig).Length;
      15                 long tempSize = new FileInfo(AppParameter.LocalPath + "temp_config.xml").Length;
      16 
      17                 if (localSize >= tempSize) result = false;
      18 
      19                 else result = true;
      20             }
      21 
      22             if (result)
      23             {
      24                 if (File.Exists(AppParameter.LocalUPdateConfig)) File.Delete(AppParameter.LocalUPdateConfig);
      25                 File.Copy(AppParameter.LocalPath + "temp_config.xml", AppParameter.LocalUPdateConfig);
      26             }
      27             else
      28                 result = false;
      29 
      30             File.Delete(AppParameter.LocalPath + "temp_config.xml");
      31             return result;
      32         }
      33 
      34         /// <summary>
      35         /// 備份
      36         /// </summary>
      37         public static bool Backup()
      38         {
      39             string sourcePath = Path.Combine(AppParameter.BackupPath, DateTime.Now.ToString("yyyy-MM-dd HH_mm_ss")+"_v_"+AppParameter.Version + ".rar");
      40             return ZipHelper.Zip(AppParameter.MainPath.Trim() , sourcePath);
      41         }

      下面則是更新的部分的代碼,使用了多線程,出于兩方面的考慮,一是進(jìn)度條需要;二是如果用單線程,萬一更新文件下載時間過長或者更新內(nèi)容過多,界面會卡死。

        1         /// <summary>
        2         /// 更新
        3         /// </summary>
        4         public void UpdateApp()
        5         {
        6             int successCount = 0;
        7             int failCount = 0;
        8             int itemIndex = 0;
        9             List<FileENT> list = ConfigHelper.GetUpdateList();
       10             if (list.Count == 0)
       11             {
       12                 MessageBox.Show("版本已是最新", "提示", MessageBoxButtons.OK, MessageBoxIcon.Information);
       13                 this.btnFinish.Enabled = true;
       14                 this.btnStart.Enabled = false;
       15                 isDelete = false;
       16                 this.Close();
       17                 return;
       18             }
       19             thread = new Thread(new ThreadStart(delegate
       20             {
       21                 #region thread method
       22 
       23                 FileENT ent = null;
       24 
       25                 while (true)
       26                 {
       27                     lock (this)
       28                     {
       29                         if (itemIndex >= list.Count)
       30                             break;
       31                         ent = list[itemIndex];
       32 
       33 
       34                         string msg = string.Empty;
       35                         if (ExecUpdateItem(ent))
       36                         {
       37                             msg = ent.FileFullName + "更新成功";
       38                             successCount++;
       39                         }
       40                         else
       41                         {
       42                             msg = ent.FileFullName + "更新失敗";
       43                             failCount++;
       44                         }
       45 
       46                         if (this.InvokeRequired)
       47                         {
       48                             this.Invoke((Action)delegate()
       49                             {
       50                                 listBox1.Items.Add(msg);
       51                                 int val = (int)Math.Ceiling(1f / list.Count * 100);
       52                                 progressBar1.Value = progressBar1.Value + val > 100 ? 100 : progressBar1.Value + val;
       53                             });
       54                         }
       55 
       56 
       57                         itemIndex++;
       58                         if (successCount + failCount == list.Count && this.InvokeRequired)
       59                         {
       60                             string finishMessage = string.Empty;
       61                             if (this.InvokeRequired)
       62                             {
       63                                 this.Invoke((Action)delegate()
       64                                 {
       65                                     btnFinish.Enabled = true;
       66                                 });
       67                             }
       68                             isDelete = failCount != 0;
       69                             if (!isDelete)
       70                             {
       71                                 AppParameter.Version = list.Last().Version;
       72                                 ConfigHelper.UpdateAppConfig("version", AppParameter.Version);
       73                                 finishMessage = "升級完成,程序已成功升級到" + AppParameter.Version;
       74                             }
       75                             else
       76                                 finishMessage = "升級完成,但不成功";
       77                             MessageBox.Show(finishMessage, "提示", MessageBoxButtons.OK, MessageBoxIcon.Information);
       78                             runningLock = false;
       79                         }
       80                     }
       81                 }
       82                 #endregion
       83             }));
       84             runningLock = true;
       85             thread.Start();
       86         }
       87 
       88         /// <summary>
       89         /// 執(zhí)行單個更新
       90         /// </summary>
       91         /// <param name="ent"></param>
       92         /// <returns></returns>
       93         public bool ExecUpdateItem(FileENT ent)
       94         {
       95             bool result = true;
       96 
       97             try
       98             {
       99 
      100                 if (ent.Option == UpdateOption.del)
      101                     File.Delete(ent.FileFullName);
      102                 else
      103                     HttpHelper.DownLoadFile(ent.Src, Path.Combine(AppParameter.MainPath, ent.FileFullName));
      104             }
      105             catch { result = false; }
      106             return result;
      107         }

      只開了一個子線程,原本是開了5個子線程的,但是考慮到多線程會導(dǎo)致下載文件的順序不確定,還是用回單線程會比較安全。線程是用了窗體實例里的thread字段,在開啟線程時還用到runningLock標(biāo)識字段,表示當(dāng)前正在更新。當(dāng)正在更新程序時關(guān)閉窗口,則要提問用戶是否結(jié)束更新,若用戶選擇了是則要結(jié)束那個更新進(jìn)程thread了,下面則是窗口關(guān)閉的時間FormClosing事件的方法。

       1             if (runningLock )
       2             {
       3                 if (MessageBox.Show("升級還在進(jìn)行中,中斷升級會導(dǎo)致程序不可用,是否中斷",
       4                           "提示", MessageBoxButtons.YesNo, MessageBoxIcon.Asterisk) == DialogResult.Yes)
       5                 {
       6                     if (thread != null) thread.Abort();
       7                     isDelete = true;
       8                     AppParameter.IsRunning = false;
       9                 }
      10                 else 
      11                 {
      12                     e.Cancel = true;
      13                     return;
      14                 }
      15             }
      16             if (isDelete) File.Delete(AppParameter.LocalUPdateConfig);

      在這里還要做另一件事,就是把之前關(guān)了的程序重新啟動

      1             try
      2             {
      3                 if (AppParameter.IsRunning) ProcessHelper.StartProcess(AppParameter.AppNames.First());
      4             }
      5             catch (Exception ex)
      6             {
      7 
      8                 MessageBox.Show("程序無法啟動!" + ex.Message, "錯誤", MessageBoxButtons.OK, MessageBoxIcon.Error);
      9             }

      在這里展示一下更新的界面。挺丑的,別笑哈。

      更新程序的配置信息如下

      1   <appSettings>
      2     <add key="backupPath" value="C:\Users\Administrator\Desktop\temp\backup"/>
      3     <add key="serverURL" value="http://localhost:8015/updateconfig.xml"/>
      4     <add key="localUPdateConfig" value="E:\HopeGi\Code\MyUpdate\MyUpdate\bin\Debug\updateconfig.xml"/>
      5     <add key="version" value="2"/>
      6     <add key="mainPath" value="C:\Users\Administrator\Desktop\temp\main"/>
      7     <add key="appName" value="D:\test.exe"/>
      8   </appSettings>
      完整文檔下載:http://pan.baidu.com/share/link?shareid=443378&uk=85241834

        相關(guān)評論

        閱讀本文后您有什么感想? 已有人給出評價!

        • 8 喜歡喜歡
        • 3 頂
        • 1 難過難過
        • 5 囧
        • 3 圍觀圍觀
        • 2 無聊無聊

        熱門評論

        最新評論

        發(fā)表評論 查看所有評論(0)

        昵稱:
        表情: 高興 可 汗 我不要 害羞 好 下下下 送花 屎 親親
        字?jǐn)?shù): 0/500 (您的評論需要經(jīng)過審核才能顯示)