Monday, November 29, 2010

Initial load

When you plan a typical internal focused provisioning system roll out one of the problems that you have to solve is how to get the information about the already existing users and accounts loaded into your new and shiny IDM system. Lets talk a little bit about design patterns for solving this problem.

In most cases you start out with one or more sources of basic user identities. These are the canonical truths about who actually works for your company. In most cases it includes a human resources system of some kind. If this system is connected to payroll it tends to contain very good data as the employees tends to complain if they don't get payed and the company don't like to continue paying people that no longer works for the company. In some cases you will discover that the HR system is only linked to payroll in some parts of the world while other, i.e. the UK office, uses another system to feed payroll. This usually results in the data in the HR system being less well maintained which can cause serious issues.

In many cases there are entities that needs to go into the IDM system that aren't present in the HR system i.e. contractors. Getting hold of data about these users is often not easy but there may be a contractor database somewhere. Worst case you may have to settle with data from the security badging system or from the corporate active directory. Even when you find basic information about the contractors you will often discover that the data quality can be very bad. Information such as manager id, current status or end date may not necessarily be well maintained. If you for example are planning to send warning emails to the manager of the contractor it will not be good if all 200 contractors in the manufacturing division reports to the division VP.

Assuming that you managed to discover your base identities the next step is to identify what target system accounts belongs to the base identities. In a perfect world there should be a unique identifier in each target system account such as an employeeid that can be traced back to one and only one account in the trusted source (i.e. the HR system). In practice this is rarely true. In most cases some target system accounts contains the unique identifier while a large percentage will need to be linked using less exact methods such as email addresses or in worst case names. Name based linking can be very time consuming and there is also a substantial risk that you will end up with false matches.

There are many tools available that will make the linkage process and if your account volume is decently high you want to start by doing automated matching using some form of script or program. Once you have cleared out the obvious matches you may want to switch over to a manual process that utilizes a simple Excel sheet to match between trusted source accounts and target system accounts.

If you can use a divide and conquer approach and divide the trusted source accounts and the target system accounts into distinct buckets things gets much easier. Lets say you have 3000 unmatched trusted source accounts and 5000 unmatched target system accounts you want to investigate if you can divide the accounts into ten country buckets based on the country attribute in both the trusted source account and the target account. This will reduce the problem to ten instances of matching 200-400 trusted accounts to 300-700 target accounts which is a much easier problem to solve. This approach of course assumes that there is a suitable "bucketing" attribute available in the target system as well as in the trusted source.

To sum things up preparing for the initial load essentially consists of the following steps:

  1. Discovering the trusted sources that will provide the base identities
  2. Extracting the user data from the trusted sources
  3. Cleaning or at least evaluating the quality of the data contained in the trusted sources
  4. Discovering the target system accounts
  5. Linking the trusted identities to the target system accounts

If the data is in good shape this can be a quick process but if the data is bad it is not that uncommon that you need to spend 3-6 months on the data cleanup. It is therefor a good idea to include a data clean up and correlation thread in your IDM program that starts at the same time as you kick off the provisioning implementation project.

Thursday, November 18, 2010

Polyarchies in pratice

In A bridge(stream) too far I talked a little bit about using polyarchies to implement role mining. Lets take a closer look at this concept including a simple example.

Lets say you have a 1000 AD groups and 2000 users in your system and you would like to do some role mining in order to figure out if you could apply a role based approach to automatically grant the correct entitlements (AD groups) to the right user.

First you look at the information you have available about your users. You may find that you are able to place them in a number of different hierarchies. Lets start by looking at the location based hierarchy.

The company has ten locations and the locations can be organized in a country -> city -> building pattern. So for example the US has offices in two cities: Boston and LA. In LA there is a single location while Boston contains two locations.

Now sort the users according to their location. You may end up with something like:


USA total: 380 users
-> Boston total: 250 users
---> Boston FS (Federal Square): 150 users
---> Boston Haymarket: 100 users

->LA downtown: 130 users

Next step is to associate AD group membership with each site and sort them according to how many members that has that specific location exists in each group. The Boston Federal Square location may have the following groups:

Boston Distribution List 143 members
Boston FS Distribution List 140 members
Sales Distribution List 138 Members
Boston FS printers and fileshare 132 Members

