AWS JAPAN APN ブログ

【APN Ambassadors ブログシリーズ第三弾】Amazon WorkSpaces で多要素認証(MFA)を利用する場合でもユーザは AD だけで管理したい

パートナーソリューションアーキテクトの大林です。
本記事は、「Japan APN Ambassador」 の方々に、AWS JAPAN APN ブログ にて技術情報をお届けいただく【APN Ambassadors ブログシリーズ】の第三弾となります。今回は、APN Ambassador である株式会社BeeX 那須 隆 様より、寄稿いただきました。
本記事は、2020 年 8 月 26 日時点の内容となります。最新の情報につきましては、AWS 公式ドキュメントを参照ください。

 



BeeX の那須と申します。約 4 ヶ月ぶり 2 度目の記事になります。

夏になると少しはいい状況になるかなと思っていたのですが、今もなかなか自由がきかない状況ですね。弊社のお客様でも在宅勤務等のリモートワークを基本として活動されている方が多いです。そのような状況で、AWS 上で稼働しているシステムにアクセスするための素敵なサービスがあります。それが Amazon WorkSpaces です。Amazon WorkSpaces が何かわからない方はまずは「Amazon WorkSpaces」をご参照ください。ものすごく簡単に表現すると仮想デスクトップのサービスです。また、Amazon WorkSpaces については、2020 年 9 月 30 日まで新規での Amazon WorkSpaces 利用の 50 ユーザ分を無料で利用できるようになっています。詳しくは、「Amazon WorkSpaces の料金」をご参照ください。

今回の記事は、とあるお客様でこの Amazon WorkSpaces を使いたいというお話を伺って、多要素認証(以降、MFA)の部分での困りごとを解決した時のお話です。MFA とは Multi-Factor Authentication の略称で、「記憶」「所持」「生体情報」の 3 要素から複数の要素を組み合わせて行う認証方式です。最近ではユーザ名 & パスワード(記憶)とワンタイムパスワード(所持)の組み合わせで認証するサービスが増えてきていますね。

それでは具体的に内容を見ていきましょう。

 

何が課題だったのか?

AWS 公式の資料である「多要素認証による Amazon WorkSpaces の利用」に MFA の利用の流れや設定方法が書かれています。この資料では MFA で利用する RADIUS サーバを FreeRADIUS で作成する例が記載されています。もちろん他の RADIUS サーバを使って MFA の仕組みを作成することも可能です。この通りに進めば確かに MFA を組み合わせた認証を実現できるのですが、p24 に記載のこの文言にどうしてもひっかかるのです。

Google Authenticator の PAM モジュールを使う場合は、”Active Directory と同名のユーザを作成した上で”、Google Authenticator のユーザ設定を行う必要があります。

Amazon WorkSpaces を利用するユーザは Active Directory(以降、AD)で提供されます。AD のユーザ名とパスワードを使って Amazon WorkSpaces を利用することになるのですが、MFA の設定箇所でなぜか FreeRADIUS サーバのローカルにユーザを作成する流れになっています。AWS の資料だけかと思って調べてみると、日本語で出てくる MFA による Amazon WorkSpaces のブログ記事はすべて FreeRADIUS サーバのローカルに AD と同名のユーザを作成する手順が紹介されていました(私がうまく見つけられていない可能性もあります)。せっかく AD ユーザで認証するのに MFA を使う場合は AD とは別のところでもユーザ管理をしないといけないとなると、運用開始後にユーザ管理が冗長となってしまうのでちょっと残念ですよね。ユーザ管理が冗長になると、作業ミス等で AD にはユーザが存在するけど RADIUS サーバにはユーザが存在しないといった状況が発生する可能性があります。

 

実現したいこと

以下の構成にて MFA を使ってAmazon WorkSpaces を利用したいと考えています。また AWS Managed Microsoft AD ではなく Amazon EC2 で AD を運用している環境に Amazon WorkSpaces を新規導入したいので、AD ユーザを参照するには Active Directory Connector(以降、AD Connector)を使います。RADIUS サーバは Amazon Linux 2 に FreeRADIUS をインストールします。この構成で、AD のユーザと RADIUS のワンタイムパスワードだけを使って認証することが今回の実現したいことです。

上記構成の Amazon EC2 で AD を構成・運用している環境では「mfa.test」というドメインがあり、そこに「nasu1」というユーザがいる前提で以降の手順を実施します。Amazon EC2 の IP アドレスは 10.255.0.120、FreeRADIUS の IP アドレスは 10.255.0.101 です。

