Compute Engine でカーネル空間の NFS キャッシュ プロキシをデプロイする

Last reviewed 2023-10-03 UTC

このチュートリアルでは、Compute Engine で Linux ベースのカーネル空間のネットワーク ファイル システム(NFS)キャッシュ プロキシをデプロイ、構成、テストする方法について説明します。このチュートリアルで説明するアーキテクチャは、NFS 送信元ファイル サーバー(オンプレミスの NFS ファイル サーバーなど)から Google Cloud にバイトレベルで読み取り専用データが同期されるシナリオ用に設計されています。あるいは、1 つの信頼できるプライマリから複数の読み取り専用レプリカにオンデマンドで同期するシナリオでも使用できます。

このチュートリアルは、読者が次の内容を理解していることを前提としています。

  • Linux オペレーティング システムのカスタム バージョンをビルドする。
  • Compute Engine で起動スクリプトを使用して、ソフトウェアのインストールと構成を行う。
  • NFS ファイル システムを構成して管理する。

このアーキテクチャはファイルのロックをサポートしていません。このアーキテクチャは、一意のファイル名を使用してファイルのバージョンを追跡するパイプラインに最適です。

アーキテクチャ

このチュートリアルのアーキテクチャには、NFS プロキシおよびキャッシュとして機能するカーネル空間 NFS Daemon(KNFSD)が含まれています。この設定により、NFS クライアントからリクエストされたときにデータを移行することで、クラウドベースのコンピューティング ノードがローカルの高速ストレージにアクセスできるようになります。NFS クライアント ノードは、ライトスルー キャッシュを使用して NFS 送信元ファイル サーバーに直接データを書き戻します。次の図は、このアーキテクチャを示しています。

Google Cloud で KNFSD プロキシを使用するアーキテクチャ。

このチュートリアルでは、KNFSD プロキシ システムをデプロイしてテストします。単一の NFS サーバー、1 つの KNFSD プロキシ、1 つの NFS クライアントをすべて Google Cloud で作成して構成します。

KNFSD プロキシ システムは、NFS サーバーからボリュームをマウントし、そのボリュームを再度エクスポートします。NFS クライアントは、エクスポートされたボリュームをプロキシからマウントします。NFS クライアントがデータをリクエストすると、KNFSD プロキシはさまざまなキャッシュ テーブルをチェックして、データがローカルに存在するかどうか確認します。データがすでにキャッシュにある場合、KNFSD プロキシはそのデータをすぐに提供します。リクエストされたデータがキャッシュにない場合、プロキシはデータを移行し、キャッシュ テーブルを更新してデータを提供します。KNFSD プロキシは、ファイルデータとメタデータの両方をバイトレベルでキャッシュに保存するため、リクエストされたときに使用されているバイトのみが転送されます。

KNFSD プロキシには、L1 と L2 の 2 つのキャッシュ レイヤがあります。L1 は、RAM に存在するオペレーティング システムの標準ブロック キャッシュです。データ量が利用可能な RAM を超えた場合、FS-Cache を使用して L2 キャッシュが実装されます。FS-Cache は、データをローカル ディスクにキャッシュする Linux カーネル モジュールです。システムを構成する方法はいくつかありますが、このデプロイでは、ローカル SSD を L2 キャッシュとして使用します。

このチュートリアルでは、アーキテクチャを実装するために NFS バージョン 2、3、4 と互換性のある標準の NFS ツールを使用しています。

ハイブリッド アーキテクチャでの KNFSD のデプロイ

ハイブリッド アーキテクチャでは、Google Cloud で実行されている NFS クライアントが必要に応じてデータをリクエストします。これらのリクエストは KNFSD プロキシに対して実行され、このプロキシがローカル キャッシュ(存在する場合)からデータを提供します。データがキャッシュにない場合、プロキシがオンプレミス サーバーとの通信を管理します。このシステムでは、単一または複数の NFS 送信元サーバーをマウントできます。プロキシは、VPN または Dedicated Interconnect 経由でオンプレミスの NFS 送信元サーバーにアクセスするために必要な通信とデータ移行をすべて管理します。次の図は、ハイブリッド アーキテクチャでのこの KNFSD のデプロイメントを示しています。

