14

Oracle データベースに顧客データを含むテーブルがあります。簡単な定義は次のとおりです。

CUSTOMER (CUSTOMER_ID NUMBER NOT NULL,
          SOURCE_SYSTEM VARCHAR2(30),
          FULL_NAME VARCHAR2(360),
          PHONE_NUMBER VARCHAR2(240)
          )

このテーブルの主キーは です(CUSTOMER_ID, SOURCE_SYSTEM)

SOURCE_SYSTEMテーブルには、 nullである多数の行があります。データベース レベルでは問題はありませんが、JPA エンティティを介してこれらの行にアクセスしようとすると、いくつかの問題が発生します。

1: を使用em.find()して null を含む行をフェッチすると、SOURCE_SYSTEM常に null が返されます。

2:テーブルにレコードが存在しない場合、em.merge()null を含む行の upsert を使用すると成功しますが、マージによって常に挿入が実行されるため、後続の更新では失敗します。SOURCE_SYSTEM

3: を使用em.createQuery()して null を含む行を明示的にクエリすると、次の例外が発生します。

Exception [EclipseLink-6044] (Eclipse Persistence Services - 2.3.1.v20111018-r10243):
   org.eclipse.persistence.exceptions.QueryException
Exception Description: The primary key read from the row [ArrayRecord(
CUSTOMER.CUSTOMER_ID => 1
CUSTOMER.FULL_NAME => GUY PERSON
CUSTOMER.PHONE_NUMBER => 555-555-1234
CUSTOMER.SOURCE_SYSTEM => null)] during the execution of the query was detected to be null.
   Primary keys must not contain null.
Query: ReadAllQuery(referenceClass=Customer sql="SELECT CUSTOMER_ID, FULL_NAME, PHONE_NUMBER, SOURCE_SYSTEM FROM CUSTOMER WHERE ((CUSTOMER_ID = ?) AND (SOURCE_SYSTEM IS NULL))")

残念ながら、「主キーにnullを含めないでください」はかなり最終的なようです。このエラーの回避策に関する情報をあまり見つけることができなかったため、解決策がないように思われます。

質問:データベースに変更を加える必要のないJava コードベースのソリューションを誰かが持っているかどうか知りたいです。私の現在の回避策は、テーブルROW_IDの として使用することですが、これは、または@Idを使用できなくなったことを意味します。em.merge()em.find()

ここに私のJavaクラスがあります:

Customer.java:

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

  @EmbeddedId
  private Customer_Id key;

  @Column(name = "CUSTOMER_ID", nullable = false, insertable = false, updatable = false)
  private Long customerId;
  @Column(name = "SOURCE_SYSTEM", length = 30, insertable = false, updatable = false)
  private String sourceSystem;

  @Column(name = "FULL_NAME", length = 360)
  private String fullName;
  @Column(name = "PHONE_NUMBER", length = 240)
  private String phoneNumber;

  //Setters, Getters, etc
  ...
}

Customer_Id.java

@Embeddable
public class Customer_Id implements Serializable {
  private static final long serialVersionUID = 1L;

  @Column(name = "CUSTOMER_ID", nullable = false)
  private Long customerId;
  @Column(name = "SOURCE_SYSTEM", length = 30)
  private String sourceSystem;

  //Setters, Getters, etc
  ...
}
4

1 に答える 1

1

主キーに null を含めることはできません (JPA またはデータベース内)。"" や " " などの別の値を使用してください。

customer_id は一意ですか? その場合は、Id から sourceSystem を削除してください。

それ以外の場合は、バグを記録して、null ID のサポートを追加してみてください。

于 2013-04-02T13:29:10.660 に答える