AD Connector についての詳細は、AWS ドキュメント「Active Directory Connector」をご参照ください。

 

調査した結果

RADIUS サーバを AD ドメインに結合できれば、RADIUS サーバから AD ユーザを確認できます。そうすればローカルに AD と同名のユーザを作成する必要はないはずだと考えましたので、以下のように調査しました。

AWS ドキュメント「Linux インスタンスを手動で結合する」を参照すると、Linux インスタンスを AD ドメインに結合することはできそうです。Linux インスタンスを AD ドメインに結合すると、当然 AD ユーザを Linux インスタンスからも見ることができますね。

また、「Enable MFA for AWS managed AD using FreeRADIUS with google-authenticator」というブログ記事も見つけまして、ほぼやりたいことが実現できそうだと思ったのですが、Join host to Domain の項目を見ると AD ドメインへの結合には samba-winbind が使われていました。一方、AWS ドキュメント「Linux インスタンスを手動で結合する」では sssd が使われています。

できれば AWS ドキュメントを参照して Linux インスタンスを AD ドメインに結合している手順を基本として、AD ユーザだけを管理すればいいように RADIUS を構成する流れをご紹介した方がいいかなと思いました。ここまでの調査でほぼ必要な情報が揃ったので、実際に作成していきます。

 

設定の流れ

①RADIUS インスタンスの AD ドメインへの結合

  1. AWS ドキュメント「Linux インスタンスを手動で結合する」に記載の “ディレクトリへのインスタンスの結合” の手順を実行します。実行するのは “Amazon Linux” タブのステップ 5 までです。その後のステップは SSH 接続する際に必要となる手順なので、今回の要件では実行不要です。
    sudo yum -y update
    sudo yum -y install sssd realmd krb5-workstation samba-common-tools
    sudo realm join -U Administrator@mfa.test mfa.test --verbose
    
  2. AD ドメインに結合されたことを以下のコマンドと結果で確認しましょう。
    [ec2-user@ip-10-255-0-101 ~]$ id nasu1@mfa.test
    uid=1639401113(nasu1@mfa.test) gid=1639400513(domain users@mfa.test) groups=1639400513(domain users@mfa.test)

    この状態で id nasu1 とドメイン名なしで実行してもそんなユーザは存在しない旨のエラーが表示されます。もしドメイン名なしでユーザ名を指定できるようにしたい場合は、以下のように sssd の設定を変更しましょう。

    [ec2-user@ip-10-255-0-101 ~]$ sudo vi /etc/sssd/sssd.conf

    変更前:
    use_fully_qualified_names = True

    変更後:
    use_fully_qualified_names = False

  3. あとは sssd を再起動してテストしてみましょう。
    [ec2-user@ip-10-255-0-101 ~]$ sudo systemctl restart sssd
    [ec2-user@ip-10-255-0-101 ~]$ id nasu1
    uid=1639401113(nasu1) gid=1639400513(domain users) groups=1639400513(domain users)

    これで AD ドメインへの結合は完了です。

②FreeRADIUS の設定

