JPAアノテーションを使用してインデックスを持っているとしてemail
などのフィールドをどのように定義しますか。 email
には一意でないキーが必要です。なぜなら、このフィールドには文字通り何百万ものクエリがあり、キーなしでは少し遅いからです。
@Entity
@Table(name="person",
uniqueConstraints=@UniqueConstraint(columnNames={"code", "uid"}))
public class Person {
// Unique on code and uid
public String code;
public String uid;
public String username;
public String name;
public String email;
}
ハイバネート固有のアノテーションを見てきましたが、まだハイバネートとデータニュークリアスを決定しているため、ベンダー固有のソリューションを回避しようとしています。
更新:
JPA 2.1以降、これを行うことができます。参照: アノテーション@Indexはこの場所では許可されていません
私の知る限り、JPAプロバイダー間でインデックスを指定する方法はありません。ただし、データベースで直接手作業でいつでも作成できます。ほとんどのデータベースは、クエリの計画時に自動的に取得します。
JPA 2.1を使用すると、これを実行できるはずです。
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.Index;
import javax.persistence.Table;
@Entity
@Table(name = "region",
indexes = {@Index(name = "my_index_name", columnList="iso_code", unique = true),
@Index(name = "my_index_name2", columnList="name", unique = false)})
public class Region{
@Column(name = "iso_code", nullable = false)
private String isoCode;
@Column(name = "name", nullable = false)
private String name;
}
更新:2つ以上の列を作成してインデックスを作成する必要がある場合は、カンマを使用できます。例えば:
@Entity
@Table(name = "company__activity",
indexes = {@Index(name = "i_company_activity", columnList = "activity_id,company_id")})
public class CompanyActivity{
JPA 2.1(最終的に)は、インデックスと外部キーのサポートを追加します!詳細については このブログ をご覧ください。 JPA 2.1はJava EE 7の一部です。
Edgeでの生活が好きな場合は、 mavenリポジトリ (groupId:org.Eclipse.persistence、artifactId:eclipselink、version:2.5.0-SNAPSHOT)からeclipselinkの最新のスナップショットを取得できます。 JPAアノテーション(2.1をサポートするプロバイダーであれば動作するはずです)のみに対して、artifactID:javax.persistence、version:2.1.0-SNAPSHOTを使用します。
リリース後まで終了しないプロジェクトに使用していますが、恐ろしい問題に気づいていません(複雑なことはしていませんが)。
更新(2013年9月26日):中央(メイン)リポジトリでeclipselinkのリリースおよびリリース候補バージョンが利用できるようになったため、Mavenプロジェクトにeclipselinkリポジトリを追加する必要がなくなりました。最新リリースバージョンは2.5.0ですが、2.5.1-RC3も存在します。 2.5.0リリースの問題のため、できるだけ早く2.5.1に切り替えます(modelgenの機能は動作しません)。
[〜#〜] jpa [〜#〜] 2.1+: javax.persistence.Index
(または JSR-000338を参照 PDF、p。452、アイテム11.1.23)
JPA @Index
注釈は、@Table
、@SecondaryTable
などの別の注釈の一部としてのみ使用できます。
@Table(indexes = { @Index(...) })
org.hibernate.annotations.Index
;org.Apache.openjpa.persistence.jdbc.Index
およびorg.Apache.openjpa.persistence.jdbc.ElementIndex
( リファレンスガイド を参照);org.Eclipse.persistence.annotations.Index
;org.datanucleus.api.jpa.annotations.Index
;com.Amazon.carbonado.Index
;org.ujorm.orm.annot.Column
、index
およびuniqueIndex
プロパティ;io.requery.Index
;Exposed ( Kotlin SQLライブラリ): org.jetbrains.exposed.sql.Index 、 org.jetbrains.exposed.sql.Table#index() 。例:
object Persons : IdTable() {
val code = varchar("code", 50).index()
}
com.activeandroid.annotation.Column
は index
、indexGroups
、unique
を持っています、およびuniqueGroups
プロパティ;com.reactiveandroid.annotation.Column
には index
、indexGroups
、unique
、およびuniqueGroups
プロパティ;com.j256.ormlite.field.DatabaseField
にはindex
プロパティがあります。org.greenrobot.greendao.annotation.Index
;org.orman.mapper.annotation.Index
;com.raizlabs.Android.dbflow.sql.index.Index
( example の使用法);io.realm.annotations.Index
;そのうちの1つに行くだけです。
JPA 2.1では、次のことを行う必要があります
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.Id;
import javax.persistence.Index;
import javax.persistence.Table;
@Entity(name="TEST_PERSON")
@Table(
name="TEST_PERSON",
indexes = {
@Index(name = "PERSON_INDX_0", columnList = "age"),
@Index(name = "PERSON_INDX_1", columnList = "fName"),
@Index(name = "PERSON_INDX_1", columnList = "sName") })
public class TestPerson {
@Column(name = "age", nullable = false)
private int age;
@Column(name = "fName", nullable = false)
private String firstName;
@Column(name = "sName", nullable = false)
private String secondName;
@Id
private long id;
public TestPerson() {
}
}
上記の例では、テーブルTEST_PERSONには3つのインデックスがあります。
主キーIDの一意のインデックス
aGEのインデックス
fNAME、SNAMEの複合インデックス
注1:同じ名前の@Indexアノテーションを2つ持つことで複合インデックスを取得します
注2:fieldNameではなくcolumnListで列名を指定します
標準化された方法でデータベースインデックスを指定できるようにしたいのですが、残念ながら、これはJPA仕様の一部ではありません(おそらく、JPA仕様ではDDL生成サポートが必要ないためです。そのような機能)。
そのため、プロバイダー固有の拡張機能に依存する必要があります。 Hibernate、OpenJPA、EclipseLinkは明らかにこのような拡張機能を提供します。 DataNucleusについては確認できませんが、インデックスの定義はJDOの一部なので、そうなると思います。
インデックスのサポートが仕様の次のバージョンで標準化されることを本当に望みます。したがって、何らかの形で他の答えに同意しません。JPAにそのようなものを含めない理由はありません(特にデータベースは常に制御されているわけではないため)最適なDDL生成サポート。
ところで、JPA 2.0仕様をダウンロードすることをお勧めします。
EclipseLinkは、列のインデックスを定義するための注釈(たとえば @ Index )を提供しました。 例 が使用されています。例の一部が含まれています...
FirstNameフィールドとlastNameフィールドには、一緒に個別にインデックスが作成されます。
@Entity
@Index(name="EMP_NAME_INDEX", columnNames={"F_NAME","L_NAME"}) // Columns indexed together
public class Employee{
@Id
private long id;
@Index // F_NAME column indexed
@Column(name="F_NAME")
private String firstName;
@Index // L_NAME column indexed
@Column(name="L_NAME")
private String lastName;
...
}
他の答えを要約するには:
org.hibernate.annotations.Index
org.Apache.openjpa.persistence.jdbc.Index
org.Eclipse.persistence.annotations.Index
私はそれらの1つだけに行きます。とにかくJPA 2.1に付属し、JPAプロバイダーを本当に切り替えたい場合に変更するのはそれほど難しくないはずです。
OpenJPAでは、非標準の注釈を指定して、プロパティのインデックスを定義できます。
詳細は こちら です。
このソリューションはEclipseLink 2.5用であり、動作します(テスト済み)。
@Table(indexes = {@Index(columnList="mycol1"), @Index(columnList="mycol2")})
@Entity
public class myclass implements Serializable{
private String mycol1;
private String mycol2;
}
これは、昇順を前提としています。
JPAアノテーションを使用してそれを行うことはできません。そして、これは理にかなっています:UniqueConstraintがビジネスルールを明確に定義している場合、インデックスは検索を高速化するための単なる方法です。したがって、これは実際にDBAが行う必要があります。