動機
いまどきのLinuxでは、/etc/shadow
等に保存されるパスワードはSHA-512で暗号されている。たとえば、Dockerfileで、コンテナ内に一般ユーザを作成するときには、平文パスワードがファイルに記されるのは避けて
RUN useradd -p 'encrypted_password' accountname
としたり、
RUN echo 'accountname:encrypted_password' | chpasswd -e
といったパスワード設定も行いたくなる。そうするとあらかじめSHA-512でパスワードを暗号化する必要があり、その方法はいくつか挙げられている。
ところが、いくつかある方法のうちどの方法が使えるかは実行環境にとても依存しているようである。
たとえばホストがmacOSのバージョンによってはpython
やperl
のcrypt
関数がSHA-512に対応していない、とかopenssl
,htpasswd
は新しいバージョンでは対応しているがCentOS7
に標準ではいっているものは対応していないとか、場合によって使い分けが必要のようだ。イメージをビルドする環境によっていちいち方法を探して変えるのはやっていられないと思うので、いくつかの方法を順次試していくスクリプトを作成した。ファイルの置き場は以下
使い方
下記のような使い方を想定している。
# useradd -p "$(./passwd_sha512encrypt -u worker)" worker
Enter password for worker:
Enter password again for check. :
# ./passwd_sha512encrypt -f -u worker | chpasswd -e
Enter password for worker:
Enter password again for check. :
これらの例の場合、プロンプトに従って標準入力から入力することになる。useradd
では暗号化したパスワードのみ、chpasswd
はアカウント名と暗号化したパスワードの対、と必要な情報が違うので-f
オプションで出力を切り替える。
もっとも、コンテナビルド等で何回もキーボード入力するのはやっていられないと思う。暗号化された物を保存しておく使い方が現実的である。ファイルに出力するオプション引数(-o output-file
)も設定しておいた。詳しい使い方は下記。
% ./passwd_sha512encrypt -h
[Usage] % passwd_sha512encrypt [options] [username] [rawpassword]
[Options]
-o output : Set outputfile (default: stdout)
-u username : Set username
-p rawpassword : Set destenation
-f : Output username:encrupted_password
(Default output is encrupted_password only)
-q : Skip type-miss check
-v : verbose output
-d : debug output
-h : Show Help (this message)
動作
内部ではopenssl
, htpassword
, PHP
, Python
(Version 3→Version2の順),perl
の順で、それぞれを環境変数PATH
に含まれるディレクトリを順番に探して、SHA-512に対応しているものかどうかを判定して実行する。
どれも対応していなかったら失敗する。この場合。-o
オプションで指定した出力されたファイルは作成されないので、このスクリプトの出力をシェルでリダイレクトする場合と動作が異なる。サイズ0のファイルが作成されないので、Makefile
でファイルの依存関係を利用して処理を停めやすいと思う。