2013-05-11 69 views
0

工作我使用的持久性單元和實體類的數據庫,都在一個JavaFX應用FXML,我成功導入我的表,因爲在我的模型實體的proble是,我得到一個異常和錯誤當我嘗試插入一個實體,這是我的全部代碼實體管理器不使用JavaFX

public class SampleController implements Initializable { 
    @PersistenceContext(unitName="RawdaPU") 
    private EntityManager em; 

    @FXML 
    private Label label; 

    @FXML 
    private void handleButtonAction(ActionEvent event) 
    { 
     Moyendidactique moyenDidactique = new Moyendidactique("1", "moyen1", "Type1"); 
     em.persist(moyenDidactique); 
     em.close(); 
    } 

    @Override 
    public void initialize(URL url, ResourceBundle rb) 
    { 
     // TODO 
    }  
} 

以下是完整的錯誤,當我按下按鈕時(handleButtonAction被解僱),我得到

java.lang.RuntimeException: java.lang.reflect.InvocationTargetException 
    at javafx.fxml.FXMLLoader$ControllerMethodEventHandler.handle(FXMLLoader.java:1440) 
    at com.sun.javafx.event.CompositeEventHandler.dispatchBubblingEvent(CompositeEventHandler.java:69) 
    at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:217) 
    at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:170) 
    at com.sun.javafx.event.CompositeEventDispatcher.dispatchBubblingEvent(CompositeEventDispatcher.java:38) 
    at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:37) 
    at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:92) 
    at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:35) 
    at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:92) 
    at com.sun.javafx.event.EventUtil.fireEventImpl(EventUtil.java:53) 
    at com.sun.javafx.event.EventUtil.fireEvent(EventUtil.java:28) 
    at javafx.event.Event.fireEvent(Event.java:171) 
    at javafx.scene.Node.fireEvent(Node.java:6863) 
    at javafx.scene.control.Button.fire(Button.java:179) 
    at com.sun.javafx.scene.control.behavior.ButtonBehavior.mouseReleased(ButtonBehavior.java:193) 
    at com.sun.javafx.scene.control.skin.SkinBase$4.handle(SkinBase.java:336) 
    at com.sun.javafx.scene.control.skin.SkinBase$4.handle(SkinBase.java:329) 
    at com.sun.javafx.event.CompositeEventHandler.dispatchBubblingEvent(CompositeEventHandler.java:64) 
    at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:217) 
    at com.sun.javafx.event.EventHandlerManager.dispatchBubblingEvent(EventHandlerManager.java:170) 
    at com.sun.javafx.event.CompositeEventDispatcher.dispatchBubblingEvent(CompositeEventDispatcher.java:38) 
    at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:37) 
    at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:92) 
    at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:35) 
    at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:92) 
    at com.sun.javafx.event.BasicEventDispatcher.dispatchEvent(BasicEventDispatcher.java:35) 
    at com.sun.javafx.event.EventDispatchChainImpl.dispatchEvent(EventDispatchChainImpl.java:92) 
    at com.sun.javafx.event.EventUtil.fireEventImpl(EventUtil.java:53) 
    at com.sun.javafx.event.EventUtil.fireEvent(EventUtil.java:33) 
    at javafx.event.Event.fireEvent(Event.java:171) 
    at javafx.scene.Scene$MouseHandler.process(Scene.java:3324) 
    at javafx.scene.Scene$MouseHandler.process(Scene.java:3164) 
    at javafx.scene.Scene$MouseHandler.access$1900(Scene.java:3119) 
    at javafx.scene.Scene.impl_processMouseEvent(Scene.java:1559) 
    at javafx.scene.Scene$ScenePeerListener.mouseEvent(Scene.java:2261) 
    at com.sun.javafx.tk.quantum.GlassViewEventHandler.handleMouseEvent(GlassViewEventHandler.java:228) 
    at com.sun.glass.ui.View.handleMouseEvent(View.java:528) 
    at com.sun.glass.ui.View.notifyMouse(View.java:922) 
    at com.sun.glass.ui.win.WinApplication._runLoop(Native Method) 
    at com.sun.glass.ui.win.WinApplication.access$100(WinApplication.java:29) 
    at com.sun.glass.ui.win.WinApplication$2$1.run(WinApplication.java:67) 
    at java.lang.Thread.run(Thread.java:722) 
Caused by: java.lang.reflect.InvocationTargetException 
    at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
    at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:57) 
    at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43) 
    at java.lang.reflect.Method.invoke(Method.java:601) 
    at javafx.fxml.FXMLLoader$ControllerMethodEventHandler.handle(FXMLLoader.java:1435) 
    ... 41 more 
Caused by: java.lang.NullPointerException 
    at rawda.Controller.SampleController.handleButtonAction(SampleController.java:37) 
    ... 46 more 

我找不到在已經存在的類似問題中的答案,無法確切地知道我是什麼失蹤,提前感謝幫助。

+0

你在這裏有空指針異常:rawda.Controller.SampleController.handleButtonAction(SampleController.java:37)它是你的代碼...看起來像em是空的... – 2013-05-11 11:17:07

