Hay William. RDN = 'cn'
class nsUserAccountRole(Account): def __init__(self, instance, dn=None): super(nsUserAccountRole, self).__init__(instance, dn) self._rdn_attribute = RDN self._create_objectclasses = [ 'top', 'LDAPsubentry', 'nsRoleDefinition', 'nsComplexRoleDefinition', 'nsFilteredRoleDefinition' ] self._childobject = Account user_compare_exclude = [ 'nsUniqueId', 'modifyTimestamp', 'createTimestamp', 'entrydn' ] self._compare_exclude = self._compare_exclude + user_compare_exclude self._protected = False class nsUserAccountRoles(DSLdapObjects): def __init__(self, instance, basedn, rdn='ou=People'): super(nsUserAccountRoles, self).__init__(instance) self._objectclasses = [ 'top', 'LDAPsubentry', 'nsRoleDefinition', 'nsComplexRoleDefinition', 'nsFilteredRoleDefinition' ] self._filterattrs = [RDN, 'cn'] self._childobject = nsUserAccountRole if rdn is None: self._basedn = basedn else: self._basedn = '{},{}'.format(rdn, basedn) Here i am not using nsUserAccount in nsUserAccountRole as it requires 'uid' which is not allowed in nsFilteredRoleDefinition and nsRoleDefinition . Below are usages: user=nsUserAccountRole(topo.standalone,'cn=tuser1,ou=People,dc=example,dc=com') user_props={'cn':'Anuj', 'nsRoleFilter':'cn=*'} user.create(properties=user_props, basedn=SUFFIX) nsUserAccountRoles(topo.standalone, DEFAULT_SUFFIX).list()[0].dn >> 'cn=tuser1,ou=People,dc=example,dc=com' nsUserAccountRoles(topo.standalone, DEFAULT_SUFFIX).create(properties=user_props) >>> <dsdsds.nsUserAccountRole object at 0x7fb72d259f98> nsUserAccountRoles(topo.standalone, DEFAULT_SUFFIX).list()[1].dn >>> 'cn=Anuj,ou=People,dc=example,dc=com' Let me know , what you think . Regards Anuj Borah On Tue, Jan 15, 2019 at 6:30 AM William Brown <wbr...@suse.de> wrote: > > > On 14 Jan 2019, at 19:28, Anuj Borah <abo...@redhat.com> wrote: > > > > Hi William , > > > > Just find out a way to do it . > > > This isn’t quite what I had in mind. > > Remember, we should be able to compose nsRole types to various other > objects if required (despite my dislike of nsRoles …). > > We have "nsUserAccount(Account)”, and we need to be able to extend it with > nsRole types. > > One way to achieve this is: > > class nsRoleDefinition(object): > def __init__(self, instance, dn=None): > if ‘_create_objectclasses’ not in self: > raise Exception …. > # So we must have been combined with a type to add roles > self._create_objectclasses.append(’nsFilteredRoleDefinition’) > > > class nsUserAccountRole(nsUserAccount, nsRoleDefinition): > def __init__(self, instance, dn=None): > super(nsUserAccount, self).__init__(instance, dn) > super(nsRoleDefinition, self).__init__(instance, dn) > > > > Then you would use the nsUserAccountRole like normal. (I think we may need > a similar “nsUserAccountRoles" for the muliple search parts) > > A benefit to this, is you could have role-specific functions like > setting/changing the filter, but you never loose the “account” features > like bind. Provided a method is uniquely sourced, I think python takes the > implementation that is unique, or it takes the “first”. So this should all > just work. > > The main benefit here is it’s really clean, we can compose this to other > types. It also avoids any duplication of class definitions and logic etc. > > I think this is how I would like to see it created. It may be worth making > a “ticket” just for the nsRole parts and splitting your test for nsRoles > out of the mega-patch you have. > > > > > class UserAccountnsRole(Account): > > > > def __init__(self, instance, dn=None): > > super(UserAccountnsRole, self).__init__(instance, dn) > > self._rdn_attribute = RDN > > self._create_objectclasses = [ > > 'top', > > 'LDAPsubentry', > > 'nsRoleDefinition', > > 'nsComplexRoleDefinition', > > 'nsFilteredRoleDefinition' > > ] > > user_compare_exclude = [ > > 'nsUniqueId', > > 'modifyTimestamp', > > 'createTimestamp', > > 'entrydn' > > ] > > self._compare_exclude = self._compare_exclude + > user_compare_exclude > > self._protected = False > > > > def _validate(self, rdn, properties, basedn): > > if 'ntUserDomainId' in properties and 'ntUser' not in > self._create_objectclasses: > > self._create_objectclasses.append('ntUser') > > > > return super(UserAccountnsRole, self)._validate(rdn, properties, > basedn) > > > > > > def create_test_user_nsrole(instance, cn, nsRoleFilter, description, > suffix=None): > > global test_user_id > > if cn is None: > > cn = "testuser_" + str(test_user_id) > > test_user_id += 1 > > if suffix is None: > > suffix = DEFAULT_SUFFIX > > dn = "cn=" + cn + "," + suffix > > properties = { > > 'cn': cn, > > "nsRoleFilter": nsRoleFilter, > > "description": description, > > } > > user = UserAccountnsRole(instance, dn) > > user.create(properties=properties) > > return user > > Now just using create_test_user_nsrole we will be able to create entries > with nsRoles. > > > > > > Regards > > Anuj Borah > > > > > > > > > > > > > > On Mon, Jan 7, 2019 at 2:30 PM William Brown <will...@blackhats.net.au> > wrote: > > Hi, > > > > I’ve been speaking to Anuj Borah about a PR they made, and how we can > properly represent nsRole. > > > > because nsRoles are an extra objectClass, rather than a standalone one, > we need a way to represent this properly. > > > > It’s probably a good idea to use some of pythons composability here, > where we could do something like: > > > > class nsFilteredRole(DSLdapObject): > > > > > > class User(DSldapObject): > > > > class User_nsFilteredRole(User, nsFilteredRole): > > > > Then to have a way to define and have each subclass called, and asserted > for correctness. A question is how we would handle: > > > > user = User.create(…) > > # How to convert user to User_nsFilteredRole > > > > We could do something like: > > > > User_nsFilteredRole.from(user) > > > > And have a from that does a valid conversion based on types and adds in > the required role parts? > > > > This isn’t a common scenario, so I think having a limited set of well > understood types that require this type of conversion would be okay. > > > > Thought? *looking at you Simon* :) > > > > PS: It’s good to be back > > > > -- > > Sincerely, > > > > William > > _______________________________________________ > > 389-devel mailing list -- 389-devel@lists.fedoraproject.org > > To unsubscribe send an email to 389-devel-le...@lists.fedoraproject.org > > Fedora Code of Conduct: https://getfedora.org/code-of-conduct.html > > List Guidelines: https://fedoraproject.org/wiki/Mailing_list_guidelines > > List Archives: > https://lists.fedoraproject.org/archives/list/389-devel@lists.fedoraproject.org > > _______________________________________________ > > 389-devel mailing list -- 389-devel@lists.fedoraproject.org > > To unsubscribe send an email to 389-devel-le...@lists.fedoraproject.org > > Fedora Code of Conduct: https://getfedora.org/code-of-conduct.html > > List Guidelines: https://fedoraproject.org/wiki/Mailing_list_guidelines > > List Archives: > https://lists.fedoraproject.org/archives/list/389-devel@lists.fedoraproject.org > _______________________________________________ > 389-devel mailing list -- 389-devel@lists.fedoraproject.org > To unsubscribe send an email to 389-devel-le...@lists.fedoraproject.org > Fedora Code of Conduct: https://getfedora.org/code-of-conduct.html > List Guidelines: https://fedoraproject.org/wiki/Mailing_list_guidelines > List Archives: > https://lists.fedoraproject.org/archives/list/389-devel@lists.fedoraproject.org >
_______________________________________________ 389-devel mailing list -- 389-devel@lists.fedoraproject.org To unsubscribe send an email to 389-devel-le...@lists.fedoraproject.org Fedora Code of Conduct: https://getfedora.org/code-of-conduct.html List Guidelines: https://fedoraproject.org/wiki/Mailing_list_guidelines List Archives: https://lists.fedoraproject.org/archives/list/389-devel@lists.fedoraproject.org