自身更新
This commit is contained in:
134
Form1.cs
134
Form1.cs
@@ -91,6 +91,9 @@ namespace CheckDownload
|
||||
private readonly object _speedLock = new object(); // 锁,用于多线程更新 UI
|
||||
private long _bytesSinceLastSpeedCalc = 0; // 距离上次速度计算新增的字节数
|
||||
|
||||
// 更新锁文件路径
|
||||
private string _updateLockFilePath;
|
||||
|
||||
/// <summary>
|
||||
/// 初始化窗体
|
||||
/// </summary>
|
||||
@@ -104,6 +107,7 @@ namespace CheckDownload
|
||||
_appName = Assembly.GetExecutingAssembly().GetName().Name;
|
||||
_currentProcessId = Process.GetCurrentProcess().Id;
|
||||
_baseDirectory = Application.StartupPath;
|
||||
_updateLockFilePath = Path.Combine(_baseDirectory, "update.lock");
|
||||
ConfigureProgressBar();
|
||||
}
|
||||
|
||||
@@ -202,6 +206,26 @@ namespace CheckDownload
|
||||
}
|
||||
finally
|
||||
{
|
||||
// 删除更新锁文件,让批处理脚本知道程序已退出
|
||||
CleanupLockFile();
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// 清理更新锁文件
|
||||
/// </summary>
|
||||
private void CleanupLockFile()
|
||||
{
|
||||
try
|
||||
{
|
||||
if (!string.IsNullOrEmpty(_updateLockFilePath) && File.Exists(_updateLockFilePath))
|
||||
{
|
||||
File.Delete(_updateLockFilePath);
|
||||
}
|
||||
}
|
||||
catch
|
||||
{
|
||||
// 忽略清理锁文件时的错误
|
||||
}
|
||||
}
|
||||
|
||||
@@ -1016,38 +1040,122 @@ namespace CheckDownload
|
||||
{
|
||||
string batchFilePath = Path.Combine(_baseDirectory, "update_files.bat");
|
||||
string processId = Process.GetCurrentProcess().Id.ToString();
|
||||
string processName = Process.GetCurrentProcess().ProcessName;
|
||||
|
||||
// 创建锁文件,程序退出前会删除它
|
||||
File.WriteAllText(_updateLockFilePath, processId);
|
||||
|
||||
var batchContent = new StringBuilder();
|
||||
batchContent.AppendLine("@echo off");
|
||||
batchContent.AppendLine("chcp 65001 > nul");
|
||||
batchContent.AppendLine(":check_process");
|
||||
batchContent.AppendLine($"tasklist /FI \"PID eq {processId}\" 2>NUL | find /I \"{processId}\" >NUL");
|
||||
batchContent.AppendLine("if %ERRORLEVEL% == 0 (");
|
||||
batchContent.AppendLine(" timeout /t 1 /nobreak > NUL");
|
||||
batchContent.AppendLine(" goto check_process");
|
||||
batchContent.AppendLine(")");
|
||||
batchContent.AppendLine("timeout /t 2 /nobreak > NUL");
|
||||
batchContent.AppendLine("title Update Process");
|
||||
|
||||
// 简化的等待逻辑,避免复杂的计数器
|
||||
batchContent.AppendLine("echo 等待程序退出...");
|
||||
batchContent.AppendLine(":wait_loop");
|
||||
|
||||
// 优先检查锁文件
|
||||
batchContent.AppendLine($"if not exist \"{_updateLockFilePath}\" goto process_check");
|
||||
|
||||
// 等待0.5秒
|
||||
batchContent.AppendLine("ping 127.0.0.1 -n 1 -w 500 >nul");
|
||||
batchContent.AppendLine("goto wait_loop");
|
||||
|
||||
batchContent.AppendLine(":process_check");
|
||||
// 再次确认进程已退出
|
||||
batchContent.AppendLine($"tasklist /FI \"PID eq {processId}\" 2>nul | find /I \"{processId}\" >nul");
|
||||
batchContent.AppendLine("if %ERRORLEVEL% equ 0 (");
|
||||
batchContent.AppendLine(" ping 127.0.0.1 -n 1 -w 500 >nul");
|
||||
batchContent.AppendLine(" goto process_check");
|
||||
batchContent.AppendLine(")");
|
||||
|
||||
// 额外等待确保完全退出
|
||||
batchContent.AppendLine("ping 127.0.0.1 -n 1 -w 1000 >nul");
|
||||
batchContent.AppendLine("echo 开始更新文件...");
|
||||
|
||||
// 简化的文件处理逻辑,避免复杂的标签
|
||||
int fileIndex = 0;
|
||||
foreach (var file in files)
|
||||
{
|
||||
batchContent.AppendLine($"del \"{file.original}\" /f /q");
|
||||
string fileName = Path.GetFileName(file.original);
|
||||
batchContent.AppendLine($"echo 处理文件: {fileName}");
|
||||
|
||||
// 检查新文件是否存在
|
||||
batchContent.AppendLine($"if not exist \"{file.newFile}\" (");
|
||||
batchContent.AppendLine($" echo 错误: 新文件不存在 - {fileName}");
|
||||
batchContent.AppendLine($" goto file_{fileIndex}_end");
|
||||
batchContent.AppendLine($")");
|
||||
|
||||
// 删除原文件(如果存在)
|
||||
batchContent.AppendLine($"if exist \"{file.original}\" (");
|
||||
batchContent.AppendLine($" echo 删除原文件: {fileName}");
|
||||
batchContent.AppendLine($" del \"{file.original}\" /f /q");
|
||||
batchContent.AppendLine($")");
|
||||
|
||||
// 复制新文件
|
||||
batchContent.AppendLine($"echo 复制新文件: {fileName}");
|
||||
batchContent.AppendLine($"copy /Y \"{file.newFile}\" \"{file.original}\"");
|
||||
|
||||
// 验证复制是否成功
|
||||
batchContent.AppendLine($"if exist \"{file.original}\" (");
|
||||
batchContent.AppendLine($" echo 成功更新: {fileName}");
|
||||
batchContent.AppendLine($" del \"{file.newFile}\" /f /q");
|
||||
batchContent.AppendLine($") else (");
|
||||
batchContent.AppendLine($" echo 失败: 无法创建 {fileName}");
|
||||
batchContent.AppendLine($")");
|
||||
|
||||
batchContent.AppendLine($":file_{fileIndex}_end");
|
||||
fileIndex++;
|
||||
}
|
||||
|
||||
// 清理工作
|
||||
batchContent.AppendLine("echo 清理临时文件...");
|
||||
|
||||
// 删除锁文件
|
||||
batchContent.AppendLine($"if exist \"{_updateLockFilePath}\" del \"{_updateLockFilePath}\" /f /q");
|
||||
|
||||
// 简化的清理逻辑
|
||||
batchContent.AppendLine($"cd /d \"{_baseDirectory}\"");
|
||||
batchContent.AppendLine("for %%f in (*.new) do del \"%%f\" /f /q");
|
||||
batchContent.AppendLine("for %%f in (*.bak) do del \"%%f\" /f /q");
|
||||
|
||||
batchContent.AppendLine("echo 更新完成");
|
||||
batchContent.AppendLine("ping 127.0.0.1 -n 1 -w 2000 >nul");
|
||||
|
||||
// 删除批处理脚本自身
|
||||
batchContent.AppendLine("del \"%~f0\" /f /q");
|
||||
batchContent.AppendLine("exit");
|
||||
|
||||
File.WriteAllText(batchFilePath, batchContent.ToString(), new UTF8Encoding(false));
|
||||
|
||||
// 使用Win7兼容的启动方式
|
||||
var startInfo = new ProcessStartInfo
|
||||
{
|
||||
FileName = batchFilePath,
|
||||
CreateNoWindow = false, // Win7下设为false更稳定
|
||||
UseShellExecute = true, // Win7下必须使用Shell执行
|
||||
WindowStyle = ProcessWindowStyle.Minimized,
|
||||
WorkingDirectory = _baseDirectory
|
||||
};
|
||||
|
||||
try
|
||||
{
|
||||
Process.Start(startInfo);
|
||||
}
|
||||
catch (Exception)
|
||||
{
|
||||
// 如果上面的方式失败,尝试直接用cmd执行
|
||||
var fallbackStartInfo = new ProcessStartInfo
|
||||
{
|
||||
FileName = "cmd.exe",
|
||||
Arguments = $"/c \"{batchFilePath}\"",
|
||||
CreateNoWindow = true,
|
||||
UseShellExecute = false,
|
||||
WindowStyle = ProcessWindowStyle.Hidden
|
||||
UseShellExecute = true,
|
||||
WindowStyle = ProcessWindowStyle.Hidden,
|
||||
WorkingDirectory = _baseDirectory
|
||||
};
|
||||
Process.Start(startInfo);
|
||||
Process.Start(fallbackStartInfo);
|
||||
}
|
||||
|
||||
UpdateStatus("已创建更新脚本,程序退出后将自动完成更新");
|
||||
}
|
||||
catch (Exception ex)
|
||||
{
|
||||
|
Reference in New Issue
Block a user