Wednesday 15 February 2017

Spring's Autowired things to be available in constructor of JPA entity


Entities are normally not eligible for Spring-driven configuration, however it is possible to make them eligible by adding `@org.springframework.beans.factory.annotation.Configurable` annotation.

Unfortunately autowired things are not available in constructor, because they are injected after the object is constructed. Luckely `Configurable` has very useful `boolean preConstruction() default false` option to make autowired fields available in constructor. Here's the example:

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.beans.factory.annotation.Configurable;
import org.springframework.context.ApplicationEventPublisher;

import javax.persistence.Entity;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;

@Entity
@Configurable(preConstruction = true)
public class MyEntity {

    @Id
    @GeneratedValue(strategy= GenerationType.AUTO)
    private Long id;

    private String field;

    @Autowired
    private transient ApplicationEventPublisher publisher;

    public MyEntity() {
        System.out.println("do something...");
        // publisher will be null at this point
        // if preConstruction = true is not used
        publisher.publishEvent("Publish something");
        /* ... more code ... */
    }

    /* ... your code here ... */
}