+0

關於@PersistenceContext初始化的規則是什麼? – 2013-05-11 11:19:48

+0

事實上它那空,我剛剛檢查出來,但問題是我有很多教程只是使用EntityManager只是我做的,相信我失去了一些東西,有件事更何況,我一直在使用Java進行僅兩個星期我有點新的給它 – AymenDaoudi 2013-05-11 11:22:08

回答

4

爲什麼你在你的代碼

@PersistenceContext註解得到一個NullPointerException「表示在容器管理的EntityManager及其相關的持久化上下文的依賴。」

默認情況下FXML控制器不是容器管理的,這意味着他們不會設置容器管理的成員,如標記爲@PersistenceContext的成員。

您可以通過定義一個controller factory您FXMLLoader使用FXML控制器在容器管理環境(例如作爲InjectionProvider用於注入值插入在Afterburner.fx framework)。

但實際上,你並不需要做注射,如果你是剛剛開始使用Java。在你習慣之前,inversion of control stuff可能會增加太多魔法。

推薦JavaFX的集成方法嘗試使用JPA初學者

相反,不依靠@PersistenceContext註釋。直接從實體經理工廠參考獲取實體經理。還有就是java2s樣品Create Query From Entity Manager在使用容器管理環境之外一個EntityManager的一個很好的例子。

在您的應用程序提供一種機制來獲取實體管理器:

public class SampleApplication extends Application { 
    static private EntityManagerFactory emf; 
    static { 
    try { 
     emf = Persistence.createEntityManagerFactory("RawdaPU"); 
    } catch (Exception e) { 
     System.out.println("Fatal: Unable to create entity manager factory"); 
     e.printStackTrace(); 
    } 
    } 

    static public EntityManager createEntityManager() { 
    return emf.createEntityManager(); 
    } 

    @Override 
    public void start(Stage stage) { 
    . . . 
    } 
} 

在你的控制,從應用程序中獲得的實體管理器並使用它作爲必要的。

class SampleController implements Initializable { 
    @FXML 
    private Label label; 

    @FXML 
    private void handleButtonAction(ActionEvent event) { 
    EntityManager em = SampleApplication.createEntityManager(); 
    Moyendidactique moyenDidactique = new Moyendidactique("1", "moyen1", "Type1"); 
    em.persist(moyenDidactique); 
    em.close(); 
    } 

    @Override 
    public void initialize(URL location, ResourceBundle resources) {} 
} 

在關閉和實體管理器壽命的

因爲你原來的例子中,堅持語句後關閉實體管理器,讓我感動的實體管理器創建成方法同樣的接近方法,使他們匹配。密切意味着實體管理器無法再次使用,所以你不妨在您關閉它在同一個地方創建它 - 這樣,你不能錯誤地重用它在其他地方。請注意,您不需要做親密這樣的,如果你喜歡可以重用實體管理器,但對於入門JPA,只是做它作爲在這個例子中答案很可能很好,你可以看看更復雜的實體管理器重複使用場景,因爲您可以獲得更多的技術經驗和信心。

併發參與討論

您還需要了解在應用程序中使用JPA的併發集成。直接在按鈕的動作處理程序中執行諸如JPA調用之類的操作通常不是一個好主意,因爲這些調用會阻止I/O,從而暫停JavaFX應用程序線程並凍結應用程序UI一段時間。相反,最好是利用JavaFX task and service concurrency utilities的處理方式類似,數據庫工作從JavaFX JDBC task sample UI線程抽象JPA互動。

對於一個小型的本地數據庫來說,併發可能不是那麼重要,所以你可以試試你的應用第一個單線程,如果它能正常工作,那麼很好,但如果它凍結了,那就查看併發實用程序。

下一步

上述方法真的是一個快速入門的事情。

一旦你理解了這個簡單的方法,你可能想看看在afterburner.fxairhacks-control框架或(更重量級)javafx/jpa/spring framework integration中演示的更結構化設計。

+0

我明白你說的是什麼,但你添加到SampleApplication類的靜態代碼仍然會拋出異常: 致命:無法創建實體管理器工廠 本地異常堆棧: 異常[EclipseLink-30005](Eclipse持久性服務 - 2.3.2.v20111125-r10461):... org.eclipse.persistence.exceptions.EntityManagerSetupException 異常說明:PersistenceUnit [RawdaPU]失敗部署前的。 防止emf被指定爲entitymanager之後,提及我正在使用NetBeans,並且我只是按照您的解釋繼續。 – AymenDaoudi 2013-05-11 14:14:33

+0

幾乎嘗試了所有的東西,可能不會得到電動勢被coorectly初始化 – AymenDaoudi 2013-05-11 16:16:02

+0

這是一個不同的問題比最初發布的。創建一個新的問題,其中包括一個[sscce](http://sscce.org/),完整的環境描述(Eclipselink版本等)和完整的堆棧跟蹤。看看你是否可以獨立地獲得我的工作答案中鏈接的java2s示例。 – jewelsea 2013-05-11 19:14:19