自动更新的.NET CF应用程序

3

我需要通过Web服务使我的CF应用程序实现自更新。我在MSDN上找到了一篇2003年的文章,讲得很清楚。但是,我想在这里谈谈实践。是否有人真正做过这个,还是每个人都依赖第三方解决方案?

我被要求以这种方式完成它,因此如果您知道任何提示/注意事项,任何信息都会受到赞赏。

谢谢!

4个回答

2

我之前曾经问过同样的问题:如何自动更新Windows Mobile应用程序

基本上你需要两个应用程序。

App1:启动实际应用程序,但也检查CAB文件(安装程序)。如果CAB文件存在,则执行CAB文件。

App2:实际应用程序。它将调用Web服务,传递版本号到服务,并在存在新版本时检索URL()。下载后,您可以选择安装cab文件并关闭。

一个潜在问题:如果您有一个安装程序放在文件系统上但无法覆盖的文件(数据库文件,日志等),则需要进行两个单独的安装。

要安装cab:请查阅wceload.exe http://msdn.microsoft.com/en-us/library/bb158700.aspx

    private static bool LaunchInstaller(string cabFile)
    {
        // Info on WceLoad.exe
        //http://msdn.microsoft.com/en-us/library/bb158700.aspx
        const string installerExe = "\\windows\\wceload.exe";

        const string processOptions = ""; 
        try
        {
            ProcessStartInfo processInfo = new ProcessStartInfo();
            processInfo.FileName = installerExe;
            processInfo.Arguments = processOptions + " \"" + cabFile + "\"";

            var process = Process.Start(processInfo);
            if (process != null)
            {
                process.WaitForExit();
            }

            return InstallationSuccessCheck(cabFile);
        }
        catch (Exception e)
        {
            MessageBox.Show("Sorry, for some reason this installation failed.\n" + e.Message);
            Console.WriteLine(e);
            throw;
        }
    }

    private static bool InstallationSuccessCheck(string cabFile)
    {
        if (File.Exists(cabFile))
        {
            MessageBox.Show("Something in the install went wrong.  Please contact support.");

            return false;
        }
        return true;
    }

获取版本号:Assembly.GetExecutingAssembly().GetName().Version.ToString()
下载cab文件:
        public void DownloadUpdatedVersion(string updateUrl)
    {
        var request = WebRequest.Create(updateUrl);
        request.Credentials = CredentialCache.DefaultCredentials;
        var response = request.GetResponse();

        try
        {
            var dataStream = response.GetResponseStream();
            string fileName = GetFileName();
            var fileStream = new FileStream(fileName, FileMode.CreateNew);

            ReadWriteStream(dataStream, fileStream);
        }
        finally
        {
            response.Close();
        }
    }

2
这个比较容易实现。基本上,您的应用程序调用一个Web服务来比较其版本与服务器上可用版本。如果服务器版本更新,则应用程序将新的EXE作为byte[]数组下载。
接下来,由于无法删除或覆盖正在运行的EXE文件,您的应用程序将原始EXE文件重命名为类似"MyApplication.old"的名称(幸运的是,操作系统允许此操作)。然后,您的应用程序将下载的byte[]数组保存在与原始EXE文件相同的文件夹中,并使用相同的原始名称(例如"MyApplication.exe")。然后向用户显示消息(例如"检测到新版本,请重新启动")并关闭应用程序。
当用户重新启动应用程序时,他们将启动新版本。新版本将删除旧文件("MyApplication.old"),更新完成。
使应用程序自动更新而不需要用户重新启动是非常麻烦的(您必须启动一个单独的进程来进行更新,这意味着不能自动更新它本身的单独的更新程序)。我从未能够使其100%可靠地工作。我从未收到过客户关于需要重新启动的抱怨。

感谢您的回答,在我的情况下,看起来我将不得不进行自动更新。原因是我们的用户不太精通,可能不会更新应用程序,最终会导致各处存在不同版本 - 这肯定会很麻烦。我宁愿在早期阶段自动处理它。 - sarsnake
在我的情况下,我可以从服务器下载 .cab 文件(cf 安装程序),它是一个安装程序,如果我们点击该文件,它将在移动设备上安装该版本。我尝试了你的答案,但它没有起作用。使用紧凑框架是否可行?请回复。 - Royal
@Royal:是的,使用紧凑框架的方法是可行的 - 实际上,我的版本可以在Windows Mobile和普通Windows上运行。你说你尝试过这样做 - 在StackOverflow上将你的尝试作为问题发布,并指向我,我会尝试看看你的实现存在什么问题。 - MusiGenesis

1
你所说的“自更新”具体是什么意思?如果你指的是配置或数据,那么Web服务应该很好用。但如果你想要实现自动下载和安装新版本的功能,那就是另一回事了。
在Microsoft上找到了this可下载的示例,看起来应该会有所帮助。

我实际上是指两者。http://msdn.microsoft.com/en-us/library/aa446487.aspx 这篇文章同时涉及到两者,但它是一篇旧的文章,我只是想知道是否有人有实际经验。 - sarsnake

0

如果你想使用第三方组件,请看一下 MoDaCo 开发的 AppToDate


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