Out of these it looks like Boston FS Distribution List and Boston FS printers and fileshares should be given to any users that have a Boston FS location. The Boston Distribution list could be checked against the parent node to see if it is also given to the Boston Haymarket users. If not then perhaps it is an additional group used for Boston FS.

The Sales Distribution List may be assigned through location but it looks more likely that it is tied to the functional hierarchy. It just happens that many sales people are based out of the Boston Federal Square office.

Doing this work by hand using Excel or a small database is very time consuming but it is fairly easy to automate this using Java or whatever is your favorite programming language.

You basically need:

  1. Extract your base user data out of the trusted source (often an HR csv file feed)
  2. Enumerate the unique values of suitable attributes (i.e. list all unique locations) that is present in the trusted source
  3. Extract the group memberships (JNDI is my favorite) as well as user identities from the target system
  4. Correlate the users form the trusted source and the target system
  5. Calculate the user population in each unique attribute value 
  6. Get the group memberships of the user population in 5
  7. Sort the groups according to the number of members
  8. Output the result in a user friendly format (Excel sheets works great) 
  9. Attach some kind of cut off value i.e. only list groups where at least 75% of the users in a particular location is a member
  10. Look at the results and pick the likely candidates
As always in role mining this is not an exact science but it will help you finding the groups that are associated with a particular attribute.

If you prefer the COTS approach there are lots of different options. In my opinion the Oracle Identity Analytics (ex Sun Role Manager, ex Vauu RBACx)  is a quite nice implementation. IBM has also included some capability in TIM 5.1 that is worth taking a closer look at if you are an IBM shop.

For further reading Oracle published a whitepaper on this subject this summer that is well worth reading.

Happy mining!

Thursday, November 11, 2010

New to OIM

Back in the bad old days when you started with Thor Xellerate (or a little bit later OIM) you usually got the three day Thor training workshop and then you basically had to figure out things on your own. There was some documentation but most things in the central OIM platform you had to basically reverse engineer and good decompiler and sniffer were your best friends.

Oracle has made great steps forward on the documentation side over the last few years and a lot of the material is available to anyone.

If you are new to OIM I would suggest starting with downloading the OIM install and taking a look at the documentation folder (9.1 release). I would start by reading through the concepts document as this will give you a good overview of what the OIM tool actually can do.

Next step is to implement a couple of the exercises in Oracle by Example. I would suggest the following:

  1. Install and configure OIM
  2. Flat file recon with GTC
  3. Database provisioning using GTC

This will give you an overview of the basic function of OIM, Once you are done with the basics you can continue to explore how to customize the user interface and creating your own connectors.

The Oracle IDM forum is another great resource and if you have a metalink account there is also a lot of good information in the support knowledge DB.

On a slightly more humorous note I suggest So You Want to be a Game Designer. The skill set that makes a good Game Designer is actually quite similar to the skill set you need as an access and identity designer although knowledge of world myths and world religions may be slightly more useful to the game designer (although both can benefit from knowing what Kerberos is).

Welcome and best of luck!

OIM Howto: Add process form child

There is a number of posts on this blog that talks about managing target system groups by manipulating child form contents.  In a recent OTN IDM discussion thread Deepika posted some useful example code so in order to make the previous posts on this subject more useful I thought it would be a good idea to link in the example.


public voidAddProcessChildData(long pKey){
   
   try {
      tcFormInstanceOperationsIntf f = (tcFormInstanceOperationsIntf)

      getUtility("Thor.API.Operations.tcFormInstanceOperationsIntf ");
      tcResultSet childFormDef = f.getChildFormDefinition(f.getProcessFormDefinitionKey(pKey),f.getProcessFormVersion(pKey));

      long childKey = childFormDef.getLongValue("Structure Utility.Child Tables.Child Key");
      //if there is only 1 child table fo rthe parent form else you need to iterate through result set

      Map attrChildData = new HashMap();
      String groupDN = "someValue";

      attrChildData .put("UD_ADUSRC_GROUPNAME",groupDN);
      f.addProcessFormChildData(childKey,pKey,attrChildData);
   
   }catch (Exception e){
      e.printStackTrace();
   } 
}

Monday, November 8, 2010

A bridge(stream) too far

