Search in sources :

Example 16 with ConnectorInstance

use of com.evolveum.midpoint.provisioning.ucf.api.ConnectorInstance in project midpoint by Evolveum.

the class EntitlementConverter method collectEntitlementsAsObjectOperationDelete.

/////////
// DELETE
/////////
/**
	 * This is somehow different that all the other methods. We are not following the content of a shadow or delta. We are following
	 * the definitions. This is to avoid the need to read the object that is going to be deleted. In fact, the object should not be there
	 * any more, but we still want to clean up entitlement membership based on the information from the shadow.  
	 */
public <T> void collectEntitlementsAsObjectOperationDelete(ProvisioningContext subjectCtx, final Map<ResourceObjectDiscriminator, ResourceObjectOperations> roMap, PrismObject<ShadowType> subjectShadow, OperationResult parentResult) throws SchemaException, CommunicationException, ObjectNotFoundException, ConfigurationException, SecurityViolationException, ExpressionEvaluationException {
    Collection<RefinedAssociationDefinition> entitlementAssociationDefs = subjectCtx.getObjectClassDefinition().getAssociationDefinitions();
    if (entitlementAssociationDefs == null || entitlementAssociationDefs.isEmpty()) {
        // Nothing to do
        LOGGER.trace("No associations in deleted shadow");
        return;
    }
    ResourceAttributeContainer subjectAttributesContainer = ShadowUtil.getAttributesContainer(subjectShadow);
    for (final RefinedAssociationDefinition assocDefType : subjectCtx.getObjectClassDefinition().getAssociationDefinitions()) {
        if (assocDefType.getResourceObjectAssociationType().getDirection() != ResourceObjectAssociationDirectionType.OBJECT_TO_SUBJECT) {
            // We can ignore these. They will die together with the object. No need to explicitly delete them.
            LOGGER.trace("Ignoring subject-to-object association in deleted shadow");
            continue;
        }
        if (!assocDefType.requiresExplicitReferentialIntegrity()) {
            // Referential integrity not required for this one
            LOGGER.trace("Ignoring association in deleted shadow because it does not require explicit referential integrity assurance");
            continue;
        }
        if (assocDefType.getAuxiliaryObjectClass() != null && !subjectCtx.getObjectClassDefinition().hasAuxiliaryObjectClass(assocDefType.getAuxiliaryObjectClass())) {
            LOGGER.trace("Ignoring association in deleted shadow because subject does not have {} auxiliary object class", assocDefType.getAuxiliaryObjectClass());
            continue;
        }
        QName associationName = assocDefType.getName();
        if (associationName == null) {
            throw new SchemaException("No name in entitlement association " + assocDefType + " in " + subjectCtx.getResource());
        }
        ShadowKindType entitlementKind = assocDefType.getKind();
        if (entitlementKind == null) {
            entitlementKind = ShadowKindType.ENTITLEMENT;
        }
        for (String entitlementIntent : assocDefType.getIntents()) {
            final ProvisioningContext entitlementCtx = subjectCtx.spawn(entitlementKind, entitlementIntent);
            final RefinedObjectClassDefinition entitlementOcDef = entitlementCtx.getObjectClassDefinition();
            if (entitlementOcDef == null) {
                throw new SchemaException("No definition for entitlement intent(s) '" + assocDefType.getIntents() + "' defined in entitlement association " + associationName + " in " + subjectCtx.getResource());
            }
            final QName assocAttrName = assocDefType.getResourceObjectAssociationType().getAssociationAttribute();
            if (assocAttrName == null) {
                throw new SchemaException("No association attribute defined in entitlement association '" + associationName + "' in " + subjectCtx.getResource());
            }
            final RefinedAttributeDefinition assocAttrDef = entitlementOcDef.findAttributeDefinition(assocAttrName);
            if (assocAttrDef == null) {
                throw new SchemaException("Association attribute '" + assocAttrName + "'defined in entitlement association '" + associationName + "' was not found in schema for " + subjectCtx.getResource());
            }
            QName valueAttrName = assocDefType.getResourceObjectAssociationType().getValueAttribute();
            if (valueAttrName == null) {
                throw new SchemaException("No value attribute defined in entitlement association '" + associationName + "' in " + subjectCtx.getResource());
            }
            final ResourceAttribute<T> valueAttr = subjectAttributesContainer.findAttribute(valueAttrName);
            if (valueAttr == null || valueAttr.isEmpty()) {
                // Although we cannot really remedy the situation now, we at least throw an error so the problem is detected.
                throw new SchemaException("Value attribute " + valueAttrName + " has no value; attribute defined in entitlement association '" + associationName + "' in " + subjectCtx.getResource());
            }
            if (valueAttr.size() > 1) {
                throw new SchemaException("Value attribute " + valueAttrName + " has no more than one value; attribute defined in entitlement association '" + associationName + "' in " + subjectCtx.getResource());
            }
            ObjectQuery query = createQuery(assocDefType, assocAttrDef, valueAttr);
            AttributesToReturn attributesToReturn = ProvisioningUtil.createAttributesToReturn(entitlementCtx);
            SearchHierarchyConstraints searchHierarchyConstraints = null;
            ResourceObjectReferenceType baseContextRef = entitlementOcDef.getBaseContext();
            if (baseContextRef != null) {
                PrismObject<ShadowType> baseContextShadow = resourceObjectReferenceResolver.resolve(subjectCtx, baseContextRef, null, "base context specification in " + entitlementOcDef, parentResult);
                RefinedObjectClassDefinition baseContextObjectClassDefinition = subjectCtx.getRefinedSchema().determineCompositeObjectClassDefinition(baseContextShadow);
                ResourceObjectIdentification baseContextIdentification = ShadowUtil.getResourceObjectIdentification(baseContextShadow, baseContextObjectClassDefinition);
                searchHierarchyConstraints = new SearchHierarchyConstraints(baseContextIdentification, null);
            }
            ResultHandler<ShadowType> handler = new ResultHandler<ShadowType>() {

                @Override
                public boolean handle(PrismObject<ShadowType> entitlementShadow) {
                    Collection<? extends ResourceAttribute<?>> primaryIdentifiers = ShadowUtil.getPrimaryIdentifiers(entitlementShadow);
                    ResourceObjectDiscriminator disc = new ResourceObjectDiscriminator(entitlementOcDef.getTypeName(), primaryIdentifiers);
                    ResourceObjectOperations operations = roMap.get(disc);
                    if (operations == null) {
                        operations = new ResourceObjectOperations();
                        roMap.put(disc, operations);
                        operations.setResourceObjectContext(entitlementCtx);
                        Collection<? extends ResourceAttribute<?>> allIdentifiers = ShadowUtil.getAllIdentifiers(entitlementShadow);
                        operations.setAllIdentifiers(allIdentifiers);
                    }
                    PropertyDelta<T> attributeDelta = null;
                    for (Operation operation : operations.getOperations()) {
                        if (operation instanceof PropertyModificationOperation) {
                            PropertyModificationOperation propOp = (PropertyModificationOperation) operation;
                            if (propOp.getPropertyDelta().getElementName().equals(assocAttrName)) {
                                attributeDelta = propOp.getPropertyDelta();
                            }
                        }
                    }
                    if (attributeDelta == null) {
                        attributeDelta = assocAttrDef.createEmptyDelta(new ItemPath(ShadowType.F_ATTRIBUTES, assocAttrName));
                        PropertyModificationOperation attributeModification = new PropertyModificationOperation(attributeDelta);
                        attributeModification.setMatchingRuleQName(assocDefType.getMatchingRule());
                        operations.add(attributeModification);
                    }
                    attributeDelta.addValuesToDelete(valueAttr.getClonedValues());
                    if (LOGGER.isTraceEnabled()) {
                        LOGGER.trace("Association in deleted shadow delta:\n{}", attributeDelta.debugDump());
                    }
                    return true;
                }
            };
            try {
                LOGGER.trace("Searching for associations in deleted shadow, query: {}", query);
                ConnectorInstance connector = subjectCtx.getConnector(ReadCapabilityType.class, parentResult);
                connector.search(entitlementOcDef, query, handler, attributesToReturn, null, searchHierarchyConstraints, subjectCtx, parentResult);
            } catch (TunnelException e) {
                throw (SchemaException) e.getCause();
            } catch (GenericFrameworkException e) {
                throw new GenericConnectorException(e.getMessage(), e);
            }
        }
    }
}
Also used : AttributesToReturn(com.evolveum.midpoint.provisioning.ucf.api.AttributesToReturn) ResourceAttributeContainer(com.evolveum.midpoint.schema.processor.ResourceAttributeContainer) ResultHandler(com.evolveum.midpoint.provisioning.ucf.api.ResultHandler) Operation(com.evolveum.midpoint.provisioning.ucf.api.Operation) PropertyModificationOperation(com.evolveum.midpoint.provisioning.ucf.api.PropertyModificationOperation) PrismObject(com.evolveum.midpoint.prism.PrismObject) TunnelException(com.evolveum.midpoint.util.exception.TunnelException) SearchHierarchyConstraints(com.evolveum.midpoint.schema.processor.SearchHierarchyConstraints) ResourceObjectIdentification(com.evolveum.midpoint.schema.processor.ResourceObjectIdentification) GenericConnectorException(com.evolveum.midpoint.provisioning.api.GenericConnectorException) PropertyModificationOperation(com.evolveum.midpoint.provisioning.ucf.api.PropertyModificationOperation) ResourceObjectReferenceType(com.evolveum.midpoint.xml.ns._public.common.common_3.ResourceObjectReferenceType) SchemaException(com.evolveum.midpoint.util.exception.SchemaException) GenericFrameworkException(com.evolveum.midpoint.provisioning.ucf.api.GenericFrameworkException) QName(javax.xml.namespace.QName) ShadowType(com.evolveum.midpoint.xml.ns._public.common.common_3.ShadowType) ObjectQuery(com.evolveum.midpoint.prism.query.ObjectQuery) ConnectorInstance(com.evolveum.midpoint.provisioning.ucf.api.ConnectorInstance) ShadowKindType(com.evolveum.midpoint.xml.ns._public.common.common_3.ShadowKindType) ItemPath(com.evolveum.midpoint.prism.path.ItemPath)

