Memorystore を使用して Spring Boot アプリのデータをキャッシュに保存する

1. 概要

Memorystore for Redis は、Google Cloud 向けのフルマネージド Redis サービスです。Google Cloud 上で動作するアプリは、スケーラビリティと可用性に優れた安全な Redis サービスを利用することで、複雑な Redis デプロイを管理する負担なく、優れたパフォーマンスを実現できます。データ キャッシュのバックエンドとして使用することで、Spring Boot アプリのパフォーマンスを改善できます。Codelab ではその設定方法について説明します。

学習内容

  • Memorystore を Spring Boot アプリのキャッシュ バックエンドとして使用する方法。

必要なもの

  • Google Cloud プロジェクト
  • ブラウザ(Google Chrome など)
  • Linux の標準的なテキスト エディタ(Vim、Emacs、GNU Nano など)を使い慣れていること

この Codelab をどのように使用しますか?

<ph type="x-smartling-placeholder"></ph> 読み取り専用 演習を読み、完了する をご覧ください。

Google Cloud サービスの利用経験をどのように評価されますか。

<ph type="x-smartling-placeholder"></ph> 初心者 中級 上達 をご覧ください。

2. 設定と要件

セルフペース型の環境設定

  1. Cloud Console にログインし、新しいプロジェクトを作成するか、既存のプロジェクトを再利用します(Gmail アカウントまたは G Suite アカウントをお持ちでない場合は、アカウントを作成する必要があります)。

dMbN6g9RawQj_VXCSYpdYncY-DbaRzr2GbnwoV7jFf1u3avxJtmGPmKpMYgiaMH-qu80a_NJ9p2IIXFppYk8x3wyymZXavjglNLJJhuXieCem56H30hwXtd8PvXGpXJO9gEUDu3cZw

ci9Oe6PgnbNuSYlMyvbXF1JdQyiHoEgnhl4PlV_MFagm2ppzhueRkqX4eLjJllZco_2zCp0V0bpTupUSKji9KkQyWqj11pqit1K1faS1V6aFxLGQdkuzGp4rsQTan7F01iePL5DtqQ

8-tA_Lheyo8SscAVKrGii2coplQp2_D1Iosb2ViABY0UUO1A8cimXUu6Wf1R9zJIRExL5OB2j946aIiFtyKTzxDcNnuznmR45vZ2HMoK3o67jxuoUJCAnqvEX6NgPGFjCVNgASc-lg

プロジェクト ID を忘れないようにしてください。プロジェクト ID はすべての Google Cloud プロジェクトを通じて一意の名前にする必要があります(上記の名前はすでに使用されているので使用できません)。以降、このコードラボでは PROJECT_ID と呼びます。

  1. 次に、Google Cloud リソースを使用するために、Cloud Console で課金を有効にする必要があります。

このコードラボを実行しても、費用はほとんどかからないはずです。このチュートリアル以外で請求が発生しないように、リソースのシャットダウン方法を説明する「クリーンアップ」セクションの手順に従うようにしてください。Google Cloud の新規ユーザーは、300 米ドル分の無料トライアル プログラムをご利用いただけます。

Cloud Shell をアクティブにする

  1. Cloud Console で、[Cloud Shell をアクティブにする] H7JlbhKGHITmsxhQIcLwoe5HXZMhDlYue4K-SPszMxUxDjIeWfOHBfxDHYpmLQTzUmQ7Xx8o6OJUlANnQF0iBuUyfp1RzVad_4nCa0Zz5LtwBlUZFXFCWFrmrWZLqg1MkZz2LdgUDQ をクリックします。

zlNW0HehB_AFW1qZ4AyebSQUdWm95n7TbnOr7UVm3j9dFcg6oWApJRlC0jnU1Mvb-IQp-trP1Px8xKNwt6o3pP6fyih947sEhOFI4IRF0W7WZk6hFqZDUGXQQXrw21GuMm2ecHrbzQ

Cloud Shell を起動したことがない場合、その内容を説明する中間画面が(スクロールしなければ見えない範囲に)が表示されます。その場合は、[続行] をクリックします(以後表示されなくなります)。このワンタイム スクリーンは次のようになります。

