Delphi:如何实现应用程序的自动更新?

42

我一直在考虑为我的Delphi应用程序编写自己的代码,以实现平滑更新,因为我将采用“尽早发布,经常发布”的方法。目前市面上有各种免费和付费的Delphi解决方案,想问一下您是否使用过其中任何一个,或者只是采用自己的解决方案?对于自动更新主题的任何评论都欢迎。

10个回答

21
无论使用哪种方案,了解到您实际上可以重命名正在运行的 .exe 文件可能是很有用的。因此,重命名文件,复制新文件可以很好地工作。下一次某人启动程序时,他们将启动新版本。在许多用户运行相同的 .exe 文件的环境中,例如在 citrix/terminal server/network share 情况下,这当然非常方便。

在Win7和Win10上是否仍然有效? :D - Edwin Yip
这篇帖子应该被标记为解决方案。 - Molochnik

12

多年前我写了一个简单的工具,这个工具启动代替真正的程序,检查更新,加载并安装它们(如果有可用的更新),最后启动真正的应用程序。

然而,在一个被正确管理的环境下运行的程序中存在问题,其中用户通常没有对程序目录的写访问权限。在这种环境下,您不能再简单地更新自己的程序。这就是为什么现在很多程序都带有自己的更新程序,可以安装以使用提升的权限运行,以便即使只有标准用户登录到系统,也可以应用程序更新。

您必须决定您的目标受众是否可以假定在运行强大的用户或管理员帐户,或者您是否将不得不处理上述问题。随着Vista的到来,事情已经变得更加困难了。

由于所有这些问题(通过代理进行网络访问,缺少安装目录的写权限,需要更新更新程序本身正在使用的文件等等),我不会再尝试自己编程。最好检查是否有任何可用的解决方案可以满足您的所有需求。


