标签: compile-time-weaving

在使用加载时间编织时未编织的超级类中的@Transactional

我正在研究的项目与DAOs下面的项目有类似的结构:

/** 
* Base DAO class
*/
@Transactional    
public class JPABase {

  @PersistenceContext
  private EntityManager entityManager;

  public void persist(Object entity) {
    entityManager.persist(entity);
  }
 //some more methods in here
}
Run Code Online (Sandbox Code Playgroud)

/** 
* Generic DAO class implementation
*/
@Transactional 
public abstract class GenericDao extends JpaBase {
   //some methods in here
}
Run Code Online (Sandbox Code Playgroud)

/** 
* Specialized DAO class
*/
@Repository
@Transactional
public class PersonDao extends GenericDao {
  //some methods in here
}
Run Code Online (Sandbox Code Playgroud)

到现在为止,该项目使用的编译时编织,但而配置也改为使用<context:load-time-weaver/>-javaagent:/opt/tomcat7-1/lib/spring-instrument.jar.

由于已经应用了这种改变,因此不再编织JpaBase's和 …

java spring aspectj compile-time-weaving load-time-weaving

38
推荐指数
1
解决办法
1395
查看次数

为什么AspectJ编译时不编织Spring的@Configurable工作?

更新5:我已经下载了基于最新Eclipse的最新Spring ToolsSuite IDE.当我将项目导入为Maven项目时,Eclipse/STS似乎使用Maven目标来构建我的项目.这意味着AspectJ最终在Eclipse中正常工作.

更新4:我最终只是使用Maven + AspectJ插件进行编译时编织,有效地绕过了Eclipse的机制.

更新3:似乎AspectJ的Eclipse插件破坏了Eclipse正确发布到Tomcat的能力.只有删除项目中的AspectJ功能,才能让它再次正确发布.很烦人.

更新2:我现在在Eclipse中工作了.这让我感到非常不舒服,但我不知道我是如何使用Eclipse或Maven构建的.它似乎是一个编译问题而不是运行时问题.

更新1:看来我已经通过Maven构建工作了,但我不知道如何.Eclipse仍然无法正常工作.我在pom.xml中唯一改变的是添加这些(无关紧要的?)配置参数:

<source>1.6</source>
<complianceLevel>1.6</complianceLevel>
<verbose>true</verbose>
<showWeaveInfo>true</showWeaveInfo>
<outxml>true</outxml>
Run Code Online (Sandbox Code Playgroud)

我实际上担心我会重复这个问题,一切都不一致.随着我了解更多信息,我会更新此问题.

关于Eclipse,我通过采用我想编织的二进制方面取得了一些进展 - 在本例中是spring-aspects.jar - 并将其复制出我的类路径.然后我将这个外部jar添加到我的Aspect Path中.执行此操作后,Eclipse在我的代码中正确显示了AspectJ标记.令人讨厌的是,我不能将spring-aspects.jar留在我的Java Build Path中,这是由Maven通过Maven插件为我维护的.但是,出于某种原因,除非将AspectJ插件显式添加到Aspect Path,否则AspectJ插件不会看到二进制方面.


原始帖子: @Configurable是一个Spring注释,它允许将依赖项注入到Spring外部实例化的对象中(例如,通过Hibernate或某些Factory类).

我以前使用这个注释与加载时编织,它主要工作.偶尔我会启动,没有任何东西会被注入.这个问题催生了这个StackOverflow问题.答案并不多,但大多数人建议我尝试编译时编织,因为可靠性更高.

我为Eclipse和Maven安装了AspectJ插件.这两个产生的似乎是正确编译的类.我在AspectJ编译之前在文本编辑器中打开了其中一个类,但未发现对AspectJ的引用.我在AspectJ编译后打开它,Eclipse和Maven生成的版本都引用了org.aspectj.weaver.MethodDeclarationLineNumber.这就是我认为它被正确编译的原因.问题是,一旦部署,就不会注入依赖项.

My Spring applicationContext.xml确实包含以下内容:

    <context:spring-configured />

    <context:component-scan base-package="com.myapp" />
Run Code Online (Sandbox Code Playgroud)

以上所有标记为@Configurable的类都需要完成DI吗?在从加载时编织到编译时编织的转换过程中,我从applicationContext.xml中删除了META-INF/aop.xml,<context:load-time-weaver />,从我的context.xml中删除了Spring的Tomcat编织器.

我该如何进一步调查此问题?可能的原因是什么?

java aop spring-aop compile-time-weaving maven

25
推荐指数
2
解决办法
3万
查看次数

如何使用Java 1.6 Annotation Processing执行编译时编织?

我创建了一个注释,将其应用于DTO并编写了Java 1.6样式的annotationProcessor.我可以看到如何让annotationProcessor编写一个新的源文件,这不是我想要做的,我看不到或者找不到如何修改现有的类(理想情况下只是修改字节代码).修改实际上是相当简单的,我希望处理器做的就是插入一个新的getter和setter,其名称来自正在处理的注释的值.