kEPbNAo_w5C_pi9QvhFwWwky1cX8hr_xEMGWySNIoMCdi-Djx9AQRqWn-__DmEpC7vKgUtl-feTcv-wBxJ8NwzzAp7mY65-fi2LJo4twUoewT1SUjd6Y3h81RG3rKIkqhoVlFR-G7w

Cloud Shell のプロビジョニングと接続に少し時間がかかる程度です。

pTv5mEKzWMWp5VBrg2eGcuRPv9dLInPToS-mohlrqDASyYGWnZ_SwE-MzOWHe76ZdCSmw0kgWogSJv27lrQE8pvA5OD6P1I47nz8vrAdK7yR1NseZKJvcxAZrPb8wRxoqyTpD-gbhA

この仮想マシンには、必要な開発ツールがすべて準備されています。5 GB の永続ホーム ディレクトリが用意されており、Google Cloud で稼働するため、ネットワーク パフォーマンスが充実しており認証もスムーズです。このコードラボでの作業のほとんどは、ブラウザまたは Chromebook から実行できます。

Cloud Shell に接続すると、すでに認証は完了しており、プロジェクトに各自のプロジェクト ID が設定されていることがわかります。

  1. Cloud Shell で次のコマンドを実行して、認証されたことを確認します。
gcloud auth list

コマンド出力

 Credentialed Accounts
ACTIVE  ACCOUNT
*       <my_account>@<my_domain.com>

To set the active account, run:
    $ gcloud config set account `ACCOUNT`
gcloud config list project

コマンド出力

[core]
project = <PROJECT_ID>

上記のようになっていない場合は、次のコマンドで設定できます。

gcloud config set project <PROJECT_ID>

コマンド出力

Updated property [core/project].

3. Memorystore for Redis インスタンスを設定する

Cloud Shell を起動します。

Cloud Shell が起動したら、コマンドラインを使用して Memorystore API を有効にし、新しい Memorystore インスタンスを作成します。

$ gcloud services enable redis.googleapis.com
$ gcloud redis instances create myinstance --size=1 --region=us-central1

オペレーションが完了すると、インスタンスを使用できるようになります。

次のコマンドを実行して、インスタンスの Redis ホスト IP アドレスを取得します。これは、後で Spring Boot アプリを構成するときに再度使用します。

$ gcloud redis instances describe myinstance --region=us-central1 \
  | grep host
host: 10.0.0.4

Google Cloud コンソールで、[データベース] >Memorystore >Redis。インスタンスが「準備完了」状態state :

ee90b43f15a6dc1f.png

4. Compute Engine インスタンスを設定する

同じリージョンに Compute Engine インスタンスを作成します。

$ gcloud compute instances create instance-1 --zone us-central1-c

オペレーションが完了すると、インスタンスを使用できるようになります。

次のコマンドを使用して、SSH 経由でインスタンスに接続します。

$ gcloud compute ssh instance-1 --zone us-central1-c

または、[コンピューティング] >Compute Engine >[VM インスタンス] をクリックし、[接続] 列の [SSH] をクリックします。

a87bd437a0c8c7b4.png

仮想マシン(VM)インスタンスのシェル(Cloud Shell ではない)で、OpenJDK、Maven、Redis ツールをインストールします。

$ sudo apt-get install openjdk-17-jdk-headless maven redis-tools

インストールが完了するまで待ってから、次のステップに進みます。

5. Spring Boot アプリを設定する

webrediscache の依存関係を持つ新しい Spring Boot プロジェクトを作成します。

$ curl https://start.spring.io/starter.tgz \
  -d dependencies=web,redis,cache -d language=java -d baseDir=cache-app \
  -d type=maven-project \
  | tar -xzvf - && cd cache-app

application.properties ファイルを編集して、Redis インスタンスの Memorystore インスタンスの IP アドレスを使用するようにアプリを構成します。

$ nano src/main/resources/application.properties

次の行を Memorystore for Redis の IP アドレスに追加します(数ステップ前のとおり)。

