Tuesday, October 12, 2021

Rule to read data from csv file and update the identity cube attributes

 Requirement is to read a csv file with contains identity's displayname, nationality and relation attributes in first, fifth and sixth columns of the file. 

Below is the Rule:

<!DOCTYPE Rule PUBLIC "sailpoint.dtd" "sailpoint.dtd">
<Rule created="" id="" language="beanshell" modified="" name="Read CSV file">
  <Description>Identity creation rules are used to set attributes on new Identity objects when they are created.  New identities may be created during the aggregation of application accounts, or optionally created after pass-through authentication.
One common operation is to change the name property of the identity when the default application name is complex (such as a directory DN).
Another common operation is to assign a set of initial capabilities based on the attributes pulled from the application account.</Description>
  <Signature returnType="void"/>
  <Source>
 import sailpoint.object.Identity;
  import sailpoint.object.QueryOptions;
  import sailpoint.object.Filter;
  
  log.error("Running Rule: Read CSV file"); 
  String line = "";
  QueryOptions identityQuery = new QueryOptions();
  
  try   
  { 
    
  BufferedReader br = new BufferedReader(new FileReader("C:\\SailPoint\\VendorsWithNationality.csv"));
  br.readLine();
  while ((line = br.readLine()) != null)  
    {  
    String[] data = line.split(","); 
    log.error("----"+ data[0] + "----"+ data[4] + "------" + data[5]);
    String dname = data[0];
    String nationality = data[4];
    String relation = data[5];
    Filter idFilter = Filter.eq("displayName", dname);
    Identity identity = context.getUniqueObject(Identity.class, idFilter);
    log.error(identity);
    if(identity != null){
    log.error("Display name: "+identity.getDisplayName());
    if(identity.getDisplayName()!=null &amp;&amp; identity.getDisplayName().equalsIgnoreCase(dname)){
    identity.setAttribute("nationality",nationality);
    identity.setAttribute("relation", relation);
    log.error("Identity "+identity.getDisplayName()+" Nationality: "+nationality + " Relation: "+ relation);
            context.saveObject(identity);
            context.commitTransaction();
   
        }else {
        log.error("************ Update skipped for user ************" + dname);
        }
    }else {
    log.error("************ Update skipped for user ************" + dname);
    }
   
    }
  } catch (IOException e)   
  {  
    log.error(e); 
  }
  
  log.error("End of Rule: Read CSV file");
  </Source>
</Rule>

 

Monday, September 20, 2021

After Provisioning Rule - When an entitlement is removed, disable the user through webservice

 Requirement: When an Active Directory entitlement (PMS Group) is removed, the identity has to be disabled in the target through webservice. This can be achieved by writing an After Provisioning rule.


<?xml version='1.0' encoding='UTF-8'?>
<!DOCTYPE Rule PUBLIC "sailpoint.dtd" "sailpoint.dtd">
<Rule created="" id="" language="beanshell" modified="" name="AD After Provisioning Disable PMS User" type="AfterProvisioning">
  <Description>An IdentityIQ server-side rule that is executed after the connector's provisioning method is called. This gives the customer the ability to customize or react to anything in the ProvisioningPlan AFTER it has been sent out to the specific applications.
This rule will be called for any application found in a plan that also has a configured 'afterProvisioningRule' configured.</Description>
  <Signature>
    <Inputs>
      <Argument name="log">
        <Description>
          The log object associated with the SailPointContext.
        </Description>
      </Argument>
      <Argument name="context">
        <Description>
          A sailpoint.api.SailPointContext object that can be used to query the database if necessary.
        </Description>
      </Argument>
      <Argument name="plan">
        <Description>
          The ProvisioningPlan object on its way to the Connector.
        </Description>
      </Argument>
      <Argument name="application">
        <Description>
          The application object that references this before/after script.
        </Description>
      </Argument>
      <Argument name="result">
        <Description>
          The ProvisioningResult object returned by the connectors provision method. This can be null and in many cases the connector will  not return a result and instead will annotate the plan's ProvisioningResult either at the plan or account level.        
        </Description>
      </Argument>
    </Inputs>
  </Signature>
  <Source>
import sailpoint.object.ProvisioningPlan;
import sailpoint.object.ProvisioningPlan.AccountRequest;    
import sailpoint.object.ProvisioningPlan.AttributeRequest;
import java.net.URL;
import java.net.HttpURLConnection;
import javax.net.ssl.HttpsURLConnection;
import org.apache.log4j.Logger;
import org.apache.log4j.Level;
  