Example 17 with ConnectorInstance

use of com.evolveum.midpoint.provisioning.ucf.api.ConnectorInstance in project midpoint by Evolveum.

the class ResourceManager method fetchResourceSchema.

private ResourceSchema fetchResourceSchema(PrismObject<ResourceType> resource, Map<String, Collection<Object>> capabilityMap, Task task, OperationResult parentResult) throws CommunicationException, GenericFrameworkException, ConfigurationException, ObjectNotFoundException, SchemaException {
    ConnectorSpec connectorSpec = selectConnectorSpec(resource, capabilityMap, SchemaCapabilityType.class);
    if (connectorSpec == null) {
        LOGGER.trace("No connector has schema capability, cannot fetch resource schema");
        return null;
    }
    InternalMonitor.recordResourceSchemaFetch();
    List<QName> generateObjectClasses = ResourceTypeUtil.getSchemaGenerationConstraints(resource);
    ConnectorInstance connectorInstance = connectorManager.getConfiguredConnectorInstance(connectorSpec, false, parentResult);
    LOGGER.trace("Trying to get schema from {}", connectorSpec);
    return connectorInstance.fetchResourceSchema(generateObjectClasses, parentResult);
}
Also used : ConnectorInstance(com.evolveum.midpoint.provisioning.ucf.api.ConnectorInstance) QName(javax.xml.namespace.QName)

