Generic LDAP Connector
The generic LDAP connector is based on JNDI, and can be used to connect to any LDAPv3-compliant directory server, such as OpenDJ, Active Directory, SunDS, Oracle Directory Server Enterprise Edition, IBM Security Directory Server, and OpenLDAP.
OpenICF provides a legacy Active Directory (AD) .NET connector. Note, however, that the AD Connector will be deprecated in a future OpenICF release, and, ultimately, support for its use with OpenIDM will be discontinued. For simple Active Directory (and Active Directory LDS) deployments, the generic LDAP Connector works better than the Active Directory connector, in most circumstances. Using the generic LDAP connector avoids the need to install a remote connector server in the overall deployment. In addition, the generic LDAP connector has significant performance advantages over the Active Directory connector. For more complex Active Directory deployments, use the PowerShell Connector Toolkit, as described in "PowerShell Connector Toolkit".
Setting Up the Generic LDAP Connector
OpenIDM 6.2 bundles version 1.4.1.2 of the LDAP connector. Three sample LDAP connector configurations are provided in the path/to/openidm/samples/provisioners/ directory:
-
provisioner.openicf-opendjldap.jsonprovides a sample LDAP connector configuration for an OpenDJ directory server. -
provisioner.openicf-adldap.jsonprovides a sample LDAP connector configuration for an Active Directory server. -
provisioner.openicf-adldsldap.jsonprovides a sample LDAP connector configuration for an Active Directory Lightweight Directory Services (AD LDS) server.
You should be able to adapt one of these sample configurations for any LDAPv3-compliant server.
The connectorRef configuration property provides information about the LDAP connector bundle, and is the same in all three sample LDAP connector configurations:
{
"connectorRef": {
"connectorHostRef": "#LOCAL",
"connectorName": "org.identityconnectors.ldap.LdapConnector",
"bundleName": "org.openidentityplatform.openicf.connectors.ldap-connector",
"bundleVersion": "[1.4.0.0,2)"
}
}
The connectorHostRef property is optional, if you use the connector .jar provided in openidm/connectors, and you use a local connector server.
The following excerpt shows the configuration properties in the sample LDAP connector for OpenDJ. These properties are described in detail later in this section. For additional information on the properties that affect synchronization, see "Controlling What the LDAP Connector Synchronizes". For a complete list of the configuration properties for the LDAP connector, see "LDAP Connector Configuration":
"configurationProperties" : {
"host" : "localhost",
"port" : 1389,
"ssl" : false,
"startTLS" : false,
"principal" : "cn=Directory Manager",
"credentials" : "password",
"baseContexts" : [
"dc=example,dc=com"
],
"baseContextsToSynchronize" : [
"dc=example,dc=com"
],
"accountSearchFilter" : null,
"accountSynchronizationFilter" : null,
"groupSearchFilter" : null,
"groupSynchronizationFilter" : null,
"passwordAttributeToSynchronize" : null,
"synchronizePasswords" : false,
"removeLogEntryObjectClassFromFilter" : true,
"modifiersNamesToFilterOut" : [ ],
"passwordDecryptionKey" : null,
"changeLogBlockSize" : 100,
"attributesToSynchronize" : [ ],
"changeNumberAttribute" : "changeNumber",
"passwordDecryptionInitializationVector" : null,
"filterWithOrInsteadOfAnd" : false,
"objectClassesToSynchronize" : [
"inetOrgPerson"
],
"vlvSortAttribute" : "uid",
"passwordAttribute" : "userPassword",
"useBlocks" : false,
"maintainPosixGroupMembership" : false,
"failover" : [ ],
"readSchema" : true,
"accountObjectClasses" : [
"top",
"person",
"organizationalPerson",
"inetOrgPerson"
],
"accountUserNameAttributes" : [
"uid"
],
"groupMemberAttribute" : "uniqueMember",
"passwordHashAlgorithm" : null,
"usePagedResultControl" : true,
"blockSize" : 100,
"uidAttribute" : "dn",
"maintainLdapGroupMembership" : false,
"respectResourcePasswordPolicyChangeAfterReset" : false
},
host-
The host name or IP address of the server on which the LDAP instance is running.
port-
The port on which the LDAP server listens for LDAP requests. The sample configuration specifies a default port of 1389.
ssl-
If
true, the specified port listens for LDAPS connections.If you use the LDAP connector over SSL, set the
sslproperty totrue, and theportto636in the connector configuration file. You must also specify the path to a truststore in your project’sconf/system.propertiesfile. A truststore is provided by default atopenidm/security/truststore. Add the following line to thesystem.propertiesfile, substituting the path to your own truststore if you do not want to use the default:# Set the truststore javax.net.ssl.trustStore=/path/to/openidm/security/truststore startTLS-
Specifies whether to use the startTLS operation to initiate a TLS/SSL session. To use startTLS, set
"startTLS":true,and"ssl":false. Your connection should use the insecure LDAP port (typically389or1389for an OpenDJ server). principal-
The bind DN that is used to connect to the LDAP server.
credentials-
The password of the
principalthat is used to connect to the LDAP server. baseContexts-
One or more starting points in the LDAP tree that will be used when searching the tree. Searches are performed when discovering users from the LDAP server or when looking for the groups of which a user is a member. During reconciliation operations, OpenIDM searches through the base contexts listed in this property for changes. (See also "Controlling What the LDAP Connector Synchronizes").
baseContextsToSynchronize-
One or more starting points in the LDAP tree that will be used to determine if a change should be synchronized. During LiveSync operations, OpenIDM searches through the base contexts listed in this property for changes. If no value is specified here, the values in listed in the
baseContextsproperty are used. (See also "Controlling What the LDAP Connector Synchronizes"). accountSynchronizationFilter-
Used during synchronization actions to filter out LDAP accounts. (See also "Controlling What the LDAP Connector Synchronizes").
accountObjectClasses-
This property lists all the object classes that represent an account. If this property has multiple values, an
ORfilter is used to determine the affected entries. For example, if the value of this property is["organizationalPerson", "inetOrgPerson"], any entry with the object classorganizationalPersonOR the object classinetOrgPersonis considered as an account entry. The value of this property must not include thetopobject class. accountSearchFilter-
Search filter that user accounts must match. (See also "Controlling What the LDAP Connector Synchronizes").
accountUserNameAttributes-
Attributes holding the account’s user name. Used during authentication to find the LDAP entry matching the user name.
attributesToSynchronize-
List of attributes used during object synchronization. OpenIDM ignores change log updates that do not include any of the specified attributes. If empty, OpenIDM considers all changes. (See also "Controlling What the LDAP Connector Synchronizes").
blockSize-
Block size for simple paged results and VLV index searches, reflecting the maximum number of entries retrieved at any one time.
changeLogBlockSize-
Block size used when fetching change log entries.
changeNumberAttribute-
Change log attribute containing the last change number.
failover-
LDAP URLs specifying alternative LDAP servers to connect to if OpenIDM cannot connect to the primary LDAP server specified in the
hostandportproperties. filterWithOrInsteadOfAnd-
In most cases, the filter to fetch change log entries is AND-based. If this property is set, the filter ORs the required change numbers instead.
groupMemberAttribute-
LDAP attribute holding members for non-POSIX static groups.
groupSearchFilter-
Search filter that group entries must match.
maintainLdapGroupMembership-
If
true, OpenIDM modifies group membership when entries are renamed or deleted.In the sample LDAP connector configuration file provided with OpenIDM, this property is set to
false. This means that LDAP group membership is not modified when entries are renamed or deleted in OpenIDM. To ensure that entries are removed from LDAP groups when the entries are deleted, set this property totrueor enable referential integrity on the LDAP server. For information about configuring referential integrity in OpenDJ, see Configuring Referential Integrity in the OpenDJ Administration Guide. maintainPosixGroupMembership-
If
true, OpenIDM modifies POSIX group membership when entries are renamed or deleted. modifiersNamesToFilterOut-
Use this property to avoid loops caused by changes made to managed user objects being synchronized. For more information, see "Controlling What the LDAP Connector Synchronizes".
objectClassesToSynchronize-
OpenIDM synchronizes only entries that have these object classes. See also "Controlling What the LDAP Connector Synchronizes".
passwordAttribute-
Attribute to which OpenIDM writes the predefined
PASSWORDattribute. passwordAttributeToSynchronize-
OpenIDM synchronizes password values on this attribute.
passwordDecryptionInitializationVector-
This is a legacy attribute, and its value should remain set to
null. To configure password synchronization between an LDAP server and OpenIDM, use one of the password synchronization plugins, described in "Synchronizing Passwords Between OpenIDM and an LDAP Server" in the Integrator’s Guide. passwordDecryptionKey-
This is a legacy attribute, and its value should remain set to
null. To configure password synchronization between an LDAP server and OpenIDM, use one of the password synchronization plugins, described in "Synchronizing Passwords Between OpenIDM and an LDAP Server" in the Integrator’s Guide. passwordHashAlgorithm-
Hash password values with the specified algorithm, if the LDAP server stores them in clear text.
The hash algorithm can be one of the following:
-
NONE- Clear text -
WIN-AD- Used for password changes to Active Directory -
SHA- Secure Hash Algorithm -
SHA-1- A 160-bit hash algorithm that resembles the MD5 algorithm -
SSHA- Salted SHA -
MD5- A 128-bit message-digest algorithm -
SMD5- Salted MD5
-
readSchema-
If
true, read the schema from the LDAP server.This property is used only during the connector setup, to generate the object types.
If this property is
false, the LDAP connector provides a basic default schema that can manage LDAP users and groups. The default schema mapsinetOrgPersonto the OpenICFACCOUNTproperty, andgroupOfUniqueNamesto the OpenICFGROUPproperty. The following LDAP object classes are also included in the default schema:-
organization -
organizationalUnit -
person -
organizationalPerson -
account -
groupOfNames
-
removeLogEntryObjectClassFromFilter-
If
true, the filter to fetch change log entries does not contain thechangeLogEntryobject class, and OpenIDM expects no entries with other object types in the change log. The default setting istrue. respectResourcePasswordPolicyChangeAfterReset-
If
true, bind with the Password Expired and Password Policy controls, and throwPasswordExpiredExceptionand other exceptions appropriately. synchronizePasswords-
This is a legacy attribute, and its value should remain set to
false. To configure password synchronization between an LDAP server and OpenIDM, use one of the password synchronization plugins, described in "Synchronizing Passwords Between OpenIDM and an LDAP Server" in the Integrator’s Guide. uidAttribute-
Specifies the LDAP attribute that should be used as the immutable ID (
UID) for the entry. For an OpenDJ resource, you should use theentryUUID. You can use theDNas the UID attribute but note that this is not immutable. useBlocks-
If
useBlocksisfalse, no pagination is used. IfuseBlocksistrue, the connector uses block-based LDAP controls, either the simple paged results control, or the virtual list view control, depending on the setting of theusePagedResultControlproperty. usePagedResultControl-
Taken into account only if
useBlocksistrue. IfusePagedResultControlisfalse, the connector uses the virtual list view (VLV) control, if it is available. IfusePagedResultControlistrue, the connector uses the simple paged results control for search operations. useTimestampsForSync-
If
true, use timestamps for LiveSync operations, instead of the change log.By default, the LDAP connector has a change log strategy for LDAP servers that support a change log (such as OpenDJ and Oracle Directory Server Enterprise Edition). If the LDAP server does not support a change log, or if the change log is disabled, LiveSync for create and modify operations can still occur, based on the timestamps of modifications.
vlvSortAttribute-
Attribute used as the sort key for virtual list view.
Controlling What the LDAP Connector Synchronizes
To control the set of LDAP entries that are affected by reconciliation and automatic synchronization operations, set the following properties in the provisioner configuration. Automatic synchronization operations includes LiveSync (synchronization of changes from the LDAP server to OpenIDM) and implicit sync (synchronization from the OpenIDM repository to the LDAP server).
baseContexts-
The starting points in the LDAP tree that are used when searching the directory tree, for example,
dc=example,dc=com. These base contexts must include the set of users and the set of groups that must be searched during reconciliation operations. baseContextsToSynchronize-
The starting points in the LDAP tree that are used to determine if a change should be synchronized. This property is used only for automatic synchronization operations. Only entries that fall under these base contexts are considered during synchronization operations.
accountSearchFilter-
Only user accounts that match this filter are searched, and therefore affected by reconciliation and synchronization operations. If you do not set this property, all accounts within the base contexts specified previously are searched.
accountSynchronizationFilter-
This property is used during reconciliation and automatic synchronization operations, and filters out any LDAP accounts that you specifically want to exclude from these operations.
objectClassesToSynchronize-
During automatic synchronization operations, only the object classes listed here are considered for changes. OpenIDM ignores change log updates (or changes to managed objects) which do not have any of the object classes listed here. If this property is not set, OpenIDM considers changes to all attributes specified in the mapping.
attributesToSynchronize-
During automatic synchronization operations, only the attributes listed here are considered for changes. Objects that include these attributes are synchronized. Objects that do not include these attributes are ignored. If this property is not set, OpenIDM considers changes to all attributes specified in the mapping. Automatic synchronization includes LiveSync and implicit synchronization operations. For more information, see "Types of Synchronization" in the Integrator’s Guide
This attribute works only with LDAP servers that log changes in a change log, not with servers (such as Active Directory) that use other mechanisms to track changes.
modifiersNamesToFilterOut-
This property enables you to define a list of DNs. During synchronization operations, the connector ignores changes made by these DNs.
When a managed user object is updated, and that change is synchronized to the LDAP server, the change made on the LDAP server is recorded in the change log. A LiveSync operation picks up the change, and attempts to replay the change on the managed user object, effectively resulting in a loop of updates.
To avoid this situation, you can specify a unique user in your LDAP directory, that will be used only for the LDAP connector. The unique user must be something other than
cn=directory manager, for examplecn=openidmuser. You can then include that user DN as the value ofmodifiersNamesToFilterOut. When a change is made through the LDAP connector, and that change is recorded in the change log, the modifier’s name (cn=openidmuser) is flagged and OpenIDM does not attempt to replay the change back to the managed user repository. So you are effectively indicating that OpenIDM should not synchronized changes back to managed user that originated from managed user, thus preventing the update loop.This attribute works only with LDAP servers that log changes in a change log, not with servers (such as Active Directory) that use other mechanisms to track changes.
Using the Generic LDAP Connector With Active Directory
The LDAP connector provides new functionality for managing Active Directory users and groups. Among other changes, the new connector can handle the following operational attributes to manage Active Directory accounts:
-
ENABLE- uses theuserAccountControlattribute to get or set the account status of an object.The LDAP connector reads the
userAccountControlto determine if an account is enabled or disabled. The connector modifies the value of theuserAccountControlattribute if OpenIDM changes the value ofENABLE. -
ACCOUNT_EXPIRES- gets or sets theaccountExpiresattribute of an Active Directory object. -
LOCK_OUT- uses themsDS-User-Account-Control-Computedsystem attribute to check if a user account has been locked.If OpenIDM sets the
LOCK_OUTtoFALSE, the LDAP connector sets the Active DirectorylockoutTimeto0to unlock the account.If OpenIDM sets the
LOCK_OUTtoTRUE, the LDAP connector ignores the change and logs a message. -
PASSWORD_EXPIRED- uses themsDS-User-Account-Control-Computedsystem attribute to check if a user password has expired.To force password expiration (to force a user to change their password when they next log in),
pwdLastSetmust be set to0. The LDAP connector setspwdLastSetto0, if OpenIDM setsPASSWORD_EXPIREDtoTRUE.To remove password expiration,
pwdLastSetmust be set to0and then-1. This sets the value ofpwdLastSetto the current time. The LDAP connector setspwdLastSetto-1if OpenIDM setsPASSWORD_EXPIREDtoFALSE.
|
You must update your provisioner configuration to be able to use these new operational attributes. You can use this sample provisioner configuration as a guide. |
Managing Active Directory Users With the LDAP Connector
If you create or update users in Active Directory, and those user entries include passwords, you must use the LDAP connector over SSL. You cannot create or update an Active Directory user password in clear text. To use the connector over SSL, set "ssl" : true in the provisioner configuration and set the path to your truststore in your project’s conf/system.properties file. For example, add the following line to that file:
# Set the truststore
javax.net.ssl.trustStore=/path/to/openidm/security/truststore
The following command adds an Active Directory user. The output shows the operational attributes described in the previous section:
$ curl \
--header "Content-Type: application/json" \
--header "X-OpenIDM-Username: openidm-admin" \
--header "X-OpenIDM-Password: openidm-admin" \
--request POST \
--data '{
"dn": "CN=Brian Smith,CN=Users,DC=example,DC=com",
"cn": "Brian Smith",
"sAMAccountName": "bsmith",
"userPrincipalName": "bsmith@example.com",
"userAccountControl": "512",
"givenName": "Brian",
"mail": "bsmith@example.com",
"__PASSWORD__": "Passw0rd"
}' \
http://localhost:8080/openidm/system/ad/account?_action=create
{
"_id": "<GUID=cb2f8cbc032f474c94c896e69db2feb3>",
"mobile": null,
"postalCode": null,
"st": null,
"employeeType": null,
"objectGUID": "<GUID=cb2f8cbc032f474c94c896e69db2feb3>",
"cn": "Brian Smith",
"department": null,
"l": null,
"description": null,
"info": null,
"manager": null,
"sAMAccountName": "bsmith",
"sn": null,
"whenChanged": "20151217131254.0Z",
"userPrincipalName": "bsmith@example.com",
"userAccountControl": "512",
"__ENABLE__": true,
"displayName": null,
"givenName": "Brian",
"middleName": null,
"facsimileTelephoneNumber": null,
"lastLogon": "0",
"countryCode": "0",
"employeeID": null,
"co": null,
"physicalDeliveryOfficeName": null,
"pwdLastSet": "2015-12-17T13:12:54Z",
"streetAddress": null,
"homePhone": null,
"__PASSWORD_NOTREQD__": false,
"telephoneNumber": null,
"dn": "CN=Brian Smith,CN=Users,DC=example,DC=com",
"title": null,
"mail": "bsmith@example.com",
"postOfficeBox": null,
"__SMARTCARD_REQUIRED__": false,
"uSNChanged": "86144",
"__PASSWORD_EXPIRED__": false,
"initials": null,
"__LOCK_OUT__": false,
"company": null,
"employeeNumber": null,
"accountExpires": "0",
"c": null,
"whenCreated": "20151217131254.0Z",
"uSNCreated": "86142",
"division": null,
"groups": [],
"__DONT_EXPIRE_PASSWORD__": false,
"otherHomePhone": []
}
Note that the command sets the userAccountControl to 512, which is an enabled account. The value of the userAccountControl determines the account policy. The following list describes the common values for the userAccountControl.
512-
Enabled account.
514-
Disabled account.
544-
Enabled account, password not required.
546-
Disabled account, password not required.
66048-
Enabled account, password does not expire.
66050-
Disabled account, password does not expire.
66080-
Enabled account, password does not expire and is not required.
66082-
Disabled account, password does not expire and is not required.
262656-
Enabled account, smartcard required.
262658-
Disabled account, smartcard required.
262688-
Enabled account, smartcard required, password not required.
262690-
Disabled account, smartcard required, password not required.
328192-
Enabled account, smartcard required, password does not expire.
328192-
Enabled account, smartcard required, password does not expire.
328194-
Disabled account, smartcard required, password does not expire.
328224-
Enabled account, smartcard required, password does not expire and is not required.
328226-
Disabled account, smartcard required, password does not expire and is not required.
Managing Active Directory Groups With the LDAP Connector
The following command creates a basic Active Directory group with the LDAP connector:
$ curl \
--header "Content-Type: application/json" \
--header "X-OpenIDM-Username: openidm-admin" \
--header "X-OpenIDM-Password: openidm-admin" \
--request POST \
--data '{
"dn": "CN=Employees,DC=example,DC=com"
}' \
http://localhost:8080/openidm/system/ad/group?_action=create
{
"_id": "<GUID=240da4e959d81547ad8629f5b2b5114d>"
}
The LDAP connector exposes two special attributes to handle Active Directory group scope and type: GROUP_SCOPE and GROUP_TYPE.
The GROUP_SCOPE attribute is defined in the provisioner configuration as follows:
...
"__GROUP_SCOPE__" : {
"type" : "string",
"nativeName" : "__GROUP_SCOPE__",
"nativeType" : "string"
},
The value of the GROUP_SCOPE attribute can be global, domain, or universal. If no group scope is set when the group is created, the scope is global by default. For more information about the different group scopes, see the corresponding Microsoft documentation.
The GROUP_TYPE attribute is defined in the provisioner configuration as follows:
...
"__GROUP_TYPE__" : {
"type" : "string",
"nativeName" : "__GROUP_TYPE__",
"nativeType" : "string"
},
The value of the GROUP_TYPE attribute can be security or distribution. If no group type is set when the group is created, the type is security by default. For more information about the different group types, see the corresponding Microsoft documentation.
The following example creates a new distribution group, with universal scope:
$ curl \
--header "Content-Type: application/json" \
--header "X-OpenIDM-Username: openidm-admin" \
--header "X-OpenIDM-Password: openidm-admin" \
--request POST \
--data '{
"dn": "CN=NewGroup,DC=example,DC=com",
"__GROUP_SCOPE__": "universal",
"__GROUP_TYPE__": "distribution"
}' \
http://localhost:8080/openidm/system/ad/group?_action=create
{
"_id": "<GUID=f189df8a276f91478ad5055b1580cbcb>"
}
Handling Active Directory Dates
Most dates in Active Directory are represented as the number of 100-nanosecond intervals since January 1, 1601 (UTC). For example:
pwdLastSet: 130698687542272930
OpenIDM generally represents dates as an ISO 8601-compliant string with yyyy-MM-dd’T’HH:mm:ssZ format. For example:
2015-03-02T20:17:48Z
The generic LDAP connector therefore converts any dates from Active Directory to ISO 8601 format, for fields such as pwdLastSet, accountExpires, lockoutTime, and lastLogon.
OpenICF Interfaces Implemented by the LDAP Connector
The LDAP Connector implements the following OpenICF interfaces.
- Authenticate
-
Provides simple authentication with two parameters, presumed to be a user name and password.
- Create
-
Creates an object and its
uid. - Delete
-
Deletes an object, referenced by its
uid. - Resolve Username
-
Resolves an object by its username and returns the
uidof the object. - Schema
-
Describes the object types, operations, and options that the connector supports.
- Script on Connector
-
Enables an application to run a script in the context of the connector. Any script that runs on the connector has the following characteristics:
-
The script runs in the same execution environment as the connector and has access to all the classes to which the connector has access.
-
The script has access to a
connectorvariable that is equivalent to an initialized instance of the connector. At a minimum, the script can access the connector configuration. -
The script has access to any script-arguments passed in by the application.
-
- Search
-
Searches the target resource for all objects that match the specified object class and filter.
- Sync
-
Polls the target resource for synchronization events, that is, native changes to objects on the target resource.
- Test
-
Tests the connector configuration. Testing a configuration checks all elements of the environment that are referred to by the configuration are available. For example, the connector might make a physical connection to a host that is specified in the configuration to verify that it exists and that the credentials that are specified in the configuration are valid.
This operation might need to connect to a resource, and, as such, might take some time. Do not invoke this operation too often, such as before every provisioning operation. The test operation is not intended to check that the connector is alive (that is, that its physical connection to the resource has not timed out).
You can invoke the test operation before a connector configuration has been validated.
- Update
-
Updates (modifies or replaces) objects on a target resource.