CSR といっても Corporate Social Responsibility ではないのだ

RubyCSR を作るだと!!
今日も明日もググったー: openssl rsa "public_key"
くやしいから Python で対抗してやる、Python だったら M2Crypto だ!!

そう思って調べてみたんですけどね、調べるまでもなくテストコードに全部書いてありました。

$ wget 'http://pypi.python.jp/packages/source/M/M2Crypto/M2Crypto-0.21.1.tar.gz'
$ tar xfz M2Crypto-0.21.1.tar.gz
$ less M2Crypto-0.21.1/tests/test_x509.pem

まぁ、折角なんで写経したものを置いておきますよ。

# coding=utf8

import M2Crypto

# ザブジェクトを作る
subject = M2Crypto.X509.X509_Name()
subject.add_entry_by_txt(
    'OU', M2Crypto.ASN1.MBSTRING_ASC, 'pakupaku', -1, -1, 0)
subject.add_entry_by_txt(
    'CN', M2Crypto.ASN1.MBSTRING_ASC, 'genkotsu', -1, -1, 0)
subject.add_entry_by_txt(
    'C', M2Crypto.ASN1.MBSTRING_ASC, 'JP', -1, -1, 0)
subject.add_entry_by_txt(
    'O', M2Crypto.ASN1.MBSTRING_ASC, 'Genkotsu Enterprise', -1, -1, 0)
subject.add_entry_by_txt(
    'L', M2Crypto.ASN1.MBSTRING_ASC, 'Ishigaki', -1, -1, 0)
subject.add_entry_by_txt(
    'ST', M2Crypto.ASN1.MBSTRING_ASC, 'Okinawa', -1, -1, 0)

# 拡張を作る
extstack = M2Crypto.X509.X509_Extension_Stack()
san = M2Crypto.X509.new_extension('subjectAltName', 'DNS:pugpug.genkotsu')
extstack.push(san)

# 秘密鍵を作る
pk = M2Crypto.EVP.PKey()
rsa = M2Crypto.RSA.gen_key(2048, 2**16+1)
pk.assign_rsa(rsa)

# CSR を作って登録
req = M2Crypto.X509.Request()
req.set_version(0)
req.set_subject(subject)
req.add_extensions(extstack)
req.set_pubkey(pk)

# TBS を signed にする
req.sign(pk, 'sha1')

# 秘密鍵は暗号化しない
print rsa.as_pem(None),
print req.as_pem(),

で、動かしてみたよ

