Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/ant/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Ant 使用Gradle构建Frege项目的Jar_Ant_Gradle_Executable Jar_Frege - Fatal编程技术网

Ant 使用Gradle构建Frege项目的Jar

Ant 使用Gradle构建Frege项目的Jar,ant,gradle,executable-jar,frege,Ant,Gradle,Executable Jar,Frege,我想: 使用Frege编程语言编写一段简单的“Hello World”代码 然后使用Frege编译器生成等效的Java源代码 然后构建一个可执行的Jar文件从命令行运行 所有前面的步骤都应该由Gradle“控制” 我能够生成源代码(上一个列表中的第1项和第2项),但是我不能在输出中指定Java源代码的“包”结构,也就是说,我不能将packageJava语句作为生成Java源代码中的第一行代码。我可以向Frege编译器指定将生成的代码放在何处(通过-d参数) 我认为这就是为什么在构建一个可执行Ja

我想:

  • 使用Frege编程语言编写一段简单的“Hello World”代码
  • 然后使用Frege编译器生成等效的Java源代码
  • 然后构建一个可执行的Jar文件从命令行运行
  • 所有前面的步骤都应该由Gradle“控制”
  • 我能够生成源代码(上一个列表中的第1项和第2项),但是我不能在输出中指定Java源代码的“包”结构,也就是说,我不能将
    package
    Java语句作为生成Java源代码中的第一行代码。我可以向Frege编译器指定将生成的代码放在何处(通过
    -d
    参数)

    我认为这就是为什么在构建一个可执行Jar,然后启动它时,我会看到类似的错误(根据对Gradle任务的不同尝试),例如:
    没有主清单属性

    Frege源代码保存在名为
    hellofree.fr
    的文件中,生成的Java源代码保存在名为
    hellofree.Java
    的文件中(我验证了该文件包含预期的
    main
    方法)

    这里有一个Gradle“Jar任务”的版本:

    这里是Gradle“Jar”任务的另一个版本:


    我怎样才能解决这个问题?我希望避免手动将包引用添加到自动生成的Java源代码文件中。

    如果您在Frege中的模块名是非限定的,例如
    HelloWorld
    ,您将看不到在Java中生成的包语句。模块名将成为类名,包将为空或默认包

    如果模块名是限定的,例如
    foo.bar.HelloWorld
    ,则
    foo.bar
    将是包名,
    HelloWorld
    将是生成的Java源中的类名


    规则是模块名的最后一部分成为类名,限定符构成生成的Java源代码中的包名。

    我不确定gradle在这方面能为您做些什么,但如果没有gradle,至少应该可以做到以下几点:

    ... build your jar, as before ...
    jar -uvfe project-all.jar HelloFrege
    java -jar project-all.jar   # run it
    
    当然,这只是创建清单的另一种方式。如果这是可行的,那么是时候调查为什么格拉德尔拒绝这么做了

    Postscriptum:在再思考一分钟问题可能是什么之后,我突然想到,您可能认为源文件名/路径与java包名有关。在Frege中情况并非如此,尽管让文件路径与包名匹配,让文件基名称与类名匹配是一种很好的做法(就像在Java中一样)。此外,为了消除一些混淆,请在frege中使用模块关键字。正如Marimuthu所解释的,Java包和类名是从frege模块名派生的

    例如:

    $ cat Foo.fr
    module my.org.Baz where
    ...
    $ java -jar fregec.jar -d bin Foo.fr
    

    这将在包
    my.org
    中生成
    Baz
    类,并在
    bin/my/org/Baz.class

    中创建类文件,我现在将我的发现发布到这里。适用于我的Gradle命令组合如下(从命令行键入
    Gradle clean generateJavaSrcFromFregeSrc fatJar调用它):

    • 清单细节需要在
      jar
      代码块中指定,如果我在
      task fatJar
      中指定它们,那么在运行jar时,我会在[…]中获得
      无主清单属性
    • 如果我只使用属性为“$projectDir”){include'lib/**'}
    的代码块
    jar
    来包含Frege jar,那么我会得到类似
    java.lang.ClassNotFoundException
    (我认为这是因为jar是按原样包含的,而不是作为一组
    .class
    文件包含的)
  • 运行Gradle之前,文件夹
    src/main/java/org/wathever
    需要在那里(其他信息:Maven约定前缀
    src/main/java
    ,后缀为
    HelloFrege.fr
    源代码:
    模块org.wathever.HelloFrege where
  • 我发现了一些有用的细节:


    但是请注意,一般情况下不能使用-j标志。例如,当A依赖于B时,编译器在编译A时将需要B的类文件。
    ... build your jar, as before ...
    jar -uvfe project-all.jar HelloFrege
    java -jar project-all.jar   # run it
    
    $ cat Foo.fr
    module my.org.Baz where
    ...
    $ java -jar fregec.jar -d bin Foo.fr
    
    task generateJavaSrcFromFregeSrc {
        ant.java(jar:"lib/frege3.21.586-g026e8d7.jar",fork:true) {
        arg(value: "-j") // do not run the java compiler
        arg(value: "-d")
        arg(value: "src/main/java") // the place where to put the generated source code (paired to the -d argument)
        arg(value: "src/main/frege/HelloFrege.fr")
        }
    }
    
    jar {
        manifest {
           attributes 'Main-Class': 'org.wathever.HelloFrege'
        }
    }
    
    task fatJar(type: Jar) {
        from files(sourceSets.main.output.classesDir)
        from files(sourceSets.main.output.resourcesDir)
        //from {configurations.compile.collect {zipTree(it)}} // this does not include the autogenerated source code
        baseName = project.name + '-fatJar'
        from { configurations.compile.collect { it.isDirectory() ? it : zipTree(it) } }
        with jar
    }