Hi,
I extend DefaultAnyObjectProvisioningManager to introduce some business logic.
When receiving an event for an AnyObject, I search for related User
object based on Attribute search and eventually create User object.
What I found:
1 - with create event, the anyObjectCR is not completed, plain
attributes missed. Even if I launch a search on it after
awfAdapter.create().
2 - in the same create event, when associate a membership to a new
User object is never persisted. Even if I update the newly created
User.
Question1: when can I access the completed AnyObject, clearly not
after awfAdapter.create() ?
Question 2: Why method membership of UserCR or UserUR didn't work ?
Best regards,
Stéphane POPOFF
The create method:
@Transactional(propagation = Propagation.REQUIRES_NEW)
@Override
public ProvisioningResult<String> create(
final AnyObjectCR anyObjectCR,
final Set<String> excludedResources,
final boolean nullPriorityAsync,
final String creator,
final String context){
if(!anyObjectCR.getType().equals("PERSON")){
LOG.info("pas un objet PERSON <> "+anyObjectCR.getType());
return super.create(anyObjectCR, excludedResources,
nullPriorityAsync, creator, context);
}
LOG.info("1 Création d'une personne name="+anyObjectCR.getName());
WorkflowResult<String> created =
awfAdapter.create(anyObjectCR, creator, context);
LOG.info("retour du workflow "+created.getResult());
//on cherche l'objet complet
List<? extends AnyObject> persons = null;
try{
persons = anyObjectDAO.findByDerAttrValue("personId==",
anyObjectCR.getName(), false);
}catch(Exception ex){
LOG.error("1a Erreur retrouve Person ", ex);
}
JPAAnyObject person;
PlainAttr nomAttr;
PlainAttr prenomAttr;
Optional<PlainAttr> nomOpt;
Optional<PlainAttr> prenomOpt;
PlainAttr nomDefo = new PlainAttr();
PlainAttr prenomDefo = new PlainAttr();
PlainAttrValue defo = new PlainAttrValue();
defo.setStringValue("pavu");
nomDefo.setSchema("nomNaissance");
nomDefo.setUniqueValue(defo);
prenomDefo.setSchema("prenomNaissance");
prenomDefo.setUniqueValue(defo);
nomAttr = nomDefo;
prenomAttr = prenomDefo;
if(persons != null && !persons.isEmpty()){
person = (JPAAnyObject)persons.get(0);
nomOpt = person.getPlainAttrs().stream()
.filter( attr ->
attr.getSchema().equals("nomNaissance")).findFirst();
LOG.info("1b nom present={} vide={}", nomOpt.isPresent(),
nomOpt.isEmpty());
nomAttr = nomOpt.orElse(nomDefo);
prenomOpt = person.getPlainAttrs().stream()
.filter( attr ->
attr.getSchema().equals("prenomNaissance")).findFirst();
LOG.info("1b prenom present={} vide={}",
prenomOpt.isPresent(), prenomOpt.isEmpty());
prenomAttr = prenomOpt.orElse(prenomDefo);
}else if(persons == null){
LOG.warn("1b Rien retrouvé Person id={}",anyObjectCR.getName());
}else{
LOG.warn("1b Pas retrouvé Person id={}",anyObjectCR.getName());
}
//je sais ce qu'il raconte en cas de réussite ou échec ?
//on cherche un USER avec un personId == anyObjectCR.getName();
List<User> users = null;
boolean erreur = false;
try{
users = userDAO.findByDerAttrValue("personId==",
anyObjectCR.getName(), false);
}catch(Exception ex){
LOG.error("Erreur recherche USER "+ex);
erreur = true;
}
List<PropagationTaskInfo> taskInfos = new ArrayList<>();
if(!erreur && users != null && !users.isEmpty()){
//on trouve un des comptes
LOG.info("2 Déjà des comptes, mais conforme aux besoins métiers ?");
}else if(!erreur){
LOG.info("2 Pas comptes, mais répondre aux besoins métiers ?");
String calendars = "training,freeTime";
MembershipTO membership = new MembershipTO.Builder("")
.groupName("appAdmin2")
.plainAttr(new
Attr.Builder("appName").value("tempo").build())
.plainAttr(new
Attr.Builder("projects").value(calendars).build())
.build();
UserCR novo = new UserCR.Builder("/", "usr-"+anyObjectCR.getName())
.plainAttr(new Attr.Builder("personId").value(
anyObjectCR.getName()).build())
.plainAttr(new Attr.Builder("nom").value(
nomAttr.getUniqueValue().getStringValue()).build())
.plainAttr(new Attr.Builder("prenom").value(
prenomAttr.getUniqueValue().getStringValue()).build())
.membership(membership)
.build();
ProvisioningResult<String> res = userProvisioningManager.create(
novo, false, creator, context);
//on récupère le compte créé
LOG.info("2a Résultat provisioning compte {}", res.toString());
List<User> lui = null;
try{
LOG.info("2b cherche compte avec personId={}",
anyObjectCR.getName());
lui = userDAO.findByDerAttrValue("personId==",
anyObjectCR.getName(), false);
}catch(Exception ex){
LOG.error("2c Erreur recherche du compte avec
personId='{}' '{}'",
anyObjectCR.getName(), ex.getLocalizedMessage());
}
if(lui == null || lui.isEmpty()){
LOG.error("2d Pas retrouvé le compte sur
personId={}",anyObjectCR.getName());
PropagationStatus status = new PropagationStatus();
status.setResource("admin");
status.setStatus(ExecStatus.NOT_ATTEMPTED);
return new ProvisioningResult<>("Erreur récupération compte",
Arrays.asList(new PropagationStatus[]{status}));
}
MembershipUR membershipu = new MembershipUR.Builder("appAdmin2")
.plainAttr(new
Attr.Builder("appName").value("tempo").build())
.plainAttr(new
Attr.Builder("projects").value(calendars).build())
.build();
UserUR change = new UserUR.Builder(lui.get(0).getKey())
.membership(membershipu)
.build();
//une deuxième change
ProvisioningResult<UserUR> resu = userProvisioningManager.update(
change, false, creator, context);
LOG.info("3 Résultat update compte {}", resu.toString());
PropagationByResource<String> propResc = new
PropagationByResource<>();
propResc.add(ResourceOperation.CREATE, "admin2");
try{
taskInfos = propagationManager.getCreateTasks(
AnyTypeKind.USER,
lui.get(0).getKey(),
true,
propResc,
excludedResources);
}catch(Exception ex){
LOG.error("4 Erreur propagation compte user", ex);
PropagationStatus status = new PropagationStatus();
status.setResource("admin");
status.setStatus(ExecStatus.FAILURE);
return new ProvisioningResult<>("Erreur propagation compte",
Arrays.asList(new PropagationStatus[]{status}));
}
if(!taskInfos.isEmpty()){
LOG.info("4 Taches de propagation nb="+taskInfos.size());
for(PropagationTaskInfo taskInfo : taskInfos){
LOG.info("5 Tache de propagation key="+taskInfo.getKey());
}
}
}
PropagationReporter propagationReporter =
taskExecutor.execute(taskInfos, nullPriorityAsync, creator);
return new ProvisioningResult<>(created.getResult(),
propagationReporter.getStatuses());
}