外部库加载时间编织为库

External library load time weaving as library

我有一个主罐 class。
我用命令 java -jar my.jar
执行它 这个主 jar 依赖于 another.jar(例如 joda-time.jar)。

现在想拦截another.jar的一个方法,说要打印log
顺便说一句,我想像往常一样使用 my.jar,我的意思是我会像往常一样调用它:java -jar my.jar.

我找到了 a very nice example on github 关于外部库编织的信息。
这个例子,截取了joda时间库的一个方法。
它有一个面向 toString() joda time 方法的方面。
但是,它使用单元测试来拦截和演示。

我已经将给定的示例编译并打包为 my_aspect.jar
之后,我将 my_aspect.jar 移动到执行目录,其中包含 my.jarjoda-time.jar.
最后,我还将 aspectjrt.jaraspectjweaver.jar 添加到同一目录。

当我调用java -jar my.jar时,拦截没有发生。
我想我必须告诉 my_aspect.jar 要拦截的内容,但我不知道该说什么。

下面是 my.jar 的主要 class。
它只是调用拦截方法。

package com.github.example;
import org.joda.time.DateTime;

public class Main {
    public static void main(String[] args) {
        System.out.println(new DateTime().toString());
    }
}

如果使用编译时编织或二进制编织,aspectjrt.jarmy_aspect.jar 都需要在 class 路径上。

对于加载时编织,您需要使用 java -javaagent:/path/to/aspectjweaver.jar -cp my_aspect.jar -jar my.jar。您用作模板的项目也是这样做的,请参阅 here

如果您不想使用 Java 代理并且不想在 Java 命令行上引用任何 AspectJ,那么您唯一的选择是 [=14 的二进制编织=],创建它的新版本,然后创建一个超级 JAR(胖 JAR),使用像 One-JAR 这样的工具(还有一个 Maven 插件)压缩你的整个应用程序,包括依赖项和 AspectJ 运行时。

你的问题不够详细,所以我无法回答得更准确。


更新: 因为您说您更喜欢 OneJar 解决方案,所以可以 search for my related posts。不过,这些帖子 org.dstovall 中的组 ID 已过时。那个版本很久以前就停止维护了,所以我切换到 com.jolira 分支,例如使用它对于支持 AspectJ 的应用程序,当然要结合 AspectJ Maven 插件:

<plugin>
  <groupId>com.jolira</groupId>
  <artifactId>onejar-maven-plugin</artifactId>
  <version>1.4.4</version>
  <executions>
    <execution>
      <goals>
        <goal>one-jar</goal>
      </goals>
    </execution>
  </executions>
  <configuration>
    <onejarVersion>0.96</onejarVersion>
    <mainClass>de.scrum_master.app.FooBar</mainClass>
    <attachToBuild>true</attachToBuild>
  </configuration>
</plugin>