FreeRADIUS の設定は、「多要素認証による Amazon WorkSpaces の利用」の p18 ~ 22 とほぼ同じです。

  1. FreeRADIUS と一緒に Google Authenticator もインストールしましょう。
    sudo amazon-linux-extras install -y epel
    sudo yum install -y freeradius freeradius-utils google-authenticator
  2. radiusd の設定ファイルを変更します。
    [ec2-user@ip-10-255-0-101 ~]$ sudo vi /etc/raddb/radiusd.conf

    認証ログをradius.logに出力する場合は、以下の箇所を yes に変更します。

    変更前:
    auth = no

    変更後:
    auth = yes

    radiusd を root で起動するよう、以下の箇所を変更します。

    変更前:

    user = radiusd
    group = radiusd

    変更後:

    user = root
    group = root
  3. 認証の際は PAM を使うように /etc/raddb/users を設定します。ここではグループでの制限は定義していません。
    [ec2-user@ip-10-255-0-101 ~]$ sudo vi /etc/raddb/users

    変更前:

    #DEFAULT        Group == "disabled", Auth-Type := Reject
    #               Reply-Message = "Your account has been disabled."
    #

    変更後:

    DEFAULT Auth-Type := PAM
    DEFAULT Group == "disabled", Auth-Type := Reject
            Reply-Message = "Your account has been disabled."
  4. 上記で設定した PAM を使えるように有効化します。
    [ec2-user@ip-10-255-0-101 ~]$ sudo vi /etc/raddb/sites-available/default

    変更前:

        #  Pluggable Authentication Modules.
    #    pam

    変更後:
    ※違いがわかりにくいですが、pam と書かれた行のコメントを外すだけです。

        #  Pluggable Authentication Modules.
        pam
  5. PAM モジュールを使えるようにシンボリックリンクを追加しましょう。
    [ec2-user@ip-10-255-0-101 ~]$ sudo ln -s /etc/raddb/mods-available/pam /etc/raddb/mods-enabled/pam
  6. PAM で認証する場合に Google Authenticator のモジュールを使うように設定します。
    [ec2-user@ip-10-255-0-101 ~]$ sudo vi /etc/pam.d/radiusd

    変更前:

    %PAM-1.0
    auth       include     password-auth
    account    required    pam_nologin.so
    account    include     password-auth
    password   include     password-auth
    session    include     password-auth

    変更後:
    ※変更前のものをすべてコメントアウトし、最後に 3 行追記します。

    #%PAM-1.0
    #auth       include     password-auth
    #account    required    pam_nologin.so
    #account    include     password-auth
    #password   include     password-auth
    #session    include     password-auth
    auth requisite pam_google_authenticator.so
    account required pam_permit.so
    session required pam_permit.so
  7. RADIUS クライアントとの接続情報を追加します。
    [ec2-user@ip-10-255-0-101 ~]$ sudo vi /etc/raddb/clients.conf

    ファイルの末尾に以下を追記します。secret の文字列は後ほど AD Connector の設定でも必要となります。ランダムな文字列等を決めて定義しましょう。

    client WorkSpaces {
        secret = XXXXXXXXXX
        ipaddr = 10.255.0.0/16
    }
  8. 上記の設定が一通り完了したら、radiusd を起動しましょう。
    sudo systemctl start radiusd
    sudo systemctl enable radiusd

    これで FreeRADIUS の設定は完了です。

③AD ユーザの MFA 設定

  1. nasu1 ユーザが MFA を利用できるように Google Authenticator を設定します。ユーザの数だけ実行する必要がありますが、この手順は避けて通れないのでなんとかがんばりましょう。スクリプト化して実行するのがよさそうですね。
    [ec2-user@ip-10-255-0-101 ~]$ sudo -u nasu1@mfa.test /usr/bin/google-authenticator -t -d -f -w 17 -r 3 -R 30

    多要素認証による Amazon WorkSpaces の利用」の p24 では対話モードで実行していますが、スクリプト等で実行する場合は上記のようにオプションをすべてつけて実行する方がいいと思います。また、生成される QR コードを表示するための URL が表示されますが、以下のコマンドでいつでも表示することができます。/home/nasu1@mfa.test/.google_authenticator ファイルの先頭にシークレットキーが書かれているので、それを URL に埋め込んでいるだけです。

    echo https://www.google.com/chart?chs=200x200&chld=M|0&cht=qr&chl=otpauth://totp/nasu1@mfa.test@ip-10-255-0-101.mfa.test%3Fsecret%3D`sudo sed -n 1p /home/nasu1@mfa.test/.google_authenticator`%26issuer%3Dip-10-255-0-101.mfa.test
  2. 生成された URL を Amazon WorkSpaces を利用するユーザに連絡します。ユーザはこの URL にアクセスして、スマートフォンで Google Authenticator 等の MFA アプリケーションで QR コードを読み取ります。これでワンタイムパスワードが生成されるはずです。MFA アプリケーションは Google Authenticator 以外のものでも問題ありません。私は Twilio Authy を使っています。Twilio Authy の場合は、以下の画像のようにワンタイムパスワードが表示されていれば完了です(デザインは環境ごとに自由に設定できます)。

