Exploring Different Methods to Trigger Provisioning in SailPoint IdentityIQ

When I first started working with SailPoint IdentityIQ, I found the provisioning process to be quite complex. There were multiple methods for different use cases, and I often found myself confused about which approach to use in various situations. However, as I gained a deeper understanding of the different methods, I was able to determine the best process for each condition. I thought it would be helpful to share this knowledge with you all to make navigating the provisioning process a bit easier

This post explores various methods to trigger provisioning, from the most direct and customizable approaches to those that leverage SailPoint’s built-in workflows.

1. Direct Provisioner API Calls: Full Control Over Provisioning

For those who need complete control over the provisioning process, utilizing the Provisioner API directly is the most comprehensive option. This approach allows for precise management by interacting directly with the underlying engine.

  • How It’s Done: You script calls to compile and execute a provisioning project using the Provisioner and ProvisioningProject classes. Here’s a sample code snippet to demonstrate this method:
import sailpoint.api.Provisioner;
import sailpoint.object.ProvisioningProject;

Provisioner prov = new Provisioner(wfcontext.getSailPointContext());
ProvisioningProject proj = prov.compile(plan);
prov.execute(proj);
  • Benefits: Offers maximum control, making it ideal for highly complex or specialized provisioning needs.
  • Considerations: This method bypasses IdentityIQ workflows, so you’ll need to handle IdentityRequest objects, error handling, and retries manually. This method will launch on the server where it is calld ignoring any load balancing.

2. Triggering Provisioning Using Workflow Methods

This approach provides a balanced level of control, allowing for customization without requiring deep API integration.

  • How It’s Done: Use workflow methods like compileProvisioningProject and provisionProject to manage the provisioning process. Below is a code snippet demonstrating this approach:
<Step action="call:compileProvisioningProject" icon="Task" name="Provision-Custom" posX="522" posY="358" resultVariable="project">
    <Arg name="identityName" value="ref:identityName"/>
    <Arg name="plan" value="ref:plan"/>
    <Arg name="requester" value="ref:launcher"/>
    <Arg name="source" value="LCM"/>
    <Arg name="optimisticProvisioning" value="false"/>
    <Transition to="Provision-Execute"/>
</Step>

<Step action="call:provisionProject" icon="Task" name="Provision-Execute" posX="632" posY="358">
    <Arg name="project" value="ref:project"/>
    <Arg name="background" value="false"/>
    <Transition to="End"/>
</Step>
  • Benefits: Offers flexibility without the complexity of direct API calls, suitable for scenarios requiring moderate customization.
  • Considerations: Since it bypasses default workflows, automatic tracking of IdentityRequest objects, approvals, notifications, and retries will need to be handled separately.

3. Manually Calling Subprocesses (Initialize, Provision, Finalize)

For those who wish to customize workflows while still utilizing IdentityIQ’s built-in capabilities, manually triggering subprocesses is an effective method.

  • How It’s Done: Directly call the Initialize, Provision, and Finalize subprocesses to manage different stages of provisioning. Here’s a snippet showing how to implement this:
<Step icon="Task" name="Provision" posX="522" posY="242">
    <Arg name="formTemplate" value="Identity Update"/>
    <Arg name="identityName" value="ref:identityName"/>
    <Arg name="identityDisplayName"/>
    <Arg name="launcher" value="ref:launcher"/>
    <Arg name="optimisticProvisioning" value="false"/>
    <Arg name="plan" value="ref:plan"/>
    <Arg name="priority" value="Normal"/>
    <Arg name="policyScheme" value="none"/>
    <Arg name="source" value="LCM"/>
    <Arg name="trace" value="false"/>
    <Arg name="flow" value="EntitlementsRequest"/>
    <Description>
        Call the standard subprocess to initialize the request, this includes
        auditing, building the approval set, compiling the plan into
        project and checking policy violations.
    </Description>
    <Return name="project" to="project"/>
    <Return name="approvalSet" to="cart"/>
    <Return name="identityRequestId" to="identityRequestId"/>
    <Return name="policyViolations" to="policyViolations"/>
    <WorkflowRef>
        <Reference class="sailpoint.object.Workflow" name="Identity Request Initialize"/>
    </WorkflowRef>
    <Transition to="Provision"/>
</Step>

<Step icon="Task" name="Provision" posX="660" posY="242">
    <Arg name="fallbackApprover" value="spadmin"/>
    <Arg name="foregroundProvisioning" value="true"/>
    <Arg name="formTemplate" value="Identity Update"/>
    <Arg name="identityDisplayName" value="ref:identityDisplayName"/>
    <Arg name="identityName" value="ref:identityName"/>
    <Arg name="launcher" value="ref:launcher"/>
    <Arg name="manualActionsEmailTemplate" value="Pending Manual Change"/>
    <Arg name="optimisticProvisioning" value="false"/>
    <Arg name="project" value="ref:project"/>
    <Arg name="policyScheme" value="none"/>
    <Arg name="trace" value="false"/>
    <Description>
        Call the standard subprocess that will process the
        approval decisions and do provisioning. This
        includes calling any configured provisioning
        connectors and building manual actions.
    </Description>
    <Return name="project" to="project"/>
    <WorkflowRef>
        <Reference class="sailpoint.object.Workflow" name="Identity Request Provision"/>
    </WorkflowRef>
    <Transition to="Finalize"/>
</Step>

<Step icon="Task" name="Finalize" posX="814" posY="242">
    <Arg name="approvalSet" value="ref:cart"/>
    <Arg name="project" value="ref:project"/>
    <Arg name="trace" value="false"/>
    <Description>
        Call the standard subprocess that can audit/finalize the request.
    </Description>
    <WorkflowRef>
        <Reference class="sailpoint.object.Workflow" name="Identity Request Finalize"/>
    </WorkflowRef>
    <Transition to="Audit"/>
</Step>
  • Benefits: Provides a balanced approach by combining customization with built-in features like retries and process queuing.
  • Considerations: Skipping certain subprocesses requires manual handling or ensuring those steps are not needed.

4. Leveraging the LCM Provisioning Workflow

For a more automated approach, passing a provisioning plan into the Lifecycle Manager (LCM) Provisioning Workflow is a straightforward and effective option.

  • How It’s Done: Submit a provisioning plan to the LCM Provisioning Workflow, which automatically manages the process, including error handling and retries. Here’s how you can implement this method:
<Step icon="Provision" name="Provision-custom" posX="640" posY="123">
    <Arg name="plan" value="ref:plan"/>
    <Arg name="flow" value="EntitlementsRequest"/>
    <Arg name="identityName" value="ref:identityName"/>
    <Return name="identityRequestId" to="identityRequestId"/>
    <WorkflowRef>
        <Reference class="sailpoint.object.Workflow" name="LCM Provisioning"/>
    </WorkflowRef>
    <Transition to="End"/>
</Step>
  • Benefits: This method simplifies the provisioning process by relying on out-of-the-box workflows, and generating identityiq requests for tracking.
  • Considerations: While easy to implement, this method offers less flexibility in customized sceanrios when certain provisioning outcomes are required for next steps.
5 Likes