我来到这个话题是因为这个问题。我的程序甚至无法写入当前的exe.bak文件。似乎整个Windows系统权限都发生了变化(w10v1909),之前一切都好好的。:( - Bianca

7
我使用Synapse例程的GetHTTP来返回特定资源,如果找到则检查本地系统是否需要更新。如果需要,则该资源告诉我要启动哪个页面,然后将URL放入shell execute中,以显示用户首选浏览器。
大多数情况下,下载是由InnoSetup创建的设置程序,可将用户系统和数据库更新为最新版本。当需要新的“付费”升级时,我会将用户发送到“购买升级”表单。我的Web资源是ASP页面,因此可以根据客户版本号重定向到不同的资源。
对于主应用程序(我们的应用程序有一个服务器部分和一个客户端部分),我有一个加载器,它将检查服务器以查看服务器上的客户端文件版本是否与客户端上的版本不同...如果是,则提示用户是否要更新/还原。 我们选择提示用户,因为有时会出现意外错误,用户必须降级/升级仅特定机器以帮助排除故障。 我通过数据库记录维护所需的最小版本,该记录通过数据库补丁进行更新,因此如果必须退役某个版本,则相应地更新记录。

6
我使用TmxWebUpdate。它是免费的,简单易用,并且可以很好地控制更新过程。实际上我拥有TMS Component Pack和TWebUpdate,但从未真正找到切换的好理由。

编辑:链接已更新


你可以在这里获取它:http://www.torry.net/authorsmore.php?id=3079 - Mick

6

我基于Indy创建了自己的解决方案用于下载和文件补丁,使用了http://sourceforge.net/projects/makeupdate/。在此之前,我尝试过几种商业工具,但都不能完全符合我的需求。


5
我们自己也开发了类似的工具,其实并不难。我们的流程大致如下:
  • 主应用程序启动时,会使用 synapse 库中的函数检查是否有可用更新(当然前提是已经配置好检查)。

  • 如果有更新,它会通知用户并询问是否要更新。

  • 如果用户同意,它将启动一个更新程序 .exe,并关闭主应用程序。

  • 更新 exe 根据检索到的文本文件中的内容下载新文件,并将文件存储在内存中。

  • 当更新程序正确下载完所有文件后,它会将下载的文件保存到磁盘中,并备份替换的任何文件。这样,如果下载被中断,你就不会只安装一半的文件。

  • 最后,它会再次启动主应用程序,并关闭自身。

Vista 的诀窍在于,你需要在更新程序的清单中加入一个条目,以强制以管理员权限运行。

4
我们使用自己的解决方案来执行以下步骤:
  1. 应用程序连接到http资源并将信息文件(ini文本文件)下载到内存中,检查最新版本号。
  2. 如果有更新版本可用,则应用程序会将压缩的二进制软件包下载到exe位置。
  3. 下载完成后,用户被要求重新启动应用程序。
  4. 启动时,应用程序会检查更新程序包是否存在。
  5. 应用程序提取包内容(通常是一个新的应用程序exe,但也可能是其他资源,如更新的语言文件等)。对于每个文件,它首先将当前/旧文件重命名为临时名称,然后提取新文件。如果在任何时候该过程失败,则还原临时文件。
  6. 完成后,应用程序执行新exe并关闭自身。
不需要额外的更新程序,应用程序exe可以独立处理所有内容。
对于压缩包,我们使用自己的更新构建器。该包含文件索引、文件哈希、目标文件夹(相对路径到主exe)和压缩文件。在更新过程中,我们将存储的哈希与提取的文件进行比较以检测损坏的文件。
在Vista中,我看到两种解决方案可以使标准用户帐户实际上更新应用程序文件:
  1. Configure your setup to change permissions of the programs installation directory. This way files in "C:\Program Files (x86)\Your Company\You App" can be modified on Accounts with limited rights.

    Example code for InnoSetup would be:

    [Dirs]
    Name: "{app}"; Permissions: users-modify
    
  2. Install files that you plan to update to the ProgramData folder instead of the user defined directory and use this directory as an override folder. If files exist in ProgramData, use those, else check in install dir.

    InnoSetup code:

    [Files]
    Source: "C:\Your Project\YourApp.exe"; DestDir: "{commonappdata}\Company Name\App Name\"; 
    

仅供参考,Inno安装程序有一个命令行选项/DIR="<path>",可用于覆盖DestDir - 当我运行下载的Inno安装程序并将<path>替换为实际安装应用程序的文件夹时,我使用此选项。 - Stuart
1
给予用户修改“Program Files”目录(或其子文件夹)中的文件权限是一个非常严重的安全问题!!!如果用户感染了任何病毒,代表用户的病毒可以修改您程序的代码! - iPath ツ
最好的做法是:1)创建一个本地用户,使用复杂的密码,专门用于更新(只有您的更新程序需要知道此密码,即其他人不能使用该用户登录!); 2)给此用户修改程序文件夹内容的权限;3)将更新程序作为服务创建;4)设置该服务以专门用户的身份运行。 - iPath ツ
@iPath 如果我安装一个在我的电脑上创建新用户并保持服务运行的程序,即使你有“良好意图”,我也会非常担心,这会让人感到非常可疑,一些杀毒软件可能会弹出巨大的警告对话框。 - Vitim.us
@Vitim.us 试着安装一下 MS SQL Server,它会为其服务创建一堆用户,出于同样/类似的原因,你有 IIS(IWAM/IUSR)的帐户,UAC 采取了类似的方法(不包括过滤令牌,这是另一个话题),等等。“用户账户”是唯一真正的安全边界。很少使用,难道就让人产生怀疑/不好吗? - iPath ツ

4

通常我们使用第三方工具。但在某些情况下它无法使用,所以我创建了自己的解决方案,这是相当标准的:

  • 获取包含更新信息的xml(或其他格式)。
  • 如果有新文件发布,下载并安装它们。

4
我使用TWebUpdate。它的功能很好,有很多有趣的选项,但文档不是很好,我遇到了一些问题 - 这就是为什么我下载完整的安装程序而不仅仅是文件的原因... 顺便说一下,我会关注这个问题...

我也使用TWebUpdate。 stg一语道破天机 - 它确实可行,但文档可以更好。然而,通过他们的新闻组和支持电子邮件提供的在线支持很好。它便宜到足以让您尝试并查看在添加其他功能时是否足够好。 - GuyWithDogs

1

和“stg”以及“GuyWithDogs”一样,我也在使用TMS的TWebUpdate。虽然文档不是很好,但学习起来并不难。

使用TWebUpdate,你可以选择使用HTTP、FTP或网络访问协议。

TWebUpdate使用WinInet作为通信层。在某些机器上,Windows/IE URL缓存可能会令人沮丧,因此我添加了一个例程,首先清除自动更新服务器地址的缓存,以确保从服务器收集的信息是最新的。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接