Search in sources :

Example 1 with StandardVersionControlInformation

use of org.apache.nifi.registry.flow.StandardVersionControlInformation in project nifi by apache.

the class StandardProcessGroupDAO method updateVersionControlInformation.

@Override
public ProcessGroup updateVersionControlInformation(final VersionControlInformationDTO versionControlInformation, final Map<String, String> versionedComponentMapping) {
    final String groupId = versionControlInformation.getGroupId();
    final ProcessGroup group = locateProcessGroup(flowController, groupId);
    final String registryId = versionControlInformation.getRegistryId();
    final FlowRegistry flowRegistry = flowController.getFlowRegistryClient().getFlowRegistry(registryId);
    final String registryName = flowRegistry == null ? registryId : flowRegistry.getName();
    final NiFiRegistryFlowMapper mapper = new NiFiRegistryFlowMapper();
    final VersionedProcessGroup flowSnapshot = mapper.mapProcessGroup(group, flowController, flowController.getFlowRegistryClient(), false);
    final StandardVersionControlInformation vci = StandardVersionControlInformation.Builder.fromDto(versionControlInformation).registryName(registryName).flowSnapshot(flowSnapshot).build();
    group.setVersionControlInformation(vci, versionedComponentMapping);
    group.onComponentModified();
    return group;
}
Also used : StandardVersionControlInformation(org.apache.nifi.registry.flow.StandardVersionControlInformation) FlowRegistry(org.apache.nifi.registry.flow.FlowRegistry) NiFiRegistryFlowMapper(org.apache.nifi.registry.flow.mapping.NiFiRegistryFlowMapper) ProcessGroup(org.apache.nifi.groups.ProcessGroup) VersionedProcessGroup(org.apache.nifi.registry.flow.VersionedProcessGroup) RemoteProcessGroup(org.apache.nifi.groups.RemoteProcessGroup) VersionedProcessGroup(org.apache.nifi.registry.flow.VersionedProcessGroup)

Example 2 with StandardVersionControlInformation

use of org.apache.nifi.registry.flow.StandardVersionControlInformation in project nifi by apache.

the class StandardProcessGroupDAO method updateProcessGroupFlow.

@Override
public ProcessGroup updateProcessGroupFlow(final String groupId, final NiFiUser user, final VersionedFlowSnapshot proposedSnapshot, final VersionControlInformationDTO versionControlInformation, final String componentIdSeed, final boolean verifyNotModified, final boolean updateSettings, final boolean updateDescendantVersionedFlows) {
    final ProcessGroup group = locateProcessGroup(flowController, groupId);
    group.updateFlow(proposedSnapshot, componentIdSeed, verifyNotModified, updateSettings, updateDescendantVersionedFlows);
    group.findAllRemoteProcessGroups().stream().forEach(RemoteProcessGroup::initialize);
    final StandardVersionControlInformation svci = StandardVersionControlInformation.Builder.fromDto(versionControlInformation).flowSnapshot(proposedSnapshot.getFlowContents()).build();
    group.setVersionControlInformation(svci, Collections.emptyMap());
    group.onComponentModified();
    return group;
}
Also used : RemoteProcessGroup(org.apache.nifi.groups.RemoteProcessGroup) StandardVersionControlInformation(org.apache.nifi.registry.flow.StandardVersionControlInformation) ProcessGroup(org.apache.nifi.groups.ProcessGroup) VersionedProcessGroup(org.apache.nifi.registry.flow.VersionedProcessGroup) RemoteProcessGroup(org.apache.nifi.groups.RemoteProcessGroup)

Example 3 with StandardVersionControlInformation

use of org.apache.nifi.registry.flow.StandardVersionControlInformation in project nifi by apache.

the class StandardProcessGroup method setVersionControlInformation.