我的注释处理器看起来像这样;

@SupportedSourceVersion(SourceVersion.RELEASE_6)
@SupportedAnnotationTypes({ "com.kn.salog.annotation.AggregateField" })
public class SalogDTOAnnotationProcessor extends AbstractProcessor {

    @Override
    public boolean process(final Set<? extends TypeElement> annotations, final RoundEnvironment roundEnv) {
        //do some stuff
    }
}
Run Code Online (Sandbox Code Playgroud)

java annotations compile-time-weaving annotation-processing

7
推荐指数
4
解决办法
8589
查看次数

AspectJ + Gradle + Lombok不起作用

ANT中有一个关于此问题的解决方案,但我们如何通过gradle实现这一目标?是否可以通过编译后编织来实现.意思是用lombok编译来获取所有生成的delombok代码,然后在这个生成的delombok代码上编织方面而不是aspectJ擦除它?

以下这些SO帖子似乎没有任何关于如何解决这个问题的决定?

Lombok无法与AspectJ一起使用? 使用AspectJ + Lombok的Gradle + RoboBinding不兼容

DiscussionThread http://aspectj.2085585.n4.nabble.com/AspectJ-with-Lombok-td4651540.html

谢谢Setzer

aspectj compile-time-weaving gradle lombok

7
推荐指数
1
解决办法
1626
查看次数

在非弹簧管理类中编译DI的时间编织

我想为标记有@Configurable注释的类配置编译时编织,以便能够将spring依赖项注入到使用newoperator 实例化的类中.我不想使用加载时编织,因为我没有访问应用程序服务器的运行脚本,所以我无法修改它.此外,我希望能够在测试中使用此类,我的意思是从IDE运行测试用例.我只发现了有关网络上的加载时间编织和弹簧参考的信息,而没有关于编译时编织配置的信息.

PS.我和maven一起使用spring

spring compile-time-weaving maven

6
推荐指数
1
解决办法
3489
查看次数

困惑ajc如何使用javac

我有点困惑AspectJ编译器如何ajc工作.据我所知,在谈论CTW时,ajc用于将方面编织到编译的字节码中 - 即:.class文件.

但是,当我查看AspectJ(aspectj-maven-plugin)的maven-plugin时,事实证明它是在generate-sourcesmaven阶段运行,在javac编译器之前.这意味着编译器在编织方面之后运行.这是有道理的,因为你可以编织ITD,修改类成员等,java编译器需要知道这些,以便编译任何依赖类.

因此,如果是这种情况,并ajc在javac之前运行,我认为ajc必须首先将所有java代码编译成字节代码才能在任何方面编织.

所以问题是,如果ajc已经经历了将所有java代码编译成字节代码的努力,为什么javac甚至需要运行呢?为什么不是ajc唯一需要的编译器?是不是两个都只是重复努力?另外,如何javac处理ajc已编译的类?是否只是忽略它们,因为自生成.class文件以来源文件没有变化?

java aop aspectj javac compile-time-weaving

6
推荐指数
1
解决办法
2314
查看次数

当没有persistence.xml时,如何使用EclipseLink静态编织JPA实体,因为这些实体由Spring管理

我有一个基于Spring的项目,因此以编程方式设置了实体管理器,不需要persistence.xml文件列出所有实体。

我目前正在使用加载时间编织,但是正在尝试使用Eclipselink和Gradle进行静态编织。我想复制由Maven eclipselink插件执行的操作:

https://github.com/ethlo/eclipselink-maven-plugin

我设置了以下gradle(请注意,这不是Kotlin DSL的常规做法):

task<JavaExec>("performJPAWeaving") {


    val compileJava: JavaCompile = tasks.getByName("compileJava") as JavaCompile
    dependsOn(compileJava)

    val destinationDir = compileJava.destinationDir

    println("Statically weaving classes in $destinationDir")
    inputs.dir(destinationDir)
    outputs.dir(destinationDir)
    main = "org.eclipse.persistence.tools.weaving.jpa.StaticWeave"
    args = listOf("-persistenceinfo", "src/main/resources", destinationDir.getAbsolutePath(), destinationDir.getAbsolutePath())

    classpath = configurations.getByName("compile")


}
Run Code Online (Sandbox Code Playgroud)

当我尝试运行任务时,编织任务失败,因为它正在寻找不存在的persistence.xml。

有什么方法可以在基于Spring的JPA项目中静态编织JPA实体?

Exception Description: An exception was thrown while processing persistence.xml from URL: file:/home/blabla/trunk/my-module/src/main/resources/
Internal Exception: java.net.MalformedURLException
        at org.eclipse.persistence.exceptions.PersistenceUnitLoadingException.exceptionProcessingPersistenceXML(PersistenceUnitLoadingException.java:117)
        at org.eclipse.persistence.internal.jpa.deployment.PersistenceUnitProcessor.processPersistenceXML(PersistenceUnitProcessor.java:579)
        at org.eclipse.persistence.internal.jpa.deployment.PersistenceUnitProcessor.processPersistenceArchive(PersistenceUnitProcessor.java:536)
        ... 6 more
