FetchType.LAZY OneToOne无法运行休眠

时间:2018-09-30 11:06:38

标签: spring hibernate transactions lazy-loading lazy-initialization

春季5.1.0,休眠5.3.6。

我有实体:

@Entity
@Table(name = "client")
public class Client extends AbstractEntity {

    @Column(name = "email", unique = true, updatable = false)
    private String email;

    @Column(name = "firstName")
    private String firstName;

    @Column(name = "lastName")
    private String lastName;

    @JsonIgnore
    @Type(type = "text")
    @Column(name = "password")
    private String password;

    @JsonIgnore
    @Column(name = "admin")
    private boolean admin;

    @JoinColumn(name = "premiumId")
    @OneToOne(targetEntity = Premium.class, mappedBy = "client", cascade = {CascadeType.MERGE, CascadeType.PERSIST}, fetch = FetchType.LAZY)
    private Premium premium;

    @JoinColumn(name = "referralId")
    @OneToOne(targetEntity = Referral.class, mappedBy = "client", cascade = {CascadeType.MERGE, CascadeType.PERSIST}, fetch = FetchType.LAZY)
    private Referral referral;

    @JoinColumn(name = "discountId")
    @OneToOne(targetEntity = Discount.class, mappedBy = "client", cascade = {CascadeType.MERGE, CascadeType.PERSIST}, fetch = FetchType.LAZY)
    private Discount discount;

    @PrePersist
    protected void onCreate() {
        super.onCreate();
        this.admin = false;
    }

    public Client() {}

    // getters and setters

    @Override
    public String toString() {
        return "Client{" +
                "email='" + email + '\'' +
                ", firstName='" + firstName + '\'' +
                ", lastName='" + lastName + '\'' +
                ", password='" + password + '\'' +
                ", admin=" + admin +
                '}';
    }

}

有下一个查询:

@Repository
public class ClientDaoImpl extends AbstractDao implements ClientDao {

    private static final Logger LOGGER = LogManager.getLogger(ClientDaoImpl.class);

    public ClientDaoImpl(SessionFactory sessionFactory) {
        super(sessionFactory);
    }

    @Override
    public List<Client> findAll() {
        return sessionFactory.getCurrentSession().createNativeQuery("SELECT * FROM Client c;", Client.class).getResultList();
    }

}

问题在于实体Client中的字段具有延迟初始化。但是,当您执行上面的查询时,将加载所有实体。为什么?

SessionFactory:

@Bean
public LocalSessionFactoryBean getSessionFactory() {

    LocalSessionFactoryBean factoryBean = new LocalSessionFactoryBean();
    factoryBean.setDataSource(getDataSource());

    Properties props = new Properties();

    props.put("hibernate.dialect", env.getProperty("hibernate.dialect", "org.hibernate.dialect.MariaDBDialect"));
    props.put("hibernate.show_sql", env.getProperty("hibernate.show_sql", "true"));
    props.put("hibernate.format_sql", env.getProperty("hibernate.format_sql", "true"));
    props.put("hibernate.hbm2ddl.auto", env.getProperty("hibernate.hbm2ddl.auto", "update"));
    props.put("hibernate.connection.charSet", env.getProperty("hibernate.connection.charSet", "UTF-8"));
    props.put("hibernate.connection.CharSet", env.getProperty("hibernate.connection.CharSet", "UTF-8"));
    props.put("hibernate.connection.characterEncoding", env.getProperty("hibernate.connection.characterEncoding", "UTF-8"));
    props.put("hibernate.connection.useUnicode", env.getProperty("hibernate.connection.useUnicode", "true"));
    props.put("hibernate.enable_lazy_load_on_trans", env.getProperty("hibernate.enable_lazy_load_on_trans", "true"));
    props.put("hibernate.id.new_generator_mappings", env.getProperty("hibernate.id.new_generator_mappings", "false"));

    props.put("hibernate.hbm2ddl.import_files_sql_extractor", env.getProperty("hibernate.hbm2ddl.import_files_sql_extractor", ""));

    factoryBean.setHibernateProperties(props);
    factoryBean.setPackagesToScan("app.site.entity");

    return factoryBean;

}

我在Scheduled任务中运行查询。没有Jackson。我不叫吸气剂。

Scheduled任务:

@Component
@Transactional
public class PremiumScheduler {

    private ClientDao clientDao;

    private PremiumDao premiumDao;

    private static final Logger LOGGER = LogManager.getLogger(PremiumScheduler.class);

    public PremiumScheduler(ClientDao clientDao, PremiumDao premiumDao) {
        this.clientDao = clientDao;
        this.premiumDao = premiumDao;
    }

    @Scheduled(cron = "0 */1 * * * *")
    public void check() {

        LOGGER.info("SCHEDULED");

        Calendar calendar = Calendar.getInstance();

        calendar.add(Calendar.DATE, -1);

        clientDao.findAll().forEach(client -> { // тут

            LOGGER.info(client);



        });

    }

}

0 个答案:

没有答案