diff --git a/Update.cs b/Update.cs
index a6f49e8..bd92ebe 100644
--- a/Update.cs
+++ b/Update.cs
@@ -202,6 +202,12 @@ namespace CheckDownload
PositionFormToBottomRight();
try
{
+ // 首先检查程序是否在正确的根目录位置
+ if (await CheckAndRelocateIfNeeded())
+ {
+ return; // 如果需要重定位,则退出当前程序
+ }
+
await UpdateFile();
}
finally
@@ -1955,5 +1961,235 @@ namespace CheckDownload
CopyDirectory(subDir, targetSubDir);
}
}
+
+ ///
+ /// 检查当前程序是否在正确的根目录位置,如果不在则复制到根目录并运行
+ ///
+ /// 如果需要重定位并成功启动新程序返回true,否则返回false
+ private async Task CheckAndRelocateIfNeeded()
+ {
+ try
+ {
+ UpdateStatus("检查程序位置...");
+
+ // 首先尝试获取MD5文件以确定根目录
+ string tempMd5Path = await DownloadMd5FileForLocationCheck();
+ if (string.IsNullOrEmpty(tempMd5Path))
+ {
+ UpdateStatus("无法获取MD5文件,继续正常更新流程");
+ return false;
+ }
+
+ // 解析MD5文件获取根目录
+ string correctRootDirectory = await DetermineRootDirectoryFromMd5(tempMd5Path);
+ if (string.IsNullOrEmpty(correctRootDirectory))
+ {
+ UpdateStatus("无法确定根目录,继续正常更新流程");
+ return false;
+ }
+
+ // 检查当前程序是否在正确的位置
+ string currentProgramPath = Application.ExecutablePath;
+ string currentProgramName = Path.GetFileName(currentProgramPath);
+ string expectedProgramPath = Path.Combine(correctRootDirectory, GetRelativePathInProject(), currentProgramName);
+
+ // 标准化路径以便比较
+ string normalizedCurrentPath = Path.GetFullPath(currentProgramPath).ToLowerInvariant();
+ string normalizedExpectedPath = Path.GetFullPath(expectedProgramPath).ToLowerInvariant();
+
+ if (normalizedCurrentPath.Equals(normalizedExpectedPath))
+ {
+ UpdateStatus("程序已在正确位置");
+ // 更新基准目录为正确的根目录
+ _baseDirectory = correctRootDirectory;
+ return false; // 继续正常流程
+ }
+
+ // 程序不在正确位置,需要复制到正确位置
+ UpdateStatus("程序位置不正确,正在复制到根目录...");
+
+ return await RelocateProgramToRoot(currentProgramPath, expectedProgramPath);
+ }
+ catch (Exception ex)
+ {
+ UpdateStatus($"检查程序位置时出错: {ex.Message}");
+ return false; // 出错时继续正常流程
+ }
+ }
+
+ ///
+ /// 下载MD5文件用于位置检查(轻量级版本)
+ ///
+ /// 临时MD5文件路径,失败返回null
+ private async Task DownloadMd5FileForLocationCheck()
+ {
+ try
+ {
+ string tempDir = Path.GetTempPath();
+ string tempMd5Path = Path.Combine(tempDir, $"{_appName}_location_check_{Guid.NewGuid()}.json");
+
+ // 尝试从123盘下载
+ if (await DownloadFromOneDrive($"http://{OneDriveMainDomain}{OneDrivePath}", Md5File, tempMd5Path))
+ {
+ return tempMd5Path;
+ }
+
+ // 尝试从OSS下载
+ if (await DownloadFileWithFallback(Md5File, tempMd5Path))
+ {
+ return tempMd5Path;
+ }
+
+ return null;
+ }
+ catch
+ {
+ return null;
+ }
+ }
+
+ ///
+ /// 从MD5文件确定项目根目录
+ ///
+ /// MD5文件路径
+ /// 项目根目录路径
+ private async Task DetermineRootDirectoryFromMd5(string md5FilePath)
+ {
+ try
+ {
+ var onlineData = ReadOnlineMd5File(md5FilePath);
+ if (!ValidateOnlineData(onlineData.Version, onlineData.Md5, onlineData.Data))
+ {
+ return null;
+ }
+
+ // 使用现有的逻辑确定基准目录
+ string currentProgramName = Path.GetFileName(Application.ExecutablePath);
+ string programPathInMd5 = FindFileInMd5Data(onlineData.Data, currentProgramName);
+
+ if (!string.IsNullOrEmpty(programPathInMd5))
+ {
+ string programDirInMd5 = Path.GetDirectoryName(programPathInMd5) ?? "";
+ string currentProgramDir = Path.GetDirectoryName(Application.ExecutablePath);
+
+ if (string.IsNullOrEmpty(programDirInMd5))
+ {
+ return currentProgramDir; // 程序就在根目录
+ }
+ else
+ {
+ return FindProjectBaseDirectory(currentProgramDir, programDirInMd5);
+ }
+ }
+
+ return Path.GetDirectoryName(Application.ExecutablePath);
+ }
+ catch
+ {
+ return null;
+ }
+ finally
+ {
+ // 清理临时文件
+ try
+ {
+ if (File.Exists(md5FilePath))
+ {
+ File.Delete(md5FilePath);
+ }
+ }
+ catch { }
+ }
+ }
+
+ ///
+ /// 获取当前程序在项目中的相对路径
+ ///
+ /// 相对路径
+ private string GetRelativePathInProject()
+ {
+ try
+ {
+ // 这里可以根据实际需要调整,默认假设程序在根目录
+ // 如果程序应该在子目录中,可以在这里指定
+ return "";
+ }
+ catch
+ {
+ return "";
+ }
+ }
+
+ ///
+ /// 将程序重定位到根目录并运行
+ ///
+ /// 当前程序路径
+ /// 目标程序路径
+ /// 成功返回true
+ private async Task RelocateProgramToRoot(string currentPath, string targetPath)
+ {
+ try
+ {
+ UpdateStatus("正在复制程序到正确位置...");
+
+ // 确保目标目录存在
+ string targetDir = Path.GetDirectoryName(targetPath);
+ if (!Directory.Exists(targetDir))
+ {
+ Directory.CreateDirectory(targetDir);
+ }
+
+ // 如果目标文件已存在,先尝试删除
+ if (File.Exists(targetPath))
+ {
+ try
+ {
+ // 检查目标文件是否正在运行
+ string targetFileName = Path.GetFileNameWithoutExtension(targetPath);
+ KillProcessByBaseName(targetFileName);
+
+ await Task.Delay(1000); // 等待进程完全退出
+ File.Delete(targetPath);
+ }
+ catch
+ {
+ // 如果无法删除,创建备份名称
+ string backupPath = targetPath + ".old";
+ if (File.Exists(backupPath))
+ {
+ File.Delete(backupPath);
+ }
+ File.Move(targetPath, backupPath);
+ }
+ }
+
+ // 复制当前程序到目标位置
+ File.Copy(currentPath, targetPath, true);
+
+ UpdateStatus("程序复制完成,正在启动新程序...");
+
+ // 启动新程序
+ var startInfo = new ProcessStartInfo
+ {
+ FileName = targetPath,
+ UseShellExecute = true,
+ WorkingDirectory = Path.GetDirectoryName(targetPath)
+ };
+
+ Process.Start(startInfo);
+
+ UpdateStatus("新程序已启动,当前程序即将退出");
+ await Task.Delay(2000);
+
+ // 关闭当前程序
+ this.Close();
+ return true;
+ }
+ catch (Exception ex)
+ {
+ UpdateStatus($"重定位程序失败: {ex.Message}");
+ return false;
+ }
+ }
}
}
\ No newline at end of file