Caused by: java.net.MalformedURLException
        at java.net.URL.<init>(URL.java:627)
        at java.net.URL.<init>(URL.java:490)
        at java.net.URL.<init>(URL.java:439)
        at com.sun.org.apache.xerces.internal.impl.XMLEntityManager.setupCurrentEntity(XMLEntityManager.java:620)
        at com.sun.org.apache.xerces.internal.impl.XMLVersionDetector.determineDocVersion(XMLVersionDetector.java:148)
        at …
Run Code Online (Sandbox Code Playgroud)

spring eclipselink compile-time-weaving spring-data-jpa

6
推荐指数
1
解决办法
245
查看次数

AspectJ - 编译时与加载时编织

我无法理解aspectJ的编译时和加载时编织,并弄清楚要使用什么(以及如何使用ajc)来编译和构建我的项目.

这是我的项目结构: -

  • TestProject:一个ja​​va服务库.其他一些项目正在使用它.该项目不包含任何方面.

  • TestProject-Aspects:包含
    在TestProject中为几个类提供建议的方面.我没有使用
    AspectJ5注释样式,我所有的连接点都只是
    当前的方法执行.

我的问题:

  • ajc vs iajc和他们有什么不同?
  • 是否需要编织?

  • 这样的事情会起作用吗?

编译TestProject-Aspects

<iajc>
    sourceroots=${sources.dir}
    destdir=${classes.dir}
    classpath=${standard.compile.classpath}
</iajc>
Run Code Online (Sandbox Code Playgroud)

编译TestProject

<iajc>
    sourceroots=${sources.dir}
    destdir=${classes.dir}
    classpath=${standard.compile.classpath}
    inpath=${[TestProject-Aspects]pkg.classpath}
</iajc>
Run Code Online (Sandbox Code Playgroud)
  • 我根本不必使用javac吗?我最初用来编译TestProject?

aspectj compile-time-weaving load-time-weaving

5
推荐指数
1
解决办法
1万
查看次数

如何配置aspectj以进行编译后的编织(使用maven)?

如何配置AspectJ以获得编译后的编织?我只是在下面的插件中将“ compile”替换为“ post-compile” :(不必说这是不成功的)

<plugin>
    <groupId>org.codehaus.mojo</groupId>
    <artifactId>aspectj-maven-plugin</artifactId>
    <version>1.5</version>
    <configuration>
        <complianceLevel>1.6</complianceLevel>
        <source>1.6</source>
        <target>1.6</target>
    </configuration>
    <executions>
        <execution>
            <goals>
                <goal>post-compile</goal>
                <goal>test-compile</goal>
            </goals>
        </execution>
    </executions>
</plugin>
Run Code Online (Sandbox Code Playgroud)

但我错过了一些东西,因为它给出了以下错误:

'post-compile' was specified in an execution, but not found in the plugin
Run Code Online (Sandbox Code Playgroud)

configuration aspectj compile-time-weaving pom.xml maven

5
推荐指数
1
解决办法
2509
查看次数

eclipselink静态编织与Java 9上的最终字段

我有一些JPA注释字段,如下所示:

@Column(name = "SOME_FIELD", updatable = false, nullable = false)
private final String someField;
Run Code Online (Sandbox Code Playgroud)

当实体插入数据库时​​,这些字段存储在数据库中.它们无法进一步更新.对于Java编程语言,可以将这些字段视为final.

使用EclipseLink静态编织插件,由于某些字节代码检测,可能会延迟加载实体.

我不知道JPA中是否正式允许这样的构造(最终字段),但我喜欢使用它们,因为它们在编译时强制执行这些字段并不是要更新.

在Java 8中,使用这种结构构建的程序运行良好.但是在Java 9中,当涉及EclipseLink静态编织时,我得到以下运行时异常:

Caused by: java.lang.IllegalAccessError: Update to non-static final field xxx.yyy.SomeEntity.someField attempted from a different method (_persistence_set) than the initializer method <init> 
Run Code Online (Sandbox Code Playgroud)

这样的错误似乎是由于以下JVM规范:

否则,如果该字段是final,则必须在当前类中声明,并且该指令必须在当前类的实例初始化方法()中发生.否则,抛出IllegalAccessError.

因此,我觉得一些编织工具需要一些更新才能实现这个JVM规范.EclipseLink静态编织工具似乎就是其中之一.

问题:

  • JPA中是否允许使用此处提供的最终字段构造?
  • 是否有JDK 9选项来禁止检查最终字段分配,而不仅仅是在类的实例初始化方法()中(作为临时解决方法)?

编辑:

根据JPA规范,JPA中不允许使用最终字段:

实体类不能是最终的.实体类的方法或持久性实例变量可能不是最终的.

jpa eclipselink compile-time-weaving java-9

5
推荐指数
2
解决办法
637
查看次数