PHPを使ってSSL証明書の情報を取得する方法を教えてください。

SSL証明書の「組織」「発行日」「有効期限」などです。
例:はてなの場合
組織:Equifax Secure Inc
発行日:2007/03/20
有効期限:2008/07/16
という文字列を取得したいです。
環境:
 Linux
 php4(php5でもどちらでも構いません)
どうぞよろしくお願いいたします。

回答の条件
  • 1人2回まで
  • 登録:2007/10/23 21:11:53
  • 終了:2007/10/24 19:27:34

ベストアンサー

id:y-kawaz No.1

y-kawaz回答回数1421ベストアンサー獲得回数2262007/10/24 01:25:49

ポイント100pt

PHPではないですがLinux環境と言うことなので、まずは openssl コマンドでそれら情報を得てみるのが簡単かと思います。

例えば以下のようなコマンドで期待する情報が得られることが分かります。

[root@localhost ~]# echo | openssl s_client -host www.hatena.ne.jp -port 443 2>/dev/null | openssl x509 -text | egrep '^[ \t]+(Issuer|Not Before|Not After ):'
        Issuer: C=US, O=Equifax Secure Inc., CN=Equifax Secure eBusiness CA-1
            Not Before: Mar 19 15:02:01 2007 GMT
            Not After : Jul 15 15:02:01 2008 GMT

とりあえず動作重視ならこのコマンドをphpで直接実行して得られる3行の文字列をパースするだけで用は足りるかと思います。

例えば上記コマンドをそのまま $str = `echo | openssl s_client ...`; と言った形で実行してやればあともう少しです。PHPの世界に降りてきた$strを正規表現なりで適当にパースしてやれば良いでしょう。


簡単にコマンドの解説をすると、

  1. まず openssl s_client で対象ホストの証明書情報を得ています。(s_client は本当はtelnet的な動作をするのですがここではダミーで入力に echo を渡してすぐ終了させています。)
  2. openssl s_clientの出力の中に -----BEGIN CERTIFICATE----- で始まり -----END CERTIFICATE----- で終わる文字列があります。これがSSLの証明書です。
  3. この証明書部分を openssl x509 コマンドに渡すと証明書のチェックが出来ます。-text は内容をテキストとして読めるようにする x509 コマンドのオプションです。(ちなみにs_clientの出力に含まれている証明書以外の余分な出力もそのままx509に喰わせていますが、opensslコマンドはその中から -----BEGIN CERTIFICATE----- と -----END CERTIFICATE----- で囲まれている部分を自動的に証明書として認識してくれるので楽ちんです)
  4. で、x509 -text はテキスト形式で証明書情報を出力してくれるので。その中から目的の情報を grep で3行切り出しています。

最後に一応PHPでも証明書をパースしてみます(^^;

PHPのOpenSSL関数を使います。

<?php
$pem = '-----BEGIN CERTIFICATE-----
MIIDFTCCAn6gAwIBAgICWKkwDQYJKoZIhvcNAQEEBQAwUzELMAkGA1UEBhMCVVMx
HDAaBgNVBAoTE0VxdWlmYXggU2VjdXJlIEluYy4xJjAkBgNVBAMTHUVxdWlmYXgg
U2VjdXJlIGVCdXNpbmVzcyBDQS0xMB4XDTA3MDMxOTE1MDIwMVoXDTA4MDcxNTE1
MDIwMVowgdwxCzAJBgNVBAYTAkpQMRkwFwYDVQQKExB3d3cuaGF0ZW5hLm5lLmpw
MTwwOgYDVQQLEzNodHRwczovL3NlcnZpY2VzLmNob2ljZXBvaW50Lm5ldC9nZXQu
anNwPzMyNDA3NTQ5OTIxJzAlBgNVBAsTHlNlZSB3d3cucmFwaWRzc2wuY29tL2Nw
cyAoYykwNTEwMC4GA1UECxMnRG9tYWluIENvbnRyb2wgVmFsaWRhdGVkIC0gUmFw
aWRTU0woVE0pMRkwFwYDVQQDExB3d3cuaGF0ZW5hLm5lLmpwMIGfMA0GCSqGSIb3
DQEBAQUAA4GNADCBiQKBgQDG/WXnUmVPTGYi5w8DC+XzTCao3wCbP1TVeKEtgHMH
svQ4tnHzeivdYgselHAvHdJimiI3cMAOpvNc0qFhTrhJBBtBsBUtBBtUV/HM9LOm
BUJ9o8orTmRlGK8gjNLj0FQRKpH5isWTp0SO2ONpHAlQHAtph5/dMkwTNGTAU7dS
1QIDAQABo24wbDAOBgNVHQ8BAf8EBAMCBPAwOQYDVR0fBDIwMDAuoCygKoYoaHR0
cDovL2NybC5nZW90cnVzdC5jb20vY3Jscy9lYml6Y2ExLmNybDAfBgNVHSMEGDAW
gBRKeDJSEdtZFjZe38EUNkBqR3xMoTANBgkqhkiG9w0BAQQFAAOBgQAe5jpdqh0j
NwKA97sFJ7XMP0NZxYr7wQ6/yWPDVLWQllsHA5CxztlbLMetvLSrBNH4bYwTT6Ik
8zs+0uib513DUpYdMXaF/eYJzxy59pPT8tqW3dP74AOWN+8ZPysN17ZIWu+FMJV1
NVxRToRkrpYxOxWXwJrsMAtLXh7C6EuZrg==
-----END CERTIFICATE-----';
$cert = openssl_x509_read($pem);
$cert_data = openssl_x509_parse($cert);
openssl_x509_free($cert);

echo $cert_data['issuer']['O'] . "\n";
echo strftime('%Y/%m/%d %H:%M:%S', $cert_data['validFrom_time_t']) . "\n";
echo strftime('%Y/%m/%d %H:%M:%S', $cert_data['validTo_time_t']) . "\n";
?>

↑これの出力結果は以下のようになります。

Equifax Secure Inc.
2007/03/20 00:02:01
2008/07/16 00:02:01

PHP: OpenSSL 関数 - Manual

id:staff14

ありがとうございます。

opensslを使えばできるんですね。

Linuxと書いていたのですが、実はwindowsでもやりたかったので、

windows版opensslをインストールして実行してみたのですが、難しかったです。

c:\openssl\bin\openssl s_client -connect www.hatena.ne.jp:443

↑このコマンドをphpのシステム関数で叩くと返ってこなくなってしまいます。

マニュアルを読みながらしばらく戦いましたが諦めました。

何か良い方法がありましたらご教授願います。


とりあえず今回は解決しましたので、これで質問を締め切りたいと思います。

ソースコードまでの丁寧な解説本当にありがとうございました。

2007/10/24 19:26:46

コメントはまだありません

この質問への反応(ブックマークコメント)

「あの人に答えてほしい」「この質問はあの人が答えられそう」というときに、回答リクエストを送ってみてましょう。

これ以上回答リクエストを送信することはできません。制限について

絞り込み :
はてなココの「ともだち」を表示します。
回答リクエストを送信したユーザーはいません