Logger log = Logger.getLogger("sailpoint.services.rule.AfterProvisioning");
log.debug("Enter Rule AD After provisioning Rule");
public void changeUserStatus(String username) {
  log.debug("username: " + username);
  String auth = "username:password";
  Base64.Encoder encoder = Base64.getEncoder();
  String encodedString = encoder.encodeToString(auth.getBytes());
 // log.debug("endocded string: " +encodedString);
 
try{
  java.net.URL url = new URL("http://example.com/ChangeUserStatus");
  log.debug("The URL to get token is "+url);
  java.net.HttpURLConnection conPost;
  conPost = (java.net.HttpURLConnection) url.openConnection();
  conPost.setRequestMethod("POST");
  conPost.setRequestProperty("Content-Type","application/json");
  conPost.setRequestProperty("Accept", "*/*");
  conPost.setRequestProperty("Content-Length", "108");
  conPost.setRequestProperty("Authorization", "Basic "+encodedString);
  //log.debug("Setting properties over");
  
  conPost.setDoOutput(true);
  
    // JSON body for POST call           
    String jsonInputString =  "{" +
   "\"users\": {   \"ActivateUser\": false, " +
       "\"Logins\":  [ \"" + username +
      "\" ] " +
    "}" +
"}";
log.debug("JSON body: " + jsonInputString);
//  log.debug("sending request");
// Send the request
  
  conPost.connect();
  
OutputStream os = conPost.getOutputStream();
    byte[] input = jsonInputString.getBytes("utf-8");
    os.write(input, 0, input.length);

//  log.debug("Reading response ");
// read the response body
 StringBuilder res = new StringBuilder();
    int responseCode = conPost.getResponseCode();
    String responseMessage = conPost.getResponseMessage();
    String geturl = conPost.getURL().toString();
 //   log.debug(geturl);
 //   log.debug(responseMessage);
    log.debug("HTTP Post Response Code :: " + responseCode);

    if (responseCode == 200) { // success
      InputStream is = conPost.getInputStream();
      int b = -1;
      do {
        b = is.read();
        char c = (char)b;
        res.append(c);
      }while(b!=-1);
      log.debug("The response is "+res.toString());
    } else {
      log.debug("Failed");
      InputStream is = conPost.getErrorStream();
      int b = -1;
      do {
        b = is.read();
        char c = (char)b;
        res.append(c);
      }while(b!=-1);
      log.debug("The failed response is "+res.toString());
    }
    
    } catch (MalformedURLException ex) {
        log.error("MalformedURLException " + ex);
    } catch (IOException ex) {
       log.error("IOException "+ ex);
    }

List &lt;AccountRequest> accountRequests = plan.getAccountRequests();
for(AccountRequest accountRequest : accountRequests){
if(accountRequest.getApplicationName().equalsIgnoreCase("Active Directory and Exchange") &amp;&amp; accountRequest.getOperation().equals(AccountRequest.Operation.Modify)){
List&lt;AttributeRequest> attributeRequests = accountRequest.getAttributeRequests();
for(AttributeRequest attributeRequest : attributeRequests){
if(attributeRequest.getName().equalsIgnoreCase("memberOf") &amp;&amp; attributeRequest.getOperation().equals(ProvisioningPlan.Operation.Remove) &amp;&amp; attributeRequest.getValue().toString().equalsIgnoreCase("CN=PMSGroup,OU=Security Groups,OU=IBM,DC=COM")){
// Invoke webservice here to Inactive user
changeUserStatus(plan.getIdentity().getName());
}
}
}
}
</Source>
</Rule> 



Thursday, September 16, 2021

Customize Approval message through Build Approval Set

 To add custom messages in Approvals, we can add it through Build Approval Set variable in Workflow.

Requirement:


Add a rule in the Build Approval Set variable.


The message that is displayed is item.setValue(). 

Below Rule is added to the Build Approval Set. 


<?xml version='1.0' encoding='UTF-8'?>
<!DOCTYPE Rule PUBLIC "sailpoint.dtd" "sailpoint.dtd">
<Rule created="" id="" language="beanshell" modified="" name="Plugin Build Identity ApprovalSet" type="Workflow">
  <Description>Build Identity ApprovalSet for request coming from vendor contract extension plugin</Description>
  <Signature returnType="Object"/>
  <Source>import sailpoint.object.ProvisioningPlan;
      import sailpoint.object.ProvisioningPlan.AttributeRequest;
      import sailpoint.object.ProvisioningPlan.AccountRequest;
      import sailpoint.object.ApprovalSet;
      import sailpoint.object.ApprovalItem;
      import sailpoint.object.Attributes;
      import sailpoint.tools.Util;
  import java.util.Date;
  import java.text.SimpleDateFormat;
      
      serilog=org.apache.commons.logging.LogFactory.getLog("sailpoint.services.rules.workflow.PluginBuildIdentityApprovalSet");
  serilog.debug("--------------------------------------------------");
      serilog.debug(plan.toXml());
      ApprovalSet set = new ApprovalSet();
if ( plan != null ) {
          List accountRequests = plan.getAccountRequests();
          for ( AccountRequest request : accountRequests ) {
              ApprovalItem item = new ApprovalItem();
              item.setApplication(request.getApplication());
              item.setInstance(request.getInstance());
              item.setNativeIdentity(request.getNativeIdentity());
              item.setOperation(request.getOperation().toString());
              List attrRequestFlat = flattenAttributeRequests(request.getAttributeRequests());
           
 
            if( pluginAction.equalsIgnoreCase("vendor-contract-extension")) {
          
              String contractExtensionComments = "Request to extend the vendor contract for "+ identityDisplayName + " from "+ currentEndDate + " to " + extensionDate; 
              item.setValue(contractExtensionComments);
            
            } else if( pluginAction.equalsIgnoreCase("vendor-disable")) {
              
              SimpleDateFormat simpleDateFormat = new SimpleDateFormat("yyyy-MM-dd");
    String date = simpleDateFormat.format(terminationDate);
              String disableComments = "Request to disable the vendor "+ identityDisplayName + " with Termination Date set to " + date; 
              item.setValue(disableComments);
            
            }else if( attrRequestFlat != null ) {
                  item.setValue(attrRequestFlat);
              } 
              Attributes attributes = getAttributeRequestArguments(request.getAttributeRequests());
              item.setAttributes(attributes);
              
              // for these requests comments come in on the plan
              String comments = plan.getComments();
              if ( Util.getString(comments) != null ) {
                  item.setRequesterComments(comments);
              }
              set.add(item);
          }
          // while we are here lets annotate the plan with previousValues
          if ( flow.equals("IdentityEditRequest") ) {
              AccountRequest iiqRequest = plan.getAccountRequest("IIQ");    
              if ( iiqRequest != null ) {
                  List attributeRequests = iiqRequest.getAttributeRequests();
                  if ( Util.size(attributeRequests) > 0 ) {
                      Identity id = context.getObject(Identity.class, identityName);
                      if ( id != null )  {
                          for ( AttributeRequest req : attributeRequests ) {
                              String name = req.getName();
                              if ( name != null ) {
                                  // We have to be carefull here, if we see manager display
                                  // the displayName
                                  Object prevValue = id.getAttribute(name);
                                  if ( prevValue != null ) {
                                      if (name.equals("manager") ) {
                                          String displayName = getIdentityProperty((String)prevValue, "displayName");
                                          if ( displayName != null ) {
                                              prevValue = displayName;
                                          }
                                      }
                                      else if (prevValue instanceof Identity) {
                                          prevValue = (String)prevValue.getDisplayableName();
                                      }
                                      else  if(prevValue instanceof List) {
                                          /* Thanks to type erasure there is no way for us to write something like
                                           * prevValue instanceof List&amp;lt;Identity> so break it into steps.  Check if
                                           * prevValue is a List.  If it has any elements get the first one. If that
                                           * is an instance of Identity then assume the rest of the elements are too
                                           * and then build a List of displayable names, because that is what we do
                                           * with Identitys. */
                                          List prevValueList = (List) prevValue;
                                          if(prevValueList.size() > 0) {
                                              if(prevValueList.get(0) instanceof Identity) {
                                                  List identityIds = new ArrayList(prevValueList.size());
                                                  for (Object value : prevValueList) {
                                                      Identity identity = (Identity) value;
                                                      identityIds.add(identity.getDisplayableName());
                                                  }
                                                  prevValue = identityIds;
                                              }
                                          }
                                      }
                                      req.put(ProvisioningPlan.ARG_PREVIOUS_VALUE, prevValue);
                                  }
                              }
                          }
                      }
                  }
              }
          }
      }
      return set;</Source>
</Rule>



SailPoint approval scheme for different events

 We can use a script in approvalScheme variable in workflow and return different values based on our requirement. 

<Variable input="true" name="approvalScheme">
    <Description>
      A String that specifies how approvals should be generated for
      this workflow there are three built-in modes
      none - disabled approvals
      manager - The user's current manager will get approvals
      newManager - The newly assigned manager will get approvals when
      manager transfers occur. Otherwise the user's manager
      current manager will be the approver.
    </Description>
    <Script>
      <Source>
        import org.apache.log4j.Logger;
        import org.apache.log4j.Level;
        private static Logger logger = Logger.getLogger("sailpoint.services.transfer");
        logger.setLevel(Level.DEBUG);
        if("Vendor Manager Transfer".equalsIgnoreCase(eventType) || "Vendor Enable".equalsIgnoreCase(eventType))
        {
if(managerStatus)
{
logger.error("managerStatus"+managerStatus);
return "newManager";
}
else {
logger.error("else block of mgrtransfer::"+managerStatus);
return "manager"+","+"newManager";
}
        }
        else if("Vendor Create".equalsIgnoreCase(eventType))
        {
logger.debug("Create Vendor::"+eventType);
return "manager";
        }
        else if("DeletePRVAccount".equalsIgnoreCase(eventType))
        {
logger.debug("Create Vendor::"+eventType);
return "manager";
        }
        else if("Create Privilaged Account".equalsIgnoreCase(eventType))
        {
logger.debug("Create Vendor::"+eventType);
return "manager";
        }
        else
        {
logger.error("else block::"+managerStatus);
return "manager"+","+"newManager";
        }
      </Source>
    </Script>
  </Variable> 



Thursday, May 20, 2021

Code to update provisioning plan to remove the "Remove entitlement requests" from the provisioning plan

 Requirement: The function takes three inputs ProvisioningPlan, application name and the list entitlements that shouldn't be removed from the user. (This funtion can be used as a part of Mover workflow where a set of entitlements must not be removed from the user after provisioning due to mover event).


public ProvisioningPlan removeADGroupRemoveRequest(ProvisioningPlan plan, String appName, List<String> groups) {
log.debug("Entered removeADGroupRemoveRequest");
// Define a new ProvisioningPlan
ProvisioningPlan newplan = new ProvisioningPlan();
List<AccountRequest> newAccountRequests = null; 
sailpoint.object.ProvisioningPlan.AccountRequest.Operation operation = null;
// Get the account requests
List<AccountRequest> accountRequests = plan.getAccountRequests();
if (accountRequests.size()>=0) {
// Iterate for every accountRequest
for (AccountRequest accountRequest : accountRequests) {
operation = accountRequest.getOperation();
String applicationName = accountRequest.getApplicationName();
//check if the application name of the accountRequest is same as the incoming appName
if(applicationName.equalsIgnoreCase(appName)) {
log.debug("Operation for Account Request: "+operation);
if(operation.equals(AccountRequest.Operation.Modify)) {
// Get attribute requests from the accountRequest
List<AttributeRequest> attributeRequests = accountRequest.getAttributeRequests();
if(attributeRequests.size()>0) {
for(AttributeRequest attributeRequest : attributeRequests) {
String name = attributeRequest.getName();
Object value = attributeRequest.getValue();
ProvisioningPlan.Operation oper = attributeRequest.getOp();
if(name!=null)
{
if(name.equalsIgnoreCase("memberOf")) {
if(attributeRequest.getOperation().equals(ProvisioningPlan.Operation.Remove)) {
log.debug("Remove entitlement operation entered");
String entValue = (String)value;
if(groups.contains(entValue)){
// remove the attribute request from account request
accountRequest.remove(attributeRequest);
}
}
}
}
}
}
}
}
//adding all the accountRequests to the newAccountRequests list
newAccountRequests.add(accountRequest);
}
  }
//add the newAccountRequests to the newplan and return newplan
newplan.setAccountRequests(newAccountRequests);
return newplan;
}

Comment below if you find this post helpful.

Monday, May 10, 2021

Quicklink to display the list of users who are expiring in next 14 days

 Requirement: Develop a Quicklink, once we click on it, return the list of users who are expiring in next 14 days.

1. Create a quicklink category. Import the below file into Sailpoint to create quicklink category. 

https://drive.google.com/file/d/1JzGYxpY_4BDZn2MZyKbRy22MNwt-hHN3/view?usp=sharing

2. Create a workflow quick link. Import the below file into Sailpoint to create quicklink.

https://drive.google.com/file/d/15_2GVWHXmHQcUQ44FYoeGGPKVUuJcBqm/view?usp=sharing

3.  Create a workflow and add a form in it. Add a field in the form and add a rule for the field which returns the users who are expiring in next 14 days.

Import the below workflow into Sailpoint.

https://drive.google.com/file/d/13fdQcrH2HAiS44anmA0sLXB2Z-DZ5uX4/view?usp=sharing 

Note: The rule is written with keeping below points in mind:

1. The user expiry is known from the Application attribute 'lastLogOn' of "HR System - Employees" application

2. The date format of 'lastLogOn' is in LDAP millisecond.

3. Convert the LDAP millisecond date to normal date and them compare it with current date. If the difference is <= 14 days, return the Identity Name.

Import the below Rule into Sailpoint.



Comment below if you find this post helpful.

Sunday, May 9, 2021

Email Template to send success message for Joiner

 Sample Email template to send success message for Joiner. Download here:

https://drive.google.com/file/d/1Rgp3Pid_rWKRp9RxOsV8vysX6VX3ULtC/view?usp=sharing

Update the logo by convert the image to base64 encoded https://www.base64encode.org/ and replace in the email template.



Comment below if you find this post helpful.

Friday, May 7, 2021

Defining Multi-level approval process

 Defining approvals in a generic way based on a custom object. The custom object contains the type of provisioning request, application details and the approvers details. 
The approval assignment rule is written to trigger the approvals based on the approvers in the custom object. 

Requirement:

If the user request for Entitlement to be added, for Active Directory the approvals has to go 3 approvers in serial manner. 
1. Manager
2. Security Admin (Work group)
3. IT Team (Work group)

For Oracle ERP application, the approval has to go only to manager (single approver). And approvals are not required for removal of Entitlements.
For Account Request and Role Request, the approval has to go to manager.

Process:

Step 1: Import the below custom object into SailPoint. The custom object file contains the Provisioning request type, application details and the corresponding approvers.

Step 2: Import the Approval assignment rule into SailPoint. The Approval assignment rule contains the actual logic to trigger the approvals with the details from the custom object.

Step 3: Edit the LCM Provisioning Workflow and provide the name of imported assignment rule in argument approvalAssignmentRule for the sub processes Split provisioning and Approve and Provision.



step 4: Make sure approval mode = serial and approvalScheme = Identity.

Request for Entitlements and the approvals are triggered as defined in the custom object mappings.

Comment below if you find this post helpful.

Trigger a Life cycle event for Active Directory users who did not login for last 90 days

 Requirement is to trigger an event for Active Directory users who are terminated and did not login for past 90 days.

Go to setup --> Lifecycle Events --> Add New Lifecycle Event.  
Enter the Name, Desription. Select Event type as Rule. 



Use the below code for the Rule:
if(newIdentity!=null){
return true;
}else{
return false;
}


Or you can import the below IdentityTrigger Rule and use it.

Select Included Identities as Rule. Use the below code for the Rule:

import sailpoint.object.Identity;
import sailpoint.api.IdentityService;
import sailpoint.object.Link;
import sailpoint.object.Attributes;
import sailpoint.object.Application;
import java.util.Calendar;
import java.util.Date;
import java.text.SimpleDateFormat;
log.error("Identity Selector Rule Triggered : " + identity.getName());
// get the application link for Active Directory
IdentityService identityService = new IdentityService(context);
Application app = context.getObjectByName(Application.class, "HR System - Employees");
List links = identityService.getLinks(identity, app);
if(!links.isEmpty()){
Link link = links.get(0);
if(link!=null){
String applicationName = link.getApplicationName();
log.error("Application Name: " + applicationName);
Attributes attributes = link.getAttributes();
if(attributes!=null){

String lastLogOn = attributes.getString("lastLogOn");
String userAccountControl = attributes.getString("userAccountControl");
if(lastLogOn != null &amp;&amp; userAccountControl != null) {
// convert from millisecond to date format
Date currentDate=new Date();
        Long diffForDateAndTime = 11644473600000L;
        Long adDate = Long.parseLong(lastLogOn);
        Long epochTime = (adDate / 10000) - diffForDateAndTime;
        Date lastLogOnDate = new Date (epochTime);
        log.error("lastLogOnDate: " + lastLogOnDate);
        
        //calucalate the diff b/w today to lastLogOn date
        int diffInDays = (int) ((currentDate.getTime() - lastLogOnDate.getTime()) / (1000*60*60*24));
        log.error("diffInDays: " + diffInDays);
        //Event generation condition
        if(diffInDays>90 &amp;&amp; userAccountControl.equalsIgnoreCase("514")){
        // log.error("**************   Returning True *******************");
                                    return true;
                                             }
}
}
}
}
return false;

Or you can import the below IdentitySelector Rule and use it.

Run the refresh identity cube task with Process Events enabled. You can see the events are generated for the users that are inactive and not login into AD for last 90 days.

Currently only the events are triggered, but no action is performed. Add a Business process to delete the users.

Thursday, May 6, 2021

Remove Identity Entitlements for any application

 Field Value Rule to remove identity entitlements for any application 


In a given application, call this rule in the Provisioning Policy entitlement field, to remove the  entitlements. Below is the rule:

    import sailpoint.object.EntitlementGroup;
    import sailpoint.object.Attributes;
    import sailpoint.object.ProvisioningPlan;
    import sailpoint.object.ProvisioningPlan.AccountRequest;
    import sailpoint.object.ProvisioningPlan.AttributeRequest;
    import sailpoint.api.Provisioner;
    
    log.error("Executing Feild Value Rule - Remove Entitlements for Identity: " + identity.getName());
    String applicationName = link.getApplicationName();
    String nativeIdentity = link.getNativeIdentity();
    ProvisioningPlan plan = new ProvisioningPlan();
    Provisioner provisioner = new Provisioner(context);
    //Calucalting Identity Entitlements
    List exceptions = identity.getExceptions();
        
    if(exceptions !=null){
    for(EntitlementGroup entitlement: exceptions){
    Attributes attributes = entitlement.getAttributes();
    Map attributesMap = attributes.getMap();
   
    for (Map.Entry attrMap : attributesMap.entrySet()){
    ProvisioningPlan.AccountRequest accountRequest = new ProvisioningPlan.AccountRequest(
    ProvisioningPlan.AccountRequest.Operation.Modify, applicationName, null, nativeIdentity);
   
    ProvisioningPlan.AttributeRequest attributeRequest = new ProvisioningPlan.AttributeRequest(
    (String) attrMap.getKey(), ProvisioningPlan.Operation.Remove, attrMap.getValue());
   
    accountRequest.add(attributeRequest);
    plan.add(accountRequest);
    provisioner.execute(plan);
    }
    }
    } 


Or simply import this xml file to import the rule. 


Comment below if you find this post helpful.

Identity Creation Rule to generate username and full name

 Identity Creation Rule to generate username and full name based on given conditions.

Username condition:
1. First letter of first name + last name
2. First letter of first name.last name
3. first name.last name
4. last name.first letter of first name
5. last name.first name
6. If middele name exists: first letter of first name.first letter of middle name + last name
7. Generate a random integer and append to "newuser"

If the username genereated based on first condition already exists, then go to second condition. If second condition also exists, then go to third condition and so on.

Full name condition:
fullName = firstName + lastName + fatherName + grandFatherName;
 
Below is the code for Identity Creation Rule:

import sailpoint.object.QueryOptions;
import sailpoint.object.Filter;
import sailpoint.object.Identity;
import sailpoint.services.custom.utility.CustomUtil;
//get the attribute values from account
String firstName = account.getStringAttribute("firstName");
String lastName = account.getStringAttribute("lastName");
String middleName = account.getStringAttribute("middleName");
String fatherName = account.getStringAttribute("fatherName");
String grandFatherName = account.getStringAttribute("grandFatherName");
String [] userNameFullName = CustomUtil.getFinalUserNameFullName(firstName, middleName, lastName, fatherName, grandFatherName, context);
Logger log = Logger.getLogger("Custom.Rules.Custom-IdenitityCreation-HRMS");
log.setLevel(Level.DEBUG);
log.debug("firstName: "+firstName);
log.debug("lastName: "+lastName);
log.debug("middleName: " +middleName );
log.debug("fatherName: " +fatherName );
log.debug("grandFatherName: " +grandFatherName );
log.debug("username: "+ userNameFullName[0]);
log.debug("fullname: "+ userNameFullName[1]);
identity.setAttribute("username", userNameFullName[0]);
identity.setAttribute("fullname", userNameFullName[1]);
}