Over the years I have run into a number of products that had lots of good ideas but perhaps simply didn't have enough resources to implement them properly. One of these is Bridgestream Smartroles (aka Oracle Role Manager). This product is no longer with us having been trumped by Sun Role Manager (aka Vauu RBACx) but I really think that the product came with some good concepts that you can use in your IDM implementation no matter what product you are using.

Business roles vs IT roles

Roles are basically a tool to group entitlements together into manageable packets. If you ask an IT person and a business person what manageable packets are and how they should be named the two groups tend to disagree a lot.

One approach to solve this problem is to let the business have their business roles (teller level two) and let the IT guys build their own roles (two AD groups, logins to two applications configured with specific application roles). Then you just combine the IT roles into business roles and the business can then be asked to certify that Emma Smith the teller should have this business role. The fact that the business role actually results in three IT roles which in turn results in a bucket load of entitlements (AD groups etc) is not really relevant to the certification decision.

In reality things rarely works out this smoothly but I have found the approach useful.

Everything is temporal

One of the nifty features in Bridgestream was the temporal engine which made the eternal problem of the ever changing nature of everything.

In many role related IDM projects it is very easy to forget that everything including the roles and the entitlement has a lifecycle and will need to change as some point. Manging this without support in the base framework can get very complex so building in proper support for temporality is key to making maintenance cheap and easy.

Polyarchy

Hierarchies are really useful when you want to organize users. One problem that you often run into is the fact that a specific user may be in a number of different hierarchies. One may be the geographical location, another may be the reporting chain and a third may be the kind of position you are in (i.e. embedded HR or IT departments that report into the business unit with dotted lines to the corporate HR or IT). It is literally impossible to capture all these relationships in a single hierarchy.

Bridgestream introduced, at least to me, the concept of polyarchy. Instead of trying to wrestle all these relationships into a single hierarchy you simply create multiple hierarchies where each hierarchy reflects one aspect of the users relationship with surrounding nodes. If you also are able to divide up the entitlements into buckets where each specific bucket is likely to be assigned due the users position in this specific hierarchy (a role called "Cambridge campus" or "Floor 3 - building 6 - Cambridge campus" are likely location based) you have a good tool that can reduce the complexity of the role discovery substantially.

There is a more expanded example of Polyarchys in action in the post Polyarchies in pratice

Friday, October 29, 2010

Avoiding issues with referrals in LDAP searches

If the target LDAP server contains referrals, especially broken ones, this may cause issues during LDAP searches.

If you switch "is there any more objects left" test from:
while (results != null && results.hasMore())
to:
while (results != null && results.hasMoreElements())
this problem goes away.

When I have run into strange LDAP error messages I have found the LDAP Status Codes and JNDI Exceptions to be very helpful.

Wednesday, October 27, 2010

AD/LDAP reconciliation using paging

Depending on the settings on your target AD/LDAP server you may need to use pageing when doing larger searches. AD2008 per default only gives you a 1000 objects in any one LDAP search which means that most recons requires either paging or many very well defined LDAP filters that gives you a very small return sets.

Paging is supported in JNDI by activating a specific RequestControl. The LDAP server will then serve you pageSize number of records together with a cookie that you send back to get another batch. Rinse and repeat until you have all the result records.

The example code was written for TDS but can be used with any LDAP V3 compliant LDAP server.

