使用 Maven Ant 任务执行码头停止时未授予权限(java.lang.RuntimePermission exitVM)

Permission (java.lang.RuntimePermission exitVM) was not granted while executing jetty stop with Maven Ant Task

我在使用 mvn 任务 运行 jetty:stop 命令时在控制台中收到以下 ant 错误,

[artifact:mvn] org.apache.tools.ant.ExitException: Permission (java.lang.RuntimePermission exitVM) was not granted.
[artifact:mvn]  at org.apache.tools.ant.types.Permissions$MySM.checkExit(Permissions.java:196)
[artifact:mvn]  at java.lang.Runtime.exit(Runtime.java:88)
[artifact:mvn]  at java.lang.System.exit(System.java:904)
[artifact:mvn]  at org.codehaus.classworlds.Launcher.main(Launcher.java:376)
[artifact:mvn]  at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
[artifact:mvn]  at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
[artifact:mvn]  at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
[artifact:mvn]  at java.lang.reflect.Method.invoke(Method.java:597)
[artifact:mvn]  at org.apache.tools.ant.taskdefs.ExecuteJava.run(ExecuteJava.java:217)
[artifact:mvn]  at org.apache.tools.ant.taskdefs.ExecuteJava.execute(ExecuteJava.java:152)
[artifact:mvn]  at org.apache.tools.ant.taskdefs.Java.run(Java.java:764)
[artifact:mvn]  at org.apache.tools.ant.taskdefs.Java.executeJava(Java.java:218)
[artifact:mvn]  at org.apache.tools.ant.taskdefs.Java.executeJava(Java.java:132)
[artifact:mvn]  at org.apache.tools.ant.taskdefs.Java.execute(Java.java:105)
[artifact:mvn]  at org.apache.maven.artifact.ant.Mvn.execute(Mvn.java:81)
[artifact:mvn]  at org.apache.tools.ant.UnknownElement.execute(UnknownElement.java:288)
[artifact:mvn]  at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
[artifact:mvn]  at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39)
[artifact:mvn]  at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25)
[artifact:mvn]  at java.lang.reflect.Method.invoke(Method.java:597)
[artifact:mvn]  at org.apache.tools.ant.dispatch.DispatchUtils.execute(DispatchUtils.java:106)
[artifact:mvn]  at org.apache.tools.ant.Task.perform(Task.java:348)
[artifact:mvn]  at org.apache.tools.ant.Target.execute(Target.java:357)
[artifact:mvn]  at org.apache.tools.ant.Target.performTasks(Target.java:385)
[artifact:mvn]  at org.apache.tools.ant.Project.executeSortedTargets(Project.java:1337)
[artifact:mvn]  at org.apache.tools.ant.Project.executeTarget(Project.java:1306)
[artifact:mvn]  at org.apache.tools.ant.helper.DefaultExecutor.executeTargets(DefaultExecutor.java:41)
[artifact:mvn]  at org.apache.tools.ant.Project.executeTargets(Project.java:1189)
[artifact:mvn]  at org.apache.tools.ant.Main.runBuild(Main.java:758)
[artifact:mvn]  at org.apache.tools.ant.Main.startAnt(Main.java:217)
[artifact:mvn]  at org.apache.tools.ant.launch.Launcher.run(Launcher.java:257)
[artifact:mvn]  at org.apache.tools.ant.launch.Launcher.main(Launcher.java:104)

在搜索这个错误时,我得到了类似的 posts,

https://issues.apache.org/jira/browse/MANTTASKS-201

https://readthefuckingmanual.net/error/1010/

建议设置 fork="true" 可以解决问题,但是当我的 fork 已经设置为 true(甚至 false)

时出现此错误

下面是我调用停止码头服务器的 ant 目标,

<target name="jetty-stop" fork="true">
    <artifact:mvn mavenHome="${maven.home}">
        <jvmarg value="-Xmx1024m" />
        <arg value="jetty:stop"/>
    </artifact:mvn>
</target>

更新:

我在初始化 c3p0 时也注意到错误消息,与此问题中提到的相同,

java.security.AccessControlException when using Ant, but runs ok when invoking java from console

在使用以下 ant-task 启动服务器时,

<target name="jetty-start-jdk8">
    <delete dir="war/WEB-INF/lib"/>
    <artifact:mvn mavenHome="${maven.home}" fork="true">
        <jvmarg value="-agentlib:jdwp=transport=dt_socket,server=y,suspend=n,address=8000" />
        <jvmarg value="-javaagent:${jrebel.path}" />
        <jvmarg value="-Xbootclasspath/p:C:/Users/admin/AppData/Local/Temp//rebelboot.jar" />
        <arg value="compile"/>
        <arg value="war:exploded"/>
        <arg value="jetty:run"/>
    </artifact:mvn>
</target>

上面post也建议设置fork="true"解决。但它已经设置为 true。这可能是什么问题?

解决方案:

在构建路径中使用 JDK 而不是 JRE。

问题是我的项目是在 Eclipse 中使用 JRE 而不是 JDK 配置的,而 build.xml 正在获取我的项目配置,它是一个 JRE。由于某些原因,运行将 ant 任务与 JRE 作为您的系统库。更改为 JDK 1.8 解决了这个问题。更改构建路径后,从 Ant View 中删除 Build.XML 并再次添加到 运行 任务。

System.exit( ) 调用直接与 JVM 对话,导致它立即终止。由于来自 Ant 的 Java 程序 运行ning 在 Ant 的 JVM 中 运行ning,任何对 System.exit( ) 的调用都会杀死 Ant 的 JVM。

由于您尝试调用 kill ant 的 JVM,您可能没有权限。

安全权限可以在 class 执行期间通过嵌套权限元素撤销和授予。有关详细信息,请参阅 https://svn.apache.org/repos/asf/ant/core/trunk/manual/Types/permissions.html

当权限 RuntimePermission exitVM 未被授予(或已被撤销)时,System.exit() 调用将被拦截并按照 failonerror 中的指示进行处理。

您可以在 java 任务中提供

<java classname="org.Whosebug.SpecialTool" fork="true">
    <permissions>
       <grant class="java.security.AllPermission"/>
    </permissions>
</java>

java 任务有一个名为 fork 的属性。

<java classname="org.Whosebug.SpecialTool" fork="true"/>

java 任务的 fork 属性使您能够避免这个问题。该属性告诉 java 任务在单独的 JVM 中 运行 class。在单独的 JVM 中意味着程序的 System.exit( ) 调用无法杀死 Ant 的 JVM。