Below is the CustomUtil.java class, which has to be deployed:


package sailpoint.services.custom.utility;
import sailpoint.object.QueryOptions;
import sailpoint.object.Filter;
import sailpoint.object.Identity;
import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;
import java.util.Random;
import sailpoint.api.SailPointContext;
import org.apache.log4j.Logger;
import org.apache.log4j.Level;
public class CustomUtil {

public String checkUserName(String username, SailPointContext context) throws Exception{

Logger log = Logger.getLogger("Custom.Rules.CustomUtil.checkUserName");
log.setLevel(Level.DEBUG);
QueryOptions identityQuery = new QueryOptions();
identityQuery.addFilter(Filter.eq("username", username));
List<Identity> identityList = context.getObjects(Identity.class,identityQuery);

if (!identityList.isEmpty()){
log.error("username already exist for identity: " + identityList);
return "TRUE";
}else{ 
  return "FALSE";
}
}

public String[] getUserNameFullName(String firstName, String middleName, String lastName, String fatherName, String grandFatherName, SailPointContext context) throws Exception{
String [] userNameFullName = {"", ""};
userNameFullName[0] = getUserName(firstName, middleName, lastName, context);
userNameFullName[1] = getFullName(firstName, lastName, fatherName, grandFatherName);
return userNameFullName;
}

public String getUserName(String firstName, String middleName, String lastName, SailPointContext context) throws Exception{

Logger log = Logger.getLogger("Custom.Rules.CustomUtil.getUserName");
log.setLevel(Level.DEBUG);

String userName = null;
if(firstName!=null && !firstName.isEmpty() && lastName !=null && !lastName.isEmpty()) {
//First Condition
userName = firstName.charAt(0) + lastName;
log.debug("First Condition userName: "+userName);
if(checkUserName(userName, context).equalsIgnoreCase("TRUE")){
//Second Condition
userName = firstName.charAt(0) + "." + lastName;
log.debug("Second Condition userName: "+userName);
}else{
return userName;
}
if(checkUserName(userName, context).equalsIgnoreCase("TRUE")){
//Third Condition
userName = firstName + "." + lastName;
log.debug("Third Condition userName: "+userName);
}else{
return userName;
}
if(checkUserName(userName, context).equalsIgnoreCase("TRUE")){
//Fourth Condition
userName = lastName + "." + firstName.charAt(0);
log.debug("Fourth Condition userName: "+userName);
}else{
return userName;
}
if(checkUserName(userName, context).equalsIgnoreCase("TRUE")){
//Fifth Condition
userName = lastName + "." + firstName;
log.debug("Fifth Condition userName: "+userName);
}else{
return userName; 
}
if(checkUserName(userName, context).equalsIgnoreCase("FALSE")){
return userName; 
}

// Final condition - if middlename exists
if(checkUserName(userName, context).equalsIgnoreCase("FALSE") && !middleName.isEmpty()){
//Sixth Condition
userName = firstName.charAt(0) + "." + middleName.charAt(0) + lastName;
log.debug("Sixth Condition userName: "+userName);
return userName;
}
}
//Final condition - generate random integer and append it to first condition
Random rand = new Random();
int rand_int = rand.nextInt(1000);
String rand_str = String.valueOf(rand_int);
userName = "newuser" + rand_str;
return userName;
}
public String getFullName(String firstName, String lastName, String fatherName, String grandFatherName){
String fullName = firstName + " "+ lastName + " " + fatherName + " " + grandFatherName;
return fullName;
}

public String[] getFinalUserNameFullName(String firstName, String middleName, String lastName, String fatherName, String grandFatherName, SailPointContext context) throws Exception{
String [] userNameFullName = getUserNameFullName(firstName, middleName, lastName, fatherName, grandFatherName, context);
return userNameFullName;
}
}