Example 18 with ConnectorInstance

use of com.evolveum.midpoint.provisioning.ucf.api.ConnectorInstance in project midpoint by Evolveum.

the class ConnectorManager method createConfiguredConnectorInstance.

private ConnectorInstance createConfiguredConnectorInstance(ConnectorSpec connectorSpec, OperationResult result) throws ObjectNotFoundException, SchemaException, CommunicationException, ConfigurationException {
    ConnectorType connectorType = getConnectorTypeReadOnly(connectorSpec, result);
    ConnectorFactory connectorFactory = determineConnectorFactory(connectorType);
    ConnectorInstance connector = null;
    try {
        connector = connectorFactory.createConnectorInstance(connectorType, ResourceTypeUtil.getResourceNamespace(connectorSpec.getResource()), connectorSpec.toString());
    } catch (ObjectNotFoundException e) {
        result.recordFatalError(e.getMessage(), e);
        throw new ObjectNotFoundException(e.getMessage(), e);
    }
    PrismContainerValue<ConnectorConfigurationType> connectorConfigurationVal = connectorSpec.getConnectorConfiguration().getValue();
    if (connectorConfigurationVal == null) {
        SchemaException e = new SchemaException("No connector configuration in " + connectorSpec);
        result.recordFatalError(e);
        throw e;
    }
    try {
        connector.configure(connectorConfigurationVal, result);
        ResourceSchema resourceSchema = RefinedResourceSchemaImpl.getResourceSchema(connectorSpec.getResource(), prismContext);
        Collection<Object> capabilities = ResourceTypeUtil.getNativeCapabilitiesCollection(connectorSpec.getResource().asObjectable());
        connector.initialize(resourceSchema, capabilities, ResourceTypeUtil.isCaseIgnoreAttributeNames(connectorSpec.getResource().asObjectable()), result);
        InternalMonitor.recordConnectorInstanceInitialization();
    } catch (GenericFrameworkException e) {
        // Not expected. Transform to system exception
        result.recordFatalError("Generic provisioning framework error", e);
        throw new SystemException("Generic provisioning framework error: " + e.getMessage(), e);
    } catch (CommunicationException e) {
        result.recordFatalError(e);
        throw e;
    } catch (ConfigurationException e) {
        result.recordFatalError(e);
        throw e;
    }
    // This log message should be INFO level. It happens only occasionally.
    // If it happens often, it may be an
    // indication of a problem. Therefore it is good for admin to see it.
    LOGGER.info("Created new connector instance for {}: {} v{}", connectorSpec, connectorType.getConnectorType(), connectorType.getConnectorVersion());
    return connector;
}
Also used : SchemaException(com.evolveum.midpoint.util.exception.SchemaException) ConnectorType(com.evolveum.midpoint.xml.ns._public.common.common_3.ConnectorType) RefinedResourceSchema(com.evolveum.midpoint.common.refinery.RefinedResourceSchema) ResourceSchema(com.evolveum.midpoint.schema.processor.ResourceSchema) GenericFrameworkException(com.evolveum.midpoint.provisioning.ucf.api.GenericFrameworkException) CommunicationException(com.evolveum.midpoint.util.exception.CommunicationException) ConnectorConfigurationType(com.evolveum.midpoint.xml.ns._public.common.common_3.ConnectorConfigurationType) ConnectorInstance(com.evolveum.midpoint.provisioning.ucf.api.ConnectorInstance) ConnectorFactory(com.evolveum.midpoint.provisioning.ucf.api.ConnectorFactory) SystemException(com.evolveum.midpoint.util.exception.SystemException) ConfigurationException(com.evolveum.midpoint.util.exception.ConfigurationException) ObjectNotFoundException(com.evolveum.midpoint.util.exception.ObjectNotFoundException) PrismObject(com.evolveum.midpoint.prism.PrismObject)

