redhat6にmod_auth_mellonをインストール

## はじめに
redhat6のapache2.2にmod_auth_mellonを導入しました。
試行錯誤の末に何とか動くようになりましたが大変時間がかかりました。
他の方が同じ思いをしないよう手順を共有します。
もう二度とやらないと思うので細かい説明は省略します。

## 環境
* redhat6
* Apache2.2
* IdP: Microsoft Azure Active Directory

## mod_auth_mellonインストール
### rpmダウンロード
https://pkgs.org/ から以下のファイルを作業用ディレクトリにダウンロードします。

* lasso-2.3.6-1.el6.x86_64.rpm
* xmlsec1-1.2.20-4.el6.x86_64.rpm
* xmlsec1-openssl-1.2.20-4.el6.x86_64.rpm
* mod_auth_mellon-0.5.0-1.el6.x86_64.rpm
* xmlsec1-devel-1.2.20-4.el6.x86_64.rpm
* xmlsec1-openssl-devel-1.2.20-4.el6.x86_64.rpm

**lasso2.3は認証後のSP側でエラーが発生するため使えませんが、mellonインストール時の「依存性の欠如」エラー解消のため一旦lasso2.3を入れます。**
後でlasso2.6をソースからインストールします。

### rpmインストール
作業用ディレクトリで以下を実行します。

```bash
# rpm -Uvh *
```

## lasso2.6インストール
### 準備
以下の作業は試行錯誤の過程で行ったことなので本当に必要かは不明です。

```bash
# export PKG_CONFIG_PATH=/usr/lib64/pkgconfig
# ln -s /usr/lib64/libltdl.so.7.2.1 /usr/lib64/libltdl.so
# pip install 'requests[security]'
# pip install six
# cp /usr/lib/python2.6/site-packages/six.py /usr/lib64/python3.4
```

### lasso2.6ダウンロード
https://repos.entrouvert.org/lasso.git から以下をダウンロードして解凍します。

* lasso-2.6.0.tar.gz

### lasso2.6インストール
lasso-2.6.0ディレクトリで以下を実行します。

```bash
# ./autogen.sh
# make install
```
make install の途中でシンタックスエラーが発生し停止します。
node.xmlの452と453行目の\<para>と\</para>の順番が逆なので修正して再度 make install します。
make install が正常終了したら以下を実行します。

```bash
ln -nfs /usr/local/lib/liblasso.so.3.13.0 /usr/lib64/liblasso.so
ln -nfs /usr/local/lib/liblasso.so.3.13.0 /usr/lib64/liblasso.so.3
```
ディレクトリはご自分の環境に合わせて読み替えて下さい。

## mod_auth_mellonの設定
### mellon_create_metadata.shの取得
/etc/httpd/saml ディレクトリを作成します。
https://gist.github.com/michaelrice/3c052dce7b1e2e1bf46e224c4e9bb692 
から mellon_create_metadata.sh を取得して /etc/httpd/saml に保存します。

### mellon_create_metadata.shの実行
/etc/httpd/saml ディレクトリで以下を実行します。

```bash
# ./mellon_create_metadata.sh \
  -k https_www.example.com_mellon_metadata.key \
  -c https_www.example.com_mellon_metadata.cert \
  -m https_www.example.com_mellon_metadata.xml \
  -e https://www.example.com/mellon/metadata \
  -b https://www.example.com/mellon
```
このコマンド実行後に出来た、
<pre>https_www.example.com_mellon_metadata.xml</pre>
をAzure ADの「メタデータファイルをアップロードする」でアップロードします。
アップロードして保存したら[フェデレーション メタデータ XML]をダウンロードして /etc/httpd/saml ディレクトリに保存します。

### auth_mellon.confの編集
/etc/httpd/conf.d/auth_mellon.conf に以下を追加します。

```html
<Location />
        MellonVariable "cookie"
        MellonSecureCookie On
        MellonCookiePath /
        MellonUser "NAME_ID"
        MellonProbeDiscoveryTimeout 30

        MellonEndpointPath "/mellon"
        MellonSPPrivateKeyFile /etc/httpd/saml/https_www.example.com_mellon_metadata.key
        MellonSPCertFile       /etc/httpd/saml/https_www.example.com_mellon_metadata.cert
        MellonSPMetadataFile   /etc/httpd/saml/https_www.example.com_mellon_metadata.xml
        MellonIdPMetadataFile "/etc/httpd/saml/test.xml"
        MellonSamlResponseDump On
        MellonSessionDump On
</Location>

<Location /test>
        Require valid-user
        AuthType "Mellon"
        MellonEnable "auth"
</Location>
```

### テスト
Azure ADのユーザーをエンタープライズ アプリケーションに追加して
https://www.example.com/test/
にアクセスし、Azure ADのログイン画面を経てtestディレクトリの中身が見られれば完了です。

## ハマった事
#### リバースプロキシ構成の場合
https://www.example.com/mellon ディレクトリをProxyPathの例外にする必要があります。

```diff
+   ProxyPass /mellon !
    ProxyPass        /  http://localhost:3000/
    ProxyPassReverse /  http://localhost:3000/
```

#### ドキュメントルートをWordPressが使っている場合
(ドキュメントルート)/.htaccess に以下を追加します。

```diff
    RewriteRule ^index.html$ index.php?url=/top/ [QSA,L]
    RewriteCond %{REQUEST_FILENAME} !-d
    RewriteCond %{REQUEST_FILENAME} !-f
+   RewriteCond %{REQUEST_URI} !(^/mellon/)
    RewriteRule ^(.*)$ index.php?url=$1 [QSA,L]
```

#### Cybozu等の別サイト内にiframe表示した自サイトがChrome80以降BadRequestになる場合
Locationに

```diff
+   MellonCookieSameSite none
```
を追加することで解消されるようですが、この機能は mod_auth_mellon のバージョン 0.16.0 以降で有効であるため redhat6 では利用不可でした。

##### クライアント側でChromeの設定を変えることで暫定対応可能です。
1. Chromeブラウザで chrome://flags/ にアクセス
2. 検索窓に「SameSite」と入力
3. [SameSite by default cookies]と[Cookies without SameSite must be secure]の２項目を[Default]から[Disabled]に変更
4. 画面右下隅の[Relaunch]をクリック