KNFSD デプロイメントを使用するハイブリッド アーキテクチャ。

このチュートリアルでは、ハイブリッド接続について説明しません。ハイブリッド アーキテクチャへのデプロイ、高パフォーマンスのスケーリング、トラブルシューティングとチューニングに指標とダッシュボードを使用する際の考慮事項など、高度なトピックについては、ワークフローに関する高度なトピックをご覧ください。

目標

  • KNFSD プロキシ システムをデプロイしてテストします。
  • Google Cloud で次のコンポーネントを作成して構成します。
    • カスタム ディスク イメージ
    • KNFSD プロキシ
    • NFS サーバー
    • NFS クライアント
  • NFS クライアントに NFS プロキシをマウントします。
  • NFS プロキシを介して NFS サーバーから NFS クライアントにファイルをコピーします。

費用

このドキュメントでは、Google Cloud の次の課金対象のコンポーネントを使用します。

料金計算ツールを使うと、予想使用量に基づいて費用の見積もりを生成できます。 新しい Google Cloud ユーザーは無料トライアルをご利用いただける場合があります。

使用量については、Google Cloud からオンプレミス ストレージに書き込まれるデータのネットワーク下り(外向き)の費用ハイブリッド接続の費用を考慮してください。

始める前に

このリファレンス ガイドでは、Google Cloud プロジェクトが必要です。新しいプロジェクトを作成することも、すでに作成済みのプロジェクトを選択することもできます。

  1. Google Cloud Console の [プロジェクト セレクタ] ページで、Google Cloud プロジェクトを選択または作成します。

    プロジェクト セレクタに移動

  2. Google Cloud プロジェクトで課金が有効になっていることを確認します

  3. Compute Engine API を有効にします。

    API を有効にする

  4. Google Cloud コンソールで、「Cloud Shell をアクティブにする」をクリックします。

    Cloud Shell をアクティブにする

  5. Cloud Shell ターミナルでログインを認証します。

    gcloud auth application-default login
    

    コマンドラインに表示される手順に沿って、認証手順を完了します。

  6. 環境変数を設定します。

    export GOOGLE_CLOUD_PROJECT=PROJECT_NAME
    gcloud config set project $GOOGLE_CLOUD_PROJECT
    

    PROJECT_NAME は、以前に作成したプロジェクトの名前または選択したプロジェクトの名前に置き換えます。

このドキュメントに記載されているタスクの完了後、作成したリソースを削除すると、それ以上の請求は発生しません。詳細については、クリーンアップをご覧ください。

チュートリアル用の構成ファイルをダウンロードする

  1. Cloud Shell で GitHub リポジトリのクローンを作成します。

    cd ~/
    git clone https://github.com/GoogleCloudPlatform/knfsd-cache-utils.git
    
  2. Git タグを既知の正常なバージョンに設定します(この場合は v0.9.0)。

    cd ~/knfsd-cache-utils
    git checkout tags/v0.9.0
    
  3. コード リポジトリの image ディレクトリに移動します。

     cd ~/knfsd-cache-utils/image
    

ネットワークを構成する

デプロイを簡単にするため、このチュートリアルではデフォルトの VPC ネットワークを使用します。構成やモニタリングのために SSH 経由でさまざまなリソースに接続できるように、このチュートリアルでは外部 IP アドレスもデプロイします。

このチュートリアルでは、VPC 設計のためのベスト プラクティスとリファレンス アーキテクチャについて説明しませんが、これらのリソースをハイブリッド環境に統合する場合は、次のようなベスト プラクティスに従うことをおすすめします。

ネットワークを構成するには、次の操作を行います。

  • Cloud Shell で、次の変数を設定します。

    export BUILD_MACHINE_NETWORK=default
    export BUILD_MACHINE_SUBNET=default
    

