You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 

191 lines
5.6 KiB

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Diagnostics;
using System.Drawing;
using System.IO;
using System.Linq;
using System.Net;
using System.Text;
using System.Threading;
using System.Windows.Forms;
namespace ButcherFactory.AutoUpdate
{
public partial class Form1 : Form
{
const string serUri = "http://172.28.1.194:7799/AutoUpdate/ClientVersion.xml";
const string PuKey = "c756e02cedb42a33f78091a466411bde8447d854";
private bool isFinished = false;
private List<UpdateFile> downloadFileList = null;
private ManualResetEvent evtDownload = null;
private ManualResetEvent evtPerDonwload = null;
private WebClient clientDownload = null;
ClientVersion old;
bool error = false;
public Form1(string[] args)
{
InitializeComponent();
if (args == null || args.Length == 0 || args[0] != PuKey)
error = true;
this.Load += Form1_Load;
}
void Form1_Load(object sender, EventArgs e)
{
if (error)
Application.Exit();
var versionFile = "ClientVersion.xml";
old = new ClientVersion();
if (File.Exists(versionFile))
old = XmlUtil.DeserializeFromFile<ClientVersion>();
if (string.IsNullOrEmpty(old.ServerUrl))
old.ServerUrl = serUri;
clientDownload = new WebClient();
var version = XmlUtil.XmlDeserializeObject<ClientVersion>(clientDownload.DownloadString(old.ServerUrl));
old.ServerUrl = version.ServerUrl;
old.Version = version.Version;
downloadFileList = version.UpdateFiles;
evtDownload = new ManualResetEvent(true);
evtDownload.Reset();
Thread t = new Thread(new ThreadStart(ProcDownload));
t.Name = "download";
t.Start();
}
long total = 0;
long nDownloadedTotal = 0;
string startFile = "ButcherFactory.Login.exe";
string oldFolder;
private void ProcDownload()
{
evtPerDonwload = new ManualResetEvent(false);
foreach (var file in this.downloadFileList)
{
total += file.Size;
}
oldFolder = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, "old");
if (!Directory.Exists(oldFolder))
Directory.CreateDirectory(oldFolder);
while (!evtDownload.WaitOne(0, false))
{
if (this.downloadFileList.Count == 0)
break;
var file = this.downloadFileList[0];
if (file.NeedRestart)
startFile = file.FileName;
this.ShowCurrentDownloadFileName(file.FileName);
//下载
clientDownload = new WebClient();
clientDownload.DownloadProgressChanged += new DownloadProgressChangedEventHandler(OnDownloadProgressChanged);
clientDownload.DownloadFileCompleted += new AsyncCompletedEventHandler(OnDownloadFileCompleted);
evtPerDonwload.Reset();
clientDownload.DownloadFileAsync(new Uri(file.Url), Path.Combine(AppDomain.CurrentDomain.BaseDirectory, file.FileName + ".tmp"), file);
//等待下载完成
evtPerDonwload.WaitOne();
clientDownload.Dispose();
clientDownload = null;
//移除已下载的文件
this.downloadFileList.Remove(file);
}
if (this.downloadFileList.Count == 0)
{
Exit(true);
evtDownload.Set();
XmlUtil.SerializerObjToFile(old);
Process.Start(Path.Combine(Application.StartupPath, startFile));
Application.Exit();
}
else
Exit(false);
evtDownload.Set();
}
void OnDownloadFileCompleted(object sender, AsyncCompletedEventArgs e)
{
var file = e.UserState as UpdateFile;
nDownloadedTotal += file.Size;
this.SetProcessBar(0, (int)(nDownloadedTotal * 100 / total));
//备份文件
string filePath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, file.FileName);
var oldFile = Path.Combine(oldFolder, file.FileName);
if (File.Exists(filePath))
{
if (File.Exists(oldFile))
File.Delete(oldFile);
File.Move(filePath, oldFile);
}
File.Move(filePath + ".tmp", filePath);
//继续下载其它文件
evtPerDonwload.Set();
}
void OnDownloadProgressChanged(object sender, DownloadProgressChangedEventArgs e)
{
this.SetProcessBar(e.ProgressPercentage, (int)((nDownloadedTotal + e.BytesReceived) * 100 / total));
}
delegate void ShowCurrentDownloadFileNameCallBack(string name);
private void ShowCurrentDownloadFileName(string name)
{
if (this.labelCurrentItem.InvokeRequired)
{
ShowCurrentDownloadFileNameCallBack cb = new ShowCurrentDownloadFileNameCallBack(ShowCurrentDownloadFileName);
this.Invoke(cb, new object[] { name });
}
else
{
this.labelCurrentItem.Text = name;
}
}
delegate void SetProcessBarCallBack(int current, int total);
private void SetProcessBar(int current, int total)
{
if (this.progressBarCurrent.InvokeRequired)
{
SetProcessBarCallBack cb = new SetProcessBarCallBack(SetProcessBar);
this.Invoke(cb, new object[] { current, total });
}
else
{
this.progressBarCurrent.Value = current;
this.progressBarTotal.Value = total;
}
}
delegate void ExitCallBack(bool success);
private void Exit(bool success)
{
if (this.InvokeRequired)
{
ExitCallBack cb = new ExitCallBack(Exit);
this.Invoke(cb, new object[] { success });
}
else
{
this.isFinished = success;
this.DialogResult = success ? DialogResult.OK : DialogResult.Cancel;
this.Close();
}
}
}
}