@Override
public void setVersionControlInformation(final VersionControlInformation versionControlInformation, final Map<String, String> versionedComponentIds) {
    final StandardVersionControlInformation svci = new StandardVersionControlInformation(versionControlInformation.getRegistryIdentifier(), versionControlInformation.getRegistryName(), versionControlInformation.getBucketIdentifier(), versionControlInformation.getFlowIdentifier(), versionControlInformation.getVersion(), stripContentsFromRemoteDescendantGroups(versionControlInformation.getFlowSnapshot(), true), versionControlInformation.getStatus()) {

        @Override
        public String getRegistryName() {
            final String registryId = versionControlInformation.getRegistryIdentifier();
            final FlowRegistry registry = flowController.getFlowRegistryClient().getFlowRegistry(registryId);
            return registry == null ? registryId : registry.getName();
        }

        private boolean isModified() {
            Set<FlowDifference> differences = versionControlFields.getFlowDifferences();
            if (differences == null) {
                differences = getModifications();
                if (differences == null) {
                    return false;
                }
                versionControlFields.setFlowDifferences(differences);
            }
            return !differences.isEmpty();
        }

        @Override
        public VersionedFlowStatus getStatus() {
            // If current state is a sync failure, then
            final String syncFailureExplanation = versionControlFields.getSyncFailureExplanation();
            if (syncFailureExplanation != null) {
                return new StandardVersionedFlowStatus(VersionedFlowState.SYNC_FAILURE, syncFailureExplanation);
            }
            final boolean modified = isModified();
            if (!modified) {
                final VersionControlInformation vci = StandardProcessGroup.this.versionControlInfo.get();
                if (vci.getFlowSnapshot() == null) {
                    return new StandardVersionedFlowStatus(VersionedFlowState.SYNC_FAILURE, "Process Group has not yet been synchronized with Flow Registry");
                }
            }
            final boolean stale = versionControlFields.isStale();
            final VersionedFlowState flowState;
            if (modified && stale) {
                flowState = VersionedFlowState.LOCALLY_MODIFIED_AND_STALE;
            } else if (modified) {
                flowState = VersionedFlowState.LOCALLY_MODIFIED;
            } else if (stale) {
                flowState = VersionedFlowState.STALE;
            } else {
                flowState = VersionedFlowState.UP_TO_DATE;
            }
            return new StandardVersionedFlowStatus(flowState, flowState.getDescription());
        }
    };
    svci.setBucketName(versionControlInformation.getBucketName());
    svci.setFlowName(versionControlInformation.getFlowName());
    svci.setFlowDescription(versionControlInformation.getFlowDescription());
    final VersionedFlowState flowState = versionControlInformation.getStatus().getState();
    versionControlFields.setStale(flowState == VersionedFlowState.STALE || flowState == VersionedFlowState.LOCALLY_MODIFIED_AND_STALE);
    versionControlFields.setLocallyModified(flowState == VersionedFlowState.LOCALLY_MODIFIED || flowState == VersionedFlowState.LOCALLY_MODIFIED_AND_STALE);
    versionControlFields.setSyncFailureExplanation(null);
    writeLock.lock();
    try {
        updateVersionedComponentIds(this, versionedComponentIds);
        this.versionControlInfo.set(svci);
        versionControlFields.setFlowDifferences(null);
        final ProcessGroup parent = getParent();
        if (parent != null) {
            parent.onComponentModified();
        }
        scheduler.submitFrameworkTask(() -> synchronizeWithFlowRegistry(flowController.getFlowRegistryClient()));
    } finally {
        writeLock.unlock();
    }
}
Also used : FlowDifference(org.apache.nifi.registry.flow.diff.FlowDifference) StandardVersionControlInformation(org.apache.nifi.registry.flow.StandardVersionControlInformation) StandardVersionControlInformation(org.apache.nifi.registry.flow.StandardVersionControlInformation) VersionControlInformation(org.apache.nifi.registry.flow.VersionControlInformation) FlowRegistry(org.apache.nifi.registry.flow.FlowRegistry) VersionedFlowState(org.apache.nifi.registry.flow.VersionedFlowState) VersionedProcessGroup(org.apache.nifi.registry.flow.VersionedProcessGroup) VersionedRemoteProcessGroup(org.apache.nifi.registry.flow.VersionedRemoteProcessGroup)

