AI エージェント向け: ドキュメントインデックスは https://www.mongodb.com/ja-jp/docs/llms.txt で利用できます。すべてのページの markdown バージョンは、いずれかの URL パスに .md を追加することで利用できます。
Docs Menu

ネイティブデータベースクエリの実行

このガイドでは、 Hibernetes ORM 用のMongoDB拡張機能 を使用してMongoDBデータベースでネイティブ クエリを実行する方法を学習します。非表示クエリ言語 (HQL) または Java 永続クエリ言語 (JavaQL) の代わりに、ネイティブ クエリではMongoDBクエリ言語 (MQL) を使用してクエリを指定できます。 MQL は、 MongoDBドキュメントベースのモデルを操作するために設計されたクエリ構文です。

Tip

MongoDB クエリ言語

MQL の構文と機能の詳細については、 MongoDB Serverマニュアルの「 MongoDBクエリ言語リファレンス 」を参照してください。

Hibernate ORM の createQuery() メソッドは、一部のMongoDBクエリ機能をサポートしていません。createNativeQuery() メソッドを使用すると、MQLでデータベースクエリを指定し、Hibernate ORM 拡張機能の一部の運用上の制限をバイパスできます。

また、クエリ機能を拡張するために、MongoClientオブジェクトに対してクエリを直接実行することもできます。

このガイドの例では、AtlasサンプルデータセットのMovie sample_mflix.moviesコレクションを表す エンティティを使用します。Movie エンティティには、次の定義があります。

import com.mongodb.hibernate.annotations.ObjectIdGenerator;
import org.bson.types.ObjectId;
import java.util.List;
import jakarta.persistence.Entity;
import jakarta.persistence.Id;
import jakarta.persistence.Table;
@Entity
@Table(name = "movies")
public class Movie {
@Id
@ObjectIdGenerator
private ObjectId id;
private String title;
private String plot;
private int year;
private int runtime;
private List<String> cast;
private List<String> directors;
public Movie(String title, String plot, int year, int runtime, List<String> cast, List<String> directors) {
this.title = title;
this.plot = plot;
this.year = year;
this.runtime = runtime;
this.cast = cast;
this.directors = directors;
}
public Movie() {
}
public ObjectId getId() {
return id;
}
public String getTitle() {
return title;
}
public void setTitle(String title) {
this.title = title;
}
public String getPlot() {
return plot;
}
public void setPlot(String plot) {
this.plot = plot;
}
public int getYear() {
return year;
}
public void setYear(int year) {
this.year = year;
}
public int getRuntime() {
return runtime;
}
public void setRuntime(int runtime) {
this.runtime = runtime;
}
public List<String> getCast() {
return cast;
}
public void setCast(List<String> cast) {
this.cast = cast;
}
public List<String> getDirectors() {
return directors;
}
public void setDirectors(List<String> directors) {
this.directors = directors;
}
}

Hibernetes ORM 用のMongoDB拡張機能を使用してこのMongoDBサンプルコレクションと交流するJavaアプリケーションを作成する方法については、Get Started チュートリアルを参照してください。

注意

永続性コンテキスト

Hibernate ORM を有効にしてデータベースと交流するには、Hibernate Session または Jakarta 永続性 EntityManager を使用して永続性コンテキスト内で操作を実行する必要があります。このガイドの例では、Session を使用しています。永続性コンテキストの詳細については、トランザクションとセッションのガイドを参照してください。

ネイティブのMongoDBクエリを実行するには、クエリするコレクションとクエリ条件を集計パイプラインで含むMongoDBクエリ言語(MQL)ステートメントを指定します。

Tip

Aggregation Pipeline

集計パイプラインの構築と集計操作の実行中の詳細については、 MongoDB Serverマニュアルの集計パイプライン参照を参照してください。

MQLステートメントは次の形式です。

String mqlSyntax = """
{
aggregate: "<collection to query>",
pipeline: [
<aggregation pipeline stages>
]
}
""";

重要

$ プロジェクトステージの要件

