我的java天地

          jpa中用table來生成主鍵

          將當前主鍵的值單獨保存到一個數據庫的表中,主鍵的值每次都是從指定的表中查詢來獲得,這種生成主鍵的方式也是很常用的。這種方法生成主鍵的策略可以適用于任何的數據庫,不必擔心不同數據庫不兼容造成的問題。

          使用以下SQL腳本創建一個表“tb_generator”,并插入兩條數據,SQL腳本如下所示。

          CREATE TABLE? tb_generator (

          ? id int(20) unsigned NOT NULL auto_increment,

          ? gen_name varchar(255) NOT NULL,

          ? gen_value int(20) NOT NULL,

          ? PRIMARY KEY? (id)

          )

          ?

          INSERT INTO tb_generator ( gen_name ,gen_value ) VALUES ( 'CUSTOMER_PK',1);

          INSERT INTO tb_generator ( gen_name ,gen_value ) VALUES ( 'CONTACT_PK',100);

          執行SQL語句后,表中的數據如圖5.1所示。


          圖5.1? 自動生成主鍵表tb_generator

          現在有另外兩個表customer和contact,它們每次新建記錄時生成主鍵的值分別“CUSTOMER_PK”所對應的value值加1,“CONTACT_PK”所對應的value值加1。

          下面就來具體看一下如何來配置主鍵的生成策略,以配置“customer”表為例,步驟如下。

          (1)在Entity標記主鍵的位置,指定主鍵生成策略為“GenerationType.TABLE”,具體設置如下。

          @Entity

          @Table(name = "customer")

          public final class CustomerEO implements java.io.Serializable {

          ?

          ???????? private Integer id;

          ?

          ???????? @Id

          ???????? @GeneratedValue(strategy = GenerationType.TABLE)

          ???????? public Integer getId() {

          ?????????????????? return this.id;

          ???????? }

          ?

          ???????? public void setId(Integer id) {

          ?????????????????? this.id = id;

          ???????? }

          }

          (2)指定生成主鍵策略的名稱,例如這里命名為“customer_gen”。

          ???????? @Id

          ???????? @GeneratedValue(strategy = GenerationType.TABLE,generator="customer_gen")

          ???????? public Integer getId() {

          ?????????????????? return this.id;

          ???????? }

          (3)使用@ TableGenerator標記定義表生成策略的具體設置,代碼如下所示。

          ???????? @Id

          ???????? @GeneratedValue(strategy = GenerationType.TABLE,generator="customer_gen")

          ???????? @TableGenerator(name = "customer_gen",

          ??????????????????????????? table="tb_generator",

          ??????????????????????????? pkColumnName="gen_name",

          ??????????????????????????? valueColumnName="gen_value",

          ??????????????????????????? pkColumnValue="CUSTOMER_PK",

          ??????????????????????????? allocationSize=1

          ???????? )

          ???????? public Integer getId() {

          ?????????????????? return this.id;

          ???????? }

          這樣,當通過以下代碼創建新的實體后,表tb_generator中“CUSTOMER_PK”的value的值將自動加1,如圖5.2所示。

          ???????????? CustomerEO customer = new CustomerEO();

          ???????????? customer.setName("Janet");

          ???????????? customer.setShortName("Jane");

          ???????????? entityManager.persist(customer);


          圖5.2? 添加新數據后表tb_generator

          (4)@TableGenerator標記用于設置主鍵使用數據表生成主鍵的策略,它的定義如下所示。

          @Target({TYPE, METHOD, FIELD}) @Retention(RUNTIME)

          public @interface TableGenerator {

          String name();

          String table() default "";

          String catalog() default "";

          String schema() default "";

          String pkColumnName() default "";

          String valueColumnName() default "";

          String pkColumnValue() default "";

          int initialValue() default 0;

          int allocationSize() default 50;

          UniqueConstraint[] uniqueConstraints() default {};

          }

          在使用此@ TableGenerator標記時,需要注意以下幾個問題。

          l???????? 該標記可以在類名、方法名、和屬性名前。并且一旦在實體中標記,它不僅可以在本實體中使用,在其他的實體中也可以引用。它的作用范圍是整個persist unit配置的實體類中。

          例如以上的定義也可以寫成:

          @Entity

          @Table(name = "customer")

          @TableGenerator(name = "customer_gen",

          ?????????????????? table="tb_generator",

          ?????????????????? pkColumnName="gen_name",

          ?????????????????? valueColumnName="gen_value",

          ?????????????????? pkColumnValue="CUSTOMER_PK",

          ?????????????????? allocationSize=1

          )

          public class CustomerEO implements java.io.Serializable {

          ???????? ……

          }

          或者將其標注在ContactEO中,也是可以的。但建議標注在所作用的實體中,這樣有助于方便查看。

          l???????? name屬性表示該表主鍵生成策略的名稱,它被引用在@GeneratedValue中設置的“generator”值中。

          l???????? table屬性表示表生成策略所持久化的表名,例如,這里表使用的是數據庫中的“tb_generator”。

          l???????? catalog屬性和schema具體指定表所在的目錄名或是數據庫名。

          l???????? pkColumnName屬性的值表示在持久化表中,該主鍵生成策略所對應鍵值的名稱。例如在“tb_generator”中將“gen_name”作為主鍵的鍵值

          l???????? valueColumnName屬性的值表示在持久化表中,該主鍵當前所生成的值,它的值將會隨著每次創建累加。例如,在“tb_generator”中將“gen_value”作為主鍵的值

          l???????? pkColumnValue屬性的值表示在持久化表中,該生成策略所對應的主鍵。例如在“tb_generator”表中,將“gen_name”的值為“CUSTOMER_PK”。

          l???????? initialValue表示主鍵初識值,默認為0。

          l???????? allocationSize表示每次主鍵值增加的大小,例如設置成1,則表示每次創建新記錄后自動加1,默認為50。

          l???????? UniqueConstraint與@Table標記中的用法類似,請讀者參閱5.2.1小節。

          用一個簡單示意圖表示持久化主鍵表和表生成策略,如圖所示。

          ?

          二.EJB3.0里的實體bean主鍵產生類型有一種是 GenerationType.TABLE,數據表如下:

          ?

          ?

          ?

          ?

          ?

          ?

          ?

          里面有的一條示例數據:

          gen_key gen_value
          VENDOR_PART_ID 5

          ?

          ?

          部分代碼如下:

          Java代碼 復制代碼
          1. @SuppressWarnings ( "serial" ) ??
          2. @Entity ??
          3. @Table (name= "vendorpart" ) ??
          4. public ? class ?VendorPart? implements ?Serializable?{ ??
          5. ??
          6. ???? private ?Long?vendorpartNumber; ??
          7. ???? private ?String?myDescription; ??
          8. ???? private ? double ?price; ??
          9. ???? ??
          10. ???? private ?Vendor?vendor; ??
          11. ???? private ?Part?part; ??
          12. ??
          13. ???? @TableGenerator ( ??
          14. ????????????name= "vendorPartGen" ,? //?命名表產生器 ??
          15. ????????????table= "sequencegenerator" ,? //?表產生器產生主鍵的表 ??
          16. ????????????pkColumnName= "gen_key" ,? //?主鍵表中主鍵列名 ??
          17. ????????????pkColumnValue= "VENDOR_PART_ID" ,? //?主鍵表中某個主鍵列 ??
          18. ????????????allocationSize= 10 , ??
          19. ????????????valueColumnName= "gen_value" ? //?主鍵表中主鍵值的列名 ??
          20. ????) ??
          21. ???? @Id ??
          22. ???? @Column (name= "vendorpartnumber" ) ??
          23. ???? @GeneratedValue (strategy=GenerationType.TABLE,generator= "vendorPartGen" )???? //?產生器名字 ??
          24. ???? public ?Long?getVendorpartNumber()?{ ??
          25. ???????? return ?vendorpartNumber; ??
          26. ????} ??
          27. ??
          28. ???? public ? void ?setVendorpartNumber(Long?vendorpartNumber)?{ ??
          29. ???????? this .vendorpartNumber?=?vendorpartNumber; ??
          30. ????} ??
          31. ??
          32. //?。。。。 ??
          33. ??
          34. }??


          ?

          posted on 2009-06-25 17:59 tobyxiong 閱讀(1192) 評論(0)  編輯  收藏 所屬分類: java

          <2009年6月>
          31123456
          78910111213
          14151617181920
          21222324252627
          2829301234
          567891011

          導航

          統計

          常用鏈接

          留言簿(3)

          隨筆分類(144)

          隨筆檔案(157)

          相冊

          最新隨筆

          搜索

          積分與排名

          最新評論

          閱讀排行榜

          評論排行榜

          主站蜘蛛池模板: 泾阳县| 冀州市| 许昌县| 涿鹿县| 福安市| 广汉市| 贵定县| 邹城市| 大新县| 阜新市| 泽普县| 奉节县| 奉化市| 林甸县| 鹿泉市| 岳阳县| 桐乡市| 寻甸| 金堂县| 徐水县| 商丘市| 大厂| 鄂托克前旗| 临猗县| 南澳县| 噶尔县| 宣化县| 锡林浩特市| 福建省| 上林县| 陆河县| 武陟县| 秭归县| 临朐县| 凤台县| 额济纳旗| 精河县| 攀枝花市| 洞口县| 兰溪市| 武乡县|