2 # Licensed under the Apache License, Version 2.0 (the "License"); you may
3 # not use this file except in compliance with the License. You may obtain
4 # a copy of the License at
6 # http://www.apache.org/licenses/LICENSE-2.0
8 # Unless required by applicable law or agreed to in writing, software
9 # distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
10 # WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
11 # License for the specific language governing permissions and limitations
14 # Copyright 2016 RIFT.io Inc
25 from Crypto
.PublicKey
import RSA
28 class ManoSshKey(object):
30 Generate a SSH key pair and store them in a file
33 def __init__(self
, log
, size
=2048):
52 def private_key(self
):
64 def private_key_file(self
):
68 def public_key_file(self
):
75 self
.log
.info("Generating key of size: {}".format(self
.size
))
77 self
._key
= RSA
.generate(self
.size
, os
.urandom
)
78 self
._key
_pem
= self
._key
.exportKey('PEM').decode('utf-8')
79 self
.log
.debug("Private key PEM: {}".format(self
._key
_pem
))
81 # Public key export as 'OpenSSH' has a bug
82 # (https://github.com/dlitz/pycrypto/issues/99)
86 username
= os
.getlogin()
87 hostname
= socket
.getfqdn()
91 pub
= self
._key
.publickey().exportKey('OpenSSH').decode('utf-8')
93 self
._pub
_ssh
= '{} {}@{}'.format(pub
, username
, hostname
)
96 self
.log
.debug("Public key SSH: {}".format(self
._pub
_ssh
))
98 def write_to_disk(self
,
101 if self
._key
is None:
104 path
= os
.path
.abspath(directory
)
105 self
._pub
_file
= "{}/{}.pub".format(path
, name
)
106 self
._key
_file
= "{}/{}.key".format(path
, name
)
108 with
open(self
._key
_file
, 'w') as content_file
:
109 content_file
.write(self
.private_key
)
110 os
.chmod(self
._key
_file
, stat
.S_IREAD|stat
.S_IWRITE
)
112 with
open(self
._pub
_file
, 'w') as content_file
:
113 content_file
.write(self
.public_key
)
115 if __name__
== "__main__":
116 parser
= argparse
.ArgumentParser(description
='Generate SSH key pair')
117 parser
.add_argument("-s", "--size", type=int, default
=2048, help="Key size")
118 parser
.add_argument("-d", "--directory", help="Directory to store the keys")
119 parser
.add_argument("-n", "--name", help="Name for the key file")
120 parser
.add_argument("--debug", help="Enable debug logging",
122 args
= parser
.parse_args()
124 fmt
= logging
.Formatter(
125 '%(asctime)-23s %(levelname)-5s (%(name)s@%(process)d:' \
126 '%(filename)s:%(lineno)d) - %(message)s')
127 stderr_handler
= logging
.StreamHandler(stream
=sys
.stderr
)
128 stderr_handler
.setFormatter(fmt
)
130 logging
.basicConfig(level
=logging
.DEBUG
)
132 logging
.basicConfig(level
=logging
.INFO
)
133 log
= logging
.getLogger('rw-mano-ssh-keys')
134 log
.addHandler(stderr_handler
)
136 log
.info("Args passed: {}".format(args
))
138 path
= args
.directory
140 path
= tempfile
.mkdtemp()
142 kp
= ManoSshKey(log
, size
=args
.size
)
143 kp
.write_to_disk(directory
=path
)
144 log
.info("Private Key: {}".format(kp
.private_key
))
145 log
.info("Public key: {}".format(kp
.public_key
))
146 log
.info("Key file: {}, Public file: {}".format(kp
.private_key_file
,