Custom adapter development

Introduction

I developed an custom adapter for Penrose for doubleSlash, an expert on Identity & Access Management (IAM). The datasource is an existing Identity & Access Managemet server based on CORBA. I used Penrose to make identity data of this IAM server available via LDAP. My custom adapter talks to the server via CORBA over TCP/IP connection. For the IAM server the adapter is a normal client.

Implementation

Methods

The CORBA adapter inherit from the abstract org.safehaus.penrose.connector.Adapter class. I didn't override all methods. I used only the following ones:

general methods:

  • init() - Initializes the adapter an my CORBA-client stub
  • openConnection() - Performs the login on the IAM server with the stored admin credential
  • dispose() - Destroy all object references of the adapter

LDAP operations:

  • bind() - Performs the login on the IAM server with the given credential
  • load() - Return the entire values of all entries matching the given filter
  • add() - Adds an account on the IAM server
  • delete() - Delete the account with the given userID
  • modify() - Modify the attributes of the account on the IAM server

I think it's not very helpful to paste all my code of the adapter implementation because it depends on the business logic of the individual IAM server. To develop an custom adapter I think the sourcecode of the JDBC-Adapter and the sample adater are very helpful to unterstand the way of Penrose. Furthermore debugging some operations on LDAP are very helpful (in my opinion!). For testing I used the open source LDAP client JXplorer.

Configuration

server.xml

In PENROSE_SERVER_HOME/conf/server.xml I added these lines:

<adapter name="CORBA">
   <adapter-class>de.doubleslash.iam.penrose.connector.CORBAAdapter</adapter-class>
</adapter>
<partition name="iam" path="iam"/>

Now I copied all other config files to the partition's directory PENROSE_SERVER_HOME/iam.  

 connection.xml

In the connection.xml in partition's directory I configured the connection of my adapter with the following lines:

<connection name="IAMServerConnection">
   <adapter-name>CORBA</adapter-name>
   <parameter>
      <param-name>internet_login</param-name>
      <param-value>false</param-value>
   </parameter>
   <parameter>
      <param-name>template_user_oid</param-name>
      <param-value>26</param-value>
   </parameter>
</connection>

 The defined parameters were used in the init() method of the adapter. These are necessary for the initialization of my CORBA-client.

sources.xml 

 In the sources.xml I defined all fields of the IAM server.

<source name="IAMServer">
    <connection-name>IAMServerConnection</connection-name>
    <field name="address1"/>
    <field name="address2"/>
    <field name="city"/>
    <field name="company"/>
    <field name="countryId"/>
    <field name="createDate"/>
    <field name="deactivated"/>
    <field name="department"/>
    <field name="email"/>
    <field name="fax"/>
    <field name="firstName"/>
    <field name="idnumber" primaryKey="true"/>
    <field name="internetLoginLockedstatus"/>
    <field name="langId"/>
    <field name="lastHistoryId"/>
    <field name="lastName"/>
    <field name="linkedWithGD"/>
    <field name="locked"/>
    <field name="login"/>
    <field name="login2"/>
    <field name="organizationId"/>
    <field name="phone"/>
    <field name="postcode"/>
    <field name="responsible_email"/>
    <field name="responsible_name"/>
    <field name="responsible_org"/>
    <field name="serviceProvider"/>
    <field name="sex"/>
    <field name="status"/>
    <field name="type"/>
    <field name="user_oid"/>
    <field name="validFrom"/>
    <field name="validTo"/>
    <field name="fullName"/>
    <field name="street"/>
    <field name="fullAddress"/>
    <field name="encryptedPassword"/>
    <parameter>
       <param-name>sizeLimit</param-name>
       <param-value>100</param-value>
    </parameter>
</source>

 The parameter "sizeLimit" will be used on the load-operation. When this limit is reached, the method returned an LDAP exception.

 mapping.xml

 In the mapping.xml I added these lines to configure the layout of the Directory Information Tree (DIT):

<entry dn="uid=...,ou=Users,dc=doubleslash,dc=de">
   <oc>inetOrgPerson</oc>
   <oc>organizationalPerson</oc>
   <oc>person</oc>
   <oc>top</oc>
   <at name="sn">
      <variable>iam.lastName</variable>
   </at>
   <at name="cn">
      <variable>iam.fullName</variable>
   </at>
   <at name="employeeNumber">
      <variable>iam.login2</variable>
   </at>
   <at name="uid" rdn="true">
      <variable>iam.idnumber</variable>
   </at>
   <at name="telephoneNumber">
      <variable>iam.phone</variable>
   </at>
   <at name="title">
      <variable>iam.sex</variable>
   </at>
   <at name="facsimileTelephoneNumber">
      <variable>iam.fax</variable>
   </at>
   <at name="street">
      <variable>iam.street</variable>
   </at>
   <at name="postalCode">
      <variable>iam.postcode</variable>
   </at>
   <at name="postalAddress">
      <variable>iam.fullAddress</variable>
   </at>
   <at name="st">
      <variable>iam.countryId</variable>
   </at>
   <at name="l">
      <variable>iam.city</variable>
   </at>
   <at name="departmentNumber">
      <variable>iam.department</variable>
   </at>
   <at name="employeeType">
      <variable>iam.serviceProvider</variable>
   </at>
   <at name="mail">
      <variable>iam.email</variable>
   </at>
   <at name="manager">
      <variable>iam.responsible_name</variable>
   </at>
   <at name="o">
      <variable>iam.company</variable>
   </at>
   <at name="preferredLanguage">
      <variable>iam.langId</variable>
   </at>
   <at name="userPassword">
      <variable>iam.encryptedPassword</variable>
   </at>
   <source name="iam">
   	<source-name>IAMServer</source-name>
     	<field name="lastName">
           <variable>sn</variable>
      	</field>
      	<field name="fullName">
      	   <variable>cn</variable>
      	</field>
	<field name="login2">
	   <variable>employeeNumber</variable>
	</field>
      	<field name="idnumber">
      	   <variable>uid</variable>
      	</field>
      	<field name="phone">
      	   <variable>telephoneNumber</variable>
      	</field>
      	<field name="sex">
	   <variable>title</variable>
      	</field>
      	<field name="fax">
      	   <variable>facsimileTelephoneNumber</variable>
      	</field>
      	<field name="street">
      	   <variable>street</variable>
      	</field>
      	<field name="postcode">
      	   <variable>postalCode</variable>
      	</field>
      	<field name="fullAddress">
	   <variable>postalAddress</variable>
      	</field>
      	<field name="countryId">
	   <variable>st</variable>
      	</field>
      	<field name="city">
	   <variable>l</variable>
      	</field>
      	<field name="department">
      	   <variable>departmentNumber</variable>
      	</field>
      	<field name="serviceProvider">
	   <variable>employeeType</variable>
      	</field>
      	<field name="email">
            <variable>mail</variable>
      	</field>
      	<field name="responsible_name">
      	    <variable>manager</variable>
      	</field>
      	<field name="company">
      	    <variable>o</variable>
      	</field>
      	<field name="langId">
      	    <variable>preferredLanguage</variable>
      	</field>
      	<field name="encryptedPassword">
      	    <variable>userPassword</variable>
      	</field>
    </source>
  </entry>

 At the moment I didn't use all fields of the IAM server.