IBM Cloud Docs
アプリ用イメージのビルド

アプリ用イメージのビルド

Docker イメージが、Red Hat® OpenShift® on IBM Cloud® で作成するすべてのコンテナーの基礎です。

イメージは、Dockerfile (イメージをビルドするための指示が入ったファイル) から作成されます。 Dockerfile の別個に保管されている指示の中で、ビルド成果物 (アプリ、アプリの構成、その従属関係) が参照されることもあります。

イメージの構築

以下の IBM Cloud サービスなど、いくつかの方法でイメージを構築できます。

IBM Cloud Code Engine
Code Engine は、Dockerfile および Cloud Native Buildpacks からイメージを構築し、イメージを IBM Cloud® Container Registry に自動的に反映させることをサポートしています。 詳しくは、ビルドの計画を参照してください。
Tekton パイプライン
Continuous Delivery サービスには、イメージを構築するためにパイプライン内で参照できるいくつかの Tekton タスクが含まれています。 詳しくは、Tekton パイプラインを参照してください。

内部レジストリーの既存のイメージ・ストリームからコンテナーをデプロイする

クラスタ管理者が Red Hat OpenShift クラスタの内部レジストリに設定した既存の イメージストリームからアプリをデプロイできます。 例えば、クラスター管理者が、IBM Cloud Container Registry などの外部プライベート・レジストリーからイメージをインポートするためにイメージ・ストリームをセットアップしている場合があります。

CLI でのイメージ・ストリームの使用

  1. Red Hat OpenShift クラスターにアクセスします

  2. プロジェクト内の使用可能なイメージ・ストリームをリストします。 イメージ・ストリームのプロジェクト、名前、およびタグがわかれば、イメージ・プル・ストリームの資格情報をセットアップすることなく、他のプロジェクトでローカルのイメージ・ストリームを使用できます。

    oc get is -n <project>
    
  3. イメージ・ストリームからアプリを作成します。

    oc new-app --image-stream="<project>/<imagestream>:<tag>"
    

Red Hat OpenShift Web コンソールからのイメージ・ストリームの使用

  1. Red Hat OpenShift Web コンソールで、**「開発者 (Developer)」パースペクティブに切り替えて、「+追加 (+Add)」**をクリックします。
  2. 「追加」ペインのメニュー・バーで、アプリを作成する以外のプロジェクトdefaultを選択し、**「コンテナー・イメージ (Container Image)」**をクリックします。
  3. **「イメージ (Image)」セクションで、「内部レジストリーのイメージ名 (Image name from internal registry)」**を選択します。
  4. 前に作成したイメージ・ストリームのdefault Project<image> イメージ・ストリーム、および<tag> Tag を選択します。
  5. アプリケーション詳細の残りの部分を確認し、**「作成」**をクリックします。

IBM Cloud Container Registry イメージから default の Red Hat OpenShift プロジェクトへのコンテナーのデプロイ

IBM 提供のパブリック・イメージや IBM Cloud Container Registry 名前空間に保管されているプライベート・イメージからクラスターにコンテナーをデプロイできます。 クラスターがレジストリー・イメージにアクセスする方法について詳しくは、IBM Cloud Container Registry からイメージをプルする権限がクラスターに与えられる仕組みについてを参照してください。

始める前に

  1. IBM Cloud Container Registry に名前空間をセットアップして、その名前空間にイメージをプッシュします

  2. クラスターを作成します。

  3. Red Hat OpenShift クラスターにアクセスします

  4. <deployment>.yaml という名前のデプロイメント構成ファイルを作成します。

  5. IBM Cloud Container Registry 内のプロジェクトから使用するイメージおよびデプロイメントを定義します。

    apiVersion: apps/v1
    kind: Deployment
    metadata:
      name: <deployment>
    spec:
      replicas: <number_of_replicas>
      selector:
        matchLabels:
          app: <app_name>
      template:
        metadata:
          labels:
            app: <app_name>
        spec:
          containers:
          - name: <app_name>
            image: <region>.icr.io/<project>/<image>:<tag>
    
    <deployment>
    デプロイメントの名前を指定します。
    <number_of_replicas>
    デプロイメントで作成するレプリカ・ポッドの数を入力します。
    app: <app_name>
    このアプリの名前をコンテナーのラベルとして使用してください。
    name: <app_name>
    コンテナーの名前を指定します。app ラベルの名前などを使用してください。
    image: <region>.icr.io/project>/image>:tag>
    イメージの URL の変数は、対象イメージの情報に置き換えます。
    region>: レジストリー・ドメインの地域 IBM Cloud Container Registry API エンドポイント。 ログイン先のリージョンのドメインをリストするには、ibmcloud cr api を実行します。
    namespace>: レジストリー名前空間。 名前空間の情報を取得するには、ibmcloud cr namespace-list を実行します。
    image>:tag>: コンテナーのために使用するイメージとタグ。 レジストリー名前空間で使用できるイメージをリストするには、ibmcloud cr images を実行します。
  6. クラスター内にデプロイメントを作成します。

    oc apply -f <deployment>.yaml
    