Example 4 with StandardVersionControlInformation

use of org.apache.nifi.registry.flow.StandardVersionControlInformation in project nifi by apache.

the class StandardProcessGroup method synchronizeWithFlowRegistry.

@Override
public void synchronizeWithFlowRegistry(final FlowRegistryClient flowRegistryClient) {
    final StandardVersionControlInformation vci = versionControlInfo.get();
    if (vci == null) {
        return;
    }
    final String registryId = vci.getRegistryIdentifier();
    final FlowRegistry flowRegistry = flowRegistryClient.getFlowRegistry(registryId);
    if (flowRegistry == null) {
        final String message = String.format("Unable to synchronize Process Group with Flow Registry because Process Group was placed under Version Control using Flow Registry " + "with identifier %s but cannot find any Flow Registry with this identifier", registryId);
        versionControlFields.setSyncFailureExplanation(message);
        LOG.error("Unable to synchronize {} with Flow Registry because Process Group was placed under Version Control using Flow Registry " + "with identifier {} but cannot find any Flow Registry with this identifier", this, registryId);
        return;
    }
    final VersionedProcessGroup snapshot = vci.getFlowSnapshot();
    if (snapshot == null) {
        // This allows us to know whether or not the flow has been modified since it was last synced with the Flow Registry.
        try {
            final VersionedFlowSnapshot registrySnapshot = flowRegistry.getFlowContents(vci.getBucketIdentifier(), vci.getFlowIdentifier(), vci.getVersion(), false);
            final VersionedProcessGroup registryFlow = registrySnapshot.getFlowContents();
            vci.setFlowSnapshot(registryFlow);
        } catch (final IOException | NiFiRegistryException e) {
            final String message = String.format("Failed to synchronize Process Group with Flow Registry because could not retrieve version %s of flow with identifier %s in bucket %s", vci.getVersion(), vci.getFlowIdentifier(), vci.getBucketIdentifier());
            versionControlFields.setSyncFailureExplanation(message);
            LOG.error("Failed to synchronize {} with Flow Registry because could not retrieve version {} of flow with identifier {} in bucket {}", this, vci.getVersion(), vci.getFlowIdentifier(), vci.getBucketIdentifier(), e);
            return;
        }
    }
    try {
        final VersionedFlow versionedFlow = flowRegistry.getVersionedFlow(vci.getBucketIdentifier(), vci.getFlowIdentifier());
        final int latestVersion = (int) versionedFlow.getVersionCount();
        vci.setBucketName(versionedFlow.getBucketName());
        vci.setFlowName(versionedFlow.getName());
        vci.setFlowDescription(versionedFlow.getDescription());
        vci.setRegistryName(flowRegistry.getName());
        if (latestVersion == vci.getVersion()) {
            LOG.debug("{} is currently at the most recent version ({}) of the flow that is under Version Control", this, latestVersion);
            versionControlFields.setStale(false);
        } else {
            LOG.info("{} is not the most recent version of the flow that is under Version Control; current version is {}; most recent version is {}", new Object[] { this, vci.getVersion(), latestVersion });
            versionControlFields.setStale(true);
        }
        versionControlFields.setSyncFailureExplanation(null);
    } catch (final IOException | NiFiRegistryException e) {
        final String message = String.format("Failed to synchronize Process Group with Flow Registry : " + e.getMessage());
        versionControlFields.setSyncFailureExplanation(message);
        LOG.error("Failed to synchronize {} with Flow Registry because could not determine the most recent version of the Flow in the Flow Registry", this, e);
    }
}
Also used : StandardVersionControlInformation(org.apache.nifi.registry.flow.StandardVersionControlInformation) FlowRegistry(org.apache.nifi.registry.flow.FlowRegistry) VersionedProcessGroup(org.apache.nifi.registry.flow.VersionedProcessGroup) VersionedFlowSnapshot(org.apache.nifi.registry.flow.VersionedFlowSnapshot) VersionedFlow(org.apache.nifi.registry.flow.VersionedFlow) IOException(java.io.IOException) NiFiRegistryException(org.apache.nifi.registry.client.NiFiRegistryException)

