c#自动更新升级工具

c#更新工具,wpf开发,所有windows桌面程序均可使用,基于.net 4.0,最低支持windos xp系统

更新工具优点

  • 使用简单
  • 批量更新
  • 跨版本更新
  • 数据备份
  • 手动还原数据
  • 体积小

程序更新使用效果

使用简单

只需添加两个类,以及三个路径的指定,就可以从任何地方下载更新包,并解压到主程序目录中,自动启动

批量更新

不管你从后台拿到了多少个升级包,都能一次性完成升级(以下升级包为本地测试数据)

手动还原数据至上一版本
体积小

依赖少,占用空间少

如何使用

添加类ClientParameter.cs

csharp 复制代码
    public class ClientParameter
    {
        /// <summary>
        /// 1:MainApp 2:UpdateApp
        /// </summary>
        public int AppType { get; set; } = 1;

        /// <summary>
        /// 启动程序名称(可以加上相对路径)
        /// </summary>
        public string AppName { get; set; }

        /// <summary>
        /// 下载的内容放到哪里
        /// </summary>
        public string DownLoadPath { get; set; }

        /// <summary>
        /// 解压的内容放到哪里
        /// </summary>
        public string UnZipPath { get; set; }
        /// <summary>
        /// 备份地址
        /// </summary>
        public string BackUpPath { get; set; }
        /// <summary>
        /// 客户端版本当前
        /// </summary>
        public string ClientVersion { get; set; }
        /// <summary>
        /// 日志访问地址
        /// </summary>
        public string UpdateLogUrl { get; set; }
        /// <summary>
        /// 是否修改目标版本(通过修改version.ini的方式统一控制版本)
        /// </summary>
        public bool IsUpdateVersion { get; set; } = true;
        /// <summary>
        /// 是否是还原版本
        /// </summary>
        public bool IsRestore { get; set; } = false;
        /// <summary>
        /// 多版本更新
        /// </summary>
        public List<UpdateVersion> UpdateVersions { get; set; }
    }
    public class UpdateVersion
    {
        public UpdateVersion(string version, string url, string name, bool isUpdate = true)
        {
            Version = version;
            Url = url;
            Name = name;
            IsUpdate = isUpdate;
        }
        public UpdateVersion(string version, string url, bool isUpdate = true)
        {
            Version = version;
            Url = url;
            IsUpdate = isUpdate;
        }
        /// <summary>
        /// 更新的包名
        /// </summary>
        public string Name { get; set; }

        /// <summary>
        /// 更新的版本
        /// </summary>
        public string Version { get; set; }

        /// <summary>
        /// 包地址
        /// </summary>
        public string Url { get; set; }
        /// <summary>
        /// 是否更新
        /// </summary>
        public bool IsUpdate { get; set; }
    }

添加类UpdateUtil.cs

csharp 复制代码
    public static class UpdateUtil
    {
        #region API函数声明-必须放在类中
        [DllImport("kernel32")]//返回0表示失败,非0为成功
        private static extern long WritePrivateProfileString(string section, string key,
          string val, string filePath);
        [DllImport("kernel32")]//返回取得字符串缓冲区的长度
        private static extern long GetPrivateProfileString(string section, string key,
          string def, StringBuilder retVal, int size, string filePath);
        #endregion

        public static string Serialize(object obj)
        {
            if (obj == null) return string.Empty;
            var json = JsonConvert.SerializeObject(obj);
            var bytes = Encoding.Default.GetBytes(json);
            var base64str = Convert.ToBase64String(bytes);
            return base64str;
        }

        public static T Deserialize<T>(string str)
        {
            var obj = default(T);
            if (string.IsNullOrEmpty(str)) return obj;
            try
            {
                byte[] bytes = Convert.FromBase64String(str);
                var json = Encoding.Default.GetString(bytes);
                var result = JsonConvert.DeserializeObject<T>(json);
                return result;

            }
            catch (Exception)
            {
                return default;
            }

        }
        #region 写Ini文件
        /// <summary>
        /// 将内容写入指定的ini文件中
        /// </summary>
        /// <param name="Section">ini文件中的节名</param>
        /// <param name="Key">ini文件中的键</param>
        /// <param name="Value">要写入该键所对应的值</param>
        /// <param name="iniFilePath">ini文件路径</param>
        /// <returns></returns>
        public static bool Write(string Section, string Key, string Value, string iniFilePath)
        {

            if (!File.Exists(iniFilePath))
            {
                try
                {
                    FileStream stream = File.Open(iniFilePath, FileMode.Create, FileAccess.Write);
                    //stream.Seek(0, SeekOrigin.Begin);
                    //stream.SetLength(0); //清空txt文件
                    stream.Dispose();
                    stream.Close();
                }
                catch (Exception ex)
                {

                    Console.WriteLine(ex);
                }

            }

            if (File.Exists(iniFilePath))
            {
                long OpStation = WritePrivateProfileString(Section, Key, Value, iniFilePath);
                if (OpStation == 0)
                {
                    return false;
                }
                else
                {
                    return true;
                }
            }
            else
            {
                return false;
            }

        }
        #endregion
        /// <summary>
        /// 读取ini文件内容的方法
        /// </summary>
        /// <param name="Section">ini文件的节名</param>
        /// <param name="Key">ini文件对应节下的健名</param>
        /// <param name="NoText">ini文件对应节对应健下无内容时返回的值</param>
        /// <param name="iniFilePath">该ini文件的路径</param>
        /// <returns></returns>
        public static string Read(string Section, string Key, string NoText, string iniFilePath)
        {
            if (File.Exists(iniFilePath))
            {
                StringBuilder temp = new StringBuilder(1024);
                GetPrivateProfileString(Section, Key, NoText, temp, 1024, iniFilePath);
                return temp.ToString();
            }
            else
            {
                return null;
            }
        }
    }

