class CertificatesPlugin(CategoryPlugin, URLHandler): text = 'Certificates' iconfont = 'gen-certificate' folder = 'system' def on_init(self): self.certs = sorted(self._cc.get_certs(), key=lambda x: x['name']) self.cas = sorted(self._cc.get_cas(), key=lambda x: x['name']) def on_session_start(self): self._cc = CertControl(self.app) self._gen = None self._tab = 0 self._wal = [] self._pal = [] self._upload = None def get_ui(self): ui = self.app.inflate('certificates:main') ui.find('tabs').set('active', self._tab) cfg = self.app.get_config(CertControl(self.app)) ui.find('kl' + cfg.keylength).set('selected', True) ui.find('kt' + cfg.keytype.lower()).set('selected', True) ui.find('ciphers').set('value', cfg.ciphers) lst = ui.find('certlist') for s in self.certs: lst.append( UI.DTR( UI.IconFont(iconfont='gen-certificate'), UI.Label(text=s['name']), UI.Label(text=', '.join(filter(None, s['assign']))), UI.HContainer( UI.TipIcon(iconfont='gen-info', text='Information', id='info/' + str(self.certs.index(s))), UI.TipIcon( iconfont='gen-close', text='Delete', id='del/' + str(self.certs.index(s)), warning= ('Are you sure you wish to remove this certificate? ' 'SSL on all associated services will be disabled' ), ), ), )) lst = ui.find('certauth') if not self.cas: lst.append(UI.Button(text="Generate New", id="cagen")) for s in self.cas: exp = s['expiry'] exp = exp[0:4] + '-' + exp[4:6] + '-' + exp[6:8] + ', ' + exp[ 8:10] + ':' + exp[10:12] lst.append( UI.FormLine(UI.HContainer( UI.Label(text='Expires ' + exp), UI.TipIcon( iconfont='gen-download', text='Download', id='cadl', onclick='window.open("/certificates/dl", "_blank")'), UI.TipIcon(iconfont='gen-close', text='Delete', id='cadel/' + str(self.cas.index(s))), ), text=s['name'])) if self._gen: ui.find('certcn').set( 'value', self.app.get_backend(IHostnameManager).gethostname().lower()) self._wal, self._pal = self._cc.get_ssl_capable() alist, wlist, plist = [], [], [] for cert in self.certs: for i in cert['assign']: if i != '': alist.append(i) if not 'Genesis SSL' in alist: ui.find('certassign').append( UI.Checkbox(text='Genesis SSL', name='genesis', value='genesis', checked=False), ) for x in self._wal: if not (x.name + ' (' + x.stype + ')') in alist: ui.find('certassign').append( UI.Checkbox(text=x.name, name='wassign[]', value=x.name, checked=False), ) wlist.append(x) self._wal = wlist for x in self._pal: if not x.text in alist: ui.find('certassign').append( UI.Checkbox(text=x.text, name='passign[]', value=x.text, checked=False), ) plist.append(x) self._pal = plist else: ui.remove('dlgGen') if self._cinfo: self._wal, self._pal = self._cc.get_ssl_capable() ui.find('certname').set('text', self._cinfo['name']) ui.find('domain').set('text', self._cinfo['domain']) ui.find('ikeytype').set( 'text', self._cinfo['keylength'] + '-bit ' + self._cinfo['keytype']) exp = self._cinfo['expiry'] exp = exp[0:4] + '-' + exp[4:6] + '-' + exp[6:8] + ', ' + exp[ 8:10] + ':' + exp[10:12] ui.find('expires').set('text', exp) alist = [] for cert in self.certs: if cert != self._cinfo: for i in cert['assign']: if i != '': alist.append(i) if not 'Genesis SSL' in alist: if 'Genesis SSL' in self._cinfo['assign']: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont='gen-arkos-round'), UI.Label(text='Genesis'), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/' + self._cinfo['name'] + '/g') if show == 'e' else None), (UI.TipIcon( iconfont='gen-close', text='Unassign', id='uc/' + self._cinfo['name'] + '/g', warning= ('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled, and you will need to ' 'reload Genesis for changes to take place.')) if show == 'd' else None), ), )) for x in self._wal: if not (x.name + ' (' + x.stype + ')') in alist: if (x.name + ' (' + x.stype + ')') in self._cinfo['assign']: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont='gen-earth'), UI.Label(text=x.name), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/' + self._cinfo['name'] + '/w/' + str(self._wal.index(x))) if show == 'e' else None), (UI.TipIcon( iconfont='gen-close', text='Unassign', id='uc/' + self._cinfo['name'] + '/w/' + str(self._wal.index(x)), warning= ('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled.')) if show == 'd' else None), ), )) for x in self._pal: if not x.text in alist: if x.text in self._cinfo['assign']: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont=x.iconfont), UI.Label(text=x.text), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/' + self._cinfo['name'] + '/p/' + str(self._pal.index(x))) if show == 'e' else None), (UI.TipIcon( iconfont='gen-close', text='Unassign', id='uc/' + self._cinfo['name'] + '/p/' + str(self._pal.index(x)), warning= ('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled.')) if show == 'd' else None), ), )) else: ui.remove('dlgInfo') if self._upload: ui.append( 'main', UI.DialogBox( UI.FormLine(UI.TextInput(name='certname'), text='Name'), UI.FormLine(UI.FileInput(id='certfile'), text='Certificate file'), UI.FormLine(UI.FileInput(id='keyfile'), text='Certificate keyfile'), UI.FormLine( UI.FileInput(id='chainfile'), text='Certificate chainfile', help= 'This is optional, only put it if you know you need one.' ), id='dlgUpload', mp=True)) return ui @url('^/certificates/dl$') def download(self, req, start_response): params = req['PATH_INFO'].split('/')[3:] + [''] filename = CertControl(self.app).get_cas()[0]['name'] + '.pem' path = os.path.join('/etc/ssl/certs/genesis/ca', filename) f = open(path, 'rb') size = os.path.getsize(path) start_response( '200 OK', [('Content-length', str(size)), ('Content-Disposition', 'attachment; filename=%s' % filename)]) return f.read() @event('button/click') def on_click(self, event, params, vars=None): if params[0] == 'info': self._tab = 0 self._cinfo = self.certs[int(params[1])] elif params[0] == 'gen': self._tab = 0 self._gen = True elif params[0] == 'del': self._tab = 0 self._cc.remove(self.certs[int(params[1])]['name']) self.put_message('info', 'Certificate successfully deleted') elif params[0] == 'ac' and params[2] == 'p': self._tab = 0 self._cc.assign(self._cinfo['name'], [('plugin', self._pal[int(params[3])])]) self.put_message( 'info', '%s added to %s plugin' % (self._cinfo['name'], self._pal[int(params[3])].text)) self._cinfo = None elif params[0] == 'ac' and params[2] == 'w': self._tab = 0 self._cc.assign(self._cinfo['name'], [('webapp', self._wal[int(params[3])])]) self.put_message( 'info', '%s added to %s webapp' % (self._cinfo['name'], self._wal[int(params[3])].name)) self._cinfo = None elif params[0] == 'ac' and params[2] == 'g': self._tab = 0 self._cc.assign(self._cinfo['name'], [[('genesis')]]) self.put_message( 'info', '%s serving as Genesis certificate. Restart Genesis for changes to take effect' % self._cinfo['name']) self._cinfo = None elif params[0] == 'uc' and params[2] == 'p': self._tab = 0 self._cc.unassign(self._cinfo['name'], [('plugin', self._pal[int(params[3])])]) self.put_message( 'info', '%s removed from %s plugin, and SSL disabled.' % (self._cinfo['name'], self._pal[int(params[3])].text)) self._cinfo = None elif params[0] == 'uc' and params[2] == 'w': self._tab = 0 self._cc.unassign(self._cinfo['name'], [('webapp', self._wal[int(params[3])])]) self.put_message( 'info', '%s removed from %s webapp, and SSL disabled.' % (self._cinfo['name'], self._wal[int(params[3])].name)) self._cinfo = None elif params[0] == 'uc' and params[2] == 'g': self._tab = 0 self._cc.unassign(self._cinfo['name'], [[('genesis')]]) self.put_message( 'info', 'Certificate removed and SSL disabled for Genesis. Reload Genesis for changes to take effect' ) self._cinfo = None elif params[0] == 'upl': self._tab = 0 self._upload = True elif params[0] == 'cagen': self._tab = 1 self._cc.create_authority( self.app.get_backend(IHostnameManager).gethostname().lower()) elif params[0] == 'cadel': self._tab = 1 self._cc.delete_authority(self.cas[int(params[1])]) @event('form/submit') @event('dialog/submit') def on_submit(self, event, params, vars=None): if params[0] == 'dlgAdd': self._tab = 0 if vars.getvalue('action', '') == 'OK': pass elif params[0] == 'dlgGen': self._tab = 0 if vars.getvalue('action', '') == 'OK': if vars.getvalue('certname', '') == '': self.put_message('err', 'Certificate name is mandatory') elif re.search('\.|-|`|\\\\|\/|[ ]', vars.getvalue('certname')): self.put_message( 'err', 'Certificate name must not contain spaces, dots, dashes or special characters' ) elif vars.getvalue('certname', '') in [x['name'] for x in self.certs]: self.put_message( 'err', 'You already have a certificate with that name.') elif len(vars.getvalue('certcountry', '')) != 2: self.put_message( 'err', 'The country field must be a two-letter abbreviation') else: lst = [] if vars.getvalue('genesis', '') == '1': lst.append([('genesis')]) for i in range(0, len(self._wal)): try: if vars.getvalue('wassign[]')[i] == '1': lst.append(('webapp', self._wal[i])) except TypeError: pass for i in range(0, len(self._pal)): try: if vars.getvalue('passign[]')[i] == '1': lst.append(('plugin', self._pal[i])) except TypeError: pass cgw = CertGenWorker(self, vars.getvalue('certname'), vars, lst) cgw.start() self._wal = [] self._pal = [] self._gen = False elif params[0] == 'dlgInfo': self._tab = 0 self._cinfo = None self._wal = [] self._pal = [] elif params[0] == 'dlgUpload': self._tab = 0 if vars.getvalue('action', '') == 'OK': if not vars.has_key('certfile') and not vars.has_key( 'keyfile'): self.put_message( 'err', 'Please select at least a certificate and private key') elif not vars.has_key('certfile'): self.put_message('err', 'Please select a certificate file') elif not vars.has_key('keyfile'): self.put_message('err', 'Please select a key file') elif not vars.getvalue('certname', ''): self.put_message('err', 'Must choose a certificate name') elif vars.getvalue('certname', '') in [x['name'] for x in self.certs]: self.put_message( 'err', 'You already have a certificate with that name.') elif re.search('\.|-|`|\\\\|\/|[ ]', vars.getvalue('certname')): self.put_message( 'err', 'Certificate name must not contain spaces, dots, dashes or special characters' ) else: try: self._cc.add_ext_cert( vars.getvalue('certname'), vars['certfile'].value, vars['keyfile'].value, vars['chainfile'].value if vars.has_key('chainfile') else None) self.put_message( 'info', 'Certificate %s installed' % vars.getvalue('certname')) except Exception, e: self.put_message( 'err', 'Couldn\'t add certificate: %s' % str(e[0])) self.app.log.error( 'Couldn\'t add certificate: %s - Error: %s' % (str(e[0]), str(e[1]))) self._upload = None elif params[0] == 'frmCertSettings': self._tab = 1 if vars.getvalue('action', '') == 'OK': cfg = self.app.get_config(CertControl(self.app)) cfg.keylength = vars.getvalue('keylength', '2048') cfg.keytype = vars.getvalue('keytype', 'RSA') cfg.ciphers = vars.getvalue('ciphers', '') cfg.save() self.put_message('info', 'Settings saved successfully')
class CertificatesPlugin(CategoryPlugin, URLHandler): text = 'Certificates' iconfont = 'gen-certificate' folder = 'tools' def on_init(self): self.certs = sorted(self._cc.get_certs(), key=lambda x: x.name) self.cas = sorted(self._cc.get_cas(), key=lambda x: x['name']) self._hostname = self.app.get_backend(IHostnameManager).gethostname().lower() def on_session_start(self): self._cc = CertControl(self.app) self._cfg = self.app.get_config(self._cc) self._gen = None self._tab = 0 self._wal = [] self._pal = [] self._hostname = '' self._upload = None def get_ui(self): ui = self.app.inflate('certificates:main') ui.find('tabs').set('active', self._tab) ui.find('kl'+self._cfg.keylength).set('selected', True) ui.find('kt'+self._cfg.keytype.lower()).set('selected', True) ui.find('ciphers').set('value', self._cfg.ciphers) for s in self.certs: ui.find('certlist').append( UI.TblBtn( id='info/'+str(self.certs.index(s)), icon='gen-certificate', name=s.name, subtext="%s-bit %s" % (s.keylength, s.keytype) ) ) ui.find('certlist').append( UI.TblBtn( id='gen', icon='gen-plus-circle', name='Generate certificate' ) ) ui.find('certlist').append( UI.TblBtn( id='upl', icon='gen-file-upload', name='Upload certificate' ) ) lst = ui.find('certauth') if not self.cas: lst.append(UI.Btn(text="Generate New", id="cagen")) for s in self.cas: exp = SystemTime.convert(s['expiry'], '%Y%m%d%H%M%SZ', self.app.gconfig.get('genesis', 'dformat', '%d %b %Y')) lst.append(UI.FormLine( UI.HContainer( UI.Label(text='Expires '+exp), UI.TipIcon(iconfont='gen-download', text='Download', id='cadl', onclick='window.open("/certificates/dl", "_blank")'), UI.TipIcon(iconfont='gen-close', text='Delete', id='cadel/' + str(self.cas.index(s))), ), text=s['name'], horizontal=True )) if self._gen: ui.find('certcn').set('value', self._hostname) self._wal, self._pal = self._cc.get_ssl_capable() alist, wlist, plist = [], [], [] for cert in self.certs: for i in cert.assign: alist.append(i) if not {'type': 'genesis'} in alist: ui.find('certassign').append( UI.FormLine( UI.Checkbox(text='Genesis SSL', name='genesis', value='genesis', checked=False), checkbox=True) ) for x in self._wal: if not {'type': 'website', 'name': x.name} in alist: ui.find('certassign').append( UI.FormLine( UI.Checkbox(text=x.name, name='wassign[]', value=x.name, checked=False), checkbox=True) ) wlist.append(x) self._wal = wlist for x in self._pal: if not {'type': 'plugin', 'name': x.text} in alist: ui.find('certassign').append( UI.FormLine( UI.Checkbox(text=x.text, name='passign[]', value=x.text, checked=False), checkbox=True) ) plist.append(x) self._pal = plist else: ui.remove('dlgGen') if self._cinfo: self._wal, self._pal = self._cc.get_ssl_capable() ui.find('certname').set('text', self._cinfo.name) ui.find('domain').set('text', self._cinfo.domain) ui.find('ikeytype').set('text', '%s-bit %s' % (self._cinfo.keylength, self._cinfo.keytype)) exp = SystemTime.convert(self._cinfo.expiry, '%Y%m%d%H%M%SZ', self.app.gconfig.get('genesis', 'dformat', '%d %b %Y')) ui.find('expires').set('text', exp) ui.find('sha1').set('text', self._cinfo.sha1) ui.find('md5').set('text', self._cinfo.md5) alist = [] for cert in self.certs: if cert != self._cinfo: for i in cert.assign: alist.append(i) if not 'genesis' in [x['type'] for x in alist]: if 'genesis' in [x['type'] for x in self._cinfo.assign]: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont='gen-arkos-round'), UI.Label(text='Genesis'), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/'+self._cinfo.name+'/g') if show == 'e' else None), (UI.TipIcon(iconfont='gen-close', text='Unassign', id='uc/'+self._cinfo.name+'/g', warning=('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled, and you will need to ' 'reload Genesis for changes to take place.')) if show == 'd' else None), ), ) ) for x in self._wal: if not x.name in [y['name'] for y in alist if y['type'] == 'website']: if x.name in [y['name'] for y in self._cinfo.assign if y['type'] == 'website']: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont='gen-earth'), UI.Label(text=x.name), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/'+self._cinfo.name+'/w/'+str(self._wal.index(x))) if show == 'e' else None), (UI.TipIcon(iconfont='gen-close', text='Unassign', id='uc/'+self._cinfo.name+'/w/'+str(self._wal.index(x)), warning=('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled.')) if show == 'd' else None), ), ) ) for x in self._pal: if not x.pid in [y['id'] for y in alist if y['type'] == 'plugin']: if x.pid in [y['id'] for y in self._cinfo.assign if y['type'] == 'plugin']: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont=x.iconfont), UI.Label(text=x.text), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/'+self._cinfo.name+'/p/'+str(self._pal.index(x))) if show == 'e' else None), (UI.TipIcon(iconfont='gen-close', text='Unassign', id='uc/'+self._cinfo.name+'/p/'+str(self._pal.index(x)), warning=('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled.')) if show == 'd' else None), ), ) ) else: ui.remove('dlgInfo') if self._upload: ui.append('main', UI.DialogBox( UI.FormLine(UI.TextInput(name='certname'), text='Name'), UI.FormLine(UI.FileInput(id='certfile'), text='Certificate file'), UI.FormLine(UI.FileInput(id='keyfile'), text='Certificate keyfile'), UI.FormLine(UI.FileInput(id='chainfile'), text='Certificate chainfile', help='This is optional, only put it if you know you need one.'), id='dlgUpload', mp=True)) return ui @url('^/certificates/dl$') def download(self, req, start_response): params = req['PATH_INFO'].split('/')[3:] + [''] filename = CertControl(self.app).get_cas()[0]['name']+'.pem' path = os.path.join('/etc/ssl/certs/genesis/ca', filename) f = open(path, 'rb') size = os.path.getsize(path) start_response('200 OK', [ ('Content-length', str(size)), ('Content-Disposition', 'attachment; filename=%s' % filename) ]) return f.read() @event('button/click') def on_click(self, event, params, vars = None): if params[0] == 'info': self._tab = 0 self._cinfo = self.certs[int(params[1])] elif params[0] == 'gen': self._tab = 0 self._gen = True elif params[0] == 'del': self._tab = 0 self._cc.remove(self._cinfo) self._cinfo = None self.put_message('success', 'Certificate successfully deleted') elif params[0] == 'ac' and params[2] == 'p': self._tab = 0 self._cc.assign(self._cinfo.name, [('plugin', self._pal[int(params[3])])]) self.put_message('success', '%s added to %s plugin' % (self._cinfo.name, self._pal[int(params[3])].text)) self._cinfo = None elif params[0] == 'ac' and params[2] == 'w': self._tab = 0 try: self._cc.assign(self._cinfo.name, [('website', self._wal[int(params[3])])]) self.put_message('success', '%s added to %s website' % (self._cinfo.name, self._wal[int(params[3])].name)) except Exception, e: self.put_message('err', str(e)) self.app.log.error(str(e)) self._cinfo = None elif params[0] == 'ac' and params[2] == 'g': self._tab = 0 self._cc.assign(self._cinfo.name, [[('genesis')]]) self.put_message('success', '%s serving as Genesis certificate. Restart Genesis for changes to take effect' % self._cinfo.name) self._cinfo = None
class CertificatesPlugin(CategoryPlugin): text = 'Certificates' iconfont = 'gen-certificate' folder = 'system' def on_init(self): self.certs = sorted(self._cc.get_certs(), key=lambda x: x['name']) def on_session_start(self): self._cc = CertControl(self.app) self._gen = None self._wal = [] self._pal = [] self._upload = None def get_ui(self): ui = self.app.inflate('certificates:main') lst = ui.find('certlist') for s in self.certs: lst.append(UI.DTR( UI.IconFont(iconfont='gen-certificate'), UI.Label(text=s['name']), UI.Label(text=', '.join(filter(None, s['assign']))), UI.HContainer( UI.TipIcon(iconfont='gen-info', text='Information', id='info/' + str(self.certs.index(s))), UI.TipIcon(iconfont='gen-close', text='Delete', id='del/' + str(self.certs.index(s)), warning=('Are you sure you wish to remove this certificate? ' 'SSL on all associated services will be disabled'), ), ), )) if self._gen: self._wal, self._pal = self._cc.get_ssl_capable() alist, wlist, plist = [], [], [] for cert in self.certs: for i in cert['assign']: if i != '': alist.append(i) if not 'Genesis SSL' in alist: ui.find('certassign').append( UI.Checkbox(text='Genesis SSL', name='genesis', value='genesis', checked=False), ) for x in self._wal: if not (x['name']+' ('+x['type']+')') in alist: ui.find('certassign').append( UI.Checkbox(text=x['name'], name='wassign[]', value=x['name'], checked=False), ) wlist.append(x) self._wal = wlist for x in self._pal: if not x.text in alist: ui.find('certassign').append( UI.Checkbox(text=x.text, name='passign[]', value=x.text, checked=False), ) plist.append(x) self._pal = plist else: ui.remove('dlgGen') if self._cinfo: self._wal, self._pal = self._cc.get_ssl_capable() ui.find('certname').set('text', self._cinfo['name']) ui.find('domain').set('text', self._cinfo['domain']) ui.find('keytype').set('text', self._cinfo['keylength']+'-bit '+self._cinfo['keytype']) exp = self._cinfo['expiry'] exp = exp[0:4] + '-' + exp[4:6] + '-' + exp[6:8] + ', ' + exp[8:10] + ':' + exp[10:12] ui.find('expires').set('text', exp) alist = [] for cert in self.certs: if cert != self._cinfo: for i in cert['assign']: if i != '': alist.append(i) if not 'Genesis SSL' in alist: if 'Genesis SSL' in self._cinfo['assign']: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont='gen-arkos-round'), UI.Label(text='Genesis'), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/'+self._cinfo['name']+'/g') if show == 'e' else None), (UI.TipIcon(iconfont='gen-close', text='Unassign', id='uc/'+self._cinfo['name']+'/g', warning=('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled, and you will need to ' 'reload Genesis for changes to take place.')) if show == 'd' else None), ), ) ) for x in self._wal: if not (x['name']+' ('+x['type']+')') in alist: if (x['name']+' ('+x['type']+')') in self._cinfo['assign']: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont='gen-earth'), UI.Label(text=x['name']), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/'+self._cinfo['name']+'/w/'+str(self._wal.index(x))) if show == 'e' else None), (UI.TipIcon(iconfont='gen-close', text='Unassign', id='uc/'+self._cinfo['name']+'/w/'+str(self._wal.index(x)), warning=('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled.')) if show == 'd' else None), ), ) ) for x in self._pal: if not x.text in alist: if x.text in self._cinfo['assign']: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont=x.iconfont), UI.Label(text=x.text), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/'+self._cinfo['name']+'/p/'+str(self._pal.index(x))) if show == 'e' else None), (UI.TipIcon(iconfont='gen-close', text='Unassign', id='uc/'+self._cinfo['name']+'/p/'+str(self._pal.index(x)), warning=('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled.')) if show == 'd' else None), ), ) ) else: ui.remove('dlgInfo') if self._upload: ui.append('main', UI.DialogBox( UI.FormLine(UI.TextInput(name='certname'), text='Name'), UI.FormLine(UI.FileInput(id='certfile'), text='Certificate file'), UI.FormLine(UI.FileInput(id='keyfile'), text='Certificate keyfile'), UI.FormLine(UI.FileInput(id='chainfile'), text='Certificate chainfile', help='This is optional, only put it if you know you need one.'), id='dlgUpload', mp=True)) return ui @event('button/click') def on_click(self, event, params, vars = None): if params[0] == 'add': pass elif params[0] == 'info': self._cinfo = self.certs[int(params[1])] elif params[0] == 'gen': self._gen = True elif params[0] == 'del': self._cc.remove(self.certs[int(params[1])]['name']) self.put_message('info', 'Certificate successfully deleted') elif params[0] == 'ac' and params[2] == 'p': self._cc.assign(self._cinfo['name'], [('plugin', self._pal[int(params[3])])]) self.put_message('info', '%s added to %s plugin' % (self._cinfo['name'], self._pal[int(params[3])].text)) self._cinfo = None elif params[0] == 'ac' and params[2] == 'w': self._cc.assign(self._cinfo['name'], [('webapp', self._wal[int(params[3])])]) self.put_message('info', '%s added to %s webapp' % (self._cinfo['name'], self._wal[int(params[3])]['name'])) self._cinfo = None elif params[0] == 'ac' and params[2] == 'g': self._cc.assign(self._cinfo['name'], [[('genesis')]]) self.put_message('info', '%s serving as Genesis certificate. Restart Genesis for changes to take effect' % self._cinfo['name']) self._cinfo = None elif params[0] == 'uc' and params[2] == 'p': self._cc.unassign(self._cinfo['name'], [('plugin', self._pal[int(params[3])])]) self.put_message('info', '%s removed from %s plugin, and SSL disabled.' % (self._cinfo['name'], self._pal[int(params[3])].text)) self._cinfo = None elif params[0] == 'uc' and params[2] == 'w': self._cc.unassign(self._cinfo['name'], [('webapp', self._wal[int(params[3])])]) self.put_message('info', '%s removed from %s webapp, and SSL disabled.' % (self._cinfo['name'], self._wal[int(params[3])]['name'])) self._cinfo = None elif params[0] == 'uc' and params[2] == 'g': self._cc.unassign(self._cinfo['name'], [[('genesis')]]) self.put_message('info', 'Certificate removed and SSL disabled for Genesis. Reload Genesis for changes to take effect') self._cinfo = None elif params[0] == 'upl': self._upload = True @event('dialog/submit') def on_submit(self, event, params, vars = None): if params[0] == 'dlgAdd': if vars.getvalue('action', '') == 'OK': pass elif params[0] == 'dlgGen': if vars.getvalue('action', '') == 'OK': if vars.getvalue('certname', '') == '': self.put_message('err', 'Certificate name is mandatory') elif vars.getvalue('certname', '') in [x['name'] for x in self.certs]: self.put_message('err', 'You already have a certificate with that name.') elif len(vars.getvalue('certcountry', '')) != 2: self.put_message('err', 'The country field must be a two-letter abbreviation') else: lst = [] if vars.getvalue('genesis', '') == '1': lst.append([('genesis')]) for i in range(0, len(self._wal)): try: if vars.getvalue('wassign[]')[i] == '1': lst.append(('webapp', self._wal[i])) except TypeError: pass for i in range(0, len(self._pal)): try: if vars.getvalue('passign[]')[i] == '1': lst.append(('plugin', self._pal[i])) except TypeError: pass cgw = CertGenWorker(self, vars.getvalue('certname'), vars, lst) cgw.start() self._wal = [] self._pal = [] self._gen = False elif params[0] == 'dlgInfo': self._cinfo = None self._wal = [] self._pal = [] elif params[0] == 'dlgUpload': if vars.getvalue('action', '') == 'OK': if not vars.has_key('certfile') and not vars.has_key('keyfile'): self.put_message('err', 'Please select at least a certificate and private key') elif not vars.has_key('certfile'): self.put_message('err', 'Please select a certificate file') elif not vars.has_key('keyfile'): self.put_message('err', 'Please select a key file') elif not vars.getvalue('certname', ''): self.put_message('err', 'Must choose a certificate name') elif vars.getvalue('certname', '') in [x['name'] for x in self.certs]: self.put_message('err', 'You already have a certificate with that name.') elif re.search('\.|-|`|\\\\|\/|[ ]', vars.getvalue('certname')): self.put_message('err', 'Certificate name must not contain spaces, dots, dashes or special characters') else: try: self._cc.add_ext_cert(vars.getvalue('certname'), vars['certfile'].value, vars['keyfile'].value, vars['chainfile'].value if vars.has_key('chainfile') else None) self.put_message('info', 'Certificate %s installed' % vars.getvalue('certname')) except Exception, e: self.put_message('err', 'Couldn\'t add certificate: %s' % str(e[0])) self.app.log.error('Couldn\'t add certificate: %s - Error: %s' % (str(e[0]), str(e[1]))) self._upload = None
class CertificatesPlugin(CategoryPlugin, URLHandler): text = 'Certificates' iconfont = 'gen-certificate' folder = 'system' def on_init(self): self.certs = sorted(self._cc.get_certs(), key=lambda x: x['name']) self.cas = sorted(self._cc.get_cas(), key=lambda x: x['name']) def on_session_start(self): self._cc = CertControl(self.app) self._gen = None self._tab = 0 self._wal = [] self._pal = [] self._upload = None def get_ui(self): ui = self.app.inflate('certificates:main') ui.find('tabs').set('active', self._tab) cfg = self.app.get_config(CertControl(self.app)) ui.find('kl'+cfg.keylength).set('selected', True) ui.find('kt'+cfg.keytype.lower()).set('selected', True) ui.find('ciphers').set('value', cfg.ciphers) lst = ui.find('certlist') for s in self.certs: lst.append(UI.DTR( UI.IconFont(iconfont='gen-certificate'), UI.Label(text=s['name']), UI.Label(text=', '.join(filter(None, s['assign']))), UI.HContainer( UI.TipIcon(iconfont='gen-info', text='Information', id='info/' + str(self.certs.index(s))), UI.TipIcon(iconfont='gen-close', text='Delete', id='del/' + str(self.certs.index(s)), warning=('Are you sure you wish to remove this certificate? ' 'SSL on all associated services will be disabled'), ), ), )) lst = ui.find('certauth') if not self.cas: lst.append(UI.Button(text="Generate New", id="cagen")) for s in self.cas: exp = s['expiry'] exp = exp[0:4] + '-' + exp[4:6] + '-' + exp[6:8] + ', ' + exp[8:10] + ':' + exp[10:12] lst.append(UI.FormLine( UI.HContainer( UI.Label(text='Expires '+exp), UI.TipIcon(iconfont='gen-download', text='Download', id='cadl', onclick='window.open("/certificates/dl", "_blank")'), UI.TipIcon(iconfont='gen-close', text='Delete', id='cadel/' + str(self.cas.index(s))), ), text=s['name'] )) if self._gen: ui.find('certcn').set('value', self.app.get_backend(IHostnameManager).gethostname().lower()) self._wal, self._pal = self._cc.get_ssl_capable() alist, wlist, plist = [], [], [] for cert in self.certs: for i in cert['assign']: if i != '': alist.append(i) if not 'Genesis SSL' in alist: ui.find('certassign').append( UI.Checkbox(text='Genesis SSL', name='genesis', value='genesis', checked=False), ) for x in self._wal: if not (x.name+' ('+x.stype+')') in alist: ui.find('certassign').append( UI.Checkbox(text=x.name, name='wassign[]', value=x.name, checked=False), ) wlist.append(x) self._wal = wlist for x in self._pal: if not x.text in alist: ui.find('certassign').append( UI.Checkbox(text=x.text, name='passign[]', value=x.text, checked=False), ) plist.append(x) self._pal = plist else: ui.remove('dlgGen') if self._cinfo: self._wal, self._pal = self._cc.get_ssl_capable() ui.find('certname').set('text', self._cinfo['name']) ui.find('domain').set('text', self._cinfo['domain']) ui.find('ikeytype').set('text', self._cinfo['keylength']+'-bit '+self._cinfo['keytype']) exp = self._cinfo['expiry'] exp = exp[0:4] + '-' + exp[4:6] + '-' + exp[6:8] + ', ' + exp[8:10] + ':' + exp[10:12] ui.find('expires').set('text', exp) alist = [] for cert in self.certs: if cert != self._cinfo: for i in cert['assign']: if i != '': alist.append(i) if not 'Genesis SSL' in alist: if 'Genesis SSL' in self._cinfo['assign']: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont='gen-arkos-round'), UI.Label(text='Genesis'), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/'+self._cinfo['name']+'/g') if show == 'e' else None), (UI.TipIcon(iconfont='gen-close', text='Unassign', id='uc/'+self._cinfo['name']+'/g', warning=('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled, and you will need to ' 'reload Genesis for changes to take place.')) if show == 'd' else None), ), ) ) for x in self._wal: if not (x.name+' ('+x.stype+')') in alist: if (x.name+' ('+x.stype+')') in self._cinfo['assign']: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont='gen-earth'), UI.Label(text=x.name), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/'+self._cinfo['name']+'/w/'+str(self._wal.index(x))) if show == 'e' else None), (UI.TipIcon(iconfont='gen-close', text='Unassign', id='uc/'+self._cinfo['name']+'/w/'+str(self._wal.index(x)), warning=('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled.')) if show == 'd' else None), ), ) ) for x in self._pal: if not x.text in alist: if x.text in self._cinfo['assign']: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont=x.iconfont), UI.Label(text=x.text), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/'+self._cinfo['name']+'/p/'+str(self._pal.index(x))) if show == 'e' else None), (UI.TipIcon(iconfont='gen-close', text='Unassign', id='uc/'+self._cinfo['name']+'/p/'+str(self._pal.index(x)), warning=('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled.')) if show == 'd' else None), ), ) ) else: ui.remove('dlgInfo') if self._upload: ui.append('main', UI.DialogBox( UI.FormLine(UI.TextInput(name='certname'), text='Name'), UI.FormLine(UI.FileInput(id='certfile'), text='Certificate file'), UI.FormLine(UI.FileInput(id='keyfile'), text='Certificate keyfile'), UI.FormLine(UI.FileInput(id='chainfile'), text='Certificate chainfile', help='This is optional, only put it if you know you need one.'), id='dlgUpload', mp=True)) return ui @url('^/certificates/dl$') def download(self, req, start_response): params = req['PATH_INFO'].split('/')[3:] + [''] filename = CertControl(self.app).get_cas()[0]['name']+'.pem' path = os.path.join('/etc/ssl/certs/genesis/ca', filename) f = open(path, 'rb') size = os.path.getsize(path) start_response('200 OK', [ ('Content-length', str(size)), ('Content-Disposition', 'attachment; filename=%s' % filename) ]) return f.read() @event('button/click') def on_click(self, event, params, vars = None): if params[0] == 'info': self._tab = 0 self._cinfo = self.certs[int(params[1])] elif params[0] == 'gen': self._tab = 0 self._gen = True elif params[0] == 'del': self._tab = 0 self._cc.remove(self.certs[int(params[1])]['name']) self.put_message('info', 'Certificate successfully deleted') elif params[0] == 'ac' and params[2] == 'p': self._tab = 0 self._cc.assign(self._cinfo['name'], [('plugin', self._pal[int(params[3])])]) self.put_message('info', '%s added to %s plugin' % (self._cinfo['name'], self._pal[int(params[3])].text)) self._cinfo = None elif params[0] == 'ac' and params[2] == 'w': self._tab = 0 self._cc.assign(self._cinfo['name'], [('webapp', self._wal[int(params[3])])]) self.put_message('info', '%s added to %s webapp' % (self._cinfo['name'], self._wal[int(params[3])].name)) self._cinfo = None elif params[0] == 'ac' and params[2] == 'g': self._tab = 0 self._cc.assign(self._cinfo['name'], [[('genesis')]]) self.put_message('info', '%s serving as Genesis certificate. Restart Genesis for changes to take effect' % self._cinfo['name']) self._cinfo = None elif params[0] == 'uc' and params[2] == 'p': self._tab = 0 self._cc.unassign(self._cinfo['name'], [('plugin', self._pal[int(params[3])])]) self.put_message('info', '%s removed from %s plugin, and SSL disabled.' % (self._cinfo['name'], self._pal[int(params[3])].text)) self._cinfo = None elif params[0] == 'uc' and params[2] == 'w': self._tab = 0 self._cc.unassign(self._cinfo['name'], [('webapp', self._wal[int(params[3])])]) self.put_message('info', '%s removed from %s webapp, and SSL disabled.' % (self._cinfo['name'], self._wal[int(params[3])].name)) self._cinfo = None elif params[0] == 'uc' and params[2] == 'g': self._tab = 0 self._cc.unassign(self._cinfo['name'], [[('genesis')]]) self.put_message('info', 'Certificate removed and SSL disabled for Genesis. Reload Genesis for changes to take effect') self._cinfo = None elif params[0] == 'upl': self._tab = 0 self._upload = True elif params[0] == 'cagen': self._tab = 1 self._cc.create_authority(self.app.get_backend(IHostnameManager).gethostname().lower()) elif params[0] == 'cadel': self._tab = 1 self._cc.delete_authority(self.cas[int(params[1])]) @event('form/submit') @event('dialog/submit') def on_submit(self, event, params, vars = None): if params[0] == 'dlgAdd': self._tab = 0 if vars.getvalue('action', '') == 'OK': pass elif params[0] == 'dlgGen': self._tab = 0 if vars.getvalue('action', '') == 'OK': if vars.getvalue('certname', '') == '': self.put_message('err', 'Certificate name is mandatory') elif re.search('\.|-|`|\\\\|\/|[ ]', vars.getvalue('certname')): self.put_message('err', 'Certificate name must not contain spaces, dots, dashes or special characters') elif vars.getvalue('certname', '') in [x['name'] for x in self.certs]: self.put_message('err', 'You already have a certificate with that name.') elif len(vars.getvalue('certcountry', '')) != 2: self.put_message('err', 'The country field must be a two-letter abbreviation') else: lst = [] if vars.getvalue('genesis', '') == '1': lst.append([('genesis')]) for i in range(0, len(self._wal)): try: if vars.getvalue('wassign[]')[i] == '1': lst.append(('webapp', self._wal[i])) except TypeError: pass for i in range(0, len(self._pal)): try: if vars.getvalue('passign[]')[i] == '1': lst.append(('plugin', self._pal[i])) except TypeError: pass cgw = CertGenWorker(self, vars.getvalue('certname'), vars, lst) cgw.start() self._wal = [] self._pal = [] self._gen = False elif params[0] == 'dlgInfo': self._tab = 0 self._cinfo = None self._wal = [] self._pal = [] elif params[0] == 'dlgUpload': self._tab = 0 if vars.getvalue('action', '') == 'OK': if not vars.has_key('certfile') and not vars.has_key('keyfile'): self.put_message('err', 'Please select at least a certificate and private key') elif not vars.has_key('certfile'): self.put_message('err', 'Please select a certificate file') elif not vars.has_key('keyfile'): self.put_message('err', 'Please select a key file') elif not vars.getvalue('certname', ''): self.put_message('err', 'Must choose a certificate name') elif vars.getvalue('certname', '') in [x['name'] for x in self.certs]: self.put_message('err', 'You already have a certificate with that name.') elif re.search('\.|-|`|\\\\|\/|[ ]', vars.getvalue('certname')): self.put_message('err', 'Certificate name must not contain spaces, dots, dashes or special characters') else: try: self._cc.add_ext_cert(vars.getvalue('certname'), vars['certfile'].value, vars['keyfile'].value, vars['chainfile'].value if vars.has_key('chainfile') else None) self.put_message('info', 'Certificate %s installed' % vars.getvalue('certname')) except Exception, e: self.put_message('err', 'Couldn\'t add certificate: %s' % str(e[0])) self.app.log.error('Couldn\'t add certificate: %s - Error: %s' % (str(e[0]), str(e[1]))) self._upload = None elif params[0] == 'frmCertSettings': self._tab = 1 if vars.getvalue('action', '') == 'OK': cfg = self.app.get_config(CertControl(self.app)) cfg.keylength = vars.getvalue('keylength', '2048') cfg.keytype = vars.getvalue('keytype', 'RSA') cfg.ciphers = vars.getvalue('ciphers', '') cfg.save() self.put_message('info', 'Settings saved successfully')
class CertificatesPlugin(CategoryPlugin, URLHandler): text = 'Certificates' iconfont = 'gen-certificate' folder = 'tools' def on_init(self): self.certs = sorted(self._cc.get_certs(), key=lambda x: x['name']) self.cas = sorted(self._cc.get_cas(), key=lambda x: x['name']) self._hostname = self.app.get_backend(IHostnameManager).gethostname().lower() def on_session_start(self): self._cc = CertControl(self.app) self._gen = None self._tab = 0 self._wal = [] self._pal = [] self._hostname = '' self._upload = None def get_ui(self): ui = self.app.inflate('certificates:main') ui.find('tabs').set('active', self._tab) cfg = self.app.get_config(CertControl(self.app)) ui.find('kl'+cfg.keylength).set('selected', True) ui.find('kt'+cfg.keytype.lower()).set('selected', True) ui.find('ciphers').set('value', cfg.ciphers) for s in self.certs: ui.find('certlist').append( UI.TblBtn( id='info/'+str(self.certs.index(s)), icon='gen-certificate', name=s['name'], subtext=s['keylength']+'-bit '+s['keytype'] ) ) ui.find('certlist').append( UI.TblBtn( id='gen', icon='gen-plus-circle', name='Generate certificate' ) ) ui.find('certlist').append( UI.TblBtn( id='upl', icon='gen-file-upload', name='Upload certificate' ) ) lst = ui.find('certauth') if not self.cas: lst.append(UI.Btn(text="Generate New", id="cagen")) for s in self.cas: exp = SystemTime.convert(s['expiry'], '%Y%m%d%H%M%SZ', self.app.gconfig.get('genesis', 'dformat', '%d %b %Y')) lst.append(UI.FormLine( UI.HContainer( UI.Label(text='Expires '+exp), UI.TipIcon(iconfont='gen-download', text='Download', id='cadl', onclick='window.open("/certificates/dl", "_blank")'), UI.TipIcon(iconfont='gen-close', text='Delete', id='cadel/' + str(self.cas.index(s))), ), text=s['name'], horizontal=True )) if self._gen: ui.find('certcn').set('value', self._hostname) self._wal, self._pal = self._cc.get_ssl_capable() alist, wlist, plist = [], [], [] for cert in self.certs: for i in cert['assign']: alist.append(i) if not {'type': 'genesis'} in alist: ui.find('certassign').append( UI.FormLine( UI.Checkbox(text='Genesis SSL', name='genesis', value='genesis', checked=False), checkbox=True) ) for x in self._wal: if not {'type': 'website', 'name': x.name} in alist: ui.find('certassign').append( UI.FormLine( UI.Checkbox(text=x.name, name='wassign[]', value=x.name, checked=False), checkbox=True) ) wlist.append(x) self._wal = wlist for x in self._pal: if not {'type': 'plugin', 'name': x.text} in alist: ui.find('certassign').append( UI.FormLine( UI.Checkbox(text=x.text, name='passign[]', value=x.text, checked=False), checkbox=True) ) plist.append(x) self._pal = plist else: ui.remove('dlgGen') if self._cinfo: self._wal, self._pal = self._cc.get_ssl_capable() ui.find('certname').set('text', self._cinfo['name']) ui.find('domain').set('text', self._cinfo['domain']) ui.find('ikeytype').set('text', self._cinfo['keylength']+'-bit '+self._cinfo['keytype']) exp = SystemTime.convert(self._cinfo['expiry'], '%Y%m%d%H%M%SZ', self.app.gconfig.get('genesis', 'dformat', '%d %b %Y')) ui.find('expires').set('text', exp) ui.find('sha1').set('text', self._cinfo['sha1']) ui.find('md5').set('text', self._cinfo['md5']) ui.find('dlgInfo').set('miscbtnid', 'del/' + str(self.certs.index(self._cinfo))) alist = [] for cert in self.certs: if cert != self._cinfo: for i in cert['assign']: alist.append(i) if not 'genesis' in [x['type'] for x in alist]: if 'genesis' in [x['type'] for x in self._cinfo['assign']]: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont='gen-arkos-round'), UI.Label(text='Genesis'), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/'+self._cinfo['name']+'/g') if show == 'e' else None), (UI.TipIcon(iconfont='gen-close', text='Unassign', id='uc/'+self._cinfo['name']+'/g', warning=('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled, and you will need to ' 'reload Genesis for changes to take place.')) if show == 'd' else None), ), ) ) for x in self._wal: if not x.name in [y['name'] for y in alist if y['type'] == 'website']: if x.name in [y['name'] for y in self._cinfo['assign'] if y['type'] == 'website']: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont='gen-earth'), UI.Label(text=x.name), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/'+self._cinfo['name']+'/w/'+str(self._wal.index(x))) if show == 'e' else None), (UI.TipIcon(iconfont='gen-close', text='Unassign', id='uc/'+self._cinfo['name']+'/w/'+str(self._wal.index(x)), warning=('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled.')) if show == 'd' else None), ), ) ) for x in self._pal: if not x.pid in [y['id'] for y in alist if y['type'] == 'plugin']: if x.pid in [y['id'] for y in self._cinfo['assign'] if y['type'] == 'plugin']: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont=x.iconfont), UI.Label(text=x.text), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/'+self._cinfo['name']+'/p/'+str(self._pal.index(x))) if show == 'e' else None), (UI.TipIcon(iconfont='gen-close', text='Unassign', id='uc/'+self._cinfo['name']+'/p/'+str(self._pal.index(x)), warning=('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled.')) if show == 'd' else None), ), ) ) else: ui.remove('dlgInfo') if self._upload: ui.append('main', UI.DialogBox( UI.FormLine(UI.TextInput(name='certname'), text='Name'), UI.FormLine(UI.FileInput(id='certfile'), text='Certificate file'), UI.FormLine(UI.FileInput(id='keyfile'), text='Certificate keyfile'), UI.FormLine(UI.FileInput(id='chainfile'), text='Certificate chainfile', help='This is optional, only put it if you know you need one.'), id='dlgUpload', mp=True)) return ui @url('^/certificates/dl$') def download(self, req, start_response): params = req['PATH_INFO'].split('/')[3:] + [''] filename = CertControl(self.app).get_cas()[0]['name']+'.pem' path = os.path.join('/etc/ssl/certs/genesis/ca', filename) f = open(path, 'rb') size = os.path.getsize(path) start_response('200 OK', [ ('Content-length', str(size)), ('Content-Disposition', 'attachment; filename=%s' % filename) ]) return f.read() @event('button/click') def on_click(self, event, params, vars = None): if params[0] == 'info': self._tab = 0 self._cinfo = self.certs[int(params[1])] elif params[0] == 'gen': self._tab = 0 self._gen = True elif params[0] == 'del': self._tab = 0 self._cinfo = None self._cc.remove(self.certs[int(params[1])]) self.put_message('success', 'Certificate successfully deleted') elif params[0] == 'ac' and params[2] == 'p': self._tab = 0 self._cc.assign(self._cinfo['name'], [('plugin', self._pal[int(params[3])])]) self.put_message('success', '%s added to %s plugin' % (self._cinfo['name'], self._pal[int(params[3])].text)) self._cinfo = None elif params[0] == 'ac' and params[2] == 'w': self._tab = 0 self._cc.assign(self._cinfo['name'], [('website', self._wal[int(params[3])])]) self.put_message('success', '%s added to %s website' % (self._cinfo['name'], self._wal[int(params[3])].name)) self._cinfo = None elif params[0] == 'ac' and params[2] == 'g': self._tab = 0 self._cc.assign(self._cinfo['name'], [[('genesis')]]) self.put_message('success', '%s serving as Genesis certificate. Restart Genesis for changes to take effect' % self._cinfo['name']) self._cinfo = None elif params[0] == 'uc' and params[2] == 'p': self._tab = 0 self._cc.unassign(('plugin', self._pal[int(params[3])])) self.put_message('success', '%s removed from %s plugin, and SSL disabled.' % (self._cinfo['name'], self._pal[int(params[3])].text)) self._cinfo = None elif params[0] == 'uc' and params[2] == 'w': self._tab = 0 self._cc.unassign(('website', self._wal[int(params[3])])) self.put_message('success', '%s removed from %s website, and SSL disabled.' % (self._cinfo['name'], self._wal[int(params[3])].name)) self._cinfo = None elif params[0] == 'uc' and params[2] == 'g': self._tab = 0 self._cc.unassign(('genesis')) self.put_message('success', 'Certificate removed and SSL disabled for Genesis. Reload Genesis for changes to take effect') self._cinfo = None elif params[0] == 'upl': self._tab = 0 self._upload = True elif params[0] == 'cagen': self._tab = 1 self._cc.create_authority(self._hostname) elif params[0] == 'cadel': self._tab = 1 self._cc.delete_authority(self.cas[int(params[1])]) @event('form/submit') @event('dialog/submit') def on_submit(self, event, params, vars = None): if params[0] == 'dlgAdd': self._tab = 0 if vars.getvalue('action', '') == 'OK': pass elif params[0] == 'dlgGen': self._tab = 0 if vars.getvalue('action', '') == 'OK': name = vars.getvalue('certname', '') if name == '': self.put_message('err', 'Certificate name is mandatory') elif re.search('\.|-|`|\\\\|\/|[ ]', name): self.put_message('err', 'Certificate name must not contain spaces, dots, dashes or special characters') elif name in [x['name'] for x in self.certs]: self.put_message('err', 'You already have a certificate with that name.') elif len(vars.getvalue('certcountry', '')) != 2: self.put_message('err', 'The country field must be a two-letter abbreviation') else: lst = [] if vars.getvalue('genesis', '') == '1': lst.append([('genesis')]) for i in range(0, len(self._wal)): try: if vars.getvalue('wassign[]')[i] == '1': lst.append(('website', self._wal[i])) except TypeError: pass for i in range(0, len(self._pal)): try: if vars.getvalue('passign[]')[i] == '1': lst.append(('plugin', self._pal[i])) except TypeError: pass self.statusmsg('Generating a certificate and key...') try: self._cc.gencert(name, vars, self._hostname) self.statusmsg('Assigning new certificate...') self._cc.assign(name, lst) self.put_message('success', 'Certificate successfully generated') except Exception, e: self.put_message('err', str(e)) self.app.log.error(str(e)) self._wal = [] self._pal = [] self._gen = False elif params[0] == 'dlgInfo': self._tab = 0 self._cinfo = None self._wal = [] self._pal = []
class CertificatesPlugin(CategoryPlugin): text = 'Certificates' iconfont = 'gen-certificate' folder = 'system' def on_init(self): self.certs = sorted(self._cc.get_certs(), key=lambda x: x['name']) def on_session_start(self): self._cc = CertControl(self.app) self._gen = None self._wal = [] self._pal = [] def get_ui(self): ui = self.app.inflate('certificates:main') lst = ui.find('certlist') for s in self.certs: lst.append(UI.DTR( UI.IconFont(iconfont='gen-certificate'), UI.Label(text=s['name']), UI.Label(text=', '.join(filter(None, s['assign']))), UI.HContainer( UI.TipIcon(iconfont='gen-info', text='Information', id='info/' + str(self.certs.index(s))), UI.TipIcon(iconfont='gen-close', text='Delete', id='del/' + str(self.certs.index(s)), warning=('Are you sure you wish to remove this certificate? ' 'SSL on all associated services will be disabled'), ), ), )) if self._gen: self._wal, self._pal = self._cc.get_ssl_capable() alist = [] for cert in self.certs: for i in cert['assign']: if i != '': alist.append(i) if not 'Genesis SSL' in alist: ui.find('certassign').append( UI.Checkbox(text='Genesis SSL', name='genesis', value='genesis', checked=False), ) for x in self._wal: if not (x['name']+' ('+x['type']+')') in alist: ui.find('certassign').append( UI.Checkbox(text=x['name'], name='wassign[]', value=x['name'], checked=False), ) for x in self._pal: if not x.text in alist: ui.find('certassign').append( UI.Checkbox(text=x.text, name='passign[]', value=x.text, checked=False), ) else: ui.remove('dlgGen') if self._cinfo: self._wal, self._pal = self._cc.get_ssl_capable() ui.find('certname').set('text', self._cinfo['name']) ui.find('domain').set('text', self._cinfo['domain']) exp = self._cinfo['expiry'] exp = exp[0:4] + '-' + exp[4:6] + '-' + exp[6:8] + ', ' + exp[8:10] + ':' + exp[10:12] ui.find('expires').set('text', exp) alist = [] for cert in self.certs: if cert != self._cinfo: for i in cert['assign']: if i != '': alist.append(i) if not 'Genesis SSL' in alist: if 'Genesis SSL' in self._cinfo['assign']: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont='gen-arkos-round'), UI.Label(text='Genesis'), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/'+self._cinfo['name']+'/g') if show == 'e' else None), (UI.TipIcon(iconfont='gen-close', text='Unassign', id='uc/'+self._cinfo['name']+'/g', warning=('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled, and you will need to ' 'reload Genesis for changes to take place.')) if show == 'd' else None), ), ) ) for x in self._wal: if not (x['name']+' ('+x['type']+')') in alist: if (x['name']+' ('+x['type']+')') in self._cinfo['assign']: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont='gen-earth'), UI.Label(text=x['name']), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/'+self._cinfo['name']+'/w/'+str(self._wal.index(x))) if show == 'e' else None), (UI.TipIcon(iconfont='gen-close', text='Unassign', id='uc/'+self._cinfo['name']+'/w/'+str(self._wal.index(x)), warning=('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled.')) if show == 'd' else None), ), ) ) for x in self._pal: if not x.text in alist: if x.text in self._cinfo['assign']: ic, ict, show = 'gen-checkmark-circle', 'Assigned', 'd' else: ic, ict, show = None, None, 'e' ui.find('certassign').append( UI.DTR( UI.IconFont(iconfont=ic, text=ict), UI.IconFont(iconfont=x.iconfont), UI.Label(text=x.text), UI.HContainer( (UI.TipIcon(iconfont='gen-checkmark-circle', text='Assign', id='ac/'+self._cinfo['name']+'/p/'+str(self._pal.index(x))) if show == 'e' else None), (UI.TipIcon(iconfont='gen-close', text='Unassign', id='uc/'+self._cinfo['name']+'/p/'+str(self._pal.index(x)), warning=('Are you sure you wish to unassign this certificate? ' 'SSL on this service will be disabled.')) if show == 'd' else None), ), ) ) else: ui.remove('dlgInfo') return ui @event('button/click') def on_click(self, event, params, vars = None): if params[0] == 'add': pass elif params[0] == 'info': self._cinfo = self.certs[int(params[1])] elif params[0] == 'gen': self._gen = True elif params[0] == 'del': self._cc.remove(self.certs[int(params[1])]['name']) self.put_message('info', 'Certificate successfully deleted') elif params[0] == 'ac' and params[2] == 'p': self._cc.assign(self._cinfo['name'], [('plugin', self._pal[int(params[3])])]) self.put_message('info', '%s added to %s plugin' % (self._cinfo['name'], self._pal[int(params[3])].text)) self._cinfo = None elif params[0] == 'ac' and params[2] == 'w': self._cc.assign(self._cinfo['name'], [('webapp', self._wal[int(params[3])])]) self.put_message('info', '%s added to %s webapp' % (self._cinfo['name'], self._wal[int(params[3])]['name'])) self._cinfo = None elif params[0] == 'ac' and params[2] == 'g': self._cc.assign(self._cinfo['name'], [[('genesis')]]) self.put_message('info', '%s serving as Genesis certificate. Restart Genesis for changes to take effect' % self._cinfo['name']) self._cinfo = None elif params[0] == 'uc' and params[2] == 'p': self._cc.unassign(self._cinfo['name'], [('plugin', self._pal[int(params[3])])]) self.put_message('info', '%s removed from %s plugin, and SSL disabled.' % (self._cinfo['name'], self._pal[int(params[3])].text)) self._cinfo = None elif params[0] == 'uc' and params[2] == 'w': self._cc.unassign(self._cinfo['name'], [('webapp', self._wal[int(params[3])])]) self.put_message('info', '%s removed from %s webapp, and SSL disabled.' % (self._cinfo['name'], self._wal[int(params[3])]['name'])) self._cinfo = None elif params[0] == 'uc' and params[2] == 'g': self._cc.unassign(self._cinfo['name'], [[('genesis')]]) self.put_message('info', 'Certificate removed and SSL disabled for Genesis. Restart Genesis for changes to take effect') self._cinfo = None @event('dialog/submit') def on_submit(self, event, params, vars = None): if params[0] == 'dlgAdd': if vars.getvalue('action', '') == 'OK': pass elif params[0] == 'dlgGen': if vars.getvalue('action', '') == 'OK': if vars.getvalue('certname', '') == '': self.put_message('err', 'Certificate name is mandatory') elif vars.getvalue('certname', '') in [x['name'] for x in self.certs]: self.put_message('err', 'You already have a certificate with that name.') else: lst = [] if vars.getvalue('genesis', '') == '1': lst.append([('genesis')]) for i in range(0, len(self._wal)): try: if vars.getvalue('wassign[]')[i] == '1': lst.append(('webapp', self._wal[i])) except TypeError: pass for i in range(0, len(self._pal)): try: if vars.getvalue('passign[]')[i] == '1': lst.append(('plugin', self._pal[i])) except TypeError: pass cgw = CertGenWorker(self, vars.getvalue('certname'), vars, lst) cgw.start() self._wal = [] self._pal = [] self._gen = False elif params[0] == 'dlgInfo': self._cinfo = None self._wal = [] self._pal = []