在JPA中处理ID表的最佳解决方案是什么?

时间:2015-10-08 10:23:40

标签: java oracle jpa

嗨,对于我的工作,我正在尝试正确处理用于保持其他表之间一致性的表格 Architects决定在Oracle Database 12c上提供此解决方案:

Relational architecture

由于数据量的原因,每个实体上的分区colomn都会对分区进行控制。实体ID由每个实体类型生成。

我尝试使用JPA实体继承来简化数据库中的插入。这段代码是我发现的最佳解决方案:

@Entity
@Table(name="ID_TABLE")
@Inheritance(strategy=InheritanceType.JOINED)
@DiscriminatorColumn(name="Entity_Type", discriminatorType=DiscriminatorType.STRING)
public abstract class IdTable implements Serializable {
    private static final long serialVersionUID = 1L;

    @EmbeddedId
    protected IdTablePK id;
}

@Embeddable
public class IdTablePK implements Serializable {
    @Column(name="Partition_col")
    protected short partitionCol;

    @Column(name="Entity_ID")
    protected long entityID;

    @Column(name="Version_ID")
    protected short versionID;

    @Column(name="Entity_Type")
    protected String entityType;
}

@Entity
@DiscriminatorValue("01")
@Table(name = "ENTITY1")
@PrimaryKeyJoinColumns({
    @PrimaryKeyJoinColumn(name="Partition_col1", referencedColumnName="Partition_col"),
    @PrimaryKeyJoinColumn(name="Entity_ID1", referencedColumnName="Entity_ID"),
    @PrimaryKeyJoinColumn(name="Version_ID1", referencedColumnName="Version_ID"),
    @PrimaryKeyJoinColumn(name="Entity_Type1", referencedColumnName="Entity_Type")
})
public class Entity1 extends IdTable{
...
}

问题是因为JPA自动生成内连接,所以我期望select命令的性能非常差:

select
    entity1.Partition_col1
    entity1.Entity_ID1
    entity1.Version_ID1
    entity1.Entity_Type1
    entity1.Data1
from
    entity1
inner join
    table_ID 
    on entity1.Partition_col=table_ID.Partition_col
        entity1.Entity_ID=table_ID.Entity_ID
        entity1.Version_ID=table_ID.Version_ID
        entity1.Entity_Type=table_ID.Entity_Type
where
    entity1.Partition_col1=?
    and entity1.Entity_ID1=?
    and entity1.Version_ID1=?
    and entity1.Entity_Type1=?

我是否有理由担心这种关系的表现?有没有更好的解决方案或任何方法来避免加入select命令?

**编辑**:克里斯给了我一个主意。如果IdTable实体已将所有相关实体加入此类怎么办?

@Entity
@Table(name="ID_TABLE")
public class IdTable implements Serializable {
    private static final long serialVersionUID = 1L;

    @EmbeddedId
    protected IdTablePK id;

    @OneToOne(fetch=FetchType.LAZY, cascade = CascadeType.PERSIST, optional = true)
    @JoinColumns({
        @JoinColumn(name="Partition_col1", referencedColumnName="Partition_col"),
        @JoinColumn(name="Entity_ID1", referencedColumnName="Entity_ID"),
        @JoinColumn(name="Version_ID1", referencedColumnName="Version_ID"),
        @JoinColumn(name="Entity_Type1", referencedColumnName="Entity_Type")
    })
    private Entity1 e1;
    ...
}

@Embeddable
public class IdTablePK implements Serializable {
    @Column(name="Partition_col")
    protected short partitionCol;

    @Column(name="Entity_ID")
    protected long entityID;

    @Column(name="Version_ID")
    protected short versionID;

    @Column(name="Entity_Type")
    protected String entityType;
}

@Entity
@Table(name = "ENTITY1")
public class Entity1 implements Serializable{
    @EmbeddedId
    protected Entity1PK id;
    ...
}

@Embeddable
public class Entity1PK implements Serializable {
    @Column(name="Partition_col1")
    protected short partitionCol1;

    @Column(name="Entity_ID1")
    protected long entityID1;

    @Column(name="Version_ID1")
    protected short versionID1;

    @Column(name="Entity_Type1")
    protected String entityType1;
}

在Entity1之前插入了IdTable,并且在请求Entity1时没有与IdTable的直接链接。

现在,是否可以使用Entity1序列填充IdTable中的Entity_ID?

1 个答案:

答案 0 :(得分:0)

在第二次尝试中使用Entity1PK(您可以删除注释),请尝试:

@Entity
@Table(name="ID_TABLE")
@IdClass(Entity1PK.class)
public class IdTable implements Serializable {
    private static final long serialVersionUID = 1L;
    @Id
    @OneToOne(fetch=FetchType.LAZY, cascade = CascadeType.PERSIST, optional = true)
    @JoinColumns({
        @JoinColumn(name="Partition_col1", referencedColumnName="Partition_col"),
        @JoinColumn(name="Entity_ID1", referencedColumnName="Entity_ID"),
        @JoinColumn(name="Version_ID1", referencedColumnName="Version_ID"),
        @JoinColumn(name="Entity_Type1", referencedColumnName="Entity_Type")
    })
    private Entity1 e1;
    ..
 }

@Entity
@Table(name = "ENTITY1")
@IdClass(Entity1PK.class)
public class Entity1 {

  @Id
  @Column(name="Partition_col1")
  protected short partitionCol1;

  @Id
  @GeneratedValue(strategy=GenerationType.TABLE)
  @Column(name="Entity_ID1")
  protected long entityID1;

  @Id
  @Column(name="Version_ID1")
  protected short versionID1;

  @Id
  @Column(name="Entity_Type1")
  protected String entityType1;
})

将任何表格的排序注释放在要使用排序的字段上。