From 434620ee342ac4767beccec647a318bfa7743dfa Mon Sep 17 00:00:00 2001 From: Rob Crittenden Date: Thu, 18 Aug 2022 08:21:58 -0400 Subject: [PATCH] doc: Update LDAP grace period design with default values New group password policies will get -1 (unlimited) on creation by default. Existing group password policies will remain untouched and those created prior will be treated as no BIND allowed. Fixes: https://pagure.io/freeipa/issue/9212 Signed-off-by: Rob Crittenden Reviewed-By: Florence Blanc-Renaud --- doc/designs/ldap_grace_period.md | 17 ++++++++++++++++- 1 file changed, 16 insertions(+), 1 deletion(-) diff --git a/doc/designs/ldap_grace_period.md b/doc/designs/ldap_grace_period.md index 4b9db3424..e26aedda9 100644 --- a/doc/designs/ldap_grace_period.md +++ b/doc/designs/ldap_grace_period.md @@ -51,7 +51,22 @@ The basic flow is: On successful password reset (by anyone) reset the user's passwordGraceUserTime to 0. -The default value on install/upgrade will be -1 to retail existing behavior. +Range values for passwordgracelimit are: + +-1 : password grace checking is disabled + 0 : no grace BIND are allowed at all post-expiration + 1..MAXINT: the number of BIND allowed post-expiration + +The default value for the global policy on install/upgrade will be -1 to +retain existing behavior. + +New group password policies will default to -1 to retain previous +behavior. + +Existing group policies with no grace limit set are updated to use +the default unlimited value, -1. This is done because lack of value in +LDAP is treated as 0 so any existing group policies would not allow +post-expiration BIND so this will avoid confusion. The per-user attempts will not be replicated. -- 2.37.2 From 497a57e7a6872fa30d1855a1d91a455bfdbf9300 Mon Sep 17 00:00:00 2001 From: Rob Crittenden Date: Thu, 4 Aug 2022 12:04:22 -0400 Subject: [PATCH] Set default gracelimit on group password policies to -1 This will retain previous behavior of unlimited LDAP BIND post-expiration. Fixes: https://pagure.io/freeipa/issue/9212 Signed-off-by: Rob Crittenden Reviewed-By: Florence Blanc-Renaud --- API.txt | 2 +- ipaserver/plugins/pwpolicy.py | 2 ++ ipatests/test_xmlrpc/test_pwpolicy_plugin.py | 2 ++ 3 files changed, 5 insertions(+), 1 deletion(-) diff --git a/API.txt b/API.txt index 5ba9add13..d7ea74f08 100644 --- a/API.txt +++ b/API.txt @@ -4075,7 +4075,7 @@ option: Int('krbpwdlockoutduration?', cli_name='lockouttime') option: Int('krbpwdmaxfailure?', cli_name='maxfail') option: Int('krbpwdmindiffchars?', cli_name='minclasses') option: Int('krbpwdminlength?', cli_name='minlength') -option: Int('passwordgracelimit?', cli_name='gracelimit', default=-1) +option: Int('passwordgracelimit?', autofill=True, cli_name='gracelimit', default=-1) option: Flag('raw', autofill=True, cli_name='raw', default=False) option: Str('setattr*', cli_name='setattr') option: Str('version?') diff --git a/ipaserver/plugins/pwpolicy.py b/ipaserver/plugins/pwpolicy.py index 4428aede2..f4ebffd5c 100644 --- a/ipaserver/plugins/pwpolicy.py +++ b/ipaserver/plugins/pwpolicy.py @@ -408,6 +408,7 @@ class pwpolicy(LDAPObject): minvalue=-1, maxvalue=Int.MAX_UINT32, default=-1, + autofill=True, ), ) @@ -539,6 +540,7 @@ class pwpolicy_add(LDAPCreate): keys[-1], krbpwdpolicyreference=dn, cospriority=options.get('cospriority') ) + return dn def post_callback(self, ldap, dn, entry_attrs, *keys, **options): diff --git a/ipatests/test_xmlrpc/test_pwpolicy_plugin.py b/ipatests/test_xmlrpc/test_pwpolicy_plugin.py index 8eee69c18..fc785223b 100644 --- a/ipatests/test_xmlrpc/test_pwpolicy_plugin.py +++ b/ipatests/test_xmlrpc/test_pwpolicy_plugin.py @@ -387,6 +387,7 @@ class test_pwpolicy_mod_cospriority(Declarative): krbpwdhistorylength=[u'10'], krbpwdmindiffchars=[u'3'], krbpwdminlength=[u'8'], + passwordgracelimit=[u'-1'], objectclass=objectclasses.pwpolicy, ), summary=None, @@ -417,6 +418,7 @@ class test_pwpolicy_mod_cospriority(Declarative): krbpwdhistorylength=[u'10'], krbpwdmindiffchars=[u'3'], krbpwdminlength=[u'8'], + passwordgracelimit=[u'-1'], ), summary=None, value=u'ipausers', -- 2.37.2 From a4ddaaf3048c4e8d78a1807af7266ee40ab3a30b Mon Sep 17 00:00:00 2001 From: Rob Crittenden Date: Thu, 4 Aug 2022 12:04:41 -0400 Subject: [PATCH] Set default on group pwpolicy with no grace limit in upgrade If an existing group policy lacks a password grace limit update it to -1 on upgrade. Fixes: https://pagure.io/freeipa/issue/9212 Signed-off-by: Rob Crittenden Reviewed-By: Florence Blanc-Renaud --- .../updates/90-post_upgrade_plugins.update | 1 + ipaserver/install/plugins/update_pwpolicy.py | 66 +++++++++++++++++++ 2 files changed, 67 insertions(+) diff --git a/install/updates/90-post_upgrade_plugins.update b/install/updates/90-post_upgrade_plugins.update index c7ec71d49..6fe91aa6c 100644 --- a/install/updates/90-post_upgrade_plugins.update +++ b/install/updates/90-post_upgrade_plugins.update @@ -26,6 +26,7 @@ plugin: update_ra_cert_store plugin: update_mapping_Guests_to_nobody plugin: fix_kra_people_entry plugin: update_pwpolicy +plugin: update_pwpolicy_grace # last # DNS version 1 diff --git a/ipaserver/install/plugins/update_pwpolicy.py b/ipaserver/install/plugins/update_pwpolicy.py index dca44ce43..4185f0343 100644 --- a/ipaserver/install/plugins/update_pwpolicy.py +++ b/ipaserver/install/plugins/update_pwpolicy.py @@ -78,3 +78,69 @@ class update_pwpolicy(Updater): return False, [] return False, [] + + +@register() +class update_pwpolicy_grace(Updater): + """ + Ensure all group policies have a grace period set. + """ + + def execute(self, **options): + ldap = self.api.Backend.ldap2 + + base_dn = DN(('cn', self.api.env.realm), ('cn', 'kerberos'), + self.api.env.basedn) + search_filter = ( + "(&(objectClass=krbpwdpolicy)(!(passwordgracelimit=*)))" + ) + + while True: + # Run the search in loop to avoid issues when LDAP limits are hit + # during update + + try: + (entries, truncated) = ldap.find_entries( + search_filter, ['objectclass'], base_dn, time_limit=0, + size_limit=0) + + except errors.EmptyResult: + logger.debug("update_pwpolicy: no policies without " + "passwordgracelimit set") + return False, [] + + except errors.ExecutionError as e: + logger.error("update_pwpolicy: cannot retrieve list " + "of policies missing passwordgracelimit: %s", e) + return False, [] + + logger.debug("update_pwpolicy: found %d " + "policies to update, truncated: %s", + len(entries), truncated) + + error = False + + for entry in entries: + # Set unlimited BIND by default + entry['passwordgracelimit'] = -1 + try: + ldap.update_entry(entry) + except (errors.EmptyModlist, errors.NotFound): + pass + except errors.ExecutionError as e: + logger.debug("update_pwpolicy: cannot " + "update policy: %s", e) + error = True + + if error: + # Exit loop to avoid infinite cycles + logger.error("update_pwpolicy: error(s) " + "detected during pwpolicy update") + return False, [] + + elif not truncated: + # All affected entries updated, exit the loop + logger.debug("update_pwpolicy: all policies updated") + return False, [] + + return False, [] -- 2.37.2