NFS プロキシ ビルドマシンを作成する

このセクションでは、NFS プロキシ ビルドマシンとして機能する VM を作成してログインします。次に、提供されたインストール スクリプトを実行してカーネル バージョンを更新し、KNFSD プロキシ システムに必要なすべてのソフトウェアをインストールします。ソフトウェアのインストール スクリプトが完了するまでに数分かかる場合がありますが、このスクリプトを実行するのは一度だけです。

  1. Cloud Shell で、次の変数を設定します。

    export BUILD_MACHINE_NAME=knfsd-build-machine
    export BUILD_MACHINE_ZONE=us-central1-a
    export IMAGE_FAMILY=knfsd-proxy
    export IMAGE_NAME=knfsd-proxy-image
    
  2. VM インスタンスを起動します。

    gcloud compute instances create $BUILD_MACHINE_NAME \
      --zone=$BUILD_MACHINE_ZONE \
      --machine-type=n1-standard-16 \
      --project=$GOOGLE_CLOUD_PROJECT \
      --image=ubuntu-2004-focal-v20220615 \
      --image-project=ubuntu-os-cloud \
      --network=$BUILD_MACHINE_NETWORK \
      --subnet=$BUILD_MACHINE_SUBNET \
      --boot-disk-size=20GB \
      --boot-disk-type=pd-ssd \
      --metadata=serial-port-enable=TRUE
    

    ディスクサイズの不一致を示す警告メッセージが表示される場合があります。このメッセージは無視できます。

  3. インストールする必要があるソフトウェアの tar ファイルを作成して、ビルドマシンにコピーします。

    tar -czf resources.tgz -C resources .
    gcloud compute scp resources.tgz build@$BUILD_MACHINE_NAME: \
      --zone=$BUILD_MACHINE_ZONE \
      --project=$GOOGLE_CLOUD_PROJECT
    
  4. VM が起動したら、VM への SSH トンネルを開きます。

    gcloud compute ssh build@$BUILD_MACHINE_NAME \
      --zone=$BUILD_MACHINE_ZONE \
      --project=$GOOGLE_CLOUD_PROJECT
    
  5. SSH トンネルが確立され、コマンドラインが knfsd-build-machine インスタンスをターゲットにしたら、インストール スクリプトを実行します。

    tar -zxf resources.tgz
    sudo bash scripts/1_build_image.sh
    

    このスクリプトは、Ubuntu カーネルコード リポジトリのクローンを作成し、カーネル バージョンを更新して、追加のソフトウェアをインストールします。リポジトリ クローンが含まれているため、スクリプトが完了するまでに時間がかかる場合があります。

  6. インストール スクリプトが完了し、SUCCESS プロンプトが表示されたら、ビルドマシンを再起動します。

    sudo reboot
    

    ビルドマシンが再起動すると、次のメッセージが表示されます。

    WARNING: Failed to send all data from [stdin]
    ERROR: (gcloud.compute.ssh) [/usr/bin/ssh] exited with return code [255]
    

    これらのエラーは、Cloud Shell が NFS プロキシ ビルドマシンからホストマシンに戻るときに発生します。これらのエラーは無視できます。

  7. VM が再起動したら、VM への SSH トンネルを再度開きます。

    gcloud compute ssh $BUILD_MACHINE_NAME \
      --zone=$BUILD_MACHINE_ZONE \
      --project=$GOOGLE_CLOUD_PROJECT
    
  8. SSH トンネルが確立され、コマンドラインが nfs-proxy-build インスタンスをターゲットにしたら、Root に切り替えて OS のバージョンを確認します。

    uname -r
    

    出力は次のようになります。これは、ソフトウェアの更新が成功したことを示します。

    linux <$BUILD_MACHINE_NAME> 5.13.*-gcp ...
    

    出力が上記の例と類似していない場合は、このプロセスを完了して、もう一度 NFS プロキシ ビルドマシンを作成します。

  9. ローカル ディスクをクリーンアップし、ビルドマシンをシャットダウンします。

    sudo bash /home/build/scripts/9_finalize.sh
    

    次のような警告が表示されます。

    userdel: user build is currently used by process 1431
    userdel: build mail spool (/var/mail/build) not found
    

    これらの警告は、Cloud Shell が NFS プロキシ ビルドマシンからホストマシンに戻るときに発生します。これらのエラーは無視できます。