生成的程序项目结构如下

主程序生成至current文件夹下,更新程序生成至update文件夹下

执行更新处添加如下代码

csharp 复制代码
 ClientParameter clientParameter = new ClientParameter {
                AppName = appName,
                BackUpPath = backUpPath,
                DownLoadPath = downLoadPath,//下载包临时存放位置 可默认
                UnZipPath = unZipPath,//解压文件存放位置,可默认
                UpdateLogUrl = "",//更新成功后会自动跳转至该路径 为空则不跳转
                UpdateVersions = new List<UpdateVersion> {
                            new UpdateVersion("1.0.2","http://127.0.0.1:5000/v3.23.12_202312051713.zip"),
                            new UpdateVersion("1.0.3","http://127.0.0.1:5000/Avalonia-11.0.0-preview4.zip"),
                            //new UpdateVersion("1.0.4","http://127.0.0.1:5000/Dragablz-master.zip"),
                            new UpdateVersion("1.0.5","http://127.0.0.1:5000/EChartsSDK-master.zip"),
                            new UpdateVersion("1.0.6","http://127.0.0.1:5000/EChartsNet-master.zip"),
                            //new UpdateVersion("1.0.7","http://127.0.0.1:5000/HandyControl-master.zip"),
                            new UpdateVersion("1.0.8","http://127.0.0.1:5000/Live-Charts-master.zip"),
                        }
            };


            string arg = UpdateUtil.Serialize(clientParameter);

            var path = directInfo.Parent.FullName + @"\download\Cloud.Update.exe";
            if (File.Exists(path))
            {
                Process.Start(path, arg);
                Process.GetCurrentProcess().Kill();
            }

关于测试下载环境的搭建

新建 asp.net core webapi 项目

如同取消勾选

program.cs添加静态文件支持

csharp 复制代码
         app.UseStaticFiles();

重新生成代码

到debug目录下新建wwwroot文件夹

将用来测试的压缩包放到wwwroot文件夹下,注意以.zip的格式结尾

回到程序目录双击启动

在浏览器输入http://localhost:5000/v3.23.12_202312051713.zip,回车测试下载服务是否正常

可以看到成功下载了压缩包,至此下载环境搭建完成

代码地址

相关推荐
云泽8089 分钟前
函数模板与类模板:C++泛型编程核心解析
java·开发语言·c++
应用市场6 小时前
构建自定义命令行工具 - 打造专属指令体
开发语言·windows·python
Dfreedom.6 小时前
一文掌握Python四大核心数据结构:变量、结构体、类与枚举
开发语言·数据结构·python·变量·数据类型
一半烟火以谋生6 小时前
Python + Pytest + Allure 自动化测试报告教程
开发语言·python·pytest
虚行6 小时前
C#上位机工程师技能清单文档
开发语言·c#
小羊在睡觉7 小时前
golang定时器
开发语言·后端·golang
CoderCodingNo7 小时前
【GESP】C++四级真题 luogu-B4068 [GESP202412 四级] Recamán
开发语言·c++·算法
Larry_Yanan8 小时前
QML学习笔记(四十四)QML与C++交互:对QML对象设置objectName
开发语言·c++·笔记·qt·学习·ui·交互
百锦再8 小时前
对前后端分离与前后端不分离(通常指服务端渲染)的架构进行全方位的对比分析
java·开发语言·python·架构·eclipse·php·maven
Want5958 小时前
C/C++大雪纷飞①
c语言·开发语言·c++