Docs Menu
Docs Home
/ /

チュートリアル: Javaと 引用符でデータをページ分割する

このチュートリアルでは、MongoDBに接続されたQuarkusアプリケーションにページ区切り手法を実装する方法を説明します。Javascript データリポジトリを使用して、オフセットベースとカーソルベースのページ区切りメソッドの両方をサポートするREST APIエンドポイントを作成する方法を学びます。

ページネーションは、大規模なデータセットを小さく、より管理しやすいチャンクに分割するために使用される手法です。このチュートリアルでは、オフセットベースカーソルベースのページ区切りメソッドを実装します。オフセットベースのページ分割では、ページ番号を使用してデータの特定のサブセットを検索します。一方、カーソルベースのページ分割では、参照点または カーソル を使用してデータセット内を移動します。

このチュートリアルでは、次のアクションを実行する方法について説明します。

  • 前提条件を確認します

  • 必要な依存関係を持つ Queryusプロジェクトを作成する

  • MongoDB接続の構成

  • データエンティティとリポジトリを定義する

  • ページネーション用のREST APIエンドポイントを実装する

  • ページネーション エンドポイントとなる接続されたデバイスをテストする

1

開始する前に、次の前提条件タスクを完了してください。

  • Java 21 のインストール

  • Install Maven

  • MongoDB AtlasまたはローカルDockerインスタンス上のMongoDBクラスターを構成する

Dockerを使用してローカルMongoDBインスタンスを起動するには、次のコマンドを実行します。

docker run --rm -d --name mongodb-instance -p 27017:27017 mongo

あるいは、 MongoDB Atlas を使用して、無料の M0 クラスターを配置することもできます。Atlas のアカウントとクラスターの作成方法については、 MongoDB の使用開始 ガイドを参照してください。

2

