らくがきちょう

なんとなく

Amazon Linux2 に Samba 4.11.1 + FreeRADIUS 3.0.13 + Keycloak 7.0.1 をインストールする

以前に Samba4 / FreeRADIUS3 / Keycloak6 の構築に関して、下記のメモを書きました。

Samba 4.11.1 や Keycloak 7.0.1 がリリースされている為、インストール手順をアップデートしておきます。

目次

ゴール

今回は最終的に以下の環境を構築します。

  • Amazon Linux release 2 (Karoo)
    • Python 3.7.4
    • Samba 4.11.1
    • Keycloak 7.0.1
    • Nginx 1.17.4

図示すると以下のようになります。

f:id:sig9:20191019135146p:plain

この構成は以下の特徴を持ちます。

  • 一台の Amazon Linux2 内に FreeRADIUS、Samba、Keycloak を同居させ、様々な認証プロトコルに対応させる
  • 認証ソース自体は Samba で一元管理する
  • Keycloak は Samba と定期的に同期し、ユーザ情報をキャッシュする
  • (認証情報をキャッシュしない為) FreeRADIUS は RADIUS 認証要求を受ける度に Samba へ問い合わせする
  • ユーザのパスワード変更は以下、どちらでも可能
    • Samba でもパスワード変更可能
    • Keycloak でもパスワード変更可能
  • Samba と Keycloak は認証情報を同期するので、どちらでパスワード変更しても問題無い
    • KeyCloak 側でパスワード変更した場合、即時 Samba と同期する
    • Samba 側でパスワード変更した場合、Keycloak ~ Samba 間の同期が実行されるまで、パスワードは同期されない (Keycloak 側から手動で強制同期させることは可能)

Samba のインストール

EPEL の有効化

Samba をインストールする事前準備として、前提となるパッケージをインストールします。 EPEL (Extra Packages for Enterprise Linux) からパッケージをインストールすることになりますが、AmazonLinux2 なので amazon-linux-extras を使って EPEL リポジトリをインストールします。

yes | amazon-linux-extras install epel

必要パッケージのインストール

必要なパッケージをインストールしていきます。 Amazon Linux2 は初期状態で Python2 がインストールされています。 しかし、Samba 4.11 のリリースノート の REMOVED FEATURES 欄によると 4.11 からは Python2 サポートが無くなったようです。

Samba 4.11 will not have any runtime support for Python 2.

