Share via


チュートリアル: シークレットを使わず、マネージド ID を使って Java Quarkus コンテナー アプリから PostgreSQL Database に接続する

Azure Container Apps からアプリ用にマネージド ID も提供されます。これは、Azure Database for PostgreSQL やその他の Azure サービスへのアクセスをセキュリティで保護するためのターンキー ソリューションです。 Container Apps のマネージド ID を使って環境変数列内の認証情報などのシークレットをアプリから排除することで、アプリのセキュリティを強化できます。

このチュートリアルでは、Azure で Java コンテナー アプリを構築、構成、デプロイ、スケーリングするプロセスを、順を追って説明します。 このチュートリアルを完了すると、PostgreSQL データベースにデータを格納する Quarkus アプリケーションと、Container Apps 上で動作するマネージド ID を作成できます。

学習内容

  • PostgreSQL データベースで Microsoft Entra ID を使って認証するように Quarkus アプリを構成する。
  • Azure コンテナー レジストリを作成し、Java アプリ イメージをそこにプッシュする。
  • Azure でコンテナー アプリを作成する。
  • Azure で PostgreSQL データベースを作成する。
  • サービス コネクタを使い、マネージド ID を使って PostgreSQL データベースに接続する。

Azure サブスクリプションをお持ちでない場合は、開始する前に Azure 無料アカウントを作成してください。

1.前提条件

2. コンテナー レジストリを作成する

az group create コマンドを使用して、リソース グループを作成します。 Azure リソース グループとは、Azure リソースのデプロイと管理に使用する論理コンテナーです。

次の例では、myResourceGroup という名前のリソース グループを米国東部リージョンに作成します。

az group create --name myResourceGroup --location eastus

az acr create コマンドを使って Azure コンテナー レジストリを作成します。 レジストリの名前は Azure 内で一意にする必要があり、英数字で 5 ~ 50 文字にする必要があります。 すべての文字は、小文字で指定する必要があります。 次の例では、mycontainerregistry007 が使用されています。 これを一意の値に更新します。

az acr create \
    --resource-group myResourceGroup \
    --name mycontainerregistry007 \
    --sku Basic

3. サンプル アプリをクローンし、コンテナー イメージを準備する

このチュートリアルでは、Azure Database for PostgreSQL を基盤とする Quarkus REST API を呼び出す Web UI を備えた、サンプルの Fruits リスト アプリを使用します。 このアプリのコードは、GitHub で入手できます。 Quarkus と PostgreSQL を使用して Java アプリを作成する方法の詳細については、『『Quarkus の Hibernate ORM with Panache ガイド』および『Quarkus のデータソース ガイド』を参照してください。

お使いのターミナルで次のコマンドを実行して、サンプル リポジトリを複製し、サンプル アプリの環境をセットアップします。

git clone https://github.com/quarkusio/quarkus-quickstarts
cd quarkus-quickstarts/hibernate-orm-panache-quickstart

