Web Service Connector

:bangbang: Please be sure you’ve read the docs and API specs before asking for help. Also, please be sure you’ve searched the forum for your answer before you create a new topi

Hi All,

I am trying to onboard one of the Application name via Web Service Connector into SailPoint Identity Security Cloud.

Test Connection is working fine

Account Aggregation is working fine

Group Aggregation is working fine

My Question:

Create Operation :

Account is getting provisioned in Target Application but I want to see the Provisioning plan and response of that on VA.

Which Rule should I use to check that ?
Will that be checked by “Web Service Before Operation Rule”?

Code:
import sailpoint.object.*;

import sailpoint.connector.webservices.EndPoint;

import org.apache.commons.logging.Log;

import org.apache.commons.logging.LogFactory;

Log log = LogFactory.getLog(“sailpoint.connector.webservices.Rule”);

log.info("Request URL: " + requestEndPoint.getFullUrl());

log.info("Request Method: " + requestEndPoint.getMethodType());

log.info("Request Headers: " + requestEndPoint.getHeader());

log.info("Request Body: " + requestEndPoint.getBody());

return requestEndPoint;

I am quite new with the Rules. So please suggest and how to check that in VA also

You can check in before provisining rule in Rule Section

Can we use Connector executed Rules i.e., Web Service Before Operation Rule to check the Provisioning plan on VA?

Yes, I’ve done that multiple times. You can create a before operation rule and ‘print’ the provisioning plan, or even the proposed body as per your webservices settings.

Please check the documentation on some more details:

Typically, you would care more about the rendered body then the provisioning plan, but perhaps that is different for your use-case?

Example code below, please adjust as per your required use case:

import sailpoint.object.ProvisioningPlan.AccountRequest;
import sailpoint.object.ProvisioningPlan.AttributeRequest;
import sailpoint.object.ProvisioningPlan.Operation;
import connector.common.Util;


if (null != provisioningPlan.getAccountRequests()) {
     for (i = 0; i < provisioningPlan.getAccountRequests().size(); i++) {
         log.error(application.getName() + ": accountRequest: " + provisioningPlan.getAccountRequests().get(i));
         log.error(application.getName() + ": operation: " + provisioningPlan.getAccountRequests().get(i).getOperation());
         for (y = 0; y < provisioningPlan.getAccountRequests().get(i).size(); y++) {
              log.error(application.getName() + ": accountRequest: " + rovisioningPlan.getAccountRequests().get(i).getAttributeRequests().get(y));
              log.error(application.getName() + ": accountRequest: " + provisioningPlan.getAccountRequests().get(i).getAttributeRequests().get(y));
         }
     }
}

Map body = requestEndPoint.getBody();
String xmlBody = (String) body.get("jsonBody");
Map currentHeader = new HashMap();
currentHeader = (Map)requestEndPoint.getHeader();
String url = requestEndPoint.getFullUrl();
log.error(application.getName() + ": body: " + xmlBody);    
log.error(application.getName() + ": currentHeader: " + currentHeader);
log.error(application.getName() + ": url: " + url);
requestEndPoint.setHeader(currentHeader);

In this way (with the log.error statement) you don’t need to adjust the log settings and you can grep on the application name as per your ISC setup. Of course you don’t want log.error for a long time, so ensure this is not in production or used for long.

Otherwise, you can use log.debug if you want it only when you up the log levels.

There you can update endpoint or request object also Provisioning plan

Yes, you can update the provisioning plan, but at this point in time (at the before operation rule) it doesn’t do anything anymore, the plan is already translated etc. So if you want to update the provisioning, you have to directly update the body of the call you are about to make.

Yes with the addition that you can grep on your log statements. The code that I provided will always prepend the log statements with the name of your source.

Example:
If your source name is “Dummy Source”, you can grep on this with the following command:

tail -f ccg.log |grep “Dummy Source”

This will allow you to filter out only the log statements that really matter.

Thanks !

In VA I can see error with the size() method and there is no log which is generating.

can you post the exact error you’re getting?

Here it is:

{“exception”:{“stacktrace”:"sailpoint.tools.GeneralException: BeanShell script error: bsh.EvalError: Sourced file: inline evaluation of: import sailpoint.object.ProvisioningPlan.AccountRequest; import sailpoint.object . . . '' : Error in method invocation: Method size() not found in class'sailpoint.object.ProvisioningPlan$AccountRequest' : at Line: 11 : in file: inline evaluation of: import sailpoint.object.ProvisioningPlan.AccountRequest; import sailpoint.object . . . ‘’ : .size ( ) \n BSF info: Before Operation Rule at line: 0 column: columnNo\n\tat sailpoint.server.BSFRuleRunner.runRule(BSFRuleRunner.java:219)\n\tat

I have pasted the same code just removed the last line, because your code will fulfil my requirement:

import sailpoint.object.ProvisioningPlan.AccountRequest;

import sailpoint.object.ProvisioningPlan.AttributeRequest;

import sailpoint.object.ProvisioningPlan.Operation;

import connector.common.Util;

if (null != provisioningPlan.getAccountRequests()) {

 for (i = 0; i < provisioningPlan.getAccountRequests().size(); i++) {

     log.error(application.getName() + ": accountRequest: " + provisioningPlan.getAccountRequests().get(i));

     log.error(application.getName() + ": operation: " + provisioningPlan.getAccountRequests().get(i).getOperation());

     for (y = 0; y < provisioningPlan.getAccountRequests().get(i).size(); y++) {

          log.error(application.getName() + ": accountRequest: " + provisioningPlan.getAccountRequests().get(i).getAttributeRequests().get(y));

          log.error(application.getName() + ": accountRequest: " + provisioningPlan.getAccountRequests().get(i).getAttributeRequests().get(y));

     }

 }

}

Map body = requestEndPoint.getBody();

String xmlBody = (String) body.get(“jsonBody”);

Map currentHeader = new HashMap();

currentHeader = (Map)requestEndPoint.getHeader();

String url = requestEndPoint.getFullUrl();

log.error(application.getName() + ": body: " + xmlBody);

log.error(application.getName() + ": currentHeader: " + currentHeader);

log.error(application.getName() + ": url: " + url);

Since the error says line 11 it looks like here is the issue:

for (y = 0; y < provisioningPlan.getAccountRequests().get(i).size(); y++) {

Can you perhaps try troubleshooting this issue by escaping this block as follows:

 if (null != provisioningPlan.getAccountRequests()) {
     for (i = 0; i < provisioningPlan.getAccountRequests().size(); i++) {
         log.error(application.getName() + ": accountRequest: " + provisioningPlan.getAccountRequests().get(i));
         log.error(application.getName() + ": operation: " + provisioningPlan.getAccountRequests().get(i).getOperation());
//          for (y = 0; y < provisioningPlan.getAccountRequests().get(i).size(); y++) {
//              log.error(application.getName() + ": accountRequest: " + provisioningPlan.getAccountRequests().get(i).getAttributeRequests().get(y));
//              log.error(application.getName() + ": accountRequest: " + provisioningPlan.getAccountRequests().get(i).getAttributeRequests().get(y));
//          }
     }
 }

You can also be nasty (but I’m not sure if that works anymore) to do a .toXml() on the provisioning plan
provisioningPlan.toXml()

This topic was automatically closed 60 days after the last reply. New replies are no longer allowed.