From 241f55154ecbfa375abe1859a8c7737476c5f6bb Mon Sep 17 00:00:00 2001 From: Valentin Samir Date: Sat, 15 Mar 2014 22:47:04 +0100 Subject: [PATCH] =?UTF-8?q?[objets]=20Cr=C3=A9ation=20et=20suppression=20d?= =?UTF-8?q?e=20compte=20crans?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- objets.py | 166 +++++++++++++++++++++++++++++++++++------------------- 1 file changed, 108 insertions(+), 58 deletions(-) diff --git a/objets.py b/objets.py index 09e9a02..b2f6c8e 100644 --- a/objets.py +++ b/objets.py @@ -44,6 +44,7 @@ import re import datetime import time import ldap +import random import traceback from ldap.modlist import addModlist, modifyModlist @@ -686,6 +687,113 @@ class proprio(CransLdapObject): self.attribs = self.attribs + crans_account_attribs self.full = True + def delete_compte(self, mail): + # Je pense qu'en pratique cette vérification ne sert à rien puisqu'on se fera jetter à la tentative de modification + # de userPassword, mail, homeDirectory, canonicalAlias, etc… + if not self.may_be(variables.deleted, self.conn.droits + self.conn._check_parent(self.dn) + self.conn._check_self(self.dn)): + raise EnvironmentError("Vous n'avez pas le droit de supprimer %s et donc vous ne pouvez supprimer son compte." % self.dn) + if not u'cransAccount' in self['objectClass']: + raise EnvironmentError("L'adhérent n'a pas de compte crans") + else: + self['userPassword'] = [] + self['mail'] = mail + self['homeDirectory'] = [] + self['canonicalAlias'] = [] + self['cn'] = [] + self['loginShell'] = [] + self['uidNumber'] = [] + self['gidNumber'] = [] + self['gecos'] = [] + self['shadowExpire' ]=[] + self['uid' ]=[] + self._modifs['objectClass'] = [u'adherent'] + self.attribs = list(set(self.attribs).difference(crans_account_attribs)) + self.full = False + + + def compte(self, login = None, uidNumber=0, hash_pass = '', shell=config.login_shell): + u"""Renvoie le nom du compte crans. S'il n'existe pas, et que login + est précisé, le crée.""" + + if u'posixAccount' in self['objectClass']: + return self.attrs['uid'][0] + + elif login: + fn = crans_utils.strip_accents(unicode(self.attrs['prenom'][0]).capitalize()) + ln = crans_utils.strip_accents(unicode(self.attrs['nom'][0]).capitalize()) + login = crans_utils.strip_spaces(crans_utils.strip_accents(login), by=u'-').lower() + if not re.match('^[a-z][-a-z]{1,15}$', login): + raise ValueError("Le login a entre 2 et 16 lettres, il peut contenir (pas au début) des - ") + if crans_utils.mailexist(login): + raise ValueError("Login existant ou correspondant à un alias mail.") + + home = u'/home/' + login + if os.path.exists(home): + raise ValueError('Création du compte impossible : home existant') + + if os.path.exists("/var/mail/" + login): + raise ValueError('Création du compte impossible : /var/mail/%s existant' % str(login)) + + if not self.full: + self.attribs = self.attribs + crans_account_attribs + self.full = True + self['uid' ] = [login] + self['homeDirectory'] = [home] + self['mail'] = [login + u"@crans.org"] + calias = crans_utils.strip_spaces(fn) + u'.' + crans_utils.strip_spaces(ln) + '@crans.org' + if crans_utils.mailexist(calias): + calias = login + self['canonicalAlias'] = [calias] + self._modifs['objectClass'] = [u'adherent', u'cransAccount', u'posixAccount', u'shadowAccount'] + self['cn'] = [ fn + u' ' + ln ] + self['loginShell'] = [unicode(shell)] + self['userPassword'] = [unicode(hash_pass)] + + if uidNumber: + if self.conn.search(u'(uidNumber=%s)' % uidNumber): + raise ValueError(u'uidNumber pris') + else: + pool_uid = range(1001, 9999) + random.shuffle(pool_uid) + while len(pool_uid) > 0: + uidNumber = pool_uid.pop() # On choisit un uid + if not self.conn.search(u'(uidNumber=%s)' % uidNumber): + break + if not len(pool_uid): + raise ValueError("Plus d'uid disponibles !") + + self['uidNumber'] = [unicode(uidNumber)] + self['gidNumber'] = [unicode(config.gid)] + self['gecos'] = [unicode(self._modifs['cn'][0]) + u',,,'] + + else: + raise EnvironmentError("L'adhérent n'a pas de compte crans") + + def may_be(self, what, liste): + """Teste si liste peut faire ce qui est dans what, pour + what élément de {create, delete, modify}. + On passe une liste de droits plutôt que l'objet car il faut ajouter + les droits soi et parent. + Retourne un booléen + """ + # On ne peut supprimer un objet que si on a au moins autant de droit que lui + if what == variables.deleted: + modifiables = set() + for i in liste: + if i in attributs.DROITS_SUPERVISEUR: + modifiables = modifiables.union(attributs.DROITS_SUPERVISEUR[i]) + modifiables = list(modifiables) + + for droit in self.get('droits', []): + if droit not in modifiables: + return False + # Notez qu'en pratique, ça ne sert à rien puisque can_be_by[variables.deleted] + # ne contient que nounou et bureau. Ça va juste empêcher le bureau de supprimer + # des nounous + + return super(proprio, self).may_be(what, liste) + + def sursis_carte(self): for h in self['historique'][::-1]: x = re.match("(.*),.* : .*(paiement\+%s|inscription).*" % (config.ann_scol,), h.value) @@ -993,64 +1101,6 @@ class adherent(proprio): self._imprimeur_clubs = self.conn.search(u'imprimeurClub=%s' % self['aid'][0], scope = 1, mode=self.mode) return self._imprimeur_clubs - def compte(self, login = None, uidNumber=0, hash_pass = '', shell=config.login_shell): - u"""Renvoie le nom du compte crans. S'il n'existe pas, et que uid - est précisé, le crée.""" - - if u'posixAccount' in self['objectClass']: - return self.attrs['uid'][0] - - elif login: - fn = crans_utils.strip_accents(unicode(self.attrs['prenom'][0]).capitalize()) - ln = crans_utils.strip_accents(unicode(self.attrs['nom'][0]).capitalize()) - login = crans_utils.strip_accents(login).lower() - if not re.match('^[a-z][-a-z]{1,15}$', login): - raise ValueError("Le login a entre 2 et 16 lettres, il peut contenir (pas au début) des - ") - if crans_utils.mailexist(login): - raise ValueError("Login existant ou correspondant à un alias mail.") - - home = u'/home/' + login - if os.path.exists(home): - raise ValueError('Création du compte impossible : home existant') - - if os.path.exists("/var/mail/" + login): - raise ValueError('Création du compte impossible : /var/mail/%s existant' % login) - - if not self.full: - self.attribs = self.attribs + crans_account_attribs - self.full = True - self['homeDirectory'] = [home] - self['mail'] = [login + u"@crans.org"] - self['uid' ] = [login] - calias = crans_utils.strip_spaces(fn) + u'.' + crans_utils.strip_spaces(ln) - if crans_utils.mailexist(calias): - calias = login - self['canonicalAlias'] = [calias] - self['objectClass'] = [u'adherent', u'cransAccount', u'posixAccount', u'shadowAccount'] - self['cn'] = [ fn + u' ' + ln ] - self['loginShell'] = [unicode(shell)] - self['userPassword'] = [unicode(hash_pass)] - - if uidNumber: - if self.conn.search(u'(uidNumber=%s)' % uidNumber): - raise ValueError(u'uidNumber pris') - else: - pool_uid = range(1001, 9999) - random.shuffle(pool_uid) - while len(pool_uid) > 0: - uidNumber = pool_uid.pop() # On choisit un uid - if not self.conn.search(u'(uidNumber=%s)' % uidNumber): - break - if not len(pool_uid): - raise ValueError("Plus d'uid disponibles !") - - self['uidNumber'] = [unicode(uidNumber)] - self['gidNumber'] = [unicode(config.gid)] - self['gecos'] = [self._modifs['cn'][0] + u',,,'] - - #self.save() - else: - raise EnvironmentError("L'adhérent n'a pas de compte crans") def delete(self, comm="", login=None): clubs = self.conn.search(u"(|(responsable=%s)(imprimeurClub=%s))" % (self['aid'][0], self['aid'][0]))