暗号化されたイメージからのコンテナーのデプロイ

Image Key Synchronizer クラスター・アドオンを使用して、暗号化されたイメージからクラスターにコンテナーをデプロイします。

Red Hat OpenShift 4.5 以降を実行するクラスタでは、 CRI-O コンテナ・ランタイムが暗号化されたコンテナ・イメージの使用をサポートしています。 暗号化されたコンテナー・イメージは、暗号化されたレイヤーの内容を含む Open Container Initiative (OCI) イメージです。 イメージをレジストリーからプルするためにイメージ・プル・シークレットを使用する開発者などの個々の開発者向けにイメージを保護する代わりに、特定のクラスターのイメージ暗号化を有効にすることができます。 これにより、暗号化されたイメージが、イメージ復号鍵を持つ特定のクラスターでのみ実行されるようにすることができます。

暗号化されたイメージを使用してアプリを実行するには、イメージを復号するための鍵を、クラスター内のワーカー・ノード上のコンテナー・ランタイムと共有する必要があります。 クラスターで Image Key Synchronizer アドオンを有効にすると、シンクロナイザー・デーモン・セットが image-key-synchronizer プロジェクトにデプロイされます。 その後、そのプロジェクト内のイメージ復号鍵を含む Kubernetes シークレットを作成できます。 アドオンによって、コンテナー・ランタイムがアクセス可能なワーカー・ノード上の特定のディレクトリーに鍵が追加されます。コンテナー・ランタイムはその鍵を使用してコンテナー・イメージを復号できます。 Image Key Synchronizer アドオンは、最初に IBM® Key Protect インスタンスに保管されているルート鍵によってラップされる秘密鍵もサポートすることに注意してください。

開始前に

  1. 以下のオープンソース・ツール用の CLI クライアントをダウンロードしてインストールします。

    • OpenSSLで、RSA鍵ペアを生成する。
    • Docker Engine CLIを使用して、イメージレジストリからローカルにイメージを取り出します。
    • Skopeo。OCI コンテナー・イメージを暗号化します。
  2. Red Hat OpenShift クラスターにアクセスします

  3. オプション: イメージ暗号化のために公開鍵と秘密鍵のペアを作成する場合、秘密鍵を直接指定することも、最初に Key Protect ルート鍵または鍵管理サービス (KMS) を使用して秘密鍵をラップすることもできます。 秘密鍵のラップを準備するには、以下のようにします。

    1. Key Protect CLI プラグインをインストールします

    2. Key Protect サービスのインスタンスを作成します

    3. Key Protect ルート・キーを作成します

    4. Key Protect インスタンスの以下の値を取得します。

    5. 取得した値を含む keyprotect-config という名前の Kubernetes シークレットを作成します。 Image Key Synchronizer アドオンは、このシークレットの環境変数を使用して、Key Protect インスタンスでの認証を行います。

      apiVersion: v1
      kind: Secret
      metadata:
        name: keyprotect-config
        namespace: image-key-synchronizer
      type: Opaque
      stringData:
        config.json: |
            {
                "keyprotect-url":"<service_endpoint>",
                "instance-id": "<service_instance_ID>",
                "apikey": "<service_instance_ID_API_key>"
            }
      