プロジェクトを変更する

  1. 必要な依存関係をプロジェクトの BOM ファイルに追加します。

    <dependency>
        <groupId>com.azure</groupId>
        <artifactId>azure-identity-providers-jdbc-postgresql</artifactId>
        <version>1.0.0-beta.1</version>
    </dependency>
    
  2. Quarkus アプリのプロパティを構成します。

    Quarkus の構成は、src/main/resources/application.properties ファイルにあります。 エディターでこのファイルを開き、いくつかの既定のプロパティを確認します。 %prod のプレフィックスが付いたプロパティは、アプリケーションがビルドおよびデプロイされている場合 (たとえば、Azure App Service にデプロイされている場合) にのみ使用されます。 アプリケーションをローカルで実行すると、%prod プロパティは無視されます。 同様に、%dev プロパティは Quarkus のライブ コーディング/開発モードで使用され、%test プロパティは継続的なテスト中に使用されます。

    application.properties 内の既存のコンテンツを削除し、次の内容に置き換えて、開発モード、テスト モード、運用モード用にデータベースを構成します。

    quarkus.package.type=uber-jar
    
    quarkus.hibernate-orm.database.generation=drop-and-create
    quarkus.datasource.db-kind=postgresql
    quarkus.datasource.jdbc.max-size=8
    quarkus.datasource.jdbc.min-size=2
    quarkus.hibernate-orm.log.sql=true
    quarkus.hibernate-orm.sql-load-script=import.sql
    quarkus.datasource.jdbc.acquisition-timeout = 10
    
    %dev.quarkus.datasource.username=${AZURE_CLIENT_NAME}
    %dev.quarkus.datasource.jdbc.url=jdbc:postgresql://${DBHOST}.postgres.database.azure.com:5432/${DBNAME}?\
    authenticationPluginClassName=com.azure.identity.providers.postgresql.AzureIdentityPostgresqlAuthenticationPlugin\
    &sslmode=require\
    &azure.clientId=${AZURE_CLIENT_ID}\
    &azure.clientSecret=${AZURE_CLIENT_SECRET}\
    &azure.tenantId=${AZURE_TENANT_ID}
    
    %prod.quarkus.datasource.username=${AZURE_MI_NAME}
    %prod.quarkus.datasource.jdbc.url=jdbc:postgresql://${DBHOST}.postgres.database.azure.com:5432/${DBNAME}?\
    authenticationPluginClassName=com.azure.identity.providers.postgresql.AzureIdentityPostgresqlAuthenticationPlugin\
    &sslmode=require
    
    %dev.quarkus.class-loading.parent-first-artifacts=com.azure:azure-core::jar,\
    com.azure:azure-core-http-netty::jar,\
    io.projectreactor.netty:reactor-netty-core::jar,\
    io.projectreactor.netty:reactor-netty-http::jar,\
    io.netty:netty-resolver-dns::jar,\
    io.netty:netty-codec::jar,\
    io.netty:netty-codec-http::jar,\
    io.netty:netty-codec-http2::jar,\
    io.netty:netty-handler::jar,\
    io.netty:netty-resolver::jar,\
    io.netty:netty-common::jar,\
    io.netty:netty-transport::jar,\
    io.netty:netty-buffer::jar,\
    com.azure:azure-identity::jar,\
    com.azure:azure-identity-providers-core::jar,\
    com.azure:azure-identity-providers-jdbc-postgresql::jar,\
    com.fasterxml.jackson.core:jackson-core::jar,\
    com.fasterxml.jackson.core:jackson-annotations::jar,\
    com.fasterxml.jackson.core:jackson-databind::jar,\
    com.fasterxml.jackson.dataformat:jackson-dataformat-xml::jar,\
    com.fasterxml.jackson.datatype:jackson-datatype-jsr310::jar,\
    org.reactivestreams:reactive-streams::jar,\
    io.projectreactor:reactor-core::jar,\
    com.microsoft.azure:msal4j::jar,\
    com.microsoft.azure:msal4j-persistence-extension::jar,\
    org.codehaus.woodstox:stax2-api::jar,\
    com.fasterxml.woodstox:woodstox-core::jar,\
    com.nimbusds:oauth2-oidc-sdk::jar,\
    com.nimbusds:content-type::jar,\
    com.nimbusds:nimbus-jose-jwt::jar,\
    net.minidev:json-smart::jar,\
    net.minidev:accessors-smart::jar,\
    io.netty:netty-transport-native-unix-common::jar
    

Docker イメージをビルドしてコンテナー レジストリにプッシュする

  1. コンテナー イメージをビルドします。

    次のコマンドを実行して Quarkus アプリ イメージをビルドします。 レジストリ ログイン サーバーの完全修飾名を使ってタグ付けする必要があります。 ログイン サーバー名は、<registry-name>.azurecr.io (すべて小文字にする必要があります) という形式です (mycontainerregistry007.azurecr.io など)。 名前は実際のレジストリ名で置き換えます。

    mvnw quarkus:add-extension -Dextensions="container-image-jib"
    mvnw clean package -Pnative -Dquarkus.native.container-build=true -Dquarkus.container-image.build=true -Dquarkus.container-image.registry=mycontainerregistry007 -Dquarkus.container-image.name=quarkus-postgres-passwordless-app -Dquarkus.container-image.tag=v1
    
  2. レジストリにログインします。

    コンテナー イメージをプッシュするには、あらかじめレジストリにログインしておく必要があります。 そのためには、[az acr login][az-acr-login] コマンドを使います。 Azure CLI を使ってサインインする際は、レジストリ リソース名のみを指定します。 完全修飾ログイン サーバー名は使用しません。

    az acr login --name <registry-name>
    

    このコマンドが完了すると、Login Succeeded というメッセージが返されます。

  3. イメージをレジストリにプッシュします。

    [docker push][docker-push] を使ってレジストリ インスタンスにイメージをプッシュします。 mycontainerregistry007 をレジストリ インスタンスのログイン サーバー名で置き換えます。 この例では、quarkus-postgres-passwordless-app レポジトリを作成します。これには、quarkus-postgres-passwordless-app:v1 イメージが含まれています。

    docker push mycontainerregistry007/quarkus-postgres-passwordless-app:v1
    