MQLステートメントの集計パイプラインには ステージが含まれている必要があります。クエリ$project ドキュメントをエンティティ$project インスタンスとして返すには、 フィールドを含む、_id ステージの各エンティティフィールドを指定する必要があります。 Hibernetes ORM 拡張機能はプロジェクトフィールドを返し、省略すると を非表示にします。 を省略するエンティティバウンド クエリは、エンティティ識別子が にマップされているため、 では失敗する可能性があります。識別子を使用したままにするには、プロジェクト_id _idUnknown column label [_id]_id_id: 1をプロジェクトします。

次に、 MQLステートメントを createNativeQuery() メソッドに渡します。

ネイティブクエリを使用して、次の操作を実行できます。

重要

拡張JSONシンタックスが必要

ネイティブ クエリは 拡張JSON v 形式で記述する必要があります。 Hibernetes ORM 拡張機能は、ネイティブ クエリで一重引用符またはMongoDB Server シェル正規式構文(2/pattern/ )をサポートしていません。例、正規式を使用してクエリを実行するには、 ではなく$regularExpression 拡張JSONタイプを使用します。/pattern/

この例ではMQLステートメントを createNativeQuery() メソッドに渡して、sample_mflix.moviesコレクションに対してネイティブクエリを実行します。このコードでは、次の集計パイプライン ステージを指定します。

  • $match: タイトルフィールドの値が のドキュメントをフィルター "The Parent Trap"

  • $sort: 一致するドキュメントを year フィールドで降順に並べ替えます

  • $project: Movie エンティティで定義されている各ドキュメントフィールドを返します

String nativeQuery = """
{
aggregate: "movies",
pipeline: [
{ $match: { title: { $eq: "The Parent Trap" } } },
{ $sort: { year: -1 } },
{ $project: { _id: 1, title: 1, plot: 1, year: 1, runtime: 1, cast: 1 } }
]
}
""";
var results = session.createNativeQuery(nativeQuery, Movie.class)
.getResultList();
for (Movie movie : results) {
System.out.println("Title: " + movie.getTitle() + ", Year: " + movie.getYear());
}

注意

ネイティブ クエリは、 Hibernetes ORM 拡張機能 でサポートされていない算術操作に最適です。 Hibernetes ORM 拡張機能がサポートする算術演算子の詳細については、 機能の互換性 ページの「クエリ サポート」セクションを参照してください。

次の例では、 sample_mflix.moviesコレクションに対して次のアクションを実行するネイティブ クエリを実行します。

  • year の値が 2000 より大きく、かつ runtimeフィールドが存在するドキュメントを検索するために、$match ステージを指定します

  • runtimeHours という新しいフィールドを追加するには $addFields ステージを指定します

  • $divide算術演算子を使用して、新しいruntimeHoursフィールドのruntime値を 分から時間に変換します

  • Movie エンティティで定義されている各ドキュメントフィールド(_idフィールドを含む)を返すには、$project ステージを指定します

  • 更新された各ドキュメントの title 値を出力します

String nativeQuery = """
{
aggregate: "movies",
pipeline: [
{ $match: { year: { $gt: 2000 }, runtime: { $exists: true } } },
{ $addFields: {
runtimeHours: { $divide: [ "$runtime", 60 ] }
}},
{ $project: {
_id: 1,
title: 1,
plot: 1,
year: 1,
runtime: 1,
cast: 1,
runtimeHours: 1
}}
]
}
""";
var results = session.createNativeQuery(nativeQuery, Movie.class)
.getResultList();
for (Movie result : results) {
System.out.println("Added field to movie: " + result.getTitle());
}

Tip

算術演算子

Hibernate と MongoDB 演算子の詳細については、次のリソースを参照してください。

ネイティブ クエリを実行すると、データベースに対してMongoDB 検索クエリを実行することができます。これは、データに対するきめ細かなテキスト検索です。これらのクエリは、テキスト フレーズの一致、関連性の結果のスコアリング、一致の強調表示など、高度な検索機能を提供します。

重要

トランザクション内ではMongoDB 検索クエリを実行できません。

検索クエリを指定するには、クエリを実行するフィールドをカバーする検索インデックスを作成します。次に、$search または $searchMeta ステージを含む集計パイプラインをcreateNativeQuery() メソッドに渡します。

Tip

MongoDB Search

