From cb689354357d5311e7ecb231a34e867c23b8a803 Mon Sep 17 00:00:00 2001 From: Nathaniel McCallum Date: Thu, 11 Apr 2013 13:24:46 -0400 Subject: Add IPA OTP schema and ACLs This commit adds schema support for two factor authentication via OTP devices, including RADIUS or TOTP. This schema will be used by future patches which will enable two factor authentication directly. https://fedorahosted.org/freeipa/ticket/3365 http://freeipa.org/page/V3/OTP --- install/share/70ipaotp.ldif | 28 +++++++++++++++++++++++ install/share/Makefile.am | 1 + install/share/copy-schema-to-ca.py | 1 + install/share/default-aci.ldif | 10 +++++++- install/updates/10-70ipaotp.update | 25 ++++++++++++++++++++ install/updates/40-otp.update | 9 ++++++++ install/updates/Makefile.am | 4 +++- ipalib/constants.py | 1 + ipaserver/install/dsinstance.py | 3 ++- ipaserver/install/plugins/update_anonymous_aci.py | 25 ++++++++++++++------ 10 files changed, 97 insertions(+), 10 deletions(-) create mode 100644 install/share/70ipaotp.ldif create mode 100644 install/updates/10-70ipaotp.update create mode 100644 install/updates/40-otp.update diff --git a/install/share/70ipaotp.ldif b/install/share/70ipaotp.ldif new file mode 100644 index 00000000..3cfe8723 --- /dev/null +++ b/install/share/70ipaotp.ldif @@ -0,0 +1,28 @@ +# IPA OTP schema +# BaseOID: 2.16.840.1.113730.3.8.16 +# See RFC 4517 for Syntax OID definitions +dn: cn=schema +attributeTypes: (2.16.840.1.113730.3.8.16.1.1 NAME 'ipatokenUniqueID' DESC 'Token Unique Identifier' EQUALITY caseIgnoreMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.2 NAME 'ipatokenDisabled' DESC 'Optionally marks token as Disabled' EQUALITY booleanMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.7 SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.3 NAME 'ipatokenNotBefore' DESC 'Token validity date' EQUALITY generalizedTimeMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.24 SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.4 NAME 'ipatokenNotAfter' DESC 'Token expiration date' EQUALITY generalizedTimeMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.24 SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.5 NAME 'ipatokenVendor' DESC 'Optional Vendor identifier' EQUALITY caseIgnoreMatch SUBSTR caseIgnoreSubstringsMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.6 NAME 'ipatokenModel' DESC 'Optional Model identifier' EQUALITY caseIgnoreMatch SUBSTR caseIgnoreSubstringsMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.7 NAME 'ipatokenSerial' DESC 'OTP Token Serial number' EQUALITY caseIgnoreMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.8 NAME 'ipatokenOTPkey' DESC 'OTP Token Key' EQUALITY octetStringMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.40 SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.9 NAME 'ipatokenOTPalgorithm' DESC 'OTP Token Algorithm' EQUALITY caseIgnoreMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.10 NAME 'ipatokenOTPdigits' DESC 'OTP Token Number of digits' EQUALITY integerMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.27 SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.11 NAME 'ipatokenTOTPclockOffset' DESC 'TOTP clock offset' EQUALITY integerMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.27 SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.12 NAME 'ipatokenTOTPtimeStep' DESC 'TOTP time-step' EQUALITY integerMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.27 SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.13 NAME 'ipatokenOwner' DESC 'User entry that owns this token' SUP distinguishedName SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.14 NAME 'ipatokenRadiusUserName' DESC 'Corresponding Radius username' EQUALITY caseIgnoreMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.15 NAME 'ipatokenRadiusConfigLink' DESC 'Corresponding Radius Configuration link' SUP distinguishedName SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.16 NAME 'ipatokenRadiusServer' DESC 'Server String Configuration' EQUALITY caseIgnoreIA5Match SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.17 NAME 'ipatokenRadiusSecret' DESC 'Server's Secret' EQUALITY octetStringMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.40 SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.18 NAME 'ipatokenRadiusTimeout' DESC 'Server Timeout' EQUALITY integerMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.27 SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.19 NAME 'ipatokenRadiusRetries' DESC 'Number of allowed Retries' EQUALITY integerMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.27 SINGLE-VALUE X-ORIGIN 'IPA OTP') +attributeTypes: (2.16.840.1.113730.3.8.16.1.20 NAME 'ipatokenUserMapAttribute' DESC 'Attribute to map from the user entry for RADIUS server authentication' EQUALITY caseIgnoreMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN 'IPA OTP') +objectClasses: (2.16.840.1.113730.3.8.16.2.1 NAME 'ipaToken' SUP top ABSTRACT DESC 'Abstract token class for tokens' MUST (ipatokenUniqueID) MAY (description $ ipatokenOwner $ ipatokenDisabled $ ipatokenNotBefore $ ipatokenNotAfter $ ipatokenVendor $ ipatokenModel $ ipatokenSerial) X-ORIGIN 'IPA OTP') +objectClasses: (2.16.840.1.113730.3.8.16.2.2 NAME 'ipatokenTOTP' SUP ipaToken STRUCTURAL DESC 'TOTP Token Type' MAY (ipatokenOTPkey $ ipatokenOTPalgorithm $ ipatokenOTPdigits $ ipatokenTOTPclockOffset $ ipatokenTOTPtimeStep) X-ORIGIN 'IPA OTP') +objectClasses: (2.16.840.1.113730.3.8.16.2.3 NAME 'ipatokenRadiusProxyUser' SUP top AUXILIARY DESC 'Radius Proxy User' MUST (ipatokenRadiusConfigLink) MAY (ipatokenRadiusUserName) X-ORIGIN 'IPA OTP') +objectClasses: (2.16.840.1.113730.3.8.16.2.4 NAME 'ipatokenRadiusConfiguration' SUP top STRUCTURAL DESC 'Proxy Radius Configuration' MUST (cn $ ipatokenRadiusServer $ ipatokenRadiusSecret) MAY (description $ ipatokenRadiusTimeout $ ipatokenRadiusRetries $ ipatokenUserMapAttribute) X-ORIGIN 'IPA OTP') diff --git a/install/share/Makefile.am b/install/share/Makefile.am index f8f9b742..8823723e 100644 --- a/install/share/Makefile.am +++ b/install/share/Makefile.am @@ -11,6 +11,7 @@ app_DATA = \ 60ipadns.ldif \ 61kerberos-ipav3.ldif \ 65ipasudo.ldif \ + 70ipaotp.ldif \ anonymous-vlv.ldif \ bootstrap-template.ldif \ caJarSigningCert.cfg.template \ diff --git a/install/share/copy-schema-to-ca.py b/install/share/copy-schema-to-ca.py index 4e2054ea..1888f125 100755 --- a/install/share/copy-schema-to-ca.py +++ b/install/share/copy-schema-to-ca.py @@ -31,6 +31,7 @@ SCHEMA_FILENAMES = ( "60ipadns.ldif", "61kerberos-ipav3.ldif", "65ipasudo.ldif", + "70ipaotp.ldif", "05rfc2247.ldif", ) diff --git a/install/share/default-aci.ldif b/install/share/default-aci.ldif index f173f797..18881ece 100644 --- a/install/share/default-aci.ldif +++ b/install/share/default-aci.ldif @@ -3,7 +3,7 @@ dn: $SUFFIX changetype: modify add: aci -aci: (target != "ldap:///idnsname=*,cn=dns,$SUFFIX")(targetattr != "userPassword || krbPrincipalKey || sambaLMPassword || sambaNTPassword || passwordHistory || krbMKey || userPKCS12 || ipaNTHash || ipaNTTrustAuthOutgoing || ipaNTTrustAuthIncoming")(version 3.0; acl "Enable Anonymous access"; allow (read, search, compare) userdn = "ldap:///anyone";) +aci: (targetfilter = "(&(!(objectClass=ipaToken))(!(objectClass=ipatokenTOTP))(!(objectClass=ipatokenRadiusProxyUser))(!(objectClass=ipatokenRadiusConfiguration)))")(target != "ldap:///idnsname=*,cn=dns,$SUFFIX")(targetattr != "userPassword || krbPrincipalKey || sambaLMPassword || sambaNTPassword || passwordHistory || krbMKey || userPKCS12 || ipaNTHash || ipaNTTrustAuthOutgoing || ipaNTTrustAuthIncoming")(version 3.0; acl "Enable Anonymous access"; allow (read, search, compare) userdn = "ldap:///anyone";) aci: (targetattr = "memberOf || memberHost || memberUser")(version 3.0; acl "No anonymous access to member information"; deny (read,search,compare) userdn != "ldap:///all";) aci: (targetattr != "userPassword || krbPrincipalKey || sambaLMPassword || sambaNTPassword || passwordHistory || krbMKey || krbPrincipalName || krbCanonicalName || krbUPEnabled || krbTicketPolicyReference || krbPrincipalExpiration || krbPasswordExpiration || krbPwdPolicyReference || krbPrincipalType || krbPwdHistory || krbLastPwdChange || krbPrincipalAliases || krbExtraData || krbLastSuccessfulAuth || krbLastFailedAuth || krbLoginFailedCount || ipaUniqueId || memberOf || serverHostName || enrolledBy || ipaNTHash")(version 3.0; acl "Admin can manage any entry"; allow (all) groupdn = "ldap:///cn=admins,cn=groups,cn=accounts,$SUFFIX";) aci: (targetattr = "userpassword || krbprincipalkey || sambalmpassword || sambantpassword")(version 3.0; acl "selfservice:Self can write own password"; allow (write) userdn="ldap:///self";) @@ -96,3 +96,11 @@ dn: cn=ipa,cn=etc,$SUFFIX changetype: modify add: aci aci: (target="ldap:///cn=*,cn=ca_renewal,cn=ipa,cn=etc,$SUFFIX")(targetattr="userCertificate")(version 3.0; acl "Modify CA Certificates for renewals"; allow(write) userdn = "ldap:///fqdn=$FQDN,cn=computers,cn=accounts,$SUFFIX";) + +# Let users manage their own tokens +dn: $SUFFIX +changetype: modify +add: aci +aci: (targetfilter = "(objectClass=ipaToken)")(targetattrs = "objectclass || ipatokenUniqueID || description || ipatokenOwner || ipatokenNotBefore || ipatokenNotAfter || ipatokenVendor || ipatokenModel || ipatokenSerial")(version 3.0; acl "Users can read basic token info"; allow (read, search, compare) userattr = "ipatokenOwner#USERDN";) +aci: (targetfilter = "(objectClass=ipaToken)")(targetattrs = "ipatokenUniqueID || description || ipatokenOwner || ipatokenNotBefore || ipatokenNotAfter || ipatokenVendor || ipatokenModel || ipatokenSerial")(version 3.0; acl "Users can write basic token info"; allow (write) userattr = "ipatokenOwner#USERDN";) +aci: (targetfilter = "(objectClass=ipatokenTOTP)")(targetattrs = "ipatokenOTPkey || ipatokenOTPalgorithm || ipatokenOTPdigits || ipatokenTOTPclockOffset || ipatokenTOTPtimeStep")(version 3.0; acl "Users can add TOTP token secrets"; allow (write, search) userattr = "ipatokenOwner#USERDN";) diff --git a/install/updates/10-70ipaotp.update b/install/updates/10-70ipaotp.update new file mode 100644 index 00000000..600ef9cf --- /dev/null +++ b/install/updates/10-70ipaotp.update @@ -0,0 +1,25 @@ +dn: cn=schema +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.1 NAME 'ipatokenUniqueID' DESC 'Token Unique Identifier' EQUALITY caseIgnoreMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.2 NAME 'ipatokenDisabled' DESC 'Optionally marks token as Disabled' EQUALITY booleanMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.7 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.3 NAME 'ipatokenNotBefore' DESC 'Token validity date' EQUALITY generalizedTimeMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.24 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.4 NAME 'ipatokenNotAfter' DESC 'Token expiration date' EQUALITY generalizedTimeMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.24 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.5 NAME 'ipatokenVendor' DESC 'Optional Vendor identifier' EQUALITY caseIgnoreMatch SUBSTR caseIgnoreSubstringsMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.6 NAME 'ipatokenModel' DESC 'Optional Model identifier' EQUALITY caseIgnoreMatch SUBSTR caseIgnoreSubstringsMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.7 NAME 'ipatokenSerial' DESC 'OTP Token Serial number' EQUALITY caseIgnoreMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.8 NAME 'ipatokenOTPkey' DESC 'OTP Token Key' EQUALITY octetStringMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.40 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.9 NAME 'ipatokenOTPalgorithm' DESC 'OTP Token Algorithm' EQUALITY caseIgnoreMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.10 NAME 'ipatokenOTPdigits' DESC 'OTP Token Number of digits' EQUALITY integerMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.27 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.11 NAME 'ipatokenTOTPclockOffset' DESC 'TOTP clock offset' EQUALITY integerMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.27 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.12 NAME 'ipatokenTOTPtimeStep' DESC 'TOTP time-step' EQUALITY integerMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.27 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.13 NAME 'ipatokenOwner' DESC 'User entry that owns this token' SUP distinguishedName SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.14 NAME 'ipatokenRadiusUserName' DESC 'Corresponding Radius username' EQUALITY caseIgnoreMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.15 NAME 'ipatokenRadiusConfigLink' DESC 'Corresponding Radius Configuration link' SUP distinguishedName SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.16 NAME 'ipatokenRadiusServer' DESC 'Server String Configuration' EQUALITY caseIgnoreIA5Match SYNTAX 1.3.6.1.4.1.1466.115.121.1.26 X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.17 NAME 'ipatokenRadiusSecret' DESC 'Server's Secret' EQUALITY octetStringMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.40 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.18 NAME 'ipatokenRadiusTimeout' DESC 'Server Timeout' EQUALITY integerMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.27 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.19 NAME 'ipatokenRadiusRetries' DESC 'Number of allowed Retries' EQUALITY integerMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.27 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:attributeTypes: (2.16.840.1.113730.3.8.16.1.20 NAME 'ipatokenUserMapAttribute' DESC 'Attribute to map from the user entry for RADIUS server authentication' EQUALITY caseIgnoreMatch SYNTAX 1.3.6.1.4.1.1466.115.121.1.15 SINGLE-VALUE X-ORIGIN 'IPA OTP') +add:objectClasses: (2.16.840.1.113730.3.8.16.2.1 NAME 'ipaToken' SUP top ABSTRACT DESC 'Abstract token class for tokens' MUST (ipatokenUniqueID) MAY (description $$ ipatokenOwner $$ ipatokenDisabled $$ ipatokenNotBefore $$ ipatokenNotAfter $$ ipatokenVendor $$ ipatokenModel $$ ipatokenSerial) X-ORIGIN 'IPA OTP') +add:objectClasses: (2.16.840.1.113730.3.8.16.2.2 NAME 'ipatokenTOTP' SUP ipaToken STRUCTURAL DESC 'TOTP Token Type' MAY (ipatokenOTPkey $$ ipatokenOTPalgorithm $$ ipatokenOTPdigits $$ ipatokenTOTPclockOffset $$ ipatokenTOTPtimeStep) X-ORIGIN 'IPA OTP') +add:objectClasses: (2.16.840.1.113730.3.8.16.2.3 NAME 'ipatokenRadiusProxyUser' SUP top AUXILIARY DESC 'Radius Proxy User' MUST (ipatokenRadiusConfigLink) MAY (ipatokenRadiusUserName) X-ORIGIN 'IPA OTP') +add:objectClasses: (2.16.840.1.113730.3.8.16.2.4 NAME 'ipatokenRadiusConfiguration' SUP top STRUCTURAL DESC 'Proxy Radius Configuration' MUST (cn $$ ipatokenRadiusServer $$ ipatokenRadiusSecret) MAY (description $$ ipatokenRadiusTimeout $$ ipatokenRadiusRetries $$ ipatokenUserMapAttribute) X-ORIGIN 'IPA OTP') diff --git a/install/updates/40-otp.update b/install/updates/40-otp.update new file mode 100644 index 00000000..ff36c87a --- /dev/null +++ b/install/updates/40-otp.update @@ -0,0 +1,9 @@ +dn: cn=otp,$SUFFIX +default: objectClass: nsContainer +default: objectClass: top +default: cn: otp + +dn: $SUFFIX +add: aci:'(targetfilter = "(objectClass=ipaToken)")(targetattrs = "objectclass || ipatokenUniqueID || description || ipatokenOwner || ipatokenNotBefore || ipatokenNotAfter || ipatokenVendor || ipatokenModel || ipatokenSerial")(version 3.0; acl "Users can read basic token info"; allow (read, search, compare) userattr = "ipatokenOwner#USERDN";)' +add: aci:'(targetfilter = "(objectClass=ipaToken)")(targetattrs = "ipatokenUniqueID || description || ipatokenOwner || ipatokenNotBefore || ipatokenNotAfter || ipatokenVendor || ipatokenModel || ipatokenSerial")(version 3.0; acl "Users can write basic token info"; allow (write) userattr = "ipatokenOwner#USERDN";)' +add: aci:'(targetfilter = "(objectClass=ipatokenTOTP)")(targetattrs = "ipatokenOTPkey || ipatokenOTPalgorithm || ipatokenOTPdigits || ipatokenTOTPclockOffset || ipatokenTOTPtimeStep")(version 3.0; acl "Users can add TOTP token secrets"; allow (write, search) userattr = "ipatokenOwner#USERDN";)' diff --git a/install/updates/Makefile.am b/install/updates/Makefile.am index ab3f4112..787a51cf 100644 --- a/install/updates/Makefile.am +++ b/install/updates/Makefile.am @@ -4,6 +4,7 @@ appdir = $(IPA_DATA_DIR)/updates app_DATA = \ 10-60basev2.update \ 10-60basev3.update \ + 10-70ipaotp.update \ 10-RFC2307bis.update \ 10-RFC4876.update \ 10-config.update \ @@ -13,6 +14,7 @@ app_DATA = \ 10-ssh.update \ 10-bind-schema.update \ 10-uniqueness.update \ + 10-schema_compat.update \ 19-managed-entries.update \ 20-aci.update \ 20-dna.update \ @@ -20,7 +22,6 @@ app_DATA = \ 20-indices.update \ 20-nss_ldap.update \ 20-replication.update \ - 10-schema_compat.update \ 20-user_private_groups.update \ 20-winsync_index.update \ 21-replicas_container.update \ @@ -32,6 +33,7 @@ app_DATA = \ 40-replication.update \ 40-dns.update \ 40-automember.update \ + 40-otp.update \ 45-roles.update \ 50-lockout-policy.update \ 50-groupuuid.update \ diff --git a/ipalib/constants.py b/ipalib/constants.py index ecb92558..de084578 100644 --- a/ipalib/constants.py +++ b/ipalib/constants.py @@ -109,6 +109,7 @@ DEFAULT_CONFIG = ( ('container_dna', DN(('cn', 'dna'), ('cn', 'ipa'), ('cn', 'etc'))), ('container_dna_posix_ids', DN(('cn', 'posix-ids'), ('cn', 'dna'), ('cn', 'ipa'), ('cn', 'etc'))), ('container_realm_domains', DN(('cn', 'Realm Domains'), ('cn', 'ipa'), ('cn', 'etc'))), + ('container_otp', DN(('cn', 'otp'))), # Ports, hosts, and URIs: # FIXME: let's renamed xmlrpc_uri to rpc_xml_uri diff --git a/ipaserver/install/dsinstance.py b/ipaserver/install/dsinstance.py index 3b841417..046480f0 100644 --- a/ipaserver/install/dsinstance.py +++ b/ipaserver/install/dsinstance.py @@ -411,7 +411,8 @@ class DsInstance(service.Service): "60basev3.ldif", "60ipadns.ldif", "61kerberos-ipav3.ldif", - "65ipasudo.ldif"): + "65ipasudo.ldif", + "70ipaotp.ldif"): target_fname = schema_dirname(self.serverid) + schema_fname shutil.copyfile(ipautil.SHARE_DIR + schema_fname, target_fname) os.chmod(target_fname, 0440) # read access for dirsrv user/group diff --git a/ipaserver/install/plugins/update_anonymous_aci.py b/ipaserver/install/plugins/update_anonymous_aci.py index 2b7446ad..1e75113f 100644 --- a/ipaserver/install/plugins/update_anonymous_aci.py +++ b/ipaserver/install/plugins/update_anonymous_aci.py @@ -20,8 +20,6 @@ from copy import deepcopy from ipaserver.install.plugins import FIRST, LAST from ipaserver.install.plugins.baseupdate import PostUpdate -#from ipalib.frontend import Updater -#from ipaserver.install.plugins import baseupdate from ipalib import api from ipalib.aci import ACI from ipalib.plugins import aci @@ -37,6 +35,8 @@ class update_anonymous_aci(PostUpdate): aciname = u'Enable Anonymous access' aciprefix = u'none' ldap = self.obj.backend + targetfilter = '(&(!(objectClass=ipaToken))(!(objectClass=ipatokenTOTP))(!(objectClass=ipatokenRadiusProxyUser))(!(objectClass=ipatokenRadiusConfiguration)))' + filter = None (dn, entry_attrs) = ldap.get_entry(api.env.basedn, ['aci']) @@ -45,6 +45,9 @@ class update_anonymous_aci(PostUpdate): rawaci = aci._find_aci_by_name(acilist, aciprefix, aciname) attrs = rawaci.target['targetattr']['expression'] + rawfilter = rawaci.target.get('targetfilter', None) + if rawfilter is not None: + filter = rawfilter['expression'] update_attrs = deepcopy(attrs) @@ -54,12 +57,10 @@ class update_anonymous_aci(PostUpdate): needed_attrs.append(attr) update_attrs.extend(needed_attrs) - if len(attrs) == len(update_attrs): + if (len(attrs) == len(update_attrs) and + filter == targetfilter): root_logger.debug("Anonymous ACI already update-to-date") return (False, False, []) - else: - root_logger.debug("New Anonymous ACI attributes needed: %s", - needed_attrs) for tmpaci in acistrs: candidate = ACI(tmpaci) @@ -67,7 +68,17 @@ class update_anonymous_aci(PostUpdate): acistrs.remove(tmpaci) break - rawaci.target['targetattr']['expression'] = update_attrs + if len(attrs) != len(update_attrs): + root_logger.debug("New Anonymous ACI attributes needed: %s", + needed_attrs) + + rawaci.target['targetattr']['expression'] = update_attrs + + if filter != targetfilter: + root_logger.debug("New Anonymous ACI targetfilter needed.") + + rawaci.set_target_filter(targetfilter) + acistrs.append(unicode(rawaci)) entry_attrs['aci'] = acistrs -- cgit