Example 5 with StandardVersionControlInformation

use of org.apache.nifi.registry.flow.StandardVersionControlInformation in project nifi by apache.

the class StandardProcessGroup method updateFlow.

@Override
public void updateFlow(final VersionedFlowSnapshot proposedSnapshot, final String componentIdSeed, final boolean verifyNotDirty, final boolean updateSettings, final boolean updateDescendantVersionedFlows) {
    writeLock.lock();
    try {
        verifyCanUpdate(proposedSnapshot, true, verifyNotDirty);
        final NiFiRegistryFlowMapper mapper = new NiFiRegistryFlowMapper();
        final VersionedProcessGroup versionedGroup = mapper.mapProcessGroup(this, controllerServiceProvider, flowController.getFlowRegistryClient(), true);
        final ComparableDataFlow localFlow = new StandardComparableDataFlow("Local Flow", versionedGroup);
        final ComparableDataFlow remoteFlow = new StandardComparableDataFlow("Remote Flow", proposedSnapshot.getFlowContents());
        final FlowComparator flowComparator = new StandardFlowComparator(remoteFlow, localFlow, getAncestorGroupServiceIds(), new StaticDifferenceDescriptor());
        final FlowComparison flowComparison = flowComparator.compare();
        final Set<String> updatedVersionedComponentIds = new HashSet<>();
        for (final FlowDifference diff : flowComparison.getDifferences()) {
            // Ignore these as local differences for now because we can't do anything with it
            if (diff.getDifferenceType() == DifferenceType.BUNDLE_CHANGED) {
                continue;
            }
            // and if so compare our VersionedControllerService to the existing service.
            if (diff.getDifferenceType() == DifferenceType.COMPONENT_ADDED) {
                final VersionedComponent component = diff.getComponentA() == null ? diff.getComponentB() : diff.getComponentA();
                if (ComponentType.CONTROLLER_SERVICE == component.getComponentType()) {
                    final ControllerServiceNode serviceNode = getVersionedControllerService(this, component.getIdentifier());
                    if (serviceNode != null) {
                        final VersionedControllerService versionedService = mapper.mapControllerService(serviceNode, controllerServiceProvider);
                        final Set<FlowDifference> differences = flowComparator.compareControllerServices(versionedService, (VersionedControllerService) component);
                        if (!differences.isEmpty()) {
                            updatedVersionedComponentIds.add(component.getIdentifier());
                        }
                        continue;
                    }
                }
            }
            final VersionedComponent component = diff.getComponentA() == null ? diff.getComponentB() : diff.getComponentA();
            updatedVersionedComponentIds.add(component.getIdentifier());
            if (component.getComponentType() == ComponentType.REMOTE_INPUT_PORT || component.getComponentType() == ComponentType.REMOTE_OUTPUT_PORT) {
                final String remoteGroupId = ((VersionedRemoteGroupPort) component).getRemoteGroupId();
                updatedVersionedComponentIds.add(remoteGroupId);
            }
        }
        if (LOG.isInfoEnabled()) {
            final String differencesByLine = flowComparison.getDifferences().stream().map(FlowDifference::toString).collect(Collectors.joining("\n"));
            LOG.info("Updating {} to {}; there are {} differences to take into account:\n{}", this, proposedSnapshot, flowComparison.getDifferences().size(), differencesByLine);
        }
        final Set<String> knownVariables = getKnownVariableNames();
        final StandardVersionControlInformation originalVci = this.versionControlInfo.get();
        try {
            updateProcessGroup(this, proposedSnapshot.getFlowContents(), componentIdSeed, updatedVersionedComponentIds, false, updateSettings, updateDescendantVersionedFlows, knownVariables);
        } catch (final Throwable t) {
            // As a result, it is safe to use the get() and then the set() methods of the AtomicReference without introducing the 'check-then-modify' problem.
            if (this.versionControlInfo.get() == null) {
                this.versionControlInfo.set(originalVci);
            }
            throw t;
        }
    } catch (final ProcessorInstantiationException pie) {
        throw new IllegalStateException("Failed to update flow", pie);
    } finally {
        writeLock.unlock();
    }
}
Also used : StandardVersionControlInformation(org.apache.nifi.registry.flow.StandardVersionControlInformation) NiFiRegistryFlowMapper(org.apache.nifi.registry.flow.mapping.NiFiRegistryFlowMapper) VersionedProcessGroup(org.apache.nifi.registry.flow.VersionedProcessGroup) FlowComparison(org.apache.nifi.registry.flow.diff.FlowComparison) VersionedRemoteGroupPort(org.apache.nifi.registry.flow.VersionedRemoteGroupPort) VersionedControllerService(org.apache.nifi.registry.flow.VersionedControllerService) StandardFlowComparator(org.apache.nifi.registry.flow.diff.StandardFlowComparator) StaticDifferenceDescriptor(org.apache.nifi.registry.flow.diff.StaticDifferenceDescriptor) StandardComparableDataFlow(org.apache.nifi.registry.flow.diff.StandardComparableDataFlow) ComparableDataFlow(org.apache.nifi.registry.flow.diff.ComparableDataFlow) VersionedComponent(org.apache.nifi.registry.flow.VersionedComponent) FlowDifference(org.apache.nifi.registry.flow.diff.FlowDifference) ControllerServiceNode(org.apache.nifi.controller.service.ControllerServiceNode) ProcessorInstantiationException(org.apache.nifi.controller.exception.ProcessorInstantiationException) StandardComparableDataFlow(org.apache.nifi.registry.flow.diff.StandardComparableDataFlow) FlowComparator(org.apache.nifi.registry.flow.diff.FlowComparator) StandardFlowComparator(org.apache.nifi.registry.flow.diff.StandardFlowComparator) LinkedHashSet(java.util.LinkedHashSet) HashSet(java.util.HashSet)