Example 19 with ConnectorInstance

use of com.evolveum.midpoint.provisioning.ucf.api.ConnectorInstance in project midpoint by Evolveum.

the class AbstractDummyTest method assertConnectorInstanceChanged.

protected void assertConnectorInstanceChanged(PrismObject<ResourceType> resource) throws ObjectNotFoundException, SchemaException, CommunicationException, ConfigurationException {
    OperationResult result = new OperationResult(TestDummyResourceAndSchemaCaching.class.getName() + ".rememberConnectorInstance");
    ConnectorInstance currentConfiguredConnectorInstance = resourceManager.getConfiguredConnectorInstance(resource, ReadCapabilityType.class, false, result);
    assertTrue("Connector instance has NOT changed", lastConfiguredConnectorInstance != currentConfiguredConnectorInstance);
    lastConfiguredConnectorInstance = currentConfiguredConnectorInstance;
}
Also used : ConnectorInstance(com.evolveum.midpoint.provisioning.ucf.api.ConnectorInstance) OperationResult(com.evolveum.midpoint.schema.result.OperationResult)

Example 20 with ConnectorInstance

use of com.evolveum.midpoint.provisioning.ucf.api.ConnectorInstance in project midpoint by Evolveum.

the class AbstractBasicDummyTest method test032ResourceAndConnectorCaching.