暗号化されたイメージを使用するコンテナーをデプロイするには、以下のようにします。

  1. Image Key Synchronizer アドオンを有効にします。

    ibmcloud oc cluster addon enable image-key-synchronizer -c <cluster_name_or_ID>
    
  2. クラスタの image-key-synchronizer プロジェクトに addon-image-key-synchronizer デーモン・セットが正常に作成されたことを確認します。

    oc get ds addon-image-key-synchronizer -n image-key-synchronizer
    
  3. openssl を使用して、RSA 秘密鍵と公開鍵のペアを生成します。

    openssl genrsa -out myprivatekey.pem
    openssl rsa -in myprivatekey.pem -pubout -out mypubkey.pem
    
  4. 秘密鍵をシークレットに直接指定するか、まず、Key Protect などの鍵管理サービス (KMS) からのルート鍵を使用して秘密鍵をラップします。 image-key-synchronizer プロジェクトにシークレットを作成すると、Image Key Synchronizer アドオンによって、秘密鍵がワーカー・ノードの /etc/crio/keys/synced ディレクトリーに自動的にコピーされます。

    • 秘密鍵を直接指定する場合: 秘密鍵を Kubernetes シークレットとして image-key-synchronizer プロジェクトに保存します。
      oc create -n image-key-synchronizer secret generic --type=key --from-file=myprivatekey.pem <secret_name>
      
    • Key Protect ルート鍵を使用して秘密鍵をラップする場合:
      1. 秘密鍵を base64 でエンコードし、出力をコピーします。

        cat myprivatekey.pem | base64
        
      2. Key Protect CLI プラグインを使用して、base64 でエンコードされた秘密鍵をルート鍵でラップします。 出力で、ラップされた秘密鍵の暗号文をコピーします。

        ibmcloud kp key wrap <root_key_ID> -p <base64_encoded_private_key>
        
      3. ラップされた秘密鍵を Kubernetes シークレットとして image-key-synchronizer プロジェクトに保存します。

        apiVersion: v1
        kind: Secret
        type: kp-key
        metadata:
          name: <secret_name>
          namespace: image-key-synchronizer
        stringData:
          rootkeyid: "<root_key_ID>"
          ciphertext: "<wrapped_private_key_cipertext>"
        
      4. シークレットを作成します。

        oc apply -n image-key-synchronizer -f <secret_name>.yaml
        
  5. docker を使用して、OCI イメージをローカルにプルします。 <source_image>をイメージのリポジトリーに置換し、<tag> を使用するイメージのタグ (latestなど) に置換します。

    docker pull <source_image>:<tag>
    
  6. skopeo を使用して、ローカル・イメージを暗号化します。 このコマンドは、以前にプルした OCI イメージをコピーし、公開鍵を使用してイメージを暗号化し、暗号化されたイメージを別のローカル・ファイルに保存します。 簡単に識別できるように、暗号化イメージに<source_image>_encryptedという名前を付けることを検討してください。

    skopeo copy --encryption-key jwe:./mypubkey.pem <source_image>:<tag> <source_image>_encrypted:<tag>
    
  7. オプション: イメージが暗号化されていることをローカルで検証するには、誤った鍵を使用してイメージの復号を試行します。

    1. 新しい秘密鍵を生成します。

      openssl genrsa --out wrongkey.pem 1024
      
    2. この新しい鍵を使用してイメージを復号しようとします。 誤った秘密鍵が指定されたため、復号コマンドは失敗します。

      skopeo copy --decryption-key ./wrongkey.pem <source_image>_encrypted:<tag> <source_image>_decrypted:<tag>
      
  8. オプション: 暗号化された OCI イメージをサポートする IBM Cloud Container Registry に、暗号化されたイメージをプッシュします。

  9. アプリ・デプロイメントで、暗号化されたイメージを指定します。 例えば、暗号化されたイメージを IBM Cloud Container Registry にプッシュした場合、IBM Cloud Container Registry イメージから default の Red Hat OpenShift プロジェクトへのコンテナーのデプロイの例に従うことができます。 クラスター内にデプロイメントを作成すると、コンテナー・ランタイムは /etc/crio/keys/synced ディレクトリー内の秘密復号鍵を使用して、イメージを実行前に復号します。

  10. 暗号化する後続のイメージについては、同じ公開鍵を使用して Skopeo でイメージを暗号化するか、これらのステップを繰り返して別の公開鍵と秘密鍵のペアを使用することができます。