MongoDB Search クエリとインデックスの詳細については、 MongoDB Serverマニュアルの「 MongoDB Search の概要 」を参照してください。

この例では、$searchパイプラインステージをcreateNativeQuery()メソッドに渡して検索クエリを実行します。このコードは、次のアクションを実行します。

  • plotフィールドをカバーする検索インデックスを指定します。<indexName> プレースホルダーを 検索インデックス名に置き換えてください。

  • plot 値に対し、3 単語以下の文字列 "whirlwind romance" が含まれるドキュメントのクエリ

  • Movie エンティティで定義されている各ドキュメントフィールド(_idフィールドを含む)を返すには、$project ステージを指定します

  • 一致するドキュメントの title と plot の値を出力します

String nativeQuery = """
{
aggregate: "movies",
pipeline: [
{
$search: {
index: "<indexName>",
phrase: {
path: "plot",
query: "whirlwind romance",
slop: 3
}
}
},
{
$project: {
_id: 1,
title: 1,
plot: 1,
year: 1,
runtime: 1,
cast: 1
}
}
]
}
""";
var results = session.createNativeQuery(nativeQuery, Movie.class)
.getResultList();
for (Movie result : results) {
System.out.println("Title: " + result.getTitle() + ", Plot: " + result.getPlot());
}

MQLステートメントで値を指定するには、名前付きパラメーター(:name)または順序付きパラメーター(?1)を使用できます。次の例では、 title パラメータの値を名前付きパラメータまたは順序付けパラメータとして指定し、次に setParameter() でパラメータ値を指定する方法を示しています。

String nativeQuery = """
{
aggregate: "movies",
pipeline: [
{ $match: { title: { $eq: :movieTitle } } },
{ $sort: { year: -1 } },
{ $project: { _id: 1, title: 1, plot: 1, year: 1, runtime: 1, cast: 1 } }
]
}
""";
var results = session.createNativeQuery(nativeQuery, Movie.class)
.setParameter("movieTitle", "The Parent Trap")
.getResultList();
for (Movie movie : results) {
System.out.println("Title: " + movie.getTitle() + ", Year: " + movie.getYear());
}
String nativeQuery = """
{
aggregate: "movies",
pipeline: [
{ $match: { title: { $eq: ?1 } } },
{ $sort: { year: -1 } },
{ $project: { _id: 1, title: 1, plot: 1, year: 1, runtime: 1, cast: 1 } }
]
}
""";
var results = session.createNativeQuery(nativeQuery, Movie.class)
.setParameter(1, "The Parent Trap")
.getResultList();
for (Movie movie : results) {
System.out.println("Title: " + movie.getTitle() + ", Year: " + movie.getYear());
}

createQuery() メソッドも createNativeQuery() メソッドもサポートしていないデータベース操作を実行する場合は、Javaアプリケーションで直接 MongoClient オブジェクトを操作できます。MongoClient を使用すると、 MongoDB Java Sync Driver の 機能にアクセスできます。

Tip

機能サポート

アクセスするには MongoClientオブジェクトを使用する必要があるサポートされていないMongoDB機能の詳細については、機能互換性ページをご覧ください。

Javaドライバーを使ってMongoDBと交流する方法を学ぶには、MongoDB Javaドライバーのドキュメントを参照してください。

Hibernate ORM 拡張機能を使用してコレクションにインデックスを作成することはできませんが、MongoClient をインスタンス化してJavaドライバーの createIndex() メソッドを使用できます。次のコードを使用することで、sample_mflix.moviesコレクションに titleフィールドインデックスが作成されます。

// Replace the <connection URI> placeholder with your MongoDB connection URI
String uri = "<connection URI>";
MongoClient mongoClient = MongoClients.create(uri);
MongoDatabase db = mongoClient.getDatabase("sample_mflix");
MongoCollection<Document> collection = db.getCollection("movies");
String indexResult = collection.createIndex(Indexes.ascending("title"));
System.out.println(String.format("Index created: %s", indexResult));

Javaドライバーを使用してインデックスを作成する方法の詳細については、Javaドライバーのドキュメントのインデックスガイドを参照してください。

このガイドで説明されているクエリ言語の詳細については、次のリソースを参照してください。