Comment below if you find this post helpful.

Sunday, April 25, 2021

Rule - Get the Entitlement which is requestable

 import sailpoint.object.QueryOptions;
import sailpoint.object.Filter;
import sailpoint.object.ManagedAttribute;
import sailpoint.object.Identity;
import sailpoint.api.ObjectUtil;
import java.util.*;
 
 List entitlements = context.getObjects(ManagedAttribute.class);
 log.debug("List of Entitlements: ");
 for (ManagedAttribute ent : entitlements){
 log.debug("getValue(): " +ent.getValue());
 }
  
 // Entitlements which are requestable
 QueryOptions qo = new QueryOptions();
 qo.addFilter(Filter.eq("requestable", (boolean) true));
 List reqEntitlements = context.getObjects(ManagedAttribute.class, qo);
 log.debug("List of Requestable Entitlements: ");
  for (ManagedAttribute ent : reqEntitlements){
 log.debug("getValue(): " +ent.getValue());
 }
 
 log.debug("\nTotal No. of Entitlements: "+entitlements.size());
 log.debug("\nTotal No. of Requestable Entitlements: "+reqEntitlements.size());


Comment below if you find this post helpful.

Rule - Get the Audit events who's action is Login

import sailpoint.object.QueryOptions;
import sailpoint.object.Filter;
import sailpoint.object.AuditEvent;

 ArrayList auditNames = new ArrayList();
 Filter loginFilter = Filter.eq("action", "login");
 List AuditList = context.getObjects(AuditEvent.class,new QueryOptions().addFilter(loginFilter));
    log.debug("\nAudit List"+AuditList);

 for (AuditEvent auditName : AuditList) {  
  log.debug(auditName.getName());
  auditNames.add(auditName.getName());
}