@Test
public void test032ResourceAndConnectorCaching() throws Exception {
    // GIVEN
    Task task = getTestTask();
    OperationResult result = createOperationResult();
    ConnectorInstance configuredConnectorInstance = resourceManager.getConfiguredConnectorInstance(resource, ReadCapabilityType.class, false, result);
    assertNotNull("No configuredConnectorInstance", configuredConnectorInstance);
    ResourceSchema resourceSchema = ResourceSchemaFactory.getRawSchema(resource);
    assertNotNull("No resource schema", resourceSchema);
    // WHEN
    when();
    PrismObject<ResourceType> resourceAgain = provisioningService.getObject(ResourceType.class, RESOURCE_DUMMY_OID, null, task, result);
    // THEN
    then();
    assertSuccess(result);
    ResourceType resourceTypeAgain = resourceAgain.asObjectable();
    assertNotNull("No connector ref", resourceTypeAgain.getConnectorRef());
    assertNotNull("No connector ref OID", resourceTypeAgain.getConnectorRef().getOid());
    PrismContainer<Containerable> configurationContainer = resource.findContainer(ResourceType.F_CONNECTOR_CONFIGURATION);
    PrismContainer<Containerable> configurationContainerAgain = resourceAgain.findContainer(ResourceType.F_CONNECTOR_CONFIGURATION);
    assertTrue("Configurations not equivalent", configurationContainer.equivalent(configurationContainerAgain));
    // Check resource schema caching
    ResourceSchema resourceSchemaAgain = ResourceSchemaFactory.getRawSchema(resourceAgain);
    assertNotNull("No resource schema (again)", resourceSchemaAgain);
    assertTrue("Resource schema was not cached", resourceSchema == resourceSchemaAgain);
    // Check capabilities caching
    CapabilitiesType capabilitiesType = resourceBean.getCapabilities();
    assertNotNull("No capabilities fetched from provisioning", capabilitiesType);
    CachingMetadataType capCachingMetadataType = capabilitiesType.getCachingMetadata();
    assertNotNull("No capabilities caching metadata fetched from provisioning", capCachingMetadataType);
    CachingMetadataType capCachingMetadataTypeAgain = resourceTypeAgain.getCapabilities().getCachingMetadata();
    assertEquals("Capabilities caching metadata serial number has changed", capCachingMetadataType.getSerialNumber(), capCachingMetadataTypeAgain.getSerialNumber());
    assertEquals("Capabilities caching metadata timestamp has changed", capCachingMetadataType.getRetrievalTimestamp(), capCachingMetadataTypeAgain.getRetrievalTimestamp());
    // Rough test if everything is fine
    resource.asObjectable().setFetchResult(null);
    resourceAgain.asObjectable().setFetchResult(null);
    ObjectDelta<ResourceType> dummyResourceDiff = DiffUtil.diff(resource, resourceAgain);
    displayDumpable("Dummy resource diff", dummyResourceDiff);
    assertTrue("The resource read again is not the same as the original. diff:" + dummyResourceDiff, dummyResourceDiff.isEmpty());
    // Now we stick our nose deep inside the provisioning impl. But we need
    // to make sure that the
    // configured connector is properly cached
    ConnectorInstance configuredConnectorInstanceAgain = resourceManager.getConfiguredConnectorInstance(resourceAgain, ReadCapabilityType.class, false, result);
    assertNotNull("No configuredConnectorInstance (again)", configuredConnectorInstanceAgain);
    assertTrue("Connector instance was not cached", configuredConnectorInstance == configuredConnectorInstanceAgain);
    // Check if the connector still works.
    OperationResult testResult = createOperationResult("test");
    configuredConnectorInstanceAgain.test(testResult);
    testResult.computeStatus();
    TestUtil.assertSuccess("Connector test failed", testResult);
    // Test connection should also refresh the connector by itself. So check if it has been refreshed
    ConnectorInstance configuredConnectorInstanceAfterTest = resourceManager.getConfiguredConnectorInstance(resourceAgain, ReadCapabilityType.class, false, result);
    assertNotNull("No configuredConnectorInstance (again)", configuredConnectorInstanceAfterTest);
    assertTrue("Connector instance was not cached", configuredConnectorInstanceAgain == configuredConnectorInstanceAfterTest);
    assertSteadyResource();
}
Also used : Task(com.evolveum.midpoint.task.api.Task) ConnectorInstance(com.evolveum.midpoint.provisioning.ucf.api.ConnectorInstance) OperationResult(com.evolveum.midpoint.schema.result.OperationResult) Test(org.testng.annotations.Test)

