I tried to implement this solution from ‘JDBC Provisioning rule to read the nativeIdentity that gets generated in the Database - #2 by AnamicaShroti’ to remove the ‘???’ signs after creating an account in a JDBC rule. The problem is that IDN gives me an error when trying to execute the code because the constructor doesn’t accept the parameters I’m sending to it. I’m not sure if the solution in that discussion still works or if I’m doing something wrong in the code. According to the documentation in SailPoint, the constructor is empty and shouldn’t accept parameters.
@lherrera can you share us your exact jdbc provisioning rule here, so that we can help?
It would definitely be easy to help you with the issue @lherrera if you can share the JDBC provisioning rule (Please do replace items which are sensitive within the code).
Additionally as a pre-check can you confirm on the following items:
i. Are you leveraging stored procedures?
ii. If yes does your stored procedure generates the nativeIdentity and is it returning the said nativeIdentity so that you can map it with the user?
iii. Correlation configuration; is it been taken care of when you have configured the source?
Thanks,
Aman
I modified and removed some unnecessary things, maybe some "if"s are not aligned, but the code for account creation would be this:
import sailpoint.object.ResourceObject;
import java.sql.Connection;
import java.sql.DriverManager;
import java.sql.PreparedStatement;
import java.sql.SQLException;
import java.sql.Types;
import java.util.List;
import sailpoint.api.SailPointContext;
import sailpoint.connector.JDBCConnector;
import java.util.HashMap;
import java.util.Map;
import java.sql.ResultSet;
import sailpoint.object.Application;
import sailpoint.object.Identity;
import sailpoint.object.ProvisioningPlan;
import sailpoint.object.ProvisioningPlan.AccountRequest;
import sailpoint.object.ProvisioningPlan.AttributeRequest;
import sailpoint.object.ProvisioningPlan.PermissionRequest;
import sailpoint.object.ProvisioningResult;
import sailpoint.object.Schema;
import java.sql.CallableStatement;
import java.math.BigDecimal;
import org.apache.logging.log4j.Logger;
import org.apache.logging.log4j.Level;
import org.apache.logging.log4j.core.config.Configurator;
public Object getAttributeRequestValue(AccountRequest acctReq, String attribute) {
if ( acctReq != null ) {
AttributeRequest attrReq = acctReq.getAttributeRequest(attribute);
if ( attrReq != null ) {
return attrReq.getValue();
}
}
return null;
}
ProvisioningResult result = new ProvisioningResult();
CallableStatement callableStatement = null;
PreparedStatement statement = null;
String posibleError = "";
//INICIO REGLA
if (plan != null) {
log.error("Inicio de la regla");
List accounts = plan.getAccountRequests();
if ((accounts != null) && (accounts.size() > 0)) {
for (AccountRequest account : accounts) {
try {
//Comprueba si el account request es un CREATE
if (AccountRequest.Operation.Create.equals(account.getOperation())) {
log.error("Entrando al create");
//Verificar con el if si ya existe esa cuenta
String USU_RUTUSUARIO = (String) account.getNativeIdentity();
//Llamo a la funcion verificarNumeroCuentas para ver si existen mas cuentas
int cantidadDeCuentas = verificarNumeroCuentas(USU_RUTUSUARIO);
//En caso que no cuente con mas cuentas se procede a la creacion
if(cantidadDeCuentas == 0){
//** */
//Traigo todo lo necesario para la creacion del usuario
String USU_USERNAME = getAttributeRequestValue(account,"USU_USERNAME");
String USU_NOMBRE = getAttributeRequestValue(account,"USU_NOMBRE");
String tipoDeEmpleado = getAttributeRequestValue(account,"tipoDeEmpleado");
//Muestro
log.error("PRUEBA INTERNOS: tipoDeEmpleado: "+tipoDeEmpleado+" " + USU_RUTUSUARIO + " " + USU_USERNAME + " " + USU_NOMBRE);
//Seteo en nulo el apellido materno y paterno, hay que considerar de que fuente autoritativa viene
String USU_APEPATERNO = null;
String USU_APEMATERNO = null;
//Segun la fuente autoritativa es el atributo de los apellidos
if("Interno".equals(tipoDeEmpleado)){
USU_APEPATERNO = getAttributeRequestValue(account,"APELLIDO_PATERNO_SSFF");
USU_APEMATERNO = getAttributeRequestValue(account,"APELLIDO_MATERNO_SSFF");
}else{
USU_APEPATERNO = getAttributeRequestValue(account,"APELLIDO_PATERNO_SAIP");
USU_APEMATERNO = getAttributeRequestValue(account,"APELLIDO_MATERNO_SAIP");
}
//Muestro
log.error("PRUEBA INTERNOS: USU_APEPATERNO: "+USU_APEPATERNO+" USU_APEMATERNO: "+USU_APEMATERNO);
//Traigo mas atributos, existenteAD y LCS son estaticos
String USU_EMAIL = getAttributeRequestValue(account,"USU_EMAIL");
String existenteAD = getAttributeRequestValue(account,"existenteAD");
String cloudLifecycleState = getAttributeRequestValue(account,"cloudLifecycleState");
//Muestro
log.error("Creating account: {}"+ account.getNativeIdentity());
//Validacion de los atributos que traemos
if (USU_RUTUSUARIO != null && USU_USERNAME != null && USU_NOMBRE != null && USU_APEPATERNO != null && USU_APEMATERNO != null && USU_EMAIL != null && cantidadDeCuentas == 0 ) {
//Validacion de la cuenta de AD y LCS
if ("true".equals(existenteAD) && ("desuso".equals(cloudLifecycleState) || "active".equals(cloudLifecycleState))){
boolean success = false;
try{
// Llamada al procedimiento almacenado con parámetros
CallableStatement callableStatement = connection.prepareCall("{call Stored Procedure (?, ?, ?, ?, ?, ?, ?, ?, ?)}");
// Configuración de los parámetros del procedimiento almacenado
callableStatement.setString(1, USU_RUTUSUARIO);
callableStatement.setString(2, USU_USERNAME);
callableStatement.setString(3, USU_NOMBRE);
callableStatement.setString(4, USU_APEPATERNO);
callableStatement.setString(5, USU_APEMATERNO);
callableStatement.setString(6, "ADMIN"); // @CodigoCargo - Ajusta según tus necesidades //Preguntar
callableStatement.setString(7, USU_EMAIL);
callableStatement.registerOutParameter(8, Types.NUMERIC); // NUMERROR$
callableStatement.registerOutParameter(9, Types.VARCHAR); // MSJERROR$
callableStatement.execute();
// Obtener los resultados de los parámetros de salida
int numError = callableStatement.getInt(8);
String msjError = callableStatement.getString(9);
// Manejar los resultados según sea necesario
if (numError != 0) {
log.error("Error al crear la cuenta: Codigo Resultado: " + numError.intValue() + ", Descripcion Resultado: " + msjError);
result.setStatus(ProvisioningResult.STATUS_FAILED);
result.addError("Error al crear la cuenta: " + msjError);
} else {
log.info("Cuenta creada correctamente");
result.setStatus(ProvisioningResult.STATUS_COMMITTED);
success = true;
}
} catch (SQLException e){
log.error("No se pudo crear la cuenta debido a una excepcion " + e.getMessage());
result.setStatus(ProvisioningResult.STATUS_FAILED);
result.addError("No se pudo crear la cuenta debido a una excepcion " + e.getMessage());
}
log.error("Success: "+success);
//Busca el numero de la tabla
if(success){
//aggregation of entitlements (I think it is not necessary to add it)
//Solution??
String USU_RUTUSUARIO = (String) account.getNativeIdentity();
String USU_USERNAME = getAttributeRequestValue(account,"USU_USERNAME");
// Holds all the account attributes;
Map attributesMap = new HashMap();
String newID = USU_RUTUSUARIO;
String usrNm = USU_USERNAME;
// Add account attributes
attributesMap.put("USU_RUTUSUARIO", newID);
attributesMap.put("USU_USERNAME", usrNm);
ResourceObject ro = new ResourceObject(
newID, // accountID just created
usrNm, // accountDisplayName
Connector.TYPE_ACCOUNT, //Object Type
attributesMap );
result.setObject( ro );
//HACER COMMIT
connection.commit();
result.setStatus(ProvisioningResult.STATUS_COMMITTED);
log.error("Cuenta modificada correctamente");
}catch(SQLException e){
// En caso de error, realizar rollback de la transacción
connection.rollback();
log.error("Error al modificar la cuenta: " + e.getMessage());
result.setStatus(ProvisioningResult.STATUS_FAILED);
result.addError("Error al modificar la cuenta: " + e.getMessage());
} finally{
// Restaurar el modo de autocommit
connection.setAutoCommit(true);
}
}else{
log.error("numUsuarioValue vacio");
result.setStatus(ProvisioningResult.STATUS_FAILED);
result.addError("Error en la creación de cuenta: numUsuarioValue vacio");
}
}else{
log.error("No se pudo obtener el valor de USU_NUMUSUARIO");
result.setStatus(ProvisioningResult.STATUS_FAILED);
result.addError("Error en la creación de cuenta: error interno de la BBDD");
}
//Comprobaciones del AD
}else if ("false".equals(existenteAD)) {
log.error("NO EXISTENTE EN AD");
result.setStatus(ProvisioningResult.STATUS_FAILED);
result.addError("La cuenta no existe en AD");
}else {
log.error("No se pudo determinar si existe en AD");
result.setStatus(ProvisioningResult.STATUS_FAILED);
result.addError("No se pudo determinar si existe en AD");
}
} else {
log.error("Uno o más campos son nulos");
result.setStatus(ProvisioningResult.STATUS_FAILED);
result.addError("Uno o más campos son nulos");
}
}else{
log.error("El usuario ya posee 1 o + cuentas en la base de datos, abortando el alta");
result.setStatus( ProvisioningResult.STATUS_FAILED );
result.addError( "El usuario ya posee 1 o + cuentas en la base de datos, abortando el alta");
}
//--------------------------------------------------------------------------------------------------------
}
} catch (SQLException e) {
result.setStatus(ProvisioningResult.STATUS_FAILED);
// if(posibleError != null || posibleError != "") {
// result.addError("CUERPO: "+posibleError);
// }else{
// result.addError(e);
// }
result.addError(e);
} finally {
if (statement != null) {
statement.close();
}
}
}
}
}
return result;
i. Are you leveraging stored procedures? Yes
ii. If yes does your stored procedure generates the nativeIdentity and is it returning the said nativeIdentity so that you can map it with the user? I would think so
iii. Correlation configuration; is it been taken care of when you have configured the source? The correlations look good
The problem, for example, is that after creating an account these fields appear with “???” until you add the account
This topic was automatically closed 60 days after the last reply. New replies are no longer allowed.