Comment below if you find this post helpful.

Rule - Get identities modified below 10 days from current date

import sailpoint.object.QueryOptions;
import sailpoint.object.Filter;
import sailpoint.object.Identity;
import sailpoint.api.ObjectUtil;
import java.util.*;

QueryOptions qo = new QueryOptions();
Calendar currentDate = Calendar.getInstance();
System.out.println("Current Date: " +currentDate); 
Date currentTime = currentDate.getTime();
System.out.println("Current Time: " +currentTime); 
currentDate.add(currentDate.DATE, -10); 

Date startDate = currentDate.getTime();
System.out.println("Start Time: " +startDate); 

Filter dateCondition = Filter.and(Filter.le("modified",currentTime), Filter.ge("modified",startDate));
qo.addFilter(dateCondition);
log.debug("============ Query ===========" +qo);

List identityObjectList = context.getObjects(Identity.class, qo);
List identityNames = ObjectUtil.getObjectNames(identityObjectList);
log.debug("List of identities modified: " +identityNames);

Comment below if you find this post helpful.

Rule - In Finance application, list out employees belongs to 'PAYROLL' department with privileged, inactive and service as 'FALSE'

 //In Finance application,list out employees belongs to 'PAYROLL' department with privileged 
//,inactive and service as 'FALSE'.Output should display identity details like first Name,LastName and email.

