/** * Returns a new Revision that has the same Client ID and Component ID as this one * but with a larger version * * @return the updated Revision */ public Revision incrementRevision(final String clientId) { return new Revision(version + 1, clientId, componentId); }
@Override public int compare(final Revision o1, final Revision o2) { final int componentComparison = o1.getComponentId().compareTo(o2.getComponentId()); if (componentComparison != 0) { return componentComparison; } final int clientComparison = o1.getClientId().compareTo(o2.getClientId()); if (clientComparison != 0) { return clientComparison; } return o1.getVersion().compareTo(o2.getVersion()); }
@Override public void verifyRevision(final Revision revision, final NiFiUser user) { final Revision curRevision = revisionManager.getRevision(revision.getComponentId()); if (revision.equals(curRevision)) { return; } throw new InvalidRevisionException(revision + " is not the most up-to-date revision. This component appears to have been modified"); }
@Override public boolean equals(final Object obj) { if (obj == null) { return false; } if (obj == this) { return true; } if ((obj instanceof Revision) == false) { return false; } Revision thatRevision = (Revision) obj; // ensure that component ID's are the same (including null) if (thatRevision.getComponentId() == null && getComponentId() != null) { return false; } if (thatRevision.getComponentId() != null && getComponentId() == null) { return false; } if (thatRevision.getComponentId() != null && !thatRevision.getComponentId().equals(getComponentId())) { return false; } if (this.version != null && this.version.equals(thatRevision.version)) { return true; } else { return clientId != null && !clientId.trim().isEmpty() && clientId.equals(thatRevision.getClientId()); } }
@Override public RevisionUpdate<D> update() { // get the updated component final C component = daoUpdate.get(); // save updated controller controllerFacade.save(); final D dto = dtoCreation.apply(component); final Revision updatedRevision = revisionManager.getRevision(revision.getComponentId()).incrementRevision(revision.getClientId()); final FlowModification lastModification = new FlowModification(updatedRevision, user.getIdentity()); return new StandardRevisionUpdate<>(dto, lastModification); } });
private Map<String, RevisionDTO> mapRevisionToDto(final Map<String, Revision> revisionMap) { final Map<String, RevisionDTO> dtos = new HashMap<>(revisionMap.size()); for (final Map.Entry<String, Revision> entry : revisionMap.entrySet()) { final Revision revision = entry.getValue(); final RevisionDTO revisionDto = new RevisionDTO(); revisionDto.setClientId(revision.getClientId()); revisionDto.setVersion(revision.getVersion()); dtos.put(entry.getKey(), revisionDto); } return dtos; }
@Override public RevisionUpdate<ControllerServiceReferencingComponentsEntity> update() { final Set<ComponentNode> updated = controllerServiceDAO.updateControllerServiceReferencingComponents(controllerServiceId, scheduledState, controllerServiceState); final ControllerServiceReference updatedReference = controllerServiceDAO.getControllerService(controllerServiceId).getReferences(); // get the revisions of the updated components final Map<String, Revision> updatedRevisions = new HashMap<>(); for (final ComponentNode component : updated) { final Revision currentRevision = revisionManager.getRevision(component.getIdentifier()); final Revision requestRevision = referenceRevisions.get(component.getIdentifier()); updatedRevisions.put(component.getIdentifier(), currentRevision.incrementRevision(requestRevision.getClientId())); } // ensure the revision for all referencing components is included regardless of whether they were updated in this request for (final ComponentNode component : updatedReference.findRecursiveReferences(ComponentNode.class)) { updatedRevisions.putIfAbsent(component.getIdentifier(), revisionManager.getRevision(component.getIdentifier())); } final ControllerServiceReferencingComponentsEntity entity = createControllerServiceReferencingComponentsEntity(updatedReference, updatedRevisions); return new StandardRevisionUpdate<>(entity, null, new HashSet<>(updatedRevisions.values())); } });
@Override public void reset(final Collection<Revision> revisions) { synchronized (this) { // avoid allowing two threads to reset versions concurrently revisionMap.clear(); for (final Revision revision : revisions) { revisionMap.put(revision.getComponentId(), revision); } } }
@Override public RevisionUpdate<ProcessGroupDTO> update() { // update the Process Group processGroupDAO.updateProcessGroupFlow(groupId, proposedFlowSnapshot, versionControlInfo, componentIdSeed, verifyNotModified, updateSettings, updateDescendantVersionedFlows); // update the revisions final Set<Revision> updatedRevisions = revisions.stream() .map(rev -> revisionManager.getRevision(rev.getComponentId()).incrementRevision(revision.getClientId())) .collect(Collectors.toSet()); // save controllerFacade.save(); // gather details for response final ProcessGroupDTO dto = dtoFactory.createProcessGroupDto(processGroup); final Revision updatedRevision = revisionManager.getRevision(groupId).incrementRevision(revision.getClientId()); final FlowModification lastModification = new FlowModification(updatedRevision, user.getIdentity()); return new StandardRevisionUpdate<>(dto, lastModification, updatedRevisions); } });
public RevisionDTO createRevisionDTO(final Revision revision) { final RevisionDTO dto = new RevisionDTO(); dto.setVersion(revision.getVersion()); dto.setClientId(revision.getClientId()); return dto; }
/** * Creates a component using the optimistic locking manager. * * @param componentDto the DTO that will be used to create the component * @param daoCreation A Supplier that will create the NiFi Component to use * @param dtoCreation a Function that will convert the NiFi Component into a corresponding DTO * @param <D> the DTO Type * @param <C> the NiFi Component Type * @return a RevisionUpdate that represents the updated configuration */ private <D, C> RevisionUpdate<D> createComponent(final Revision revision, final ComponentDTO componentDto, final Supplier<C> daoCreation, final Function<C, D> dtoCreation) { final NiFiUser user = NiFiUserUtils.getNiFiUser(); // read lock on the containing group // request claim for component to be created... revision already verified (version == 0) final RevisionClaim claim = new StandardRevisionClaim(revision); // update revision through revision manager return revisionManager.updateRevision(claim, user, () -> { // add the component final C component = daoCreation.get(); // save the flow controllerFacade.save(); final D dto = dtoCreation.apply(component); final FlowModification lastMod = new FlowModification(revision.incrementRevision(revision.getClientId()), user.getIdentity()); return new StandardRevisionUpdate<>(dto, lastMod); }); }
private Map<String, Revision> getRevisions(final String groupId, final Set<String> componentIds) { final Set<Revision> processorRevisions = serviceFacade.getRevisionsFromGroup(groupId, group -> componentIds); return processorRevisions.stream().collect(Collectors.toMap(revision -> revision.getComponentId(), Function.identity())); }
@Override public Revision getRevision(final String componentId) { return revisionMap.computeIfAbsent(componentId, id -> new Revision(0L, null, componentId)); }
public static ComponentRevision fromRevision(final Revision revision) { final ComponentRevision componentRevision = new ComponentRevision(); componentRevision.setVersion(revision.getVersion()); componentRevision.setClientId(revision.getClientId()); componentRevision.setComponentId(revision.getComponentId()); return componentRevision; }
@Override public RevisionUpdate<ActivateControllerServicesEntity> update() { // schedule the components processGroupDAO.activateControllerServices(processGroupId, state, serviceRevisions.keySet()); // update the revisions final Map<String, Revision> updatedRevisions = new HashMap<>(); for (final Revision revision : serviceRevisions.values()) { final Revision currentRevision = revisionManager.getRevision(revision.getComponentId()); updatedRevisions.put(revision.getComponentId(), currentRevision.incrementRevision(revision.getClientId())); } // save controllerFacade.save(); // gather details for response final ActivateControllerServicesEntity entity = new ActivateControllerServicesEntity(); entity.setId(processGroupId); entity.setState(state.name()); return new StandardRevisionUpdate<>(entity, null, new HashSet<>(updatedRevisions.values())); } });
/** * Factory method for creating a new RevisionDTO based on this controller. * * @param lastMod mod * @return dto */ public RevisionDTO createRevisionDTO(final FlowModification lastMod) { final Revision revision = lastMod.getRevision(); // create the dto final RevisionDTO revisionDTO = new RevisionDTO(); revisionDTO.setVersion(revision.getVersion()); revisionDTO.setClientId(revision.getClientId()); revisionDTO.setLastModifier(lastMod.getLastModifier()); return revisionDTO; }
@Override public RegistryClientEntity createRegistryClient(Revision revision, RegistryDTO registryDTO) { final NiFiUser user = NiFiUserUtils.getNiFiUser(); // request claim for component to be created... revision already verified (version == 0) final RevisionClaim claim = new StandardRevisionClaim(revision); // update revision through revision manager final RevisionUpdate<FlowRegistry> revisionUpdate = revisionManager.updateRevision(claim, user, () -> { // add the component final FlowRegistry registry = registryDAO.createFlowRegistry(registryDTO); // save the flow controllerFacade.save(); final FlowModification lastMod = new FlowModification(revision.incrementRevision(revision.getClientId()), user.getIdentity()); return new StandardRevisionUpdate<>(registry, lastMod); }); final FlowRegistry registry = revisionUpdate.getComponent(); return createRegistryClientEntity(registry); }
@Override public <T> T deleteRevision(final RevisionClaim claim, final NiFiUser user, final DeleteRevisionTask<T> task) throws ExpiredRevisionClaimException { Objects.requireNonNull(user); logger.debug("Attempting to delete revision using {}", claim); final List<Revision> revisionList = new ArrayList<>(claim.getRevisions()); revisionList.sort(new RevisionComparator()); // Verify the provided revisions. String failedId = null; for (final Revision revision : revisionList) { final Revision curRevision = getRevision(revision.getComponentId()); if (!curRevision.equals(revision)) { throw new ExpiredRevisionClaimException("Invalid Revision was given for component with ID '" + failedId + "'"); } } // Perform the action provided final T taskResult = task.performTask(); for (final Revision revision : revisionList) { revisionMap.remove(revision.getComponentId()); } return taskResult; }
private Map<String, Revision> getRevisions(final String groupId, final Set<String> componentIds) { final Set<Revision> processorRevisions = serviceFacade.getRevisionsFromGroup(groupId, group -> componentIds); return processorRevisions.stream().collect(Collectors.toMap(revision -> revision.getComponentId(), Function.identity())); }
/** * @return the revision retrieved from the request parameters with keys * equal to "clientId", "revision", and "id". */ @Override public Revision getRevision() { final String revisionParamVal = request.getParameter(REVISION_PARAM); Long revision; try { revision = Long.parseLong(revisionParamVal); } catch (final Exception ex) { revision = null; } final String clientId = request.getParameter(CLIENT_ID_PARAM); final String componentId = request.getParameter(ID_PARAM); return new Revision(revision, clientId, componentId); }