zoukankan      html  css  js  c++  java
  • JavaFX桌面应用-版本升级

    好久没有写博客,2021年就以 “JavaFX桌面应用-版本升级” 开篇吧,记录一下JavaFX应用版本升级的开发流程。

    桌面应用升级的方案应该很多,这里只是自己想到的方案。

    1. 效果展示

    首先,先看一下版本升级的最终效果(先不讨论UI美不美观的问题,UI美化可以查看其他博客)

    如上图,程序启动后会自动检测是否有最新版本,如果用则提示用户,由用户决定是否进行应用升级,如果用户点击了升级,则会启动升级程序进行升级,并在升级后重新启动新版的APP。

    2. 升级流程

    在展开说明具体的功能开发前,简单介绍一下应用升级的流程,以及涉及的各个端。

    这里的应用升级主要涉及3个方面:

    • App(主应用)
    • 升级SDK(封装升级流程,App集成即可)
    • 升级程序(负责App升级)

    应用升级的流程其实比较简单,大致分为这几个步骤:

    1. 获取最新版本信息
    2. 询问用户是否升级
    3. 执行版本升级

    升级的流程如下图所示:

    3. 升级细节

    在上面的升级流程看起来没有什么问题,但实际应用起来有一些细节需要注意,比如:

    • 版本怎么计算
    • 升级程序怎么获取更新包
    • 升级程序怎么打开APP

    一般来说,升级程序开发完成后可能很少修改,或者说,希望只开发一个升级程序,供所有app升级使用,这样就不需要为每一个应用都开发一个升级程序。

    上图是升级程序获取更新包的流程,这里SDK和升级程序是通过本地文件update_info作为通讯的媒介,具体的流程为:

    1. APP启动后调用SDK向服务器拉取版本信息,并将拉取版本信息的地址写入到本地文件update_info
    2. 如果发现有新版本,并且用户同意升级,那么启动升级程序
    3. 升级程序启动后,从本地文件update_info读取获取获取版本信息的地址,从服务器获取版本信息及更新包,执行版本更新

    这里为什么需要SDK每一次都把获取版本信息的地址写入到本地文件中呢?就如上面所说的,升级程序可以是通用的,但每一个APP获取版本信息的地址是不同的,另外同一个APP不同版本获取版本信息的地址也可能是不同的(比如服务器在某个时间点更换了域名等等)。

    升级程序和SDK的通讯解决了,整理流程也没有什么大问题,那么版本应该怎么计算呢?

    最简单的处理方式就是,发现版本号不一样时就升级,这种方式不是不可以,但是可能会有很多问题,因为有些时候APP可能更新了一些不兼容旧版的功能,对于兼容的情况可以选择增量更新APP,而对于不兼容的情况就需要全量更新APP了,而且不排除让用户重新安装程序的情况。

    这里介绍一下自己使用的一种方案,版本号规范约定为 x.y.z,客户端APP将x.y.z转化为整数(x*100+y*10+z)与服务器返回的版本进行比较,如果APP的版本小于服务版本则进行升级,服务端可以根据客户端提供的x.y.z提供合适的升级版本信息及更新包。

    版本计算简要代码如下:

    private int versionToInt(String version) {
        String[] items = version.split("\.");
        int versionInt = 0;
        for (String item : items) {
            versionInt *= 10;
            versionInt += Integer.parseInt(item.trim());
        }
        return versionInt;
    }
    

    所以每一个APP都得提供自己的版本号以及获取最新版本的接口地址,这个可以在APP通过定义一些常量来记录:

    public interface Version {
        // 获取版本的接口地址
        String versionUri = "http://localhost:8090/itqn/version";
        // 当前版本号
        String version = "1.0.0";
    }
    

    这样,程序就可以每次启动后获取自己版本号,再从服务器获取版本信息计算是否需要升级,但是这样对有“跳过版本”这种升级流程来说是有问题的,按照上面的流程,当用户点击了“跳过版本”后,下次启动APP时,从服务器获取升级信息计算后仍需要升级,会弹出升级提示,这样很不友好。

    这里稍微调整一下读取版本的流程:

    1. 用户点击跳过版本后,将最新版本号写入到本地文件version
    2. APP正常升级后,升级程序也将最新版本号写入到本地文件version
    3. 程序启动的时候,优先读取本地文件version的版本号进行计算,如果本地没有version文件,才读取APP版本号常量

    对应的版本计算实现代码如下:

    private void checkVersion() {
        int curVersion = 0;
        File f = new File("version");
        char[] buf = new char[30];
        try (FileReader fr = new FileReader(f)) {
            int ret = fr.read(buf);
            curVersion = versionToInt(new String(buf, 0, ret));
        } catch (Exception ignore) {
            // use AppVersion if occur exception
        }
        if (curVersion == 0) {
            curVersion = versionToInt(Version.version);
        }
        UpdateExecutor.execute(Version.versionUri, curVersion);
    }
    

    最后,关于升级程序怎么打开APP这个问题可以参考升级程序和SDK的通讯方案。当然也用更新简单的方案,就是升级程序打开非自己名称的exe应用,这种方式只能用于应用程序只有一个exe文件的情况。

    // 这里ITQN_update是升级程序的名称
    File[] fs = new File(".").listFiles((dir, name) -> name.endsWith(".exe") && !name.equals("ITQN_update.exe"));
        if (fs != null && fs.length > 0) {
        try {
            Desktop.getDesktop().open(fs[0]);
        } catch (IOException e) {
            new Alert(Alert.AlertType.ERROR, e.getMessage()).show();
        }
    }
    

    应用升级这一块涉及的问题比较多,更多的细节可以通过公众号获取源码,具体阅读源码吧,展开说明的话太多了。

    =========================================================
    关注 公众号 “HiIT青年” 源码可以在公众号搜索“JavaFX桌面应用-版本升级”获取。

    HiIT青年
    关注公众号,阅读更多文章。

  • 相关阅读:
    angular2学习
    随笔
    angular 中ng-repeat后ng-click失效
    一个hover效果
    获取屏幕高度
    延时加载 lazyload使用技巧
    关于MVC模板渲染的一点小事type="text/template"
    JsRender实用教程(tag else使用、循环嵌套访问父级数据)
    jQuery Validate 插件为表单提供了强大的验证功能
    日期时间选择器bootstrap-datetimepicker表单组件
  • 原文地址:https://www.cnblogs.com/itqn/p/14458239.html
Copyright © 2011-2022 走看看