import sailpoint.object.QueryOptions;
import sailpoint.object.Filter;
import sailpoint.object.Identity;
import sailpoint.object.Link;
import sailpoint.object.Attributes;
 List linksList = new ArrayList();
 ArrayList accountInfo = new ArrayList();
 String privileged = null;
 String service = null;
 
 QueryOptions qo = new QueryOptions();
 Filter linkFilter = Filter.eq("links.application.name","Financials");
 Filter depFilter = Filter.eq("department","Accounting");
 qo.addFilter(Filter.and(linkFilter, depFilter));
 List identityList = context.getObjects(Identity.class, qo); 
 
 if(identityList != null){
  for(Identity identity : identityList){
 
  List links = identity.getLinks();
  if(links != null){
  for(Link link : links){
  String applicationName = link.getApplicationName();
 
  if(applicationName!= null && (applicationName.equalsIgnoreCase("Financials"))){
  Attributes attributes = link.getAttributes();
  if (attributes != null){
  if(attributes.getString("app2_privileged") != null && 
  (attributes.getString("app2_privileged").equalsIgnoreCase("false")) &&
  (attributes.getString("app2_service") != null) && 
  (attributes.getString("app2_service").equalsIgnoreCase("false")) ){
   
  privileged = attributes.getString("app2_privileged");
  service = attributes.getString("app2_service");
 
  accountInfo.add(identity.getName() + " :: " + identity.getFirstname() + " :: " + 
  " :: " + applicationName + " :: " + privileged + " :: "+ service);
  }
  }
  }
 
  }
  }
 
  log.debug( accountInfo);
 }

Comment below if you find this post helpful.

Thursday, April 22, 2021

Rule - List out distinct department name for all Identities

  import sailpoint.object.Identity;
 
HashSet depName = new HashSet();
 List identityList = context.getObjects(Identity.class);
 
 for(Identity identity : identityList){
  if(identity != null)
  depName.add(identity.getAttribute("department"));
 }
 log.error("Departments: " + depName);

Comment below if you find this post helpful.

Rule - Adding Identity to WorkGroup

 import sailpoint.object.QueryOptions;
import sailpoint.object.Filter;
import sailpoint.object.Identity;
  //get the workgroup
  Identity workGroupName = context.getObjectByName(Identity.class,"DemoWorkGroup");
  // get the identity
  Identity identityName = context.getObjectByName(Identity.class,"Aaron.Nichols");
  if(workGroupName!=null && identityName!=null ){
  identityName.add(workGroupName);
  context.saveObject(identityName);
  context.commitTransaction();
  }

Comment below if you find this post helpful.

Rule - Get the Identities who have "AcctsPayable" entitlement assigned

 import sailpoint.object.QueryOptions;
import sailpoint.object.Filter;
import sailpoint.object.IdentityEntitlement;
 
// Query the IdentityEntitlement object
QueryOptions qo = new QueryOptions();
qo.add(Filter.eq("value", "AcctsPayable"));
 
List entitlements = context.getObjects(IdentityEntitlement.class, qo);
log.error("List of Identities: ");
for (IdentityEntitlement ent : entitlements){
log.error(ent.getIdentity().getName());
}
log.error("No of identites having the Entitlements: " +entitlements.size());

Comment below if you find this post helpful.

Rule - Get Identities whose Department attribute is null

        import sailpoint.object.QueryOptions;
import sailpoint.object.Filter;
import sailpoint.object.Identity;
import sailpoint.api.ObjectUtil;

//Filter  for identity attribute - department
QueryOptions qo = new QueryOptions();
qo.addFilter(Filter.isnull("department"));

List identity = context.getObjects(Identity.class, qo);
List identityNames = ObjectUtil.getObjectNames(identity);

log.error("List of Identities having department is null : " +identityNames);
log.error("No of identites having department is null: " +identity.size());




Comment below if you find this post helpful.

Monday, April 19, 2021

Rule - Get the Uncorrelated Identities List

  import java.util.Iterator;
  import sailpoint.object.QueryOptions;
  import sailpoint.object.Identity;
  import sailpoint.object.Filter;

  try {
Logger log = Logger.getLogger("sailpoint.rules.GetUncorrelatedIdentityList");
log.setLevel(Level.DEBUG);
QueryOptions qo = new QueryOptions();
        qo.addFilter(Filter.eq("correlated",(Boolean)false));
        int i=0;
        Iterator result = context.search(Identity.class, qo);
        while (result.hasNext()) {
i++;
Identity user = (Identity)result.next();
log.debug("\nIdentity: " + user.getName());
}
log.debug("\n No of uncorrelated Identities: " + i);
} catch (Exception e) {
//Catch exception if any
log.error("Error: " + e.getMessage());
}


Comment below if you find this post helpful.

Rule - Save Identities to a text File

 Use the below script to write all the Identity Names in SailPoint to a text file.


  import java.util.ArrayList;
  import java.util.List;
  import sailpoint.api.SailPointContext;
  import sailpoint.object.Filter;
  import sailpoint.object.Identity;
  import sailpoint.object.QueryOptions;
  import sailpoint.tools.GeneralException;
  import org.apache.log4j.Logger;
  import org.apache.log4j.Level;
  import sailpoint.api.ObjectUtil;
  import sailpoint.object.EmailOptions;
  import sailpoint.object.EmailTemplate;
  import java.sql.Connection;
  import sailpoint.object.QueryOptions;
  import sailpoint.api.ObjectUtil;
  import sailpoint.object.TaskDefinition;
  import java.io.File;
  import java.io.IOException;
  import java.io.PrintWriter;
  import java.io.FileWriter;
   
List readIdentities(){
Logger log = Logger.getLogger("sailpoint.services.bshdemo.iterateItems");
  log.setLevel(Level.DEBUG);
  // Get list of all the Identities
List identityNames = context.getObjects(Identity.class);
  log.debug("Reading Identities");
  return identityNames;
}

void saveToFile(){
List identityNames = readIdentities();
try {
FileWriter fw = new FileWriter("C:\\identityiq\\identitydata.txt",  true);
PrintWriter out = new  PrintWriter(fw);
for(Identity identity: identityNames){
out.println(identity.getName());
}
out.close();
} catch (Exception e) {
log.error("An error occurred.");
e.printStackTrace();
}
log.debug("File created successfully");
}

readIdentities();
saveToFile();


Comment below if you find this post helpful.

Form AllowedValues rule to filter Identities with Active Regular Active Directory accounts and identity is active and correlated

 The rule type is AllowedValues. import org.apache.log4j.Level ; import org.apache.log4j.Logger ; import sailpoint.object.Filter ; import sa...