【问题标题】:JPA annotation to add and view values from a reference table用于添加和查看引用表中的值的 JPA 注释
【发布时间】:2011-11-28 00:20:59
【问题描述】:

假设我有这门课:

@Entity
@Table(name="PICTURE")
public class Picture{
   private String category1, category2;
}

但是数据库结构是这样的:

TABLE PICTURE {
   int category1;
   int category2;
   ...
}

TABLE PICTURE_REF {
   int category;
   String categoryName;
   ...
}

我将如何在 Picture 上使用 JPA 注释,以便任何时候我请求它的实例,category1category2 包含来自 PICTURE_REF 表的 categoryName,而不是存储在 PICTURE 中的实际整数 id桌子?

我还想知道保存将如何工作,因为用户将从下拉列表中选择一个类别,并且相应的类别整数 ID 将存储在 PICTURE 表中。

【问题讨论】:

  • 我想这也是一个设计问题。

标签: jpa jpa-2.0


【解决方案1】:

根据您的描述,PICTURE.category1PICTURE.category2PICTURE_REF 具有多对一关系

下面展示了它们之间使用注解的双向映射:

对于表格图片:

@Entity
@Table(name="PICTURE")
public Class Picture{

   @Id
   private Integer id;

   @ManyToOne(fetch = FetchType.EAGER)
   @JoinColumn(name = "category1")
   private PictureRef category1, 

   @ManyToOne(fetch = FetchType.EAGER)
   @JoinColumn(name = "category2")
   private PictureRef category2;


   //getter and setters 

}

对于表 PICTURE_REF:

@Entity
@Table(name="PICTURE_REF")
public Class PictureRef{

   @Id
   private Integer id;

   @OneToMany(mappedBy = "category1")
   List <Picture> listOfCat1Picture= new ArrayList<Picture>();  

   @OneToMany(mappedBy = "category2")
   List <Picture> listOfCat2Picture= new ArrayList<Picture>(); 

   //getter and setters 

}

要点:

  • @Entity 将 java 类标记为休眠实体。它映射到@Table中指定的表名

  • 使用@ManyToOne 定义多对一关系

    在关系型数据库中,多对一的关系用如下外键约束来表示: “多边桌”有一个FK列,只接受“单边桌”的PK。

    在您的情况下,这些 FK 列是 PICTURE.category1PICTURE.category2。这些 FK 列的名称可以由 @JoinColumnname 属性显式定义。

  • FetchType.EAGER 使得每当Picture 被加载或获取时,PictureRef 都会被急切地获取

  • 根据您的要求,您可以通过在PictureRef 中省略@OneToMany 来进行unidirectional 映射。它也可以。但是给定PictureRef,您无法访问其图片

  • 给定一个图片实例,你可以通过

    获取它的categoryName和categoryId
    • picture.getCategory1().getCategoryName()
    • picture.getCategory1().getId()
    • picture.getCategory2().getCategoryName()
    • picture.getCategory2().getId()

【讨论】:

    【解决方案2】:

    如果您无法修改架构

    您可以修改您的映射,以便 Category 是一个实体,而不仅仅是一个字符串。然后,对于 category1 和 category2,您将有一个 OneToOne 或(更有可能)一个从图片到类别的 ManyToOne。

    如果您可以修改架构 您可以在 Picture 上使用 ElementCollection 来存储列表,而不是使用 category1 和 category2。这会给你一个类似于

    的模式
    TABLE PICTURE {
       long key;
    }
    
    TABLE PICTURE_CATEGORY {
        long picture_key;
        String category_name;
    }
    

    或者您可以再次将 Category 映射到实体并使用从 Picture 到 Category 的 ManyToMany,这将为您提供类似的架构

    TABLE PICTURE {
       long key;
       ...
    }
    
    TABLE PICTURE_CATEGORY {
        long picture_key;
        long category_key;
    }
    
    TABLE CATEGORY {
        long key;
        String name;
    }
    

    至于保存,您可以在任何视图技术中使用转换器,将键转换为类别,或者您可以从控制器中的键加载类别并在保存之前将其设置在图片中。我怀疑您是否希望保存图片以级联到类别中。

    【讨论】:

    • 嗨,我有一个类似的场景,你上面描述的有三个表。对于这种场景,您将如何映射您的实体?就我而言,CATEGORY 表是一种查找表,我的意思是应用程序不应该插入或更新。我将 ManyToMany 注释与 JoinTable 注释一起使用,它尝试将新记录插入到我不想要的 Caetgory 表中。你能帮忙吗:stackoverflow.com/questions/25771892/…
    猜你喜欢
    • 2019-12-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-03-08
    • 2011-07-06
    • 2010-09-10
    • 1970-01-01
    相关资源
    最近更新 更多