④RADIUS での ワンタイムパスワードのテスト

  1. FreeRADIUS でワンタイムパスワードが受け付けられることを確認するため、RADIUS クライアントをインストールしたテスト用の Amazon Linux 2 インスタンスを起動しましょう。RADIUS クライアントのインストールは以下のコマンドを実行すれば完了です。
    sudo yum install -y freeradius freeradius-utils
  2. 以下コマンドを実行してワンタイムパスワードが有効かどうかを確認します。137036 の部分は MFA アプリケーションで表示されているコードを入力しましょう。10.255.0.101 の部分は RADIUS サーバの IP アドレスです。末尾の XXXXXXXXXX は、RADIUS サーバの /etc/raddb/clients.conf で定義した secret の文字列です。
    [ec2-user@ip-10-255-0-17 ~]$ radtest nasu1@mfa.test 137036 10.255.0.101 0 XXXXXXXXXX

    以下のような出力であれば正常にワンタイムパスワードが受け付けられています。

    Sent Access-Request Id 165 from 0.0.0.0:45094 to 10.255.0.101:1812 length 84
            User-Name = "nasu1@mfa.test"
            User-Password = "137036"
            NAS-IP-Address = 10.255.0.17
            NAS-Port = 0
            Message-Authenticator = 0x00
            Cleartext-Password = "137036"
    Received Access-Accept Id 165 from 10.255.0.101:1812 to 0.0.0.0:0 length 20

⑤AD Connector の作成

  1. AD Connector を作成する前に、AD で AWS ドキュメント「AD Connector の前提条件」の権限をサービスアカウントに委任するに記載されている手順を実行して AD Connector 用のサービスアカウントを作成しておく必要があります。今回は adconn1 というユーザを事前に作成しました。
  2. AD Connector を以下のコマンドで作成します。このコマンド実行には AWS CLI v2 が作業 PC で使える状態である必要があります。AWS CloudFormation テンプレートを作成しようとしたのですが、残念ながら AD Connector リソースが AWS CloudFormation に対応していなかったので AWS CLI v2 を使いました。もし AWS CLI が使えないようなら、AWS マネジメントコンソールから同様の作業を実施しましょう。
    password の部分はAD Connector 用のサービスアカウントのパスワードを指定します。今回の例では adconn1 ユーザのパスワードとなります。CustomerDnsIps の部分は Amazon EC2 の IP アドレスを指定します。

    aws ds connect-directory --name mfa.test --password "YYYYYYYYYY" --size Small \
        --connect-settings VpcId=vpc-11111111111111111,SubnetIds=subnet-11111111111111111,subnet-22222222222222222,CustomerDnsIps=10.255.0.120,CustomerUserName=adconn1
  3. AD Connector が作成されたら、以下のコマンドで RADIUS を有効化します。RadiusServers の部分は RADIUS サーバの IP アドレス、SharedSecret の部分は RADIUS サーバの /etc/raddb/clients.conf で定義した secret の文字列を指定します。
    aws ds enable-radius --directory-id d-1111111111 \
        --radius-settings RadiusServers=10.255.0.101,RadiusPort=1812,RadiusTimeout=10,RadiusRetries=3,SharedSecret=XXXXXXXXXX,AuthenticationProtocol=PAP,DisplayLabel=radius-test
  4. 上記の RADIUS 有効化コマンドが成功したら、以下のコマンドで設定値が正しいこととステータスが「Completed」になっていることを確認しましょう。
    $ aws ds describe-directories --directory-ids d-1111111111 | jq '.DirectoryDescriptions[] | {"RadiusSettings": .RadiusSettings, "RadiusStatus": .RadiusStatus}'
    {
      "RadiusSettings": {
        "RadiusServers": [
          "10.255.0.101"
        ],
        "RadiusPort": 1812,
        "RadiusTimeout": 10,
        "RadiusRetries": 3,
        "SharedSecret": "",
        "AuthenticationProtocol": "PAP",
        "DisplayLabel": "radius-test",
        "UseSameUsername": false
      },
      "RadiusStatus": "Completed"
    }

