gluon-mobile 插件无法处理多版本 jar

gluon-mobile plugin cannot handle multi-release jars

通过 gluon-mobile Eclipse 插件将我的示例 JavaFX 应用程序之一部署到 Android 设备失败,retrolambda 插件中出现 IllegalArgumentException。这是由于我的项目对 jaxb-api-2.3.0.jar 的间接依赖,这是一个多版本 jar。 Retrolambda 显然无法处理此文件中的 Java 9 部分,而不是仅仅忽略它们并抛出异常。如何解决或避免这种情况?

较新版本的 retrolambda(2.5.3 而不是 2.5.1)已经可以处理模块-info.class,但不能处理 META-INF/versions/9/... 这个问题可以通过删除 META-INF 东西来解决,但是当我手动删除它时,它总是由 gluon 插件重新创建。

更新 1:

正在添加

    packagingOptions {
        exclude '/META-INF/versions/9/javax/xml/bind/ModuleUtil.class'
    }            

到构建文件中的 android 部分没有任何区别。报错信息还是一样:

java.lang.IllegalArgumentException
at net.orfjackal.retrolambda.asm.ClassReader.<init>(ClassReader.java:185)
at net.orfjackal.retrolambda.asm.ClassReader.<init>(ClassReader.java:168)
at net.orfjackal.retrolambda.ClassAnalyzer.analyze(ClassAnalyzer.java:25)
at net.orfjackal.retrolambda.Retrolambda.visitClass(Retrolambda.java:71)
at net.orfjackal.retrolambda.files.ClasspathVisitor.visitFile(ClasspathVisitor.java:29)
at net.orfjackal.retrolambda.files.ClasspathVisitor.visitFile(ClasspathVisitor.java:11)
at java.nio.file.Files.walkFileTree(Files.java:2670)
at java.nio.file.Files.walkFileTree(Files.java:2742)
at net.orfjackal.retrolambda.Retrolambda.visitFiles(Retrolambda.java:107)
at net.orfjackal.retrolambda.Retrolambda.run(Retrolambda.java:68)
at net.orfjackal.retrolambda.Main.main(Main.java:28)

这也可以通过 运行 retrlambda 的命令行版本在提取的 jaxb-api-2.3 的 类 上轻松验证。0.jar

更新 2:

使用 Java 9 和 Gluon-VM 失败:

Execution failed for task ':SingleViewProject - Gluon VMApp:apkDebug'.
> Duplicate files at the same path inside the APK: META-INF/LICENSE.txt
  File 1: /Users/mpaus/.m2/repository/org/apache/commons/commons-math3/3.6.1/commons-math3-3.6.1.jar
  File 2: /Users/mpaus/.m2/repository/javax/xml/bind/jaxb-api/2.3.0/jaxb-api-2.3.0.jar

jaxb-api-2.3.0.jar是一个多版本jar,目前jfxmobile插件1.3.10无法处理。

针对 Java 7/8 的插件使用 retrolambda 移植回 Java 6/7 给定的依赖项。

即使您尝试删除 module-info.class or the 9 versionMETA-INF.versions.9.javax.xml.bind`,这些 类 也会由 retrolambda 插件处理,这将导致问题中发布的异常。使用最新的 retrolambda 版本也无济于事。

android {
    retrolambdaVersion = "2.5.3"
    manifest = 'src/android/AndroidManifest.xml'
    packagingOptions {
        exclude '/module-info.class'
        exclude '/META-INF.versions.9.javax.xml.bind/ModuleUtil.class'
    }
}

使其在 Java 8/jfxmobile 1.3.10 下工作的唯一方法是修改插件,将以下异常添加到 JFXMobilePlugin:

copyClassesForRetrolambda.include '**/*.class'
copyClassesForRetrolambda.includeEmptyDirs = false
// exception for multi-release jars    
copyClassesForRetrolambda.exclude 'META-INF/versions/**/*.class'
copyClassesForRetrolambda.exclude 'module-info.class'

然后构建插件并使用本地快照。

好消息是,使用 jfxmobile 插件版本 2.0.20 和 Gluon VM,目标是 Java 9+,上面已经是 included.

如果您可以切换到 Java 9/10,请修改您的项目以使用此插件,使用 Gluon IDE 插件 ('single view project with Gluon VM') 创建一个新项目,或按照这个 sample,但使用的是最新版本(目前为 2.0.20)。

buildscript {
    repositories {
        jcenter()
        google()
        maven {
            url 'http://nexus.gluonhq.com/nexus/content/repositories/releases'
        }
    }
    dependencies {
        classpath 'org.javafxports:jfxmobile-plugin:2.0.20'
    }
}

apply plugin: 'org.javafxports.jfxmobile'

repositories {
    jcenter()
    maven {
        url 'http://nexus.gluonhq.com/nexus/content/repositories/releases'
    }
}

mainClassName = '...'

sourceCompatibility = 1.8
targetCompatibility = 1.8

dependencies {
    compile 'com.gluonhq:charm:5.0.0-jdk9'
    androidRuntime 'com.gluonhq:charm:5.0.0'
    compile 'javax.xml.bind:jaxb-api:2.3.0'
}