$ python gen_csr.py 
........+++
.............................+++
-----BEGIN RSA PRIVATE KEY-----
MIIEogIBAAKCAQEAl4XyHGeB80fLw7COHHRzg6ichW7WiTWxGsyP5ZFVI97FB2uc
0ih8rYI4Bi7P20cZXyGUuPDFXIdqO/Ef1vDRzdmVamSdnJcuK30maXnCGBPCSWSa
kSJ7GCgUVRpWBwbIAmsPMrgTy37DqQjgO9cWHZoc9kvD4brbqO+wvfyI6f9t67Kl
hrrzbFi/cBMiiGFFi6quM+f8MsvU5lu56a+wZGgXsiNWmH+/XfAlZYezaCCzInPP
lPaDQUHZ7YKXH0DFEBmRJzTlWmR7q5NYZolkLW9EXIQYkNt8D6yMJOu433dW/WeW
3U19SPgdL56gSP1K2Y1oDJEFS2iNcqT3j+T34QIDAQABAoIBACiXBSh+wdz92qPt
Y+RTfa5DOMq1ylqvO2ZGbjW9HOWjA3zdYwEZP2zreT6Ow7el8DH/uOth9Dy5Ocgc
676UfF98bf42PdJ43TFhMS0IJOp2QJGQladTaU4rTmcNywXO1z1umH+puAPHTXq2
mfrtv0rmweNooGyTtcwniV0bjUHBdZBYGGh+FELHPEBeL1/rRYNpaOqy469Hsdsa
TdDE8w0Ak1DQe8LUyQFYMR8noWC168yQHRRLiby75O6k5u+8ETQ5OIgDf7NrWj3J
+ZEc1lCAyErlej0l6jDWBb2n8B9qMufvO+g3jlSAkDXs7l4V+gSmSfCl4GNK3C19
xlH8n5ECgYEAyY2aer8oROzg0SbyWMmz6ZYqY8zsuBnCT0pMfOhGd5+BFFlU9M5k
kp35L9VVBwrbuOg0WSQJqtPes81a5VVxDnbNktEsaS+0qJS3lMQXxnCakjnK/1eL
yvqB2qrd+R4MHdVltrK1CEBFZCjyYnFpIJ4xbUWs/pRWXB4XRyZBpTsCgYEAwHSG
vs56SilxS6yKijICuuCTxGwPEAm0wVrJ35QBom4stcA5WLNKxcVBSn9yaupuu4wk
JDF0qS2Nlk+bZLptauKjPZqCZNn5pKTTJB8r7EkQS4rA9MoFGa6ul8JME0pHqvsQ
V9zaRZzd0QVQi9cqW2wO8wjrl/4CKQrqX92b1ZMCgYB+hbmXnC/3NIvcP4qaWePq
mi16AMYIu4LSq11ge57gsOwijgFau8U+lJQ8hrqddR+A76MM4iZ/agi+7gZFOGGE
JufdZhlu3leWC+VCKeaS11Twvf7EU3yZqq+hSOmW3FnW0ILNMVmbGF13Bo1BZtgL
dcKpSbfTB+M+aFVMgKNsyQKBgENOfXFttMcLB1x301vRcbL5p7QiNoJdYqHcpo1S
rd+ouGo399ZVnejcu6DaQaGyq1dcA6fExBAGpmXTIX1w1aNz77MzvjaXJP+3xT/0
xt+0Dcbdl+4EWRRKSzU39nMonzfk5ipUSuHdopXfTfQaI+4lNHU6wWo+o3LHJoCw
eDeRAoGAZBUNjBYPWi4ju8NKzkomJqNAzIpUcWimCscR0piFufJ4uzd95gpsftHG
J8n2/2ggSjtLmyWeDAAISL7chq/RqODMlzX1BCoz9klepZS9m+iYHA35P+2AABii
WU2F7nV61WuewZMnenbDyWHFpxpAx0jCcQiI0YcP2BRElOvRqpI=
-----END RSA PRIVATE KEY-----
-----BEGIN CERTIFICATE REQUEST-----
MIIC6DCCAdACAQAwdjERMA8GA1UECxMIcGFrdXBha3UxETAPBgNVBAMTCGdlbmtv
dHN1MQswCQYDVQQGEwJKUDEcMBoGA1UEChMTR2Vua290c3UgRW50ZXJwcmlzZTER
MA8GA1UEBxMISXNoaWdha2kxEDAOBgNVBAgTB09raW5hd2EwggEiMA0GCSqGSIb3
DQEBAQUAA4IBDwAwggEKAoIBAQCXhfIcZ4HzR8vDsI4cdHODqJyFbtaJNbEazI/l
kVUj3sUHa5zSKHytgjgGLs/bRxlfIZS48MVch2o78R/W8NHN2ZVqZJ2cly4rfSZp
ecIYE8JJZJqRInsYKBRVGlYHBsgCaw8yuBPLfsOpCOA71xYdmhz2S8Phutuo77C9
/Ijp/23rsqWGuvNsWL9wEyKIYUWLqq4z5/wyy9TmW7npr7BkaBeyI1aYf79d8CVl
h7NoILMic8+U9oNBQdntgpcfQMUQGZEnNOVaZHurk1hmiWQtb0RchBiQ23wPrIwk
67jfd1b9Z5bdTX1I+B0vnqBI/UrZjWgMkQVLaI1ypPeP5PfhAgMBAAGgLTArBgkq
hkiG9w0BCQ4xHjAcMBoGA1UdEQQTMBGCD3B1Z3B1Zy5nZW5rb3RzdTANBgkqhkiG
9w0BAQUFAAOCAQEAJmtCRKuHs5nMDUJ4r8xTm+SyaeBCFPZsS5B+svFrSfOpuEjo
kVw2b0OBTRlF5YKaMXC3SPQpT5Qdl4scP4thbfPOwD5nI4IZ9dEeqXreItN8Uqez
C/WWGLGQRKM0kRNsG0vGM3cf9FTHMBfPbUUEaTIWzopglV8X+n4e1WTM+90v0SUq
flcz4SL7ELyH0Q1imIEfDnV6BXieIV7YEHH5zMIv5iuI8U3QyUfIzIFHL8xLdhxo
A3NR4ZAjAZP+WGcSSYHw4ijIZ7QxWEySdPd0OVP5IG1IxWOyeezP7S1feKuYAPCc
NLIw6Vw1oVXx8QxU3Eq4kej3p9VQmT0WbGaOAQ==
-----END CERTIFICATE REQUEST-----
$

うふふ