カスタム ディスク イメージを作成する

このセクションでは、インスタンスからカスタム イメージを作成します。カスタム イメージは、米国にあるマルチリージョンの Cloud Storage バケットに保存されます。

  1. Cloud Shell で、次の変数を設定します。

    export IMAGE_NAME=knfsd-image
    export IMAGE_DESCRIPTION="first knfsd image from tutorial"
    export IMAGE_LOCATION=us
    
  2. ディスク イメージを作成します。

    gcloud compute images create $IMAGE_NAME \
      --project=$GOOGLE_CLOUD_PROJECT \
      --description="$IMAGE_DESCRIPTION" \
      --source-disk=$BUILD_MACHINE_NAME \
      --source-disk-zone=$BUILD_MACHINE_ZONE \
      --storage-location=$IMAGE_LOCATION
    
  3. ディスク イメージが作成されたら、インスタンスを削除します。

    gcloud compute instances delete $BUILD_MACHINE_NAME \
      --zone=$BUILD_MACHINE_ZONE
    
  4. 続行するよう求められたら、「Y」と入力します。

    $BUILD_MACHINE_NAME インスタンスを削除すると、VM にアタッチされているディスクが削除されることを示すプロンプトが表示されます。カスタム イメージが保存され、この一時ディスクは不要になったため、安全に削除できます。

NFS 配信元サーバーを作成する

前述のように、このアーキテクチャはクラウドベースのリソースをオンプレミスのファイル サーバーに接続するように設計されています。このチュートリアルのプロセスを簡単にするために、Google Cloud プロジェクトで実行されるスタンドアロン リソースを作成して、この接続をシミュレートします。スタンドアロン リソースに nfs-server という名前を付けます。ソフトウェアのインストールと設定は起動スクリプトに含まれています。詳細については、スクリプト ~/knfsd-cache-utils/tutorial/nfs-server/1_build_nfs-server.sh をご覧ください。

  1. Cloud Shell で、ダウンロードした nfs-server スクリプト ディレクトリに移動します。

    cd ~/knfsd-cache-utils/tutorial
    
  2. スタンドアロン NFS サーバーを作成します。

    gcloud compute \
      --project=$GOOGLE_CLOUD_PROJECT instances create nfs-server \
      --zone=$BUILD_MACHINE_ZONE \
      --machine-type=n1-highcpu-2 \
      --maintenance-policy=MIGRATE \
      --image-family=ubuntu-2004-lts \
      --image-project=ubuntu-os-cloud \
      --boot-disk-size=100GB \
      --boot-disk-type=pd-standard \
      --boot-disk-device-name=nfs-server \
      --metadata-from-file startup-script=nfs-server-startup.sh
    

    このスクリプトが完了するまで数分かかることがあります。ディスクサイズが 200 GB 未満であるという警告メッセージが表示されることがあります。この警告は無視できます。

NFS プロキシを作成する