Aggregations

StandardVersionControlInformation (org.apache.nifi.registry.flow.StandardVersionControlInformation)10 VersionedProcessGroup (org.apache.nifi.registry.flow.VersionedProcessGroup)7 FlowRegistry (org.apache.nifi.registry.flow.FlowRegistry)4 ProcessGroup (org.apache.nifi.groups.ProcessGroup)3 RemoteProcessGroup (org.apache.nifi.groups.RemoteProcessGroup)3 FlowDifference (org.apache.nifi.registry.flow.diff.FlowDifference)3 NiFiRegistryFlowMapper (org.apache.nifi.registry.flow.mapping.NiFiRegistryFlowMapper)3 HashSet (java.util.HashSet)2 ProcessorInstantiationException (org.apache.nifi.controller.exception.ProcessorInstantiationException)2 ControllerServiceNode (org.apache.nifi.controller.service.ControllerServiceNode)2 VersionedFlowState (org.apache.nifi.registry.flow.VersionedFlowState)2 VersionedRemoteProcessGroup (org.apache.nifi.registry.flow.VersionedRemoteProcessGroup)2 ComparableDataFlow (org.apache.nifi.registry.flow.diff.ComparableDataFlow)2 FlowComparator (org.apache.nifi.registry.flow.diff.FlowComparator)2 FlowComparison (org.apache.nifi.registry.flow.diff.FlowComparison)2 StandardComparableDataFlow (org.apache.nifi.registry.flow.diff.StandardComparableDataFlow)2 StandardFlowComparator (org.apache.nifi.registry.flow.diff.StandardFlowComparator)2 IOException (java.io.IOException)1 ArrayList (java.util.ArrayList)1 HashMap (java.util.HashMap)1