5 Gentoo-keys - gkeyldap/actions.py
7 Primary api interface module
9 @copyright: 2012 by Brian Dolbec <dol-sen@gentoo.org>
10 @license: GNU GPL2, see COPYING for details.
16 from gkeys.config import GKEY
17 from gkeys.seed import Seeds
18 from gkeyldap.search import (LdapSearch, UID, gkey2ldap_map, gkey2SEARCH)
28 Avialable_Actions = ['ldapsearch', 'updateseeds']
31 def get_key_ids(key, info):
32 '''Small utility function to return only keyid (short)
35 @param key: string, the key length desired
36 @param info: list of keysid's to process
37 @return list of the desired key length id's
41 if x.startswith('0x'):
42 mylen = KEY_LEN[key] + 2
50 class Actions(object):
53 def __init__(self, config, output=None, logger=None):
58 self.fingerprint_re = re.compile('[0-9A-Fa-f]{40}')
61 def ldapsearch(self, args):
63 self.logger.info("Search...establishing connection")
64 self.output("Search...establishing connection")
66 self.logger.info("Aborting Search...Connection failed")
67 self.output("Aborting Search...Connection failed")
69 self.logger.debug("MAIN: _action_ldapsearch; args = %s" % str(args))
70 x, target, search_field = self.get_args(args)
71 results = l.search(target, search_field)
72 devs = l.result2dict(results, gkey2ldap_map[x])
73 for dev in sorted(devs):
74 self.output(dev, devs[dev])
75 self.output("============================================")
76 self.output("Total number of devs in results:", len(devs))
80 def updateseeds(self, args):
81 self.logger.info("Beginning ldap search...")
82 self.output("Beginning ldap search...")
85 self.output("Aborting Update...Connection failed")
87 results = l.search('*', UID)
88 info = l.result2dict(results, 'uid')
90 "MAIN: _action_updateseeds; got results :) converted to info")
91 if not self.create_seedfile(info):
92 self.logger.error("Dev seed file update failure: "
93 "Original seed file is intact & untouched.")
94 old = self.config['dev-seedfile'] + '.old'
96 self.output("Backing up existing file...")
97 if os.path.exists(old):
99 "MAIN: _action_updateseeds; Removing 'old' seed file: %s"
102 if os.path.exists(self.config['dev-seedfile']):
104 "MAIN: _action_updateseeds; Renaming current seed file to: "
106 os.rename(self.config['dev-seedfile'], old)
108 "MAIN: _action_updateseeds; Renaming '.new' seed file to: %s"
109 % self.config['dev-seedfile'])
110 os.rename(self.config['dev-seedfile'] + '.new',
111 self.config['dev-seedfile'])
114 self.output("Developer Seed file updated")
118 def create_seedfile(self, devs):
119 self.output("Creating seeds from ldap data...")
120 filename = self.config['dev-seedfile'] + '.new'
121 self.seeds = Seeds(filename)
123 for dev in sorted(devs):
124 if devs[dev]['gentooStatus'][0] not in ['active']:
126 #self.logger.debug("create_seedfile, dev = "
127 # "%s, %s" % (str(dev), str(devs[dev])))
128 keyinfo = self.build_gkeylist(devs[dev])
130 new_gkey = GKEY._make(keyinfo)
131 self.seeds.add(new_gkey)
133 self.output("Total number of seeds created:", count)
134 self.output("Seeds created...saving file: %s" % filename)
135 return self.seeds.save()
140 for x in ['nick', 'name', 'gpgkey', 'fingerprint', 'status']:
142 target = getattr(args, x)
143 search_field = gkey2SEARCH[x]
145 return (x, target, search_field)
149 def build_gkeydict(self, info):
151 for x in GKEY._fields:
152 field = gkey2ldap_map[x]
156 # strip errant line feeds
157 values = [y.strip('\n') for y in info[field]]
158 if values and values in ['uid', 'cn' ]:
160 # separate out short/long key id's
161 elif values and x in ['keyid', 'longkeyid']:
162 value = get_key_ids(x, values)
165 if 'undefined' in values:
166 self.logger.error('%s = "undefined" for %s, %s'
167 %(field, info['uid'][0], info['cn'][0]))
175 def build_gkeylist(self, info):
178 keyid_missing = False
179 # assume it's good until found an error is found
181 #self.logger.debug("MAIN: build_gkeylist; info = %s" % str(info))
182 for x in GKEY._fields:
183 field = gkey2ldap_map[x]
188 # strip errant line feeds
189 values = [y.strip('\n') for y in info[field]]
190 if values and field in ['uid', 'cn' ]:
192 # separate out short/long key id's
193 elif values and x in ['keyid', 'longkeyid']:
194 value = get_key_ids(x, values)
197 elif values and x in ['fingerprint']:
198 value = [v.replace(' ', '') for v in values]
201 if 'undefined' in values:
202 self.logger.error('ERROR in ldap info for: %s, %s'
203 %(info['uid'][0],info['cn'][0]))
204 self.logger.error(' %s = "undefined"' %(field))
206 keyinfo.append(value)
208 self.logger.error('ERROR in ldap info for: %s, %s'
209 %(info['uid'][0],info['cn'][0]))
210 self.logger.error(' MISSING or EMPTY ldap field ' +
211 '[%s] GPGKey field [%s]' %(field, x))
212 if x in ['keyid', 'longkeyid']:
216 if not keyid_found and not keyid_missing:
218 gpgkey = info[gkey2ldap_map['longkeyid']]
220 gpgkey = 'Missing from ldap info'
221 self.logger.error('ERROR in ldap info for: %s, %s'
222 %(info['uid'][0],info['cn'][0]))
223 self.logger.error(' A valid keyid or longkeyid was not found '
224 "%s : gpgkey = %s" %(info['cn'][0], gpgkey))
227 if keyinfo[5]: # fingerprints exist check
228 is_ok = self._check_fingerprint_integrity(info, keyinfo)
229 is_match = self._check_id_fingerprint_match(info, keyinfo)
230 if not is_ok or not is_match:
237 def _check_id_fingerprint_match(self, info, keyinfo):
238 # assume it's good until found an error is found
241 # skip blank id field
245 index = len(y.lstrip('0x'))
246 if y.lstrip('0x').lower() not in [x[-index:].lower() for x in keyinfo[5]]:
247 self.logger.error('ERROR in ldap info for: %s, %s'
248 %(info['uid'][0],info['cn'][0]))
249 self.logger.error(' ' + str(keyinfo))
250 self.logger.error(' GPGKey id %s not found in the '
251 % y.lstrip('0x') + 'listed fingerprint(s)')
256 def _check_fingerprint_integrity(self, info, keyinfo):
257 # assume it's good until found an error is found
260 # check fingerprint integrity
262 self.logger.error('ERROR in ldap info for: %s, %s'
263 %(info['uid'][0],info['cn'][0]))
264 self.logger.error(' GPGKey incorrect fingerprint ' +
265 'length (%s) for fingerprint: %s' %(len(x), x))
268 if not self.fingerprint_re.match(x):
269 self.logger.error('ERROR in ldap info for: %s, %s'
270 %(info['uid'][0],info['cn'][0]))
271 self.logger.error(' GPGKey: Non hexadecimal digits in ' +
272 'fingerprint for fingerprint: ' + x)