private HashMap performTimSearch(String ouPath){
  
  NamingEnumeration results=null;
  //keyed on the String name, contains SearchResult objects
  HashMap totalResults=new HashMap(30000);  
  
  if(timAdminPassword.equals("")){   
   logger.debug("\nNo TIM admin password. No TIM search will be performed.");
   return totalResults;
  }
  try {
      // Create initial context
      LdapContext ctx = new InitialLdapContext(timEnv,null);
     
      // Activate paged results
      int pageSize = 400;
      byte[] cookie = null;
      PagedResultsControl pageControl = new PagedResultsControl(pageSize, Control.NONCRITICAL);

      //activate search controls
      SearchControls searchCtrl = new SearchControls();
      searchCtrl.setReturningAttributes(timAttributes);
      searchCtrl.setSearchScope(SearchControls.SUBTREE_SCOPE);
     
      ctx.setRequestControls(new Control[] { new PagedResultsControl(pageSize, Control.NONCRITICAL) });
   
      int total=0;
     
      // Specify the attributes to match     
      String matchAttrs = "(objectclass=user)";

      do {
          /* perform the search */
       results = ctx.search(ouPath, matchAttrs, searchCtrl);

       while (results != null && results.hasMore()) {
        SearchResult entry = (SearchResult) results.next();
        totalResults.put(entry.getName(), entry);
        total=total+1;
       }
       
          // Examine the paged results control response
          Control[] controls = ctx.getResponseControls();
          if (controls != null) {
            for (int i = 0; i < controls.length; i++) {
              if (controls[i] instanceof PagedResultsResponseControl) {
                PagedResultsResponseControl prrc = (PagedResultsResponseControl) controls[i];    
                cookie = prrc.getCookie();
              }
            }
          } else {
            logger.debug("No controls were sent from the server");
          }
          // Re-activate paged results
          ctx.setRequestControls(new Control[] { new PagedResultsControl(
              pageSize, cookie, Control.CRITICAL) });

        } while (cookie != null);

     
      logger.debug("Finished TIM search. Found " + total + " users.");
     
      // Close the context when we're done
      ctx.close();
     
  } catch (Exception e) {
   logger.error("TIM search failed");
   logger.error(e.getMessage());
  }
    
     return totalResults;
 }

Monday, October 11, 2010

OIM Howto: Date based enable/disable of resources

In some cases you don't want to give a user access to a resource immediately but rather start the access at a certain point in time. In a similar fashion you may not want to give the access permanently but rather up until a certain end date.

There is a number of ways to implement this but I would recommend using the following approach:
  1. Add start date and end date to the process form.
  2. As a part of the provisioning process add a step that disables the resource if the start date hasn't happened yet or end date has passed.
  3. Create a scheduled task that checks all provisioned resources of this type and enables/disables as appropriate given the start date and end dates.
Another option is to hold the object in provisioning state until the start date hits (add a task to the provisioning process that checks the date, let the scheduled task re execute the provisioning task).

Sunday, October 3, 2010

[OIM vs TIM] Basic RBAC

In my previous post RBAC vs ABAC I talked about using your favorite provisioning tool to implement a simple case of AD group membership management. I thought it might be interesting to compare how you implement this use case in OIM and TIM.

In OIM there is a large number of different ways to do AD group memberships but lets concentrate on the most standard and out of the box method: rules, groups and access policies. In the use case that we are dealing with OIM's standard functionality actually works great. If the rules that governs which AD group is given to which group of users would be slightly different i.e. give everyone whose cost center is between 1200 - 1299 AD group X and 1300-1399 AD group Y then the OIM standard functionality basically stops working and you will have to bring an entity adapter based approach to bear (see Role based group memberships in OIM for more details on how to solve this problem)

In TIM the OIM groups are basically called Roles. The TIM role basically contains it's own OIM rule definition. The TIM role membership definition is done through an LDAP filter which of course is a much more flexible mechanism than OIM's rules. as you have access to wildcards and everything else an LDAP filter can offer you.

In TIM you use a provisioning policy to implement the mapping of TIM role (OIM group) to entitlement. A TIM provisioning policy more or less is equivalent to an Access Policy in OIM. The TIM provisioning policy contains more configuration as some of the things that is configured in pre pop adapters and the process form in OIM is controlled by the provisioning policy in TIM. The configuration in TIM is done through Javascript while you usually tend to use Java code in OIM.

To implement the use case in TIM you would:
  1. Create a TIM role for each AD group that you want to provision. 
  2. Configure each TIM role to only include the correct users using an LDAP filter.
  3. Attach a provisioning policy to each TIM role that gives the specific AD group.
  4. Done!
Overall I think that TIM is the winner in this specific battle as you can do more things without having to resort to coding in TIM. You can do the same things in OIM as in TIM but in many cases you will have to resort to coding at an earlier stage in OIM as TIM has a more flexible configuration interface.

Saturday, September 25, 2010

RBAC vs ABAC

Over the last week there has been a very interesting discussion around role based access control vs attribute based access control. My personal opinion is that there really isn't any razor sharp division between the different paradigms and that in many cases a blended solution is what gives best support for the business case. Let me demonstrate what I mean with an example.