後でアドオンを無効にすると、 addon-image-key-synchronizer デーモンセットは削除されますが、 image-key-synchronizer プロジェクトとそのプロジェクトで作成したシークレットは削除されず、コンテナランタイムはシークレットを使用して暗号化イメージを実行できます。 ワーカー・ノードからも鍵を削除する場合は、アドオンを無効にする前に、image-key-synchronizer プロジェクトから対応するシークレットを削除する必要があります。

各 Image Key Synchronizer アドオンバージョンの変更リストについては、 IBM Cloud Image Key Synchronizer アドオン変更ログを 参照してください。

ポッド・デプロイメントでイメージ・プル・シークレットを参照する

クラスター管理者が Kubernetes サービス・アカウントにイメージ・プル・シークレットを保管しなかった場合、サービス・アカウントを指定していないすべてのデプロイメントは、コンテナーをデプロイする際にイメージ・プル・シークレットを使用することができません。 代わりに、ポッド・デプロイメントでイメージ・プル・シークレットを定義できます。 ポッド・デプロイメントでイメージ・プル・シークレットを参照する場合、イメージ・プル・シークレットはこのポッドでのみ有効であり、Red Hat OpenShift プロジェクト内のポッド間で共有することはできません。

開始前に

ポッド・デプロイメントでイメージ・プル・シークレットを参照するには、以下のようにします。

  1. mypod.yaml という名前のポッド構成ファイルを作成します。

  2. IBM Cloud Container Registry 内のイメージにアクセスするためのイメージ・プル・シークレットとポッドを定義します。

    プライベート・イメージにアクセスするには、

    apiVersion: v1
    kind: Pod
    metadata:
      name: mypod
    spec:
      containers:
        - name: <container_name>
          image: <region>.icr.io/<namespace_name>/<image_name>:<tag>
      imagePullSecrets:
        - name: <secret_name>
    

    IBM Cloud パブリック・イメージにアクセスするには、

    apiVersion: v1
    kind: Pod
    metadata:
      name: mypod
    spec:
      containers:
        - name: <container_name>
          image: icr.io/<image_name>:<tag>
      imagePullSecrets:
        - name: <secret_name>
    
    container_name>
    クラスターにデプロイするコンテナーの名前。 namespace_name>: イメージが保管されているレジストリー名前空間。 使用可能な名前空間をリストするには、ibmcloud cr namespace-list を実行します。 image_name>: 使用するイメージの名前。 IBM Cloud アカウント内の使用可能なイメージをリストするには、ibmcloud cr image-list を実行します。 tag>: 使用するイメージのバージョン。 タグが指定されていない場合、latest というタグが付いたイメージがデフォルトで使用されます。 <secret_name>: 以前に作成したイメージ・プル・シークレットの名前。
  3. 変更内容を保存します。

  4. クラスター内にデプロイメントを作成します。

    oc apply -f mypod.yaml
    

イメージを IBM Cloud Container Registry にプッシュする

クラスター管理者が IBM Cloud Container Registry でイメージ・レジストリーをセットアップしたら、Docker イメージを名前空間に追加して安全にイメージを保管し、他のユーザーと共有することができます。

例えば、プライベート・レジストリーまたはパブリック・レジストリーのソースからイメージをプルし、タグを付けて IBM Cloud Container Registry で後で使用することができます。 または、他のユーザーがイメージにアクセスできるように、作業対象の Docker イメージを名前空間にプッシュすることもできます。 まずは、名前空間へのイメージの追加を参照してください。

脆弱性アドバイザーによる IBM Cloud Container Registry でのイメージのセキュリティー管理

Vulnerability Advisorは、IBM やサード・パーティーから提供されたコンテナー・イメージや、組織の IBM Cloud Container Registry 名前空間に追加されたコンテナー・イメージのセキュリティー状況を検査します。