このセクションでは、NFS プロキシを作成します。このプロキシは、起動するとローカル ストレージを構成し、NFS サーバーのマウント オプションを準備して、キャッシュ内の結果をエクスポートします。このワークフローの大部分は、用意されている起動スクリプトによってオーケストレートされます。

  1. Cloud Shell で、次の変数を設定します。

    export PROXY_NAME=nfs-proxy
    
  2. nfs-proxy VM を作成します。

    gcloud compute instances create $PROXY_NAME \
      --machine-type=n1-highmem-16 \
      --project=$GOOGLE_CLOUD_PROJECT \
      --maintenance-policy=MIGRATE \
      --zone=$BUILD_MACHINE_ZONE \
      --min-cpu-platform="Intel Skylake" \
      --image=$IMAGE_NAME \
      --image-project=$GOOGLE_CLOUD_PROJECT \
      --boot-disk-size=20GB \
      --boot-disk-type=pd-standard \
      --boot-disk-device-name=$PROXY_NAME \
      --local-ssd=interface=NVME \
      --local-ssd=interface=NVME \
      --local-ssd=interface=NVME \
      --local-ssd=interface=NVME \
      --metadata-from-file startup-script=proxy-startup.sh
    

    ディスクサイズが 200 GB 未満であるという警告メッセージが表示される場合があります。この警告は無視できます。

    起動スクリプトによって NFS マウント コマンドが構成されます。これにより、システムを調整できます。NFS バージョン、同期または非同期、noctoactimeo の設定は、起動スクリプトで最適化する必要がある変数です。これらの設定の詳細については、NFS ファイル システムの最適化をご覧ください。

    この手順のコマンドでは、--metadata-from-file フラグを定義します。これにより、起動スクリプトがイメージ テンプレートに挿入されます。このチュートリアルでは、シンプルな proxy-startup.sh スクリプトを使用します。このスクリプトには、いくつかの事前設定変数が含まれていますが、パイプラインに統合する際に使用するオプションは含まれていません。より高度なユースケースについては、knfsd-cache-utils GitHub リポジトリをご覧ください。

NFS クライアントを作成する

この手順では、規模の大きいマネージド インスタンス グループ(MIG)の代わりに単一の NFS クライアント(nfs-client)を作成します。

  • Cloud Shell で、NFS クライアントを作成します。

    gcloud compute \
      --project=$GOOGLE_CLOUD_PROJECT instances create nfs-client \
      --zone=$BUILD_MACHINE_ZONE \
      --machine-type=n1-highcpu-8 \
      --network-tier=PREMIUM \
      --maintenance-policy=MIGRATE \
      --image-family=ubuntu-2004-lts \
      --image-project=ubuntu-os-cloud \
      --boot-disk-size=10GB \
      --boot-disk-type=pd-standard \
      --boot-disk-device-name=nfs-client
    

    ディスクサイズが 200 GB 未満であるという警告メッセージが表示される場合があります。この警告は無視できます。

NFS クライアントに NFS プロキシをマウントする

この手順では、NFS クライアントで別の SSH セッションを開き、NFS プロキシをマウントします。次のセクションでは、この同じシェルを使用してシステムをテストします。

  1. Google Cloud コンソールで [VM インスタンス] ページに移動します。

    [VM インスタンス] に移動

  2. nfs-client に接続するには、[接続] 列で [SSH] をクリックします。

  3. nfs-client SSH ウィンドウで、必要な NFS ツールを nfs-client にインストールします。

    sudo apt-get install nfs-common -y
    
  4. マウント ポイントを作成して、NFS プロキシをマウントします。

    sudo mkdir /data
    sudo mount -t nfs -o vers=3 nfs-proxy:/data /data
    

システムをテストする

これですべてのリソースが作成されました。このセクションでは、NFS プロキシを介して NFS サーバーから NFS クライアントにファイルをコピーして、テストを行います。このテストを初めて実施する場合、元のサーバーからデータが取得されます。この処理には 1 分以上かかることがあります。

