2e80029bd72a9114ec9e978159a80ee2f181175f
[stack/cam.git] / cam / main.py
1 #!/usr/bin/python
2
3 import logging
4 import optparse
5 import os
6 import sys
7 import time
8 from cam import config
9
10
11 USAGE = '''cam [<OPTIONS>] <COMMAND> [<ARG>...]
12 CAM v2.0 - (c)2012 by <ale@incal.net> 
13 A Certification Authority manager for complex situations.
14
15 Known commands:
16
17   init [<RSA_CRT> [<DSA_CRT>]]
18     Initialize the environment and create a new CA certificate
19     (you can also import your own existing certificates)
20
21   gen <TAG>...
22     Create (or re-create) the certificates corresponding
23     to TAG
24
25   gencrl
26     Update the CRL
27
28   list
29     List all known certificates
30
31   files <TAG>...
32     Dump all the certificate-related files of this TAG
33
34   check 
35     Should be run weekly from a cron job to warn you if some
36     certificates are about to expire (controlled by the 'warning_days'
37     parameter in the 'global' section of the configuration)
38
39 The configuration file consists of a ini-style file, with one 'ca'
40 section that specifies global CA parameters, and more sections for
41 each tag with certificate-specific information. See the examples for
42 more details on how to write your own configuration.
43 '''
44
45
46 def find_cert(certs, name):
47     for c in certs:
48         if c.name == name:
49             return c
50     raise Exception('Certificate "%s" not found' % name)
51
52
53 def main():
54     parser = optparse.OptionParser(usage=USAGE)
55     parser.add_option('-d', '--debug', dest='debug', help='Be verbose',
56                       action='store_true')
57     parser.add_option('-c', '--config', dest='config', help='Config file')
58     opts, args = parser.parse_args()
59     if not opts.config:
60         parser.error('Must specify --config')
61     if len(args) < 1:
62         parser.error('Must specify a command')
63
64     logging.basicConfig()
65     logging.getLogger().setLevel(opts.debug and logging.DEBUG or logging.INFO)
66
67     global_config, ca, certs = config.read_config(opts.config)
68
69     cmd, args = args[0], args[1:]
70
71     try:
72         if cmd == 'init':
73             ca.create()
74         elif cmd == 'gen':
75             if len(args) != 1:
76                 parser.error('Wrong number of arguments')
77             ca.generate(find_cert(certs, args[0]))
78         elif cmd == 'gencrl':
79             ca.gencrl()
80         elif cmd == 'files':
81             if len(args) != 1:
82                 parser.error('Wrong number of arguments')
83             c = find_cert(certs, args[0])
84             print c.public_key_file
85             print c.private_key_file
86         elif cmd == 'list':
87             for cert in sorted(certs, key=lambda x: x.name):
88                 print cert.name, cert.cn, cert.get_expiration_date()
89         elif cmd == 'check':
90             now = time.time()
91             warning_time = 8640000 * int(global_config.get('warning_days', 15))
92             for cert in certs:
93                 exp = cert.get_expiration_date()
94                 if exp and (exp - now) < warning_time:
95                     print '%s (%s) is about to expire.' % (cert.name, cert.cn)
96         else:
97             parser.error('unknown command "%s"' % cmd)
98     finally:
99         ca.close()
100
101
102 def main_wrapper():
103     try:
104         main()
105         return 0
106     except Exception, e:
107         logging.exception('uncaught exception')
108         return 1
109
110
111 if __name__ == '__main__':
112     sys.exit(main_wrapper())