spring.data.redis.host=<memorystore-host-ip-address> 

その後に新しい行を追加し、REST コントローラの Java クラスを作成します。

$ nano src/main/java/com/example/demo/HelloWorldController.java

このファイルに次の内容を追加します。

package com.example.demo;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.cache.annotation.Cacheable;
import org.springframework.data.redis.core.StringRedisTemplate;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

@RestController
public class HelloWorldController {
@Autowired
private StringRedisTemplate template;

@RequestMapping("/hello/{name}")
@Cacheable("hello")
public String hello(@PathVariable String name) throws InterruptedException {
  Thread.sleep(5000);
  return "Hello " + name;
 }
}

@RequestMapping アノテーションは、メソッドを HTTP エンドポイントとして公開し、パスの一部をメソッド パラメータにマッピングします(@PathVariable アノテーションで示されます)。

@Cacheable("hello") アノテーションは、メソッドの実行をキャッシュに保存する必要があることを示し、キャッシュ名は「hello」です。キャッシュキーとしてパラメータ値と組み合わせて使用されます。サンプルは、この Codelab で後ほど説明します。

次に、Spring Boot アプリクラスでキャッシュを有効にします。DemoApplication.java を編集します。

$ nano src/main/java/com/example/demo/DemoApplication.java

org.springframework.cache.annotation.EnableCaching をインポートし、このアノテーションをクラスに付けます。結果は次のようになります。

package com.example.demo;

import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.cache.annotation.EnableCaching;

@SpringBootApplication
@EnableCaching
public class DemoApplication {

public static void main(String[] args) {
  SpringApplication.run(DemoApplication.class, args);
 }
}

6. アプリを実行してエンドポイントにアクセスする

JAVA_HOME が正しいバージョンに設定されていることを確認します。

export JAVA_HOME=/usr/lib/jvm/java-17-openjdk-amd64/

これでアプリを実行する準備が整いました。

$ mvn spring-boot:run

以前と同じ方法で、インスタンスへの別の SSH 接続を開きます。新しい SSH ウィンドウで、/hello/ エンドポイントに複数回アクセスして「bob」を渡します。指定します。

$ time curl http://localhost:8080/hello/bob
Hello bob!

real        0m5.408s
user        0m0.036s
sys        0m0.009s

$ time curl http://localhost:8080/hello/bob
Hello bob!

real        0m0.092s
user        0m0.021s
sys        0m0.027s

初回のリクエストは 5 秒かかりましたが、このメソッドに Thread.sleep(5000) の呼び出しがあるにもかかわらず、次のリクエストはかなり高速になりました。これは、実際のメソッドが 1 回だけ実行され、結果がキャッシュに保存されたためです。その後のすべての呼び出しは、キャッシュから直接結果を返します。

7. キャッシュに保存されたオブジェクトを確認する

アプリがキャッシュした内容を正確に確認できます。前のステップで使用したのと同じターミナルから、redis-cli を使用して Memorystore for Redis ホストに接続します。

$ redis-cli -h <memorystore-host-ip-address>

キャッシュキーのリストを表示するには、次のコマンドを使用します。

:6379> KEYS *
1) "hello::bob"

ご覧のとおり、キャッシュ名はキーの接頭辞として使用され、パラメータ値は 2 番目の部分として使用されます。

値を取得するには、GET コマンドを使用します。

:6379> GET hello::bob
   Hello bob!

exit コマンドを使用して終了します。

8. クリーンアップ

クリーンアップするには、Cloud Shell から Compute Engine インスタンスと Memorystore インスタンスを削除します。

Compute インスタンスを削除します。

$ gcloud compute instances delete instance-1 --zone us-central1-c

Memorystore for Redis インスタンスを削除します。

$ gcloud redis instances delete myinstance --region=us-central1

9. 完了

Memorystore for Redis と Compute Engine インスタンスを作成しました。また、Spring Boot キャッシュで Memorystore を使用するように Spring Boot アプリを構成しました。

詳細

ライセンス

この作業はクリエイティブ・コモンズの表示 2.0 汎用ライセンスにより使用許諾されています。