BlackBerry:在 Ant 脚本中从 JAR 源文件创建 COD

标签 blackberry ant

我如何使用 Ant ( bb-ant-tools ) 到 将 JAR 文件编译成 COD ?即没有其他源文件

原因

最终,我需要一个可以运行的脚本 Jar Jar Links (jarjar)在构建期间,解决在多个应用程序中使用我们的 sdk 的命名空间问题。 Jarjar 将一个 JAR 文件作为输入,我假设它输出一个 JAR 文件。

所以要在 bb-ant-tools 构建中运行 jarjar,我需要知道 如何将该输出 JAR 编译为 COD .

我只关注问题的这一部分,以尽量减少其他可能的错误来源。一旦我能够熟练地将 JAR 构建到 COD 中,我将尝试 jarjar 步骤。

进步

1) 我可以将我的项目构建成一个有效的 COD,签名并在设备上运行。

2) 为了包含 sdk 代码,我目前将源文件夹添加到主项目构建中。 (将来我想知道如何将库作为 JAR 包含在构建中 - BlackBerry - Ant script to include JAR in project without external dependancies)

3) 此步骤的输出包括常用文件:

  • MyApp.cod(如果我签名,它会在设备上完美运行)
  • MyApp.csl
  • MyApp.cso
  • MyApp.debug
  • MyApp.jad
  • MyApp.jar (我想在这个上运行 jarjar)
  • MyApp.rapc

  • 4) 我尝试运行第二个构建,采用上述 JAR 文件并将其用作 rapc 中唯一的源文件。称呼。我通过指向 src 来做到这一点rapc 的标签在仅包含我的 JAR 文件的文件夹中。

    在构建的最后部分,当 rapc 是 adding文件,我收到错误:
     java.util.zip.ZipException: duplicate entry: MyApp-1.cod
    

    (以下已编辑的构建输出中错误的完整详细信息)

    我可以看到这是 rapc 第二次尝试添加此文件 .我不明白为什么,因为 JAR 中只有该文件的一个副本。

    构建输出(使用 ...etc 编辑以使其可读)
    build:
        [mkdir] Skipping C:\development\ant\new_test\MyApp\build because it already exists.
         [copy] Copying 1 file to C:\development\ant\new_test\MyApp\build
         [copy] Copying C:\development\ant\new_test\MyApp\icon.png to C:\development\ant\new_test\MyApp\build\icon.png
         [rapc] Compiling 1 source files to MyApp.cod
         [rapc] Executing 'C:\Java\jdk1.6.0_24\jre\bin\java.exe' with arguments:
         [rapc] '-classpath'
         [rapc] 'C:\Java\jdk1.6.0_24\lib\tools.jar;C:\development\tools\bb-jde\jde5.0\components\bin\rapc.jar'
         [rapc] 'net.rim.tools.compiler.Compiler'
         [rapc] '-verbose'
         [rapc] 'import=C:\development\tools\bb-jde\jde5.0\components\lib\net_rim_api.jar'
         [rapc] 'codename=MyApp'
         [rapc] 'MyApp.rapc'
         [rapc] '@sources.txt'
         [rapc]
         [rapc] The ' characters around the executable and arguments are
         [rapc] not part of the command.
         [rapc] Setting environment variable: PATH=........etc
         [rapc] Reading resource: MyApp.cod
    ...etc
         [rapc] Parsing classfile: com/MyApp/ui/views/WelcomeBar.class
    ...etc
         [rapc] Parsing import: C:\development\tools\bb-jde\jde5.0\components\lib\net_rim_api.jar(net_rim_amms.cod)
    ...etc
         [rapc] Resolving
    ...etc
         [rapc] Optimizing
         [rapc] Utilities.java:449: Warning!: local variable(s) { finished } initialized but not used in: com.cobi.library.Utilities.split(String,String)
    ...etc
         [rapc] Populating
         [rapc] Invoking: jar -cfmv C:\development\ant\new_test\MyApp\build\MyApp.jar C:\Users\Richard\AppData\Local\Temp\rapc_598c0c5a.dir\META-INF\MANIFEST.MF MyApp.cod MyApp-1.cod MyApp-2.cod MyApp.csl MyApp.cso -C C:\Users\Richard\AppData\Local\Temp\rapc_598c2ad7.dir .
         [rapc] added manifest
         [rapc] adding: MyApp.cod(in = 63208) (out= 41042)(deflated 35%)
         [rapc] adding: MyApp-1.cod(in = 75448) (out= 42559)(deflated 43%)
         [rapc] adding: MyApp.csl(in = 91) (out= 69)(deflated 24%)
         [rapc] adding: MyApp.cso(in = 157) (out= 93)(deflated 40%)
    ...etc - adding all files I can see in the JAR...
    
         [rapc] adding: MyApp-1.cod
    
         java.util.zip.ZipException: duplicate entry: MyApp-1.cod
         [rapc]     at java.util.zip.ZipOutputStream.putNextEntry(ZipOutputStream.java:175)
         [rapc]     at java.util.jar.JarOutputStream.putNextEntry(JarOutputStream.java:92)
         [rapc]     at sun.tools.jar.Main.addFile(Main.java:713)
         [rapc]     at sun.tools.jar.Main.create(Main.java:466)
         [rapc]     at sun.tools.jar.Main.run(Main.java:180)
         [rapc]     at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
         [rapc]     at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
         [rapc]     at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
         [rapc]     at java.lang.reflect.Method.invoke(Method.java:597)
         [rapc]     at net.rim.tools.compiler.c.e.if(Unknown Source)
         [rapc]     at net.rim.tools.compiler.c.e.a(Unknown Source)
         [rapc]     at net.rim.tools.compiler.Compiler.a(Unknown Source)
         [rapc]     at net.rim.tools.compiler.Compiler.a(Unknown Source)
         [rapc]     at net.rim.tools.compiler.Compiler.compile(Unknown Source)
         [rapc]     at net.rim.tools.compiler.Compiler.main(Unknown Source)
    
         [rapc] java.io.IOException: jar command failed: jar -cfmv C:\development\ant\new_test\MyApp\build\MyApp.jar C:\Users\Richard\AppData\Local\Temp\rapc_598c0c5a.dir\META-INF\MANIFEST.MF MyApp.cod MyApp-1.cod MyApp-2.cod MyApp.csl MyApp.cso -C C:\Users\Richard\AppData\Local\Temp\rapc_598c2ad7.dir .
         [rapc]     at net.rim.tools.compiler.Compiler.a(Unknown Source)
         [rapc]     at net.rim.tools.compiler.Compiler.a(Unknown Source)
         [rapc]     at net.rim.tools.I/O Error: jar command failed: jar -cfmv C:\development\ant\new_test\MyApp\build\MyApp.jar C:\Users\Richard\AppData\Local\Temp\rapc_598c0c5a.dir\META-INF\MANIFEST.MF MyApp.cod MyApp-1.cod MyApp-2.cocompiler.Compiler.compile(Unknown Source)
         [rapc]     at net.rim.tools.compiler.Compiler.main(Unknown Source)
         [rapc] d MyApp.csl MyApp.cso -C C:\Users\Richard\AppData\Local\Temp\rapc_598c2ad7.dir .
    
    BUILD FAILED
    C:\development\ant\new_test\MyApp\build.xml:65: Java returned: -1
            at org.apache.tools.ant.taskdefs.Java.execute(Java.java:111)
            at ca.slashdev.bb.tasks.RapcTask.executeRapc(RapcTask.java:583)
            at ca.slashdev.bb.tasks.RapcTask.execute(RapcTask.java:401)
            at org.apache.tools.ant.UnknownElement.execute(UnknownElement.java:291)
            at sun.reflect.GeneratedMethodAccessor4.invoke(Unknown Source)
            at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
            at java.lang.reflect.Method.invoke(Method.java:597)
            at org.apache.tools.ant.dispatch.DispatchUtils.execute(DispatchUtils.java:106)
            at org.apache.tools.ant.Task.perform(Task.java:348)
            at org.apache.tools.ant.Target.execute(Target.java:390)
            at org.apache.tools.ant.Target.performTasks(Target.java:411)
            at org.apache.tools.ant.Project.executeSortedTargets(Project.java:1399)
            at org.apache.tools.ant.Project.executeTarget(Project.java:1368)
            at org.apache.tools.ant.helper.DefaultExecutor.executeTargets(DefaultExecutor.java:41)
            at org.apache.tools.ant.Project.executeTargets(Project.java:1251)
            at org.apache.tools.ant.Main.runBuild(Main.java:809)
            at org.apache.tools.ant.Main.startAnt(Main.java:217)
            at org.apache.tools.ant.launch.Launcher.run(Launcher.java:280)
            at org.apache.tools.ant.launch.Launcher.main(Launcher.java:109)
    
    Total time: 9 seconds
    
    C:\development\ant\new_test\MyApp>
    

    解决方法

    Esaj有一个 good answer below运行 Ant replace在进行编译之前对源代码执行任务。这意味着不需要运行 jarjar在任何生成的 JAR 文件上解决命名空间问题。

    这对我有用,因为我有 SDK 源代码。它不适用于我的客户,因为我以 JAR 格式分发我的 SDK。所以我仍然希望得到这个问题的答案。

    有关的

    是重复的 [ How to convert JAR FILE to COD file using Ant Build ] 但这个问题还没有得到解答,我补充了更多细节。

    这是不是 副本:
  • [ Convert a .jar file into a .cod file using bb-ant ] - 我已经使用了接受的答案,我的错误是不同的。
  • [ BlackBerry - Ant script to include JAR in project without external dependancies ] - 这个问题是关于将库作为 JAR 添加,而不是像我上面那样使用源代码。在某种程度上,这是一个先导步骤,因为它的输出仍然需要通过 jarjar 运行。
  • 最佳答案

    BlackBerry - Ant script to include JAR in project without external dependancies 复制此答案根据@RichardLeMesurier 的要求:

    去年我遇到了类似的问题,我创建了一个“框架”,用作多个 BB 应用程序的基础,但遇到了多个 COD 的问题(我不记得到底是什么,比如设备拒绝安装具有相同外部代码的多个应用程序,如果没有首先单独安装外部代码,然后是应用程序)。由于应用程序可以单独安装(一个人可能只安装应用程序 A,另一个人可能只安装应用程序 B,而另一个人可能同时安装 A 和 B),整个框架需要包含在所有使用它的应用程序中。我使用 bb-ant-tools 编写了这个 Ant 脚本(希望我没有破坏任何东西,删除一些特定于我们的应用程序的东西和混淆包名称等):

    <?xml version="1.0" encoding="UTF-8"?>
    
    <project name="${description}" default="build" basedir=".">
    
        <taskdef resource="bb-ant-defs.xml" classpath="lib/bb-ant-tools.jar" />
    
        <!-- rapc and sigtool require the jde.home property to be set -->
        <!-- NOTE: You may need to copy the signature files from Eclipse\plugins\net.rim.ejde\vmTools to the components\bin -dir 
            if the keys were installed using the Eclipse-plugin     -->
        <property name="jdehome" value="C:\BB\Eclipse\plugins\net.rim.ejde.componentpack5.0.0_5.0.0.25\components" />
    
        <!-- Framework source locations, these must be set correctly -->
        <property name="frameworkRes.dir" value="C:\BB\workspace\BB_Framework\res" />
        <property name="frameworkSrc.dir" value="C:\BB\workspace\BB_Framework\src\com\whatever\frame" />
    
        <!-- Locations for simulator, binaries, jde home, don't touch these -->
        <property name="simulator" value="${jdehome}\simulator" />
        <property name="bin" value="${jdehome}\bin" />
        <property name="jde.home" location="${jdehome}" />
    
        <!-- directory of simulator to copy files to -->
        <property name="simulator.home" location="${simulator}" />
    
        <property name="src.dir" location="src" />
        <property name="build.dir" location="build" />
        <property name="temp.dir" location="C:\tempsrc" />
    
        <!-- Project specific -->
        <!-- Application title -->
        <property name="app.title" value="Application Name" />
        <property name="app.version" value="1.0.0" />
        <!-- Value to prepend before frame-class packages -->
        <property name="frame.prefix" value="appname" />
        <!-- Name of the COD to produce --> 
        <property name="cod.name" value="Appname" />
    
        <target name="build">
            <mkdir dir="${build.dir}" />
            <delete dir="${temp.dir}" />
            <mkdir dir="${temp.dir}" />
            <mkdir dir="${temp.dir}\${frame.prefix}" />
    
            <copy toDir="${temp.dir}">
                <fileset dir="${src.dir}">
                    <include name="**/*.java" />
                </fileset>
            </copy>
    
            <copy toDir="${temp.dir}\${frame.prefix}">
                <fileset dir="${frameworkSrc.dir}">
                    <include name="**/*.java" />
                </fileset>
            </copy>
    
            <copy toDir="${temp.dir}\res">
                <fileset dir="${frameworkRes.dir}">
                    <include name="**/*" />
                </fileset>
            </copy>
    
            <copy toDir="${temp.dir}\res">
                <fileset dir="res">
                    <include name="**/*" />
                </fileset>
            </copy>
    
            <!-- This replaces the package names for classes copied from under 
                framework-directory to ${frame.prefix} -directory as well as changing any 
                imports using the classes in framework-package -->  
            <replace dir="${temp.dir}" value="${frame.prefix}">
                <include name="**/*.java"/>
                <replacetoken>com.whatever.frame</replacetoken>
            </replace>
    
            <rapc output="${cod.name}" srcdir="${temp.dir}" destdir="${build.dir}">
                <jdp title="${app.title}" 
                    version="${app.version}" 
                    vendor="Your Company"
                    icon="../res/img/icon.png"
                />
            </rapc>
        </target>
    
        <target name="sign">
            <sigtool codfile="${build.dir}/${cod.name}.cod" />
        </target>
    
        <target name="clean">
            <delete dir="${build.dir}" />
        </target>
    
        <target name="load-simulator" depends="build">
            <copy todir="${simulator.home}">
                <fileset dir="${build.dir}" includes="*.cod,*.cso,*.debug,*.jad,*.jar" />
            </copy>
        </target>
    
    </project>
    

    它的作用是将当前项目中的所有 java 文件和资源,然后从框架项目复制到一个临时目录,替换框架文件途中的包名称(因为它们被单独放入命名目录),这与设备也拒绝安装在相同包下具有相同类的多个应用程序有关(即框架类,对于您的情况,这可能不是必需的)。复制和替换完成后,应用程序将使用 rapc 构建到目标构建目录。签名、清理和将应用程序加载到模拟器有单独的任务。希望这可以帮助。

    关于BlackBerry:在 Ant 脚本中从 JAR 源文件创建 COD,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/10632262/

    相关文章:

    java - 将图像设置为第二个图像

    eclipse - 在 Eclipse 中运行 ant (sql2java) - 没有输出到控制台

    java - 你可以在已经有java的共享主机上安装ant吗?

    android - 如何调试playbook模拟器?

    java - 使用 Ant 中的 JUnit 在单独的 VM 中运行 <batchtest> 的每个测试

    java - Ant 目标运行 Windows BAT,包括更改目录

    java - Ant 最佳实践的好例子

    java - 在黑莓上使用 HttpCore

    user-interface - 黑莓自定义 OVERLAY 横向菜单

    java - 对基类访问的怀疑