4. Azure でコンテナー アプリを作成する

  1. 次のコマンドを実行して Container Apps インスタンスを作成します。 環境変数の値は、使用する実際の名前と場所に置き換えてください。

    RESOURCE_GROUP="myResourceGroup"
    LOCATION="eastus"
    CONTAINERAPPS_ENVIRONMENT="my-environment"
    
    az containerapp env create \
        --resource-group $RESOURCE_GROUP \
        --name $CONTAINERAPPS_ENVIRONMENT \
        --location $LOCATION
    
  2. 次のコマンドを実行し、アプリ イメージを使ってコンテナー アプリを作成します。 プレースホルダーを実際の値に置き換えます。 コンテナー レジストリ管理者アカウントの詳細については、「Azure コンテナー レジストリでの認証」を参照してください。

    CONTAINER_IMAGE_NAME=quarkus-postgres-passwordless-app:v1
    REGISTRY_SERVER=mycontainerregistry007
    REGISTRY_USERNAME=<REGISTRY_USERNAME>
    REGISTRY_PASSWORD=<REGISTRY_PASSWORD>
    
    az containerapp create \
        --resource-group $RESOURCE_GROUP \
        --name my-container-app \
        --image $CONTAINER_IMAGE_NAME \
        --environment $CONTAINERAPPS_ENVIRONMENT \
        --registry-server $REGISTRY_SERVER \
        --registry-username $REGISTRY_USERNAME \
        --registry-password $REGISTRY_PASSWORD
    

5. PostgreSQL データベースを作成し、ID 接続を使って接続する

次に、PostgreSQL Database を作成し、システム割り当てマネージド ID を使って PostgreSQL Database に接続するようにコンテナー アプリを構成します。 Quarkus アプリは、このデータベースに接続し、実行時にデータを格納します。アプリケーションの状態は、アプリケーションを実行する場所に関わらず存続します。

  1. データベース サービスを作成します。

    DB_SERVER_NAME='msdocs-quarkus-postgres-webapp-db'
    ADMIN_USERNAME='demoadmin'
    ADMIN_PASSWORD='<admin-password>'
    
    az postgres flexible-server create \
        --resource-group $RESOURCE_GROUP \
        --name $DB_SERVER_NAME \
        --location $LOCATION \
        --admin-user $DB_USERNAME \
        --admin-password $DB_PASSWORD \
        --sku-name GP_Gen5_2
    

上記の Azure CLI コマンドでは、次のパラメーターが使用されます。

  • resource-group → Web アプリを作成したのと同じリソース グループ名を使用します (例: msdocs-quarkus-postgres-webapp-rg)。

  • name → PostgreSQL データベース サーバー名。 この名前は、Azure 全体で一意である必要があります (サーバー エンドポイントは https://<name>.postgres.database.azure.comになります)。 有効な文字は、A-Z0-9、および - です。 会社名とサーバー識別子を組み合わせて使用すると、適切なパターンになります。 (msdocs-quarkus-postgres-webapp-db)

  • location → Web アプリに使用したのと同じ場所を使用します。

  • admin-user → 管理者アカウントのユーザー名。 azure_superuseradmin, administratorroot, guest、または public とすることはできません。 たとえば、demoadmin は問題ありません。

  • admin-password → 管理者ユーザーのパスワード。 これには、次のうちの 3 つのカテゴリの、8 から 128 文字が含まれている必要があります。英大文字、英小文字、数字、英数字以外の文字のうち、3 つのカテゴリの文字が含まれている必要があります。

    重要

    ユーザー名またはパスワードを作成するとき、$ 文字は使用しないでください。 このチュートリアルの後半で、これらの値を使用して環境変数を作成しますが、Java アプリの実行に使用する Linux コンテナー内では、環境変数内の $ 文字に特殊な意味があります。

  • public-accessNone とします。これにより、ファイアウォール規則のないパブリック アクセス モードでサーバーを設定します。 規則は後の手順で作成します。

  • sku-name → 価格レベルとコンピューティング構成の名前。たとえば GP_Gen5_2 とします。 詳しくは、「Azure Database for PostgreSQL の価格」をご覧ください。

  1. 次のコマンドを使用して、PostgreSQL サービス内に fruits という名前のデータベースを作成します。

    az postgres flexible-server db create \
        --resource-group $RESOURCE_GROUP \
        --server-name $DB_SERVER_NAME \
        --database-name fruits
    
  2. Azure CLI 用 Service Connector パスワードレス拡張機能をインストールします。

    az extension add --name serviceconnector-passwordless --upgrade
    
  3. connection コマンドを使い、システム割り当てマネージド ID を使ってコンテナー アプリにデータベースを接続します。

    az containerapp connection create postgres-flexible \
        --resource-group $RESOURCE_GROUP \
        --name my-container-app \
        --target-resource-group $RESOURCE_GROUP \
        --server $DB_SERVER_NAME \
        --database fruits \
        --managed-identity
    

6. 変更内容を確認する

アプリケーションの URL (FQDN) は、次のコマンドを使って見つけることができます。

az containerapp list --resource-group $RESOURCE_GROUP

新しい Web ページに fruits リストを表示するとき、アプリはマネージド ID を使用してデータベースに接続しています。 以前と同様に fruits リストを編集できるようになりました。

リソースをクリーンアップする

前の手順では、リソース グループ内に Azure リソースを作成しました。 これらのリソースが将来必要になると想定していない場合、Cloud Shell で次のコマンドを実行して、リソース グループを削除します。

az group delete --name myResourceGroup

このコマンドの実行には、少し時間がかかる場合があります。

次のステップ

開発者ガイドの Azure 上で Java アプリを実行する方法を確認します。