MongoDB クエリ ジェネレーターに移動し、次の設定でプロジェクトを構成します。

  1. ご希望のグループとアーティファクトIDを選択します。

  2. 次の依存関係を追加します。

    • JNoSQL ドキュメントMongoDB (quarkus-jnosql-document-mongodb

    • REST簡単リアクティブ(quarkus-resteasy-reactive

    • RESTKey Reactive JSON(quarkus-resteasy-reactive-jackson

    • OpenAPI (quarkus-smallrye-openapi)

  3. プロジェクトを生成し、ZIPファイルをダウンロードして抽出します。

注意

ジェネレーターで依存関係が見つからない場合は、pom.xmlファイルに手動で追加します。

設定が完了したら、pom.xmlファイルに次の依存関係が含まれていることを確認します。

<dependencies>
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-smallrye-openapi</artifactId>
</dependency>
<dependency>
<groupId>io.quarkiverse.jnosql</groupId>
<artifactId>quarkus-jnosql-document-mongodb</artifactId>
<version>3.3.0</version>
</dependency>
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-resteasy-reactive</artifactId>
</dependency>
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-resteasy-reactive-jackson</artifactId>
</dependency>
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-arc</artifactId>
</dependency>
<dependency>
<groupId>io.quarkus</groupId>
<artifactId>quarkus-junit5</artifactId>
<scope>test</scope>
</dependency>
<dependency>
<groupId>io.rest-assured</groupId>
<artifactId>rest-assured</artifactId>
<scope>test</scope>
</dependency>
</dependencies>
3

application.propertiesファイルを開き、 MongoDBインスタンスに接続するために次の構成プロパティを追加します。

quarkus.mongodb.connection-string = <your connection string>
jnosql.document.database = fruits

この構成により、アプリケーションは指定された接続文字列のMongoDBクラスターに接続し、fruitsデータベースを使用できるようになります。

重要

本番環境では、アクセス制御を有効にし、認証を強制します 。詳細については、セキュリティ チェックリスト を参照してください。

環境変数を使用することでこれらのプロパティを上書きできます。これにより、コードを変更せずに開発、テスト、本番用のさまざまな構成を指定できます。

4

src/main/javaディレクトリに Fruit エンティティクラスを作成します。次のコードは、id フィールドと name フィールドを持つエンティティを定義します。

import jakarta.nosql.Column;
import jakarta.nosql.Convert;
import jakarta.nosql.Entity;
import jakarta.nosql.Id;
import org.eclipse.jnosql.databases.mongodb.mapping.ObjectIdConverter;
@Entity
public class Fruit {
@Id
@Convert(ObjectIdConverter.class)
private String id;
@Column
private String name;
public String getId() {
return id;
}
public void setId(String id) {
this.id = id;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
@Override
public String toString() {
return "Fruit{" +
"id='" + id + '\'' +
", name='" + name + '\'' +
'}';
}
public static Fruit of(String name) {
Fruit fruit = new Fruit();
fruit.setName(name);
return fruit;
}
}
5

BasicRepositoryクラスを拡張する FruitRepository インターフェースを作成します。次のコードでは、オフセットとカーソルベースのページ分割の両方のメソッドを定義します。

import jakarta.data.Sort;
import jakarta.data.page.CursoredPage;
import jakarta.data.page.Page;
import jakarta.data.page.PageRequest;
import jakarta.data.repository.BasicRepository;
import jakarta.data.repository.Find;
import jakarta.data.repository.OrderBy;
import jakarta.data.repository.Repository;
@Repository
public interface FruitRepository extends BasicRepository<Fruit, String> {
@Find
CursoredPage<Fruit> cursor(PageRequest pageRequest, Sort<Fruit> order);
@Find
@OrderBy("name")
Page<Fruit> offSet(PageRequest pageRequest);
long countBy();
}

フレームワークはこのインターフェースを自動的に実装するため、ブロッキングコードを記述せずにデータベース操作を実行できるようになります。

6

src/main/javaディレクトリに SetupDatabaseクラスを作成します。次のコードは、スタートアップ時にデータベースにサンプルデータを入力し、シャットダウン時にそのデータを削除します。

import jakarta.enterprise.context.ApplicationScoped;
import jakarta.enterprise.event.Observes;
import io.quarkus.runtime.ShutdownEvent;
import io.quarkus.runtime.StartupEvent;
import org.jboss.logging.Logger;
import java.util.List;
@ApplicationScoped
public class SetupDatabase {
private static final Logger LOGGER = Logger.getLogger(SetupDatabase.class.getName());
private final FruitRepository fruitRepository;
public SetupDatabase(FruitRepository fruitRepository) {
this.fruitRepository = fruitRepository;
}
void onStart(@Observes StartupEvent ev) {
LOGGER.info("The application is starting...");
long count = fruitRepository.countBy();
if (count > 0) {
LOGGER.info("Database already populated");
return;
}
List<Fruit> fruits = List.of(
Fruit.of("apple"),
Fruit.of("banana"),
Fruit.of("cherry"),
Fruit.of("date"),
Fruit.of("elderberry"),
Fruit.of("fig"),
Fruit.of("grape"),
Fruit.of("honeydew"),
Fruit.of("kiwi"),
Fruit.of("lemon")
);
fruitRepository.saveAll(fruits);
}
void onStop(@Observes ShutdownEvent ev) {
LOGGER.info("The application is stopping...");
fruitRepository.deleteAll(fruitRepository.findAll().toList());
}
}
7

src/main/javaディレクトリに FruitResourceクラスを作成します。次に、次のコードをクラスファイルに貼り付けます。

import jakarta.data.Sort;
import jakarta.data.page.PageRequest;
import jakarta.ws.rs.DefaultValue;
import jakarta.ws.rs.GET;
import jakarta.ws.rs.Path;
import jakarta.ws.rs.Produces;
import jakarta.ws.rs.QueryParam;
import jakarta.ws.rs.core.MediaType;
@Path("/fruits")
public class FruitResource {
private final FruitRepository fruitRepository;
private static final Sort<Fruit> ASC = Sort.asc("name");
private static final Sort<Fruit> DESC = Sort.desc("name");
public FruitResource(FruitRepository fruitRepository) {
this.fruitRepository = fruitRepository;
}
@Path("/offset")
@GET
@Produces(MediaType.APPLICATION_JSON)
public Iterable<Fruit> offset(@QueryParam("page") @DefaultValue("1") long page,
@QueryParam("size") @DefaultValue("2") int size) {
var pageRequest = PageRequest.ofPage(page).size(size);
return fruitRepository.offSet(pageRequest).content();
}
@Path("/cursor")
@GET
@Produces(MediaType.APPLICATION_JSON)
public Iterable<Fruit> cursor(@QueryParam("after") @DefaultValue("") String after,
@QueryParam("before") @DefaultValue("") String before,
@QueryParam("size") @DefaultValue("2") int size) {
if (!after.isBlank()) {
var pageRequest = PageRequest.ofSize(size).afterCursor(PageRequest.Cursor.forKey(after));
return fruitRepository.cursor(pageRequest, ASC).content();
} else if (!before.isBlank()) {
var pageRequest = PageRequest.ofSize(size).beforeCursor(PageRequest.Cursor.forKey(before));
return fruitRepository.cursor(pageRequest, DESC).stream().toList();
}
var pageRequest = PageRequest.ofSize(size);
return fruitRepository.cursor(pageRequest, ASC).content();
}
}

このクラスは、次のエンドポイントとなる接続されたデバイスを定義します。

  • /fruits/offset: page クエリ パラメータを使用して、オフセットベースのページ分割をサポートします。

  • /fruits/cursor: afterbefore クエリ パラメータを使用して、カーソルベースのページ分割をサポートします。

どちらのエンドポイントも、ページあたりのアイテム数を指定するために size クエリ パラメータを受け入れます。

8

プロジェクトディレクトリから次のコマンドを実行し、Quarkusアプリケーションを開発モードで起動します。

./mvnw compile quarkus:dev
9

別のターミナルウィンドウで、次の curl コマンドを使用して、オフセット ページネーション エンドポイントをテストします。これらのコマンドは、実稼働データのさまざまなページをリクエスト。

最初のページを取得するには、次のコマンドを実行します。

curl --location http://localhost:8080/fruits/offset?page=1

2 番目のページを取得するには、次のコマンドを実行します。

curl --location http://localhost:8080/fruits/offset?page=2

5 ページを取得するには、次のコマンドを実行します。

curl --location http://localhost:8080/fruits/offset?page=5
10

カーソル ページネーション エンドポイントをテストするには、次の curl コマンドを使用します。これらのコマンドは、afterbefore パラメーターを使用してデータセット内を移動します。

結果の初期セットを取得するには、次のコマンドを実行する:

curl --location http://localhost:8080/fruits/cursor

"banana" の後に続く nameフィールド値を持つ結果を取得するには、次のコマンドを実行します。

curl --location http://localhost:8080/fruits/cursor?after=banana

"date" より前に到着する nameフィールド値を持つ実を取得するには、次のコマンドを実行します。

curl --location http://localhost:8080/fruits/cursor?before=date

MongoDBでのページ分割の詳細については、 MongoDB Atlasドキュメントの「 結果のページ分割」ガイドを参照してください。

Quarkus の詳細については、Quarkus のドキュメントを参照してください。

戻る

Cluster とMongoDBによる MongoDB