⑥Amazon WorkSpaces の作成

  1. Amazon WorkSpaces を作成するには、最初にバンドル ID を調べておく必要があります。バンドルとは、簡単に説明すると OS と仮想デスクトップのスペックの組み合わせです。バンドルについての詳細は「WorkSpace バンドルとイメージ」をご参照ください。
    バンドル ID を以下のコマンドで確認します。PCoIP で絞っている理由は、WSP がまだ Beta 版で本稼働環境での利用が推奨されないためです。いくつかのバンドルの情報が表示されますので、必要に応じて使いたいバンドルのバンドル ID をメモしましょう。今回は Standard with Windows 10 を使います。

    $ aws workspaces describe-workspace-bundles --owner AMAZON | jq '.Bundles[] | select((.Description | contains("PCoIP")) and (.ComputeType.Name == "STANDARD"))| {"BundleId": .BundleId, "Name": .Name, "ComputeType": .ComputeType.Name, "Description": .Description}'
    ...
    {
      "BundleId": "wsb-8vbljg4r6",
      "Name": "Standard with Windows 10",
      "ComputeType": "STANDARD",
      "Description": "Windows 10 Experience provided by Windows Server 2016 with PCoIP 2 vCPU 4GiB Memory 50GB Storage"
    }
    ...
  2. では先ほど確認したバンドル ID を使って Amazon WorkSpaces を作成しましょう。Amazon WorkSpaces の作成には多くのパラメータ指定が必要ですので、json 形式であらかじめ定義しておきます。以下の内容で create-workspaces.json ファイルを作成します。
    {
        "Workspaces": [
            {
                "DirectoryId": "d-1111111111",
                "UserName": "nasu1@mfa.test",
                "BundleId": "wsb-8vbljg4r6",
                "VolumeEncryptionKey": "alias/aws/workspaces",
                "UserVolumeEncryptionEnabled": true,
                "RootVolumeEncryptionEnabled": true,
                "WorkspaceProperties": {
                    "RunningMode": "AUTO_STOP",
                    "RunningModeAutoStopTimeoutInMinutes": 60,
                    "RootVolumeSizeGib": 80,
                    "UserVolumeSizeGib": 50,
                    "ComputeTypeName": "STANDARD"
                }
            }
        ]
    }
  3. create-workspaces.json ファイルを作成したら、以下のコマンドで Amazon WorkSpaces を作成しましょう。State が PENDING で結果が返ってきたら作成成功です。Amazon WorkSpaces が利用可能になるまでは約 20 分かかりますので、それまで待ちましょう。
    $ aws workspaces create-workspaces --cli-input-json file://create-workspaces.json
    {
        "FailedRequests": [],
        "PendingRequests": [
            {
                "WorkspaceId": "ws-zzzzzzzzzz",
                "DirectoryId": "d-1111111111",
                "UserName": "nasu1",
                "State": "PENDING",
                "BundleId": "wsb-8vbljg4r6",
                "VolumeEncryptionKey": "alias/aws/workspaces",
                "UserVolumeEncryptionEnabled": true,
                "RootVolumeEncryptionEnabled": true
            }
        ]
    }
  4. Amazon WorkSpaces の作成が完了したら、登録コードを以下のコマンドで確認します。
    $ aws workspaces describe-workspace-directories --directory-ids d-1111111111 | jq -r '.Directories[].RegistrationCode'
    WSpdx+123456

    これで Amazon WorkSpaces を利用する準備が整いました。

Amazon WorkSpaces への接続

  1. ここからは Amazon WorkSpaces を利用するユーザの PC での作業になります。まずは Amazon WorkSpaces クライアントをインストールして起動しましょう。起動したら、Change Registration Code をクリックします。以降の Amazon WorkSpaces の画面がすべて英語表記になっていますが、言語設定で簡単に日本語表記に変更することもできます。本記事ではこのまま英語表記の画面でご説明します。
  2. ここで先ほど確認した登録コードを入力して Register ボタンを押しましょう。これによって、これまでの手順で作成した Amazon WorkSpaces に接続できるようになります。
  3. では実際に Amazon WorkSpaces に接続してみましょう。ユーザ名、パスワード、ワンタイムパスワードを入力して Sign In ボタンを押すだけです。
  4. RADIUS サーバでドメイン名をつけなくても認証できるように設定した場合は、このようにドメイン名を省略してユーザ名を指定することもできます。
  5. AD および RADIUS で認証されると、このように Amazon WorkSpaces の画面が表示されます。これで AD ユーザとワンタイムパスワードだけで Amazon WorkSpaces を利用できる環境が完成しました!

さいごに

FreeRADIUS を使って AD ユーザとワンタイムパスワードを組み合わせた多要素認証による Amazon WorkSpaces の利用方法についてお伝えしました。この方法であれば、EC2 インスタンスのローカルにユーザを作成することなく MFA を利用できることがおわかりいただけたと思います。まだまだ今の状況は続きそうですし新たな働き方が普通になりつつありますので、Amazon WorkSpaces をはじめ AWS Client VPN や Amazon AppStream 2.0 も活用してどこでも業務に対応できる環境を作っていきましょう。



 

以上が、APN Ambassador である株式会社BeeX 那須 隆 様より、寄稿いただいた内容となります。那須様、ありがとうございました!第四弾もご期待いただければと思います。