2017-07-14 109 views
3

我已經運行在JBoss上的Hibernate 4.2.21 AS 7.2Hibernate的延遲加載與@LazyToOne(LazyToOneOption.NO_PROXY)

我們目前有幾個@OneToOne關係的應用程序,它由於known limitations of lazy loading,總是支持急切地取上反面。

爲了啓用反向關係的延遲加載,我試圖啓用構建時字節碼檢測。

這是我到目前爲止已經完成了...

1)激活使用maven-antrun-plugin儀表(我試過的休眠,提高-Maven的插件並不能得到它的工作,但多數民衆贊成另一個問題),我現在得到的生成日誌以下Maven輸出:

[INFO] --- maven-antrun-plugin:1.7:run (Instrument domain classes) @ MyApp-entities --- 
[INFO] Executing tasks 

instrument: 
[instrument] starting instrumentation 
[INFO] Executed tasks 

2)接下來,我所有的註釋@OneToOne關係如下...

@OneToOne(cascade = CascadeType.ALL, fetch = FetchType.LAZY, mappedBy = "client", optional=false) 
    @LazyToOne(LazyToOneOption.NO_PROXY) 
    public ClientPrefs getClientPrefs() { 
     return clientPrefs; 
    } 

    public void setClientPrefs(ClientPrefs clientPrefs) { 
     this.clientPrefs = clientPrefs; 
    } 

3) n個I添加implement FieldHandled到@Entity類與私人領域和getter和setter沿:

private FieldHandler fieldHandler; 

成功......現在我正在按照部署日誌輸出:現在

15:54:09,720 INFO [org.hibernate.tuple.entity.EntityMetamodel] (ServerService Thread Pool -- 56) HHH000157: Lazy property fetching available for: uk.co.myapp.entities.Session 
15:54:09,730 INFO [org.hibernate.tuple.entity.EntityMetamodel] (ServerService Thread Pool -- 57) HHH000157: Lazy property fetching available for: uk.co.myapp.entities.Session 
15:54:09,969 INFO [org.hibernate.tuple.entity.EntityMetamodel] (ServerService Thread Pool -- 56) HHH000157: Lazy property fetching available for: uk.co.myapp.entities.Client 
15:54:09,970 INFO [org.hibernate.tuple.entity.EntityMetamodel] (ServerService Thread Pool -- 57) HHH000157: Lazy property fetching available for: uk.co.myapp.entities.Client 
15:54:09,999 INFO [org.hibernate.tuple.entity.EntityMetamodel] (ServerService Thread Pool -- 56) HHH000157: Lazy property fetching available for: uk.co.myapp.entities.Country 
15:54:10,003 INFO [org.hibernate.tuple.entity.EntityMetamodel] (ServerService Thread Pool -- 57) HHH000157: Lazy property fetching available for: uk.co.myapp.entities.Country 
15:54:10,054 INFO [org.hibernate.tuple.entity.EntityMetamodel] (ServerService Thread Pool -- 56) HHH000157: Lazy property fetching available for: uk.co.myapp.entities.Pool 
15:54:10,054 INFO [org.hibernate.tuple.entity.EntityMetamodel] (ServerService Thread Pool -- 57) HHH000157: Lazy property fetching available for: uk.co.myapp.entities.Pool 
15:54:10,569 INFO [org.hibernate.tuple.entity.EntityMetamodel] (ServerService Thread Pool -- 56) HHH000157: Lazy property fetching available for: uk.co.myapp.entities.User 
15:54:10,624 INFO [org.hibernate.tuple.entity.EntityMetamodel] (ServerService Thread Pool -- 57) HHH000157: Lazy property fetching available for: uk.co.myapp.entities.User 

的關係不再急切地加載......但是它們也不會懶惰加載,它們只是靜靜地返回null。

我試圖從實體移除FieldHandled接口和FieldHandler場因爲我不知道這是否是必要的,在這之後我不再獲得在啓動時'HHH000157: Lazy property fetching available for:'消息,並將其返回到默認加載熱切。

我在這裏錯過了什麼嗎?休眠文件並非如何實際設置此

編輯明確:增加了Ant任務配置爲每評論:

<build> 
     <plugins> 
       <plugin> 
        <artifactId>maven-antrun-plugin</artifactId> 
        <version>1.7</version> 
        <executions> 
         <execution> 
          <phase>process-classes</phase> 
          <id>Instrument domain classes</id> 
          <configuration> 
           <target name="instrument"> 
            <taskdef name="instrument" 
             classname="org.hibernate.tool.instrument.javassist.InstrumentTask"> 
             <classpath> 
              <path refid="maven.dependency.classpath" /> 
              <path refid="maven.plugin.classpath" /> 
             </classpath> 
            </taskdef> 
            <instrument verbose="true"> 
             <fileset dir="${project.build.outputDirectory}"> 
              <include name="MyApp-entities/co/uk/myapp/entities/*.class" /> 
             </fileset> 
            </instrument> 
           </target> 
          </configuration> 
          <goals> 
           <goal>run</goal> 
          </goals> 
         </execution> 
        </executions> 
        <dependencies> 
         <dependency> 
          <groupId>org.hibernate</groupId> 
          <artifactId>hibernate-core</artifactId> 
          <version>4.2.21.Final</version> 
         </dependency> 

         <dependency> 
          <groupId>org.javassist</groupId> 
          <artifactId>javassist</artifactId> 
          <version>3.18.1-GA</version> 
         </dependency> 
        </dependencies> 
       </plugin> 
      </plugins> 
    </build> 
+0

如果您想手動執行_instrumentation_,只需要添加FieldHandled接口。在這種情況下,您需要在每次訪問您的懶惰字段之前調用FieldHandler.readObject,以確保其正確初始化。但是如果你啓動儀器,你不能實施'FieldHandled'。看起來你沒有正確配置檢測任務 - 請添加你的配置的片段。順便說一句。如果您正在使用IDE,則可能會立即覆蓋已檢測的類。 –

+0

我只是覺得你先通過命令行來增強它,然後你在IDE中註釋它,然後編譯一組覆蓋增強類的新類。 – Itherael

+0

@TobiasLiefke右鍵確定,這是有道理的,我已經添加了螞蟻儀器任務配置的細節,也許你可以找到丟失的東西 – DaveB

回答

0

像往常一樣,這是一個配置問題,似乎螞蟻運行插件需要指出到包含的實體,而不是父目錄

這爲我工作的一個精確的目錄...

<instrument verbose="true"> 
    <fileset dir="${project.build.directory}/classes/uk/co/myapp/entities"> 
     <include name="*.class" /> 
    </fileset> 
</instrument> 
0

@LazyToOne(LazyToOneOption.NO_PROXY)需要<property name="hibernate.ejb.use_class_enhancer" value="true"/>在persistance.xml

懶,給(該選項強制使用字節碼增強,如果該類不增強則回退到PROXY)除非您無法使用代理服務器,否則應避免使用此選項

NO_PROXY option

+0

此選項用於運行時檢測,我試圖在構建時啓用檢測 – DaveB