イメージを名前空間に追加すると、Vulnerability Advisorによってイメージが自動的にスキャンされ、セキュリティー問題や潜在的な脆弱性が検出されます。 セキュリティー問題が検出されると、報告された脆弱性の解決に役立つ指示が提供されます。 まずは、脆弱性アドバイザーを使用したイメージ・セキュリティーの管理を参照してください。

コンテナー・イメージのための信頼できるコンテンツのセットアップ

署名ありで IBM Cloud Container Registry に保管されている信頼できるイメージからコンテナーを構築できます。また、署名なしのイメージや脆弱なイメージのデプロイを防止できます。

  1. 信頼できるコンテンツとしてイメージに署名します。 イメージに信頼をセットアップしたら、信頼できるコンテンツと、レジストリーにイメージをプッシュできる署名者を管理できるようになります。
  2. クラスターでコンテナーの作成に署名付きのイメージしか使用できないようにするポリシーを適用するには、オープンソースの Portieris プロジェクトをインストールします。
  3. クラスター・ユーザーは、信頼できるイメージから作成されたアプリをデプロイできます。
    1. Kubernetes 名前空間 default にデプロイします
    2. 別の Kubernetes 名前空間にデプロイするか、別の IBM Cloud リージョンまたはアカウントからデプロイします

クラスターでのイメージ・セキュリティー制約の有効化

クラスターでイメージ・セキュリティー制約を有効にする場合は、オープンソースの Kubernetes プロジェクト Portieris をインストールします。 その後、イメージ・ポリシーを作成して、ポリシーを満たさないポッド (署名されていないイメージなど) がクラスター内で実行されないようにすることができます。

詳しくは、 Portieris のドキュメントを参照。

変更されたイメージ: デフォルトでは、Portieris は MutatingAdmissionWebhook アドミッション・コントローラーを使用して、タグではなくダイジェストでイメージを参照するようにイメージを変更します。 ただし、変更されたイメージを拒否するデプロイメント・テクノロジーが存在する場合があります。 その場合は、 画像変異オプションと ポリシーを使って、デフォルトの動作を変更することができます。

イメージ・セキュリティー制約の有効化または無効化

CLIまたはコンソールから、クラスタに対するイメージ・セキュリティの実施を有効または無効にできます。 それ以前のバージョンについては、 Portieris のドキュメントを参照のこと。

CLI を使用したイメージ・セキュリティー適用の有効化または無効化

以下のコマンドを参照してください。

コンソールからのイメージ・セキュリティー適用の有効化または無効化

  1. コンソールから、クラスタを選択します。
  2. 画像セキュリティの適用フィールドを見つけ、 [有効] または [無効] をクリックします。

デフォルトのイメージ・ポリシー

イメージ・セキュリティー制約を有効にすると、Red Hat OpenShift on IBM Cloud が自動的にいくつかのイメージ・ポリシーをクラスターに作成します。 この機能を無効にすると、基礎となるClusterImagePolicy CRD が削除されます。これにより、作成したすべてのデフォルト・イメージ・ポリシーとすべてのカスタム・イメージ・ポリシーが削除されます。

  • ibm-signed-image-enforcement という名前のイメージ・ポリシーによって、プロジェクトで実行されるイメージが Red Hat OpenShift on IBM Cloud イメージのみに制限されます。 これらのイメージ・ポリシーは変更しないでください。 変更しても数分以内に上書きされます。
  • defaultdefault-allow-all などのように、別のイメージ・ポリシーで制限されていないイメージを許可するイメージ・ポリシーもあります。 これらのイメージ・ポリシーは変更でき、変更は保持されますが、イメージ・ポリシーの名前は変更しないでください。 ポリシーの名前を変更すると、デフォルトの名前と設定を含むポリシーが別に作成されます。

クラスター内のイメージ・ポリシーを確認するには、以下のようにします。

開始前に

Red Hat OpenShift クラスターにアクセスします

  1. クラスターにグローバルに適用されるイメージ・ポリシーをリスト表示します。 設定例については、 Portieris ポリシーのドキュメントを参照してください。

    oc get ClusterImagePolicy
    
  2. クラスター内の特定の名前空間に適用されるイメージ・ポリシーをリスト表示します。 設定例については、 Portieris ポリシーのドキュメントを参照してください。

    oc get ImagePolicy --all-namespaces