仮想化通信

日本仮想化技術株式会社の公式エンジニアブログ

最近のJuju Bundleで構築したOpenStackでOpenStack CLI (OSC) 実行時のエラーの対策

先日構築したOpenStackですが

tech.virtualtech.jp

いつものように手元の環境にOpenStack Clientを入れてコマンド操作しようとしたらエラーが発生し、うまくいきませんでした。エラー出力の結果からSSL周りのエラーであることがわかりました。

$ source admin-openrc.sh 
$ openstack server list
Readline features including tab completion have been disabled because
no supported version of readline was found. To resolve this, install
pyreadline on Windows or gnureadline on Mac.

Failed to discover available identity versions when contacting https://172.17.28.104:5000/v3. Attempting to parse version from URL.
SSL exception connecting to https://172.17.28.104:5000/v3/auth/tokens: HTTPSConnectionPool(host='172.17.28.104', port=5000): Max retries exceeded with url: /v3/auth/tokens (Caused by SSLError(SSLCertVerificationError(1, '[SSL: CERTIFICATE_VERIFY_FAILED] certificate verify failed: unable to get local issuer certificate (_ssl.c:1123)')))

JujuでOpenStackをデプロイする場合、Vaultを使った構成にするとValutからルートCAを取得し、openrcファイル内のそのファイルにOS_CACERT環境変数として参照させる必要があるようです。

stackoverflow.com

この環境はJujuを使って構築したOpenStackでした。そこで、Bundleに含まれるopenrcを確認してみます。

if [ -d ~/snap/openstackclients/common/ ]; then
  # When using the openstackclients confined snap the certificate has to be
  # placed in a location reachable by the clients in the snap.
  _root_ca=~/snap/openstackclients/common/root-ca.crt
else
  _root_ca=/tmp/root-ca.crt
fi
juju run $_juju_model_arg --unit vault/leader 'leader-get root-ca' | tee $_root_ca >/dev/null 2>&1

別のopenrcをみたら、次のように定義されていました。

if [ ! -z "$_root_ca" -a -s "$_root_ca" ]; then
    export OS_AUTH_PROTOCOL=https
    export OS_CACERT=${_root_ca}
fi

そこでとりあえずこの環境を構築したときに使った環境にOpenStack Clientが入っていたので、openrcを読み込んで変数に何が入っているか調べてみました。

$ source openrc
Using Keystone v3 API
$ echo $OS_CACERT
/home/user/snap/openstackclients/common/root-ca.crt

この環境はsnapインストールでOpenStack Clientをインストールしていました。このroot-ca.crtを手元の環境でも持ってくればアクセスできそうです。このファイル(root-ca.crt)をscpコマンドなどでクライアントにコピーします。

Horizonなどからエクスポートしてきたopenrcにexport OS_CACERT行を追加して、root-ca.crtをコピーしたパスを指定します。

export OS_AUTH_URL=https://172.17.28.104:5000/v3
export OS_CACERT=/Users/user/working/openstack/juju/root-ca.crt ←追加した行

OS_CACERTを書き加えたopenrcを読み込むと、OpenStack Clientを使うことができるようになります。

$ source admin-openrc.sh 
$ openstack server list
Readline features including tab completion have been disabled because
no supported version of readline was found. To resolve this, install
pyreadline on Windows or gnureadline on Mac.

+--------------------------------------+--------+--------+-------------------------------------+-------+---------+
| ID                                   | Name   | Status | Networks                            | Image | Flavor  |
+--------------------------------------+--------+--------+-------------------------------------+-------+---------+
| a592a1ca-a858-470c-af9e-ca97f974bde3 | test-3 | ACTIVE | user1-net=10.1.0.216, 172.16.214.86 | focal | m1.nano |
| d70d808a-0a1b-445e-99fa-d83ff4709c4a | test-2 | ACTIVE | user1-net=10.1.0.44, 172.16.214.75  | focal | m1.nano |
| b3f1f55a-32bf-4687-9e46-f0bb071c3df0 | test-1 | ACTIVE | user1-net=10.1.0.63, 172.16.214.74  | focal | m1.nano |
+--------------------------------------+--------+--------+-------------------------------------+-------+---------+

これで、従来のように手元のクライアントでOpenStack Clientによる操作などができるようになりました。

Readlineの警告は、警告にあるように該当のpyreadlineないしgnureadlineをインストールすれば回避できそうです。 私が使っているクライアントはmacOSなので、次のモジュールのインストールで警告が出なくなりました(ただモジュールのページにあるようにあまり推奨されないようです。私はvenvで仮想環境を作ってからpipでモジュールをインストールするので、無視してインストールしてしまいました)。

pypi.org