The business case is that VPN system needs to be converted from a "if you can authenticate then you have full access" to a system that only gives access to the systems the user needs. The idea is that you somehow can define groups of users that need access to certain systems. For now the only user groups that have been defined are the different company divisions and consultants vs employees but the system needs to be flexible to support other group definitions further down the line.

The access control device supports definition of access groups through either AD groups or through AD attributes. The AD attributes are analyzed in an XACML light module (if attribute company="truck manufacturing" and user_type="employee" -> user_is_member_of_access_group_employee_in_truck_manufacturing). Alternatively the access control device can simply look for users that are member of the AD group employee_in_truck_manufacturing and then apply the access rules for this  group.

This means that at first glance you have a choice between a more ABAC oriented approach (access device looks at attributes and makes a decision) or a more RBAC oriented approach (access device looks at a group membership/role).

The complexity here is how do you populate the attributes and/or place the user in the correct AD group?

Assuming that the attributes exists somewhere, i.e. in the HR system, you can populate the AD record using your favorite provisioning tool at AD account creation time and then maintain them either using the provisioning tool or a separate metadirectory product.

The AD group membership can be solved by implementing a rule based AD group allocation module in the provisioning product. The provisioning product simply evaluates rules written in XACML or other suitable language (LDAP filters, simple boolean logic, regexp) and then provisions AD group memberships.

Now the conclusion you can draw from this is that in the use case where the access control decision is done based on user attributes the essential difference between the two choices is only the exact location of the evaluation logic. Should it live in the run time access control device or should the decision be made in the provisioning product?

In most cases I would argue that the correct choice depends more on the capabilities of respective product. If the decision rules are easily modeled in the rules language offered by the provisioning product then it may make more sense to place the logic there. If the access control offers the better platform then use that.

One advantage of using the provisioning platform may be that it is easier to explain to the helpdesk and the end users that "if you aren't member of the AD group truck_manufacturing_employees then you won't have remote access to the trucking portal" then having to say "if your employee_type attribute is employee and your company attribute is truck_manufacturing then you have access". This is especially true if the attributes contains codes instead of names.

If you want to learn more about ABAC I recommend David Brossard's excellent ABAC primer "Authorization is not just about who you are".

Thursday, September 23, 2010

Upgrading MIIS 2003 to ILM 2007

I recently upgraded a Microsoft Identity Integration Server 2003 to Identity Lifecycle Manager 2007. As far as I have been able to determine there are very few differences between these two products other than the fact that ILM supports AD 2008.

MIIS/ILM is basically a quite decent metadirectory engine that also can be used as a poor mans provisioning solution although the total lack of support for requests, approval workflows, self service and recertification to just pick a few of the features you normally would expect in a provisioning solution can be a tiny bit limiting. Microsoft has addressed some of these concerns in Microsoft Forefront that was released earlier this year.

The upgrade process was actually very straightforward.

  1. Take backup of encryption key in old MIIS install
  2. Take backup of old database (SQL 2000)
  3. Import backup into new database (SQL 2005)
  4. Put the encryption key on new app server
  5. Start install and do some basic configuration
  6. Get some coffe and let the upgrade run for about an hour
  7. Load up the encryption key in the new ILM install
  8. Patch with the latest patch
  9. Done

The whole process took about two hours for the db steps and another hour or so for the application step. I was very impressed with the ease of the upgrade process. Normally IDM upgrades are really complex and time consuming so this was a very pleasant surprise.

One interesting feature was that the custom dlls that contain our custom rules actually got copied over to the file system of the new application server automatically. I assume that MIIS/ILM keeps them in form of blobs in the database and the upgrade process copy the files out of the db.

Friday, September 10, 2010

What a difference a year makes

There was a posting in of the IDM groups on LinkedIn today that made me take another look at the 2009 Forrester IAM wave report. The report is getting a bit old but it is sometimes interesting to look back and see what has happend in the IAM market over the last year.

In my opinion the biggest change is clearly the aquisition of Sun and the demise of Sun Identity Manager. Suddenly one of the strongest players in the market just disappeared which opened up a lot of room for other systems. One of biggest winners seems to be Courian that suddenly got a shining example of why buying a suite from one of the big boys doesn't neccessarily mean that you have a stronger support and continued development track in front of you.