2 回目以降のテストでは、NFS プロキシのローカル SSD に保存されているキャッシュからデータが提供されます。この転送では、データのコピーにかかる時間が大幅に短縮され、キャッシュによってデータ転送が高速化されていることが確認できます。

  1. 前のセクションで開いた nfs-client SSH ウィンドウで、test ファイルをコピーして、対応する出力を確認します。

    time dd if=/data/test.data of=/dev/null iflag=direct bs=1M status=progress
    

    出力は次のようになり、ファイルサイズ、転送時間、転送速度を示す行が含まれます。

    10737418240 bytes (11 GB, 10 GiB) copied, 88.5224 s, 121 MB/s
    real    1m28.533s
    

    この転送では、ファイルが NFS サーバーの永続ディスクから提供されるため、NFS サーバーのディスク速度の影響を受けます。

  2. 同じコマンドをもう一度実行します。

    time dd if=/data/test.data of=/dev/null iflag=direct bs=1M status=progress
    

    出力は次のようになり、ファイルサイズ、転送時間、転送速度を示す行が含まれます。

    10737418240 bytes (11 GB, 10 GiB) copied, 9.41952 s, 948 MB/s
    real    0m9.423s
    

    この転送では、ファイルが NFS プロキシのキャッシュから提供されるため、処理が速く完了します。

これで、KNFSD キャッシュ プロキシのデプロイとテストが完了しました。

ワークフローに関する高度なトピック

このセクションでは、ハイブリッド アーキテクチャへのデプロイ、高パフォーマンスのためのスケーリング、トラブルシューティングと調整で指標とダッシュボードを使用する方法について説明します。

パフォーマンス特性とリソース サイジング

前述のように、このチュートリアルでは単一の KNFSD プロキシを使用しています。システムをスケーリングするには、個々のプロキシ リソースを変更して、CPU、RAM、ネットワーク、ストレージ容量、またはパフォーマンスを最適化する必要があります。このチュートリアルでは、次のオプションを使用して KNFSD を単一の Compute Engine VM にデプロイしました。

  • 16 個の vCPU、104 GB の RAM(n1-highmem-16)。
    • 16 個の vCPU と Sandy Bridge 以降のアーキテクチャを使用すると、32 Gbps の最大ネットワーク速度を実現できます。
  • ブートディスクとして 10 GB の永続ディスク。
  • 4 個のローカル SSD ディスク。この構成では、1.5 TB の高速ファイル システムが提供されます。

このチュートリアルでは説明していませんが、MIG に複数の KNFSD プロキシを作成し、TCP ロードバランサで NFS クライアントと NFS プロキシの間の接続を管理することでアーキテクチャをスケーリングできます。詳細については、knfsd-cache-utils GitHub リポジトリをご覧ください。このリポジトリには、Terraform スクリプト、デプロイのサンプルコード、ワークロードのスケーリングに関するよくある質問が含まれています。

ハイブリッド デプロイに関する考慮事項

多くのデプロイでは、オンプレミスからクラウドへの接続帯域幅がシステム構成時に考慮すべき重要な要素となります。このチュートリアルでは、ハイブリッド接続について説明しません。使用可能なオプションの概要については、ハイブリッド接続のドキュメントをご覧ください。ベスト プラクティスと設計パターンのガイダンスについては、Google Cloud を使用したハイブリッド アーキテクチャとマルチクラウド アーキテクチャの構築のシリーズをご覧ください。

指標の探索

パフォーマンス調整や全体的なトラブルシューティングで使用する指標に関するフィードバックを提供する際にダッシュボードが役立ちます。このチュートリアルでは指標の探索について説明しませんが、指標のダッシュボードは、knfsd-cache-utils GitHub リポジトリで定義されているマルチノード システムのデプロイ時に利用できます。

クリーンアップ

このチュートリアルで使用したリソースについて、Google Cloud アカウントに課金されないようにするには、リソースを含むプロジェクトを削除するか、プロジェクトを維持して個々のリソースを削除します。

プロジェクトを削除する

課金を停止する最も簡単な方法は、チュートリアル用に作成したプロジェクトを削除することです。

  1. Google Cloud コンソールで、[リソースの管理] ページに移動します。

    [リソースの管理] に移動

  2. プロジェクト リストで、削除するプロジェクトを選択し、[削除] をクリックします。
  3. ダイアログでプロジェクト ID を入力し、[シャットダウン] をクリックしてプロジェクトを削除します。

次のステップ