If you are building Samba using the '--disable-python' option (i.e. you're excluding all the run-time Python support), then this will continue to work on a system that supports either python2 or python3.

その為、python3-devel をインストールし、Python3 が利用出来るようにします。

yum -y install \
    docbook-style-xsl \
    gcc \
    gdb \
    gnutls-devel \
    gpgme-devel \
    jansson-devel \
    keyutils-libs-devel \
    krb5-workstation \
    libacl-devel \
    libaio-devel \
    libarchive-devel \
    libattr-devel \
    libblkid-devel \
    libtasn1 \
    libtasn1-tools \
    libxml2-devel \
    libxslt \
    lmdb-devel \
    openldap-devel \
    perl \
    perl-ExtUtils-MakeMaker \
    perl-Parse-Yapp \
    popt-devel \
    python3-devel \
    readline-devel \
    systemd-devel \
    tar \
    zlib-devel

追加で pam-devel もインストールします。 先にインストールしたパッケージ群と同時に pam-devel をインストールしようとすると上手くいかない (pam-devel がインストールされない) 為、pam-devel は別にインストールします。

yum -y install pam-devel

ソースコードからインストールする

現時点ではリポジトリからインストール出来るのは 4.8.3 とバージョンがやや古く、少なくても 2 カ月以上アップデートされていません。 しかも、この 4.8.3 のパッケージには Samba をドメインコントローラとして構築する際には多用することになる samba-tool がなぜかインストールされません。 この件についてはネット上でも How to install samba-tool on Amazon Linux と質問されている方がおり、現時点では回答されていません。

# yum info samba
Loaded plugins: extras_suggestions, langpacks, priorities, update-motd
187 packages excluded due to repository priority protections
Available Packages
Name        : samba
Arch        : x86_64
Version     : 4.8.3
Release     : 4.amzn2.0.1
Size        : 682 k
Repo        : amzn2-core/2/x86_64
Summary     : Server and Client software to interoperate with Windows machines
URL         : http://www.samba.org/
License     : GPLv3+ and LGPLv3+
Description : Samba is the standard Windows interoperability suite of programs for Linux and
            : Unix.

その為、今回はソースコードから Samba をインストールしていきます。 Samba 4.10 系までは PYTHON=python2 を指定することで Python2 で Samba をビルド出来たのですが、Samba 4.11 系からは Python2 系がサポートされなくなりました。 しかし、今回は Python3 をインストールしてあるので、Python バージョンを指定せず、そのまま ./configure; make; make install します。

mkdir -p /usr/local/src/samba/
cd /usr/local/src/samba/
wget https://download.samba.org/pub/samba/samba-latest.tar.gz
tar zxvf samba-latest.tar.gz
cd samba-4.11.1/
./configure
make
make install

パスを追加する

ソースコードから Samba をインストールした場合、パスを指定しない限り実行ファイルは /usr/local/samba/bin 配下にインストールされます。 標準でここにはパスが通っていない為、利便性を考えてパスを通しておきます。 今回は root ユーザで操作することだけを想定し、/root/.bash_profile にパスを追加しました。

echo "export PATH=\"/usr/local/samba/bin:/usr/local/samba/sbin:${PATH}\"" >> ~/.bash_profile

パス追加後は source ~/.bash_profile するか、または SSH アクセスをログアウト / ログインし直してパス追加を反映します。 これで Samba のインストールは完了です。

ドメインの設定

次はドメインを設定していきます。

ドメインの作成

まず、ドメイン自体を新規作成します。 対話的にドメインを構築する場合は以下のように実行します。

samba-tool domain provision --use-rfc2307 --interactive

ある程度、パラメータを指定して非対話的に構築する場合は以下のように実行します。 非対話式の実行オプションを見る限り、DNS Forwarder の指定が見当たらないようですが、実際に非対話で実行した後で生成される設定ファイルを確認すると、「予め /etc/resolv.conf に設定されていた DNS サーバ」を DNS Forwarder として設定されていました。

samba-tool domain provision \
  --use-rfc2307 \
  --realm=EXAMPLE.COM \
  --server-role=dc \
  --dns-backend=SAMBA_INTERNAL \
  --domain=EXAMPLE \
  --adminpass="PASSWORD"

ドメインを構築すると設定ファイルは /usr/local/samba/etc/smb.conf に生成されます。 例えば以下のような内容になっているはずです。

# Global parameters
[global]
        dns forwarder = 192.168.1.2
        netbios name = AD
        realm = EXAMPLE.COM
        server role = active directory domain controller
        workgroup = EXAMPLE
        idmap_ldb:use rfc2307 = yes

[netlogon]
        path = /usr/local/samba/var/locks/sysvol/example.com/scripts
        read only = No

[sysvol]
        path = /usr/local/samba/var/locks/sysvol
        read only = No

LDAPS を強制しない設定

初期状態では LDAPS を強制する設定になっているようです。 セキュリティ上はこの方が好ましいですが、検証上の理由から LDAPS を強制しない設定へ変更するには /usr/local/samba/etc/smb.conf の [global] セクションへ以下を追加します。

        client ldap sasl wrapping = sign
        ldap server require strong auth = no

LDAPS 接続用のサーバ証明書を用意する

LDAPS 接続にサーバ証明書を用意します。 自己証明書なり、Let's Encrypt で取得するなり、いずれかの方法で用意します。 取得した証明書や秘密鍵/etc/letsencrypt/certificates に配置するものとします。

mkdir -p /etc/letsencrypt/certificates

証明書 / 秘密鍵パーミッションを修正し、所有者以外はアクセス出来ないようにしておきます。

chmod 600 /etc/letsencrypt/certificates/*

配置した証明書 / 秘密鍵を参照するよう、/usr/local/samba/etc/smb.conf の [global] セクションに下記を追加します。

        tls enabled = yes
        tls keyfile = /etc/letsencrypt/certificates/example.com.key
        tls certfile = /etc/letsencrypt/certificates/example.com.crt
        tls cafile = /etc/letsencrypt/certificates/example.com.issuer.crt

パスワードポリシーの設定

Samba のパスワードポリシーは samba-tool domain passwordsettings show で確認出来ます。 Samba 4.11.1 の初期状態では以下のようになっていました。

# samba-tool domain passwordsettings show
Password information for domain 'DC=example,DC=com'

Password complexity: on
Store plaintext passwords: off
Password history length: 24
Minimum password length: 7
Minimum password age (days): 1
Maximum password age (days): 42
Account lockout duration (mins): 30
Account lockout threshold (attempts): 0
Reset account lockout after (mins): 30

各々の項目は以下の意味を持ちます。

No. Item Default Description
1 Password complexity on パスワードの複雑さを強制するか (英数記号混在、3 文字以上、ユーザ名を含まない)
2 Store plaintext passwords off 平文でパスワードを保存するか
3 Password history length 24 保存するパスワードの世代数
4 Minimum password length 7 パスワード長の最小
5 Minimum password age (days) 1 パスワード変更禁止期間 (0 だと即時変更可能)
6 Maximum password age (days) 42 パスワード有効期限 (0 だと無期限)
7 Account lockout duration (mins) 30 「Account lockout threshold」で定義された回数、パスワード入力を間違えた場合にロックアウトする期間
8 Account lockout threshold (attempts) 0 パスワード入力に失敗を許容する回数 (0 だとロックアウトしない)
9 Reset account lockout after (mins) 30 パスワード試行回数がゼロに戻るまでの時間

デフォルトから以下のように変更します。

  1. パスワード長の最小を「8」へ変更
  2. パスワード変更禁止期間を「0」へ設定 (パスワードを即時、変更可能にする)
  3. パスワード変更期間を「0」へ設定 (パスワードを無期限にする)
  4. パスワードがロックアウトされるまでの入力試行回数を「5」へ設定 (5 回連続でパスワードを間違えるとロックアウト)

実際には以下のコマンドで変更します。

samba-tool domain passwordsettings set --min-pwd-length=8
samba-tool domain passwordsettings set --min-pwd-age=0
samba-tool domain passwordsettings set --max-pwd-age=0
samba-tool domain passwordsettings set --account-lockout-threshold=5

変更後のパスワードポリシーは以下のように表示されます。

# samba-tool domain passwordsettings show
Password information for domain 'DC=example,DC=com'

Password complexity: on
Store plaintext passwords: off
Password history length: 24
Minimum password length: 8
Minimum password age (days): 0
Maximum password age (days): 0
Account lockout duration (mins): 30
Account lockout threshold (attempts): 5
Reset account lockout after (mins): 30

DNS 設定の変更

DNS の設定は以下の方針で変更します。

  • AmazonLinux2 自身が参照する DNS サーバを自分自身 (127.0.0.1) にする
  • SAMBA_INTERNAL な DNS サービスの DNS Forwarder は Amazon 提供の DNS サーバにする

初期状態のままでは DNS の設定を変更しても OS を再起動する度… というより、正確には DHCP Client が実行される度、DHCP サーバから受信した DNS サーバ設定を上書きしてしまいます。 これを避ける為、DHCP の設定を変更し、DNS 関連のパラメータは受信しない (上書きしない) ようにします。 具体的には /etc/sysconfig/network-scripts/ifcfg-eth0 のうち、PEERDNS=yesno へ変更します。

DEVICE=eth0
BOOTPROTO=dhcp
ONBOOT=yes
TYPE=Ethernet
USERCTL=yes
PEERDNS=no
DHCPV6C=yes
DHCPV6C_OPTIONS=-nw
PERSISTENT_DHCLIENT=yes
RES_OPTIONS="timeout:2 attempts:5"
DHCP_ARP_CHECK=no

ワンライナーで実行したければ以下のようにします。

sed -i -e "s/PEERDNS=yes/PEERDNS=no/g" /etc/sysconfig/network-scripts/ifcfg-eth0

これで DNS 関連の設定は上書きされなくなりました。 続いて OS が参照する DNS サーバのアドレスを変更します。 対象の設定ファイルは /etc/resolv.conf です。 変更前は以下のようになっているはずです。

options timeout:2 attempts:5
; generated by /usr/sbin/dhclient-script
search ap-northeast-1.compute.internal example.com
nameserver 192.168.1.2

これを以下のように nameserver 127.0.0.1 へ書き換えます。

options timeout:2 attempts:5
; generated by /usr/sbin/dhclient-script
search ap-northeast-1.compute.internal example.com
nameserver 127.0.0.1

設定ファイルの修正が完了したら network サービスを再起動し、設定変更を反映します。

systemctl restart network

起動&自動起動の設定

今回はパッケージマネージャでは無く、ソースコードから Samba をインストールした為、systemd 用のスクリプトがありません。 その為、以下の内容で systemd 用のスクリプトを新規作成しておきます。 後で構築する FreeRADIUS も Keycloak も認証の一時ソースは Samba で行う為、Samba が停止しても自動的に再起動するよう Restart=always を指定しておきます。

cat << EOF > /etc/systemd/system/samba.service
[Unit]
Description= Samba 4 Active Directory
After=syslog.target
After=network.target
 
[Service]
Type=forking
PIDFile=/usr/local/samba/var/run/samba.pid
ExecStart=/usr/local/samba/sbin/samba
Restart=always
 
[Install]
WantedBy=multi-user.target
EOF

これで systemctl コマンドを通じての起動や自動起動が行えるようになりました。 ファイルを追加したので daemon-reload した後、Samba を起動&自動起動するようにしておきます。

systemctl daemon-reload
systemctl enable samba
systemctl start samba

OU / ユーザ / グループの作成

ドメインのセットアップが完了したので OU やユーザ、グループを作成していきます。 ほぼ全ての作業を samba-tool で実施していきます。 ここでは以下の作業を実施するものとします。

  1. ユーザ格納用に People という OU を作成する
  2. グループ格納用に Groups という OU を作成する
  3. Groups OU 内に Members というグループを作成する
  4. People OU 内に User1 ユーザを Pass1 というパスワードで作成する
  5. User1 ユーザのパスワード有効期限を「無期限」にする
  6. User1 ユーザを Members グループに所属させる

この要件を満たす場合、実行するコマンドは以下の通りです。

samba-tool ou create 'OU=People,DC=example,DC=com'
samba-tool ou create 'OU=Groups,DC=example,DC=com'

samba-tool group add Members --groupou='OU=Groups'

samba-tool user create User1 Pass1 --userou='OU=People'
samba-tool user setexpiry User1 --noexpiry

samba-tool group addmembers Members User1

FreeRADIUS のインストール

FreeRADIUS をインストールしていきます。

標準リポジトリからインストールする

現時点で AmazonLinux の標準リポジトリからインストール出来る FreeRADIUS のバージョンは 3.0.13 でした。

# yum info freeradius
Loaded plugins: extras_suggestions, langpacks, priorities, update-motd
187 packages excluded due to repository priority protections
Available Packages
Name        : freeradius
Arch        : x86_64
Version     : 3.0.13
Release     : 10.amzn2
Size        : 1.1 M
Repo        : amzn2-core/2/x86_64
Summary     : High-performance and highly configurable free RADIUS server
URL         : http://www.freeradius.org/
License     : GPLv2+ and LGPLv2+
Description : The FreeRADIUS Server Project is a high performance and highly configurable
            : GPL'd free RADIUS server. The server is similar in some respects to
            : Livingston's 2.0 server.  While FreeRADIUS started as a variant of the
            : Cistron RADIUS server, they don't share a lot in common any more. It now has
            : many more features than Cistron or Livingston, and is much more configurable.
            :
            : FreeRADIUS is an Internet authentication daemon, which implements the RADIUS
            : protocol, as defined in RFC 2865 (and others). It allows Network Access
            : Servers (NAS boxes) to perform authentication for dial-up users. There are
            : also RADIUS clients available for Web servers, firewalls, Unix logins, and
            : more.  Using RADIUS allows authentication and authorization for a network to
            : be centralized, and minimizes the amount of re-configuration which has to be
            : done when adding or deleting new users.

FreeRADIUS をインストールします。

yum -y install freeradius freeradius-ldap freeradius-utils

LDAP モジュールの設定

LDAP との接続は /etc/raddb/mods-available/ldap に定義されています。 設定例は以下の通りです。 ここでは「グループに応じて認証先を分けられる」ように、3 つの設定を行っています。

  1. ldap
  2. ldap admin (Admins グループで認証する)
  3. ldap members (Members グループで認証する)
ldap {
    server = "127.0.0.1"
    port = 389

    identity = "CN=Administrator,CN=Users,DC=example,DC=com"
    password = "PASSWORD"

    update {
        control:Password-With-Header += 'userPassword'
        reply:Reply-Message += 'distinguishedName'
    }

    edir = no
    user {
        base_dn = "OU=People,DC=example,DC=com"
        filter = "(sAMAccountName=%{%{Stripped-User-Name}:-%{User-Name}})"
    }
}
ldap admins {
    server = "127.0.0.1"
    port = 389

    identity = "CN=Administrator,CN=Users,DC=example,DC=com"
    password = "PASSWORD"

    update {
        control:Password-With-Header += 'userPassword'
        reply:Reply-Message += 'distinguishedName'
    }

    edir = no
    user {
        base_dn = "OU=People,DC=example,DC=com"
        filter = "(&(sAMAccountName=%{%{Stripped-User-Name}:-%{User-Name}})(memberOf=CN=Admins,OU=Groups,DC=example,DC=com"))"
    }
}
ldap members {
    server = "127.0.0.1"
    port = 389

    identity = "CN=Administrator,CN=Users,DC=example,DC=com"
    password = "PASSWORD"

    update {
        control:Password-With-Header += 'userPassword'
        reply:Reply-Message += 'distinguishedName'
    }

    edir = no
    user {
        base_dn = "OU=People,DC=example,DC=com"
        filter = "(&(sAMAccountName=%{%{Stripped-User-Name}:-%{User-Name}})(memberOf=CN=Members,OU=Groups,DC=example,DC=com))"
    }
}

ファイルの用意が出来たらシンボリックリンクを作成し、有効化します。

ln -s /etc/raddb/mods-available/ldap /etc/raddb/mods-enabled/ldap

サイトの設定

LDAP 認証毎のサイト設定を行います。 先の手順で LDAP 設定を 3 グループ作成したので、ここでは対になるサイトを 3 つ、定義します。

/etc/raddb/sites-available/ldap

cat << EOF > /etc/raddb/sites-available/ldap
server ldap {
    authorize {
        update {
            control:Auth-Type := ldap
        }
    }

    authenticate {
        Auth-Type ldap {
            ldap
        }
    }

    post-auth {
        Post-Auth-Type Reject {
        }
    }
}
WantedBy=multi-user.target
EOF

/etc/raddb/sites-available/ldap_admins

cat << EOF > /etc/raddb/sites-available/ldap_admins
server ldap_admins {
    authorize {
        update {
            control:Auth-Type := ldap
        }
    }

    authenticate {
        Auth-Type ldap {
            admins
        }
    }

    post-auth {
        update reply {
            cisco-avpair = "shell:priv-lvl=15",
            Juniper-Local-User-Name = "superuser"
        }
        Post-Auth-Type Reject {
        }
    }
}
EOF

/etc/raddb/sites-available/ldap_members

cat << EOF > /etc/raddb/sites-available/ldap_members
server ldap_members {
    authorize {
        update {
            control:Auth-Type := ldap
        }
    }

    authenticate {
        Auth-Type ldap {
            members
        }
    }

    post-auth {
        update reply {
            cisco-avpair = "shell:priv-lvl=15",
            Juniper-Local-User-Name = "superuser"
        }
        Post-Auth-Type Reject {
        }
    }
}
EOF

ファイルの用意が出来たらパーミッションとオーナーを修正してからシンボリックリンクを作成し、サイトを有効化します。

chown root:radiusd /etc/raddb/sites-available/ldap*
chmod 640 /etc/raddb/sites-available/ldap*

ln -s /etc/raddb/sites-available/ldap /etc/raddb/sites-enabled/ldap
ln -s /etc/raddb/sites-available/ldap_admins /etc/raddb/sites-enabled/ldap_admins
ln -s /etc/raddb/sites-available/ldap_members /etc/raddb/sites-enabled/ldap_members

クライアントの定義

cat << EOF > /etc/raddb/clients.conf
client 10.0.0.1/32 {
    ipaddr = 10.0.0.1
    netmask = 32
    secret = SECRET1
    virtual_server = ldap
}
client 10.0.0.2/32 {
    ipaddr = 10.0.0.2
    netmask = 32
    secret = SECRET2
    virtual_server = ldap_admins
}
client 10.0.0.3/32 {
    ipaddr = 10.0.0.3
    aetmask = 32
    secret = SECRET3
    virtual_server = ldap_members
}
EOF

起動&自動起動の設定

これで FreeRADIUS の設定は完了です。 デーモンを起動&自動起動設定します。

systemctl start radiusd
systemctl enable radiusd

認証テストを実施する

radtest を使うと RADIUS の認証テストを行うことが出来ます。 実行例は以下の通りです。

radtest [USERNAME] [PASSWORD] [ADDRESS] 0 [SECRET]

Keycloak のインストール

続いて Keycloak をインストールしていきます。

Java のインストール

Keycloak は Java で書かれている為、まず Java をインストールします。

amazon-linux-extras enable java-openjdk11
yum clean metadata
yum -y install java-11-openjdk

インストール

Keycloak をインストールするにはパッケージをダウンロードし、任意の位置に配置するだけです。 今回は /opt/keycloak 配下に配置しました。

curl -O https://downloads.jboss.org/keycloak/7.0.1/keycloak-7.0.1.tar.gz
tar zxvf keycloak-7.0.1.tar.gz
mv keycloak-7.0.1/ /opt/keycloak

管理用ユーザの作成

初期状態ではユーザが存在しないので、Keycloak を起動する前に管理ユーザを作成します。

/opt/keycloak/bin/add-user-keycloak.sh -r master -u [USERNAME] -p [PASSWORD]

proxy-address-forwarding の設定

今回は SSL/TLS 終端を Nginx に担当させる Reverse Proxy 構成にします。 その為、/opt/keycloak/standalone/configuration/standalone.xml の http-listner 定義箇所を探し、下記のように proxy-address-forwarding="true" の設定を追加します。

変更前

<http-listener name="default" socket-binding="http" redirect-socket="https" enable-http2="true"/>

変更後

<http-listener name="default" socket-binding="http" redirect-socket="https" enable-http2="true" proxy-address-forwarding="true"/>

ワンライナーで実行したい場合は以下のようにします。

sed -i -e "s/<http-listener name=\"default\" socket-binding=\"http\" redirect-socket=\"https\" enable-http2=\"true\"\/>/<http-listener name=\"default\" socket-binding=\"http\" redirect-socket=\"https\" enable-http2=\"true\" proxy-address-forwarding=\"true\"\/>/g" /opt/keycloak/standalone/configuration/standalone.xml

サービス登録 及び 起動&自動起動の設定

systemd から制御出来るよう、サービス登録を行います。

cat << EOF > /etc/systemd/system/keycloak.service
[Unit]
Description=Jboss Application Server
After=network.target

[Service]
Type=idle
Environment=JBOSS_HOME=/opt/keycloak JBOSS_LOG_DIR=/var/log/keycloak "JAVA_OPTS=
-Xms1024m -Xmx20480m -XX:MaxPermSize=768m"
User=root
Group=root
ExecStart=/opt/keycloak/bin/standalone.sh
TimeoutStartSec=600
TimeoutStopSec=600
Restart=always

[Install]
WantedBy=multi-user.target
EOF

用意が出来ましたので、自動起動&起動設定を実施します。 Keycloak が完全に起動するまでには、やや時間がかかるかも知れません。

systemctl daemon-reload
systemctl enable keycloak
systemctl start keycloak

Nginx のインストール

続いて Keycloak のフロントエンド用 Nginx をインストールします。

Nginx Mainline リポジトリからインストールする

AmazonLinux 標準リポジトリ上の Nginx は 1.12.2 とややバージョンが古いです。

# yum info nginx
Loaded plugins: extras_suggestions, langpacks, priorities, update-motd
187 packages excluded due to repository priority protections
Available Packages
Name        : nginx
Arch        : x86_64
Epoch       : 1
Version     : 1.12.2
Release     : 3.el7
Size        : 531 k
Repo        : epel/x86_64
Summary     : A high performance web server and reverse proxy server
URL         : http://nginx.org/
License     : BSD
Description : Nginx is a web server and a reverse proxy server for HTTP, SMTP, POP3 and
            : IMAP protocols, with a strong focus on high concurrency, performance and low
            : memory usage.

その為、Nginx の Mainline リポジトリからインストールします。 下記を実行し、Nginx 公式リポジトリを追加します

cat << EOF > /etc/yum.repos.d/nginx.repo
[nginx]
name=nginx repo
baseurl=http://nginx.org/packages/mainline/centos/\$releasever/\$basearch/
gpgcheck=1
enabled=1
gpgkey=https://nginx.org/keys/nginx_signing.key
EOF

現時点では Nginx 1.17.4 がインストールされるようです。

# yum info nginx
Loaded plugins: extras_suggestions, langpacks, priorities, update-motd
187 packages excluded due to repository priority protections
Available Packages
Name        : nginx
Arch        : x86_64
Epoch       : 1
Version     : 1.17.4
Release     : 1.el7.ngx
Size        : 767 k
Repo        : nginx/x86_64
Summary     : High performance web server
URL         : http://nginx.org/
License     : 2-clause BSD-like license
Description : nginx [engine x] is an HTTP and reverse proxy server, as well as
            : a mail proxy server.

Nginx をインストールします。

yum -y install nginx

Keycloak 用の設定追加

Nginx に Keycloak のフロントエンド処理をさせる為、以下の内容で /etc/nginx/conf.d/keycloak.conf を新規作成します。 証明書 / 秘密鍵は環境に応じて、パスを変更します。

cat << EOF > /etc/nginx/conf.d/keycloak.conf
upstream keycloak {
  server localhost:8080;
}

server {
    listen       80;
    server_name  www.example.com;
    return       301 https://\$host\$request_uri;
}

server {
    listen              443 ssl http2;
    server_name         www.example.com;
    ssl_certificate     /etc/letsencrypt/certificates/example.com.crt;
    ssl_certificate_key /etc/letsencrypt/certificates/example.com.key;
    ssl_protocols       TLSv1.1 TLSv1.2;
    ssl_ciphers         'ECDH !aNULL !eNULL !SSLv2 !SSLv3';

    proxy_set_header Host               \$host;
    proxy_set_header X-Real-IP          \$remote_addr;
    proxy_set_header X-Forwarded-Proto  \$scheme;
    proxy_set_header X-Forwarded-Host   \$host;
    proxy_set_header X-Forwarded-Server \$host;
    proxy_set_header X-Forwarded-For    \$proxy_add_x_forwarded_for;

    location / {
        proxy_pass http://keycloak;
        proxy_redirect http:// https://;
    }
}
EOF

起動&自動起動の設定

Nginx の自動起動&起動設定を実施しておきます。

systemctl enable nginx
systemctl start nginx

Keycloak の設定

ここからは Keycloak を設定していきます。

Step.1

ブラウザから https:://www.example.com (FQDN は環境に応じて修正) へアクセスすることで以下のように Keycloak のログイン画面が表示されることを確認します。 トップ画面が表示されることが確認出来たら Administration Console をクリックします。

f:id:sig9:20190804184216p:plain:w800

Step.2

管理ユーザ名とパスワードを入力してログインします。

f:id:sig9:20190804184225p:plain:w800

Step.3

デフォルトで Master という Realm が存在しています。 今回は新たに Relam を追加しますので、画面左上の Realm 名 (ここでは Master) にマウスカーソルを合わせ、表示されたメニューから Add realm をクリックします。

f:id:sig9:20190804184235p:plain:w800

Step.4

Name に追加したい Realm 名を入力します。 今回は Smaba 上の Members グループで認証させる想定とし、Realm 名は members にしました。

f:id:sig9:20190804184245p:plain:w800

Step.5

必須の設定ではありませんが、表示を日本語化することも可能です。 Realm の Themes はデフォルトで以下のようになっていました。

f:id:sig9:20190804185028p:plain:w800

Internationalization EnabledON にするとサポートされる言語の一覧が表示されます。 Default Localeja にし、Save をクリックします。

f:id:sig9:20190804185040p:plain:w800

Step.6

今回はユーザ認証を Samba ドメインで行います。 Keycloak からは LDAP で Samba へ接続しますので、画面左側にあるメニューから User Federation をクリックし、Add provider... から ldap をクリックします。

f:id:sig9:20190804185633p:plain:w800

Step.7

以下のように LDAP 接続用パラメータを入力する画面になります。

f:id:sig9:20191019150050p:plain

設定例は以下の通りです。

Required Settings

必須 項目 デフォルト値 設定例
Enabled ON ON
Console Display Name ldap ldap
Priority 0 0
Import Users ON ON
Edit Mode WRITABLE
Sync Registrations OFF OFF
* Vendor Active Directory
* Username LDAP attribute sAMAccountName
* RDN LDAP attribute sAMAccountName
* UUID LDAP attribute objectGUID
* User Object Classes person, organizationalPerson, user
* Connection URL ldap://127.0.0.1
* Users DN OU=People,DC=example,DC=com
* Bind Type simple simple
Enable StartTLS OFF OFF
* Bind DN CN=Administrator,CN=Users,DC=example,DC=com
* Bind Credential (Administrator のパスワード)
Custom User LDAP Filter (&(objectCategory=Person)(sAMAccountName=*)(memberOf=CN=Members,OU=Groups,DC=example,DC=com))
Search Scope One Level One Level
Validate Password Policy OFF OFF
Use Truststore SPI Only for ldaps Only for ldaps
Connection Pooling ON ON
Connection Timeout
Read Timeout
Pagination ON ON

Kerberos Integration

必須 項目 デフォルト値 設定例
Allow Kerberos authentication OFF OFF
Use Kerberos For Password Authentication OFF OFF

Sync Settings

必須 項目 デフォルト値 設定例
Batch Size 1000 1000
Periodic Full Sync OFF OFF
Periodic Changed Users Sync OFF OFF

Cache Settings

必須 項目 デフォルト値 設定例
Cache Policy DEFAULT DEFAULT

Step.8

初期設定では first Name の項目が cn 属性とマッピングされています。 これでは不都合なので first Name を (cn では無く) givennameマッピングし直します。 先ほど定義した LDAP の設定画面上部の Mappters を選択し、表示された項目の中から first Name をクリックして次に進みます。

f:id:sig9:20191019151313p:plain

first Name は、初期状態で以下の設定になっていました (LDAP Attribute が cn になっているのが分かります)。

f:id:sig9:20191019151323p:plain

以下のように LDAP Attribute を givenname に変更したら画面下部にある Save をクリックします。

f:id:sig9:20191019151333p:plain

Step.9

ここまでの設定が終わったら LDAP 設定の Settings 画面下部に幾つかボタンが表示されます。 このボタンのうち、Synchronize all users をクリックし、LDAP からユーザ情報を読み込みます。

f:id:sig9:20190806223009p:plain:w800

Step.10

左側のナビゲーションメニューから User を選択し、画面上部の View all users ボタンをクリックします。 LDAP と正しく連携出来ていれば、LDAP から読みだしたユーザ情報の一覧が表示されるはずです。

f:id:sig9:20190806223301p:plain:w800

Step.11

以降は SAMLOpenID Connect で認証を行う SP 側の設定を左側のナビゲーションメニューの Clients から実施していきます。

Keycloak からパスワードを変更する

Keycloak からパスワードを変更してみます。

Step.1

Keycloak からパスワードを変更するには、まずパスワードを変更したい Realm のユーザログイン画面へアクセスします。 URL は以下のようになります。

  • https://[FQDN]/auth/realms/[REALM]/account

例えば FQDN が「www.example.com」、Realm 名が「members」であれば URL は以下のようになります。

  • https://www.example.com/auth/realms/members/account

実際のログイン画面は以下の通りです。 ユーザ名とパスワードを入力してログインします。

f:id:sig9:20191019153319p:plain

Step.2

ログイン直後は アカウントの編集 画面が表示されます。 左側のナビゲーションメニューから パスワード をクリックします。

f:id:sig9:20191019153330p:plain

Step.3

パスワード変更 画面が表示されます。 現在のパスワードと変更後のパスワードを入力して 保存 をクリックします。 これでパスワード変更は完了です。

f:id:sig9:20191019153339p:plain