Other big changes are IBM TIM 5.1, Microsoft Forefront and Oracle 11g.

TIM 5.1 meant that IBM got substantially improved role management, access recertification and group management. I think largely that the features are well implemented but they really don't have the depth that some of the free standing role management tools have (i.e. Oracle Identity Analytics). Martin Kuppinger at Kuppinger Cole wrote an interesting posting about TIM5.1 in his very good blog.

Microsoft Forefront really means that ILM stops being a glorified metadirectory engine and takes the step into being a proper provisioning platform. If I was in a Microsoft only shop and had a business that was trying to deploy ten different Sharepoint portals (don't they all these days?) I would clearly consider taking a deeper look at the product.

Oracle 11g has a lot of nifty new features that I have been talking about in various posts.

Overall I think that the wave still gives a good overview of the IAM marketspace and I am really looking forward to the 2010 version of the Forrester IAM wave.

(Full disclosure note: I have an immediate family members that works for Forrester)

Monday, September 6, 2010

OIM Howto: Target system group memberships through OIM groups and access policies

In OIM there is often multiple ways to implement the same functionality.

One such case is target system group memberships. In Leverage standard connector group management I described how to leverage the functionality provided by the OIM AD connector to manage AD group memberships. You can also use the exact same functionality as well as the OIM rules, groups and access policies framework to manage group memberships.

  1. Create a rule that adds users to an OIM group under certain circumstances (i.e. user location is "New York" or costcenter is 2387)
  2. Add an access policy to that group that provisions the AD user object to the user with the group child form row set to give out the appropriate AD group

You can give a specific user more than one AD group through this strategy as the access policy evaluation engine basically adds the union of all child form rows to the process form of the access policy with the highest priority. Where you do run into trouble is if the same AD group membership is given to the same user by more than one access policy. If this happen the second group membership add will result in an error.

Taking the route over OIM groups and access policies has the advantage of making things clearer for administrators as well as auditors. It makes it possible to use certain out of the box OIM reports that covers OIM group memberships as proxies for AD group membership reports which certainly is helpful in certain situations.

OIM Howto: One resource object per target system group

In most cases of target system group management you need to manage a large number of different groups but sometimes you only need to handle a handful of groups. This commonly happens if the primary purpose of the OIM system is to manage some specific target system that actually uses groups on an LDAP server (often AD) to do fine, medium or coarse grained authorization. In some cases access to an application may be granted by an AD group membership (commonly used by portal software such as Plumtree).

In these cases it may be appropriate to create an independent resource object for each target system group. There are some substantial advantages to this approach:

  • In the user resource view an administrator will clearly see what target system group or application the user has access to
  • Attestation works cleaner
  • Out of the box reports works better

There is also nothing that stops you from doing a "mix and match" approach where some AD groups are represented as independent resource objects and other are grouped under a general "Add AD group" resource object.

The implementation basically follows the steps in Support for request based OIM group memberships other than the fact that you will not need any object form as the group name is reflected in the resource object itself.

Thursday, September 2, 2010

The downside of OIM resource object proliferation

The basic function of a resource object in OIM is to represent access for a specific user to a specific system. In many OIM architectures you chose to leverage the resource object to represent all kinds of entities in order to make the entity requestable in the request interface or attestable in the attestation framework.

Examples of entities that can be modelled as resource objects are:


One problem you will get if you have a lot of "transaction oriented resource objects" is that the user resource view can get drowned in objects so that it is hard for the OIM administrators to find the resource object instances that they really are interested in. Lets say that you have a user that has worked for the company for five years and have twenty AD group membership adds, five removals and ten resource object instances that represents user data updates. This user will have thirtyfive extra resource object instances in his resource object instance view.

You can of course argue that the state changes and group memberships should be properly recorded in the user's resource object instance view (it is not a bug, it is a feature!). If your customer insists that it will look ugly and limit administrator productivity you can simply change the design to have the resource object being raised against a dummy organisation or user. Simply add the real target user login to the object and process form and problem is solved.

Well, of course excluding training the end users about the fact that they need to pick "AD group user" instead of "John Smith" as the user when they want to request an AD group membership for John Smith. Depending on how big your user population with request generation privileges this may or may not be a problem.