Aggregations

ConnectorInstance (com.evolveum.midpoint.provisioning.ucf.api.ConnectorInstance)29 GenericFrameworkException (com.evolveum.midpoint.provisioning.ucf.api.GenericFrameworkException)10 OperationResult (com.evolveum.midpoint.schema.result.OperationResult)10 GenericConnectorException (com.evolveum.midpoint.provisioning.api.GenericConnectorException)5 SchemaException (com.evolveum.midpoint.util.exception.SchemaException)5 Test (org.testng.annotations.Test)5 AbstractManagedConnectorInstance (com.evolveum.midpoint.provisioning.ucf.api.connectors.AbstractManagedConnectorInstance)4 AbstractManualConnectorInstance (com.evolveum.midpoint.provisioning.ucf.api.connectors.AbstractManualConnectorInstance)4 ResourceObjectIdentification (com.evolveum.midpoint.schema.processor.ResourceObjectIdentification)4 Task (com.evolveum.midpoint.task.api.Task)4 ObjectNotFoundException (com.evolveum.midpoint.util.exception.ObjectNotFoundException)4 ResourceType (com.evolveum.midpoint.xml.ns._public.common.common_3.ResourceType)4 RefinedResourceSchema (com.evolveum.midpoint.common.refinery.RefinedResourceSchema)3 Containerable (com.evolveum.midpoint.prism.Containerable)3 PrismObject (com.evolveum.midpoint.prism.PrismObject)3 ResourceSchema (com.evolveum.midpoint.schema.processor.ResourceSchema)3 CommunicationException (com.evolveum.midpoint.util.exception.CommunicationException)3 ConfigurationException (com.evolveum.midpoint.util.exception.ConfigurationException)3 QName (javax.xml.namespace.QName)3 RefinedObjectClassDefinition (com.evolveum.midpoint.common.refinery.RefinedObjectClassDefinition)2