From 5fd6b873feac38d2e5f5a8e767c87f16c710ec8f Mon Sep 17 00:00:00 2001 From: Bryan Bende Date: Thu, 22 Aug 2019 15:28:10 -0400 Subject: [PATCH] NIFI-6582 Add diff-flow-versions command to CLI --- .../cli/impl/command/CommandOption.java | 3 + .../registry/NiFiRegistryCommandGroup.java | 6 +- .../registry/flow/DiffFlowVersions.java | 64 +++++++++++++++ .../VersionedFlowDifferenceResult.java | 81 +++++++++++++++++++ 4 files changed, 152 insertions(+), 2 deletions(-) create mode 100644 nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/command/registry/flow/DiffFlowVersions.java create mode 100644 nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/result/registry/VersionedFlowDifferenceResult.java diff --git a/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/command/CommandOption.java b/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/command/CommandOption.java index 538c1981b3..79d77a0f44 100644 --- a/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/command/CommandOption.java +++ b/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/command/CommandOption.java @@ -46,6 +46,9 @@ public enum CommandOption { FLOW_DESC("fd", "flowDesc", "A flow description", true), FLOW_VERSION("fv", "flowVersion", "A version of a flow", true), + FLOW_VERSION_1("fv1", "flowVersion1", "A version of a flow", true), + FLOW_VERSION_2("fv2", "flowVersion2", "A version of a flow", true), + // Registry - Source options for when there are two registries involved and one is a source SRC_PROPS("sp", "sourceProps", "A properties file to load for the source", true, true), SRC_FLOW_ID("sf", "sourceFlowIdentifier", "A flow identifier from the source registry", true), diff --git a/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/command/registry/NiFiRegistryCommandGroup.java b/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/command/registry/NiFiRegistryCommandGroup.java index bb077d9886..3e14906c1e 100644 --- a/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/command/registry/NiFiRegistryCommandGroup.java +++ b/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/command/registry/NiFiRegistryCommandGroup.java @@ -23,15 +23,16 @@ import org.apache.nifi.toolkit.cli.impl.command.registry.bucket.DeleteBucket; import org.apache.nifi.toolkit.cli.impl.command.registry.bucket.ListBuckets; import org.apache.nifi.toolkit.cli.impl.command.registry.extension.DownloadBundle; import org.apache.nifi.toolkit.cli.impl.command.registry.extension.GetBundleChecksum; -import org.apache.nifi.toolkit.cli.impl.command.registry.extension.ListExtensions; -import org.apache.nifi.toolkit.cli.impl.command.registry.extension.ListExtensionTags; import org.apache.nifi.toolkit.cli.impl.command.registry.extension.ListBundleArtifacts; import org.apache.nifi.toolkit.cli.impl.command.registry.extension.ListBundleGroups; import org.apache.nifi.toolkit.cli.impl.command.registry.extension.ListBundleVersions; +import org.apache.nifi.toolkit.cli.impl.command.registry.extension.ListExtensionTags; +import org.apache.nifi.toolkit.cli.impl.command.registry.extension.ListExtensions; import org.apache.nifi.toolkit.cli.impl.command.registry.extension.UploadBundle; import org.apache.nifi.toolkit.cli.impl.command.registry.extension.UploadBundles; import org.apache.nifi.toolkit.cli.impl.command.registry.flow.CreateFlow; import org.apache.nifi.toolkit.cli.impl.command.registry.flow.DeleteFlow; +import org.apache.nifi.toolkit.cli.impl.command.registry.flow.DiffFlowVersions; import org.apache.nifi.toolkit.cli.impl.command.registry.flow.ExportFlowVersion; import org.apache.nifi.toolkit.cli.impl.command.registry.flow.ImportFlowVersion; import org.apache.nifi.toolkit.cli.impl.command.registry.flow.ListFlowVersions; @@ -69,6 +70,7 @@ public class NiFiRegistryCommandGroup extends AbstractCommandGroup { commandList.add(new ImportFlowVersion()); commandList.add(new SyncFlowVersions()); commandList.add(new TransferFlowVersion()); + commandList.add(new DiffFlowVersions()); commandList.add(new UploadBundle()); commandList.add(new UploadBundles()); commandList.add(new ListBundleGroups()); diff --git a/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/command/registry/flow/DiffFlowVersions.java b/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/command/registry/flow/DiffFlowVersions.java new file mode 100644 index 0000000000..fc985d7b87 --- /dev/null +++ b/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/command/registry/flow/DiffFlowVersions.java @@ -0,0 +1,64 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.apache.nifi.toolkit.cli.impl.command.registry.flow; + +import org.apache.commons.cli.ParseException; +import org.apache.nifi.registry.client.FlowClient; +import org.apache.nifi.registry.client.NiFiRegistryClient; +import org.apache.nifi.registry.client.NiFiRegistryException; +import org.apache.nifi.registry.diff.VersionedFlowDifference; +import org.apache.nifi.toolkit.cli.api.Context; +import org.apache.nifi.toolkit.cli.impl.command.CommandOption; +import org.apache.nifi.toolkit.cli.impl.command.registry.AbstractNiFiRegistryCommand; +import org.apache.nifi.toolkit.cli.impl.result.registry.VersionedFlowDifferenceResult; + +import java.io.IOException; +import java.util.Properties; + +public class DiffFlowVersions extends AbstractNiFiRegistryCommand { + + public DiffFlowVersions() { + super("diff-flow-versions", VersionedFlowDifferenceResult.class); + } + + @Override + public String getDescription() { + return "Shows the differences between two versions of a flow."; + } + + @Override + public void doInitialize(final Context context) { + addOption(CommandOption.BUCKET_ID.createOption()); + addOption(CommandOption.FLOW_ID.createOption()); + addOption(CommandOption.FLOW_VERSION_1.createOption()); + addOption(CommandOption.FLOW_VERSION_2.createOption()); + } + + @Override + public VersionedFlowDifferenceResult doExecute(final NiFiRegistryClient client, final Properties properties) + throws IOException, NiFiRegistryException, ParseException { + + final String bucketId = getRequiredArg(properties, CommandOption.BUCKET_ID); + final String flowId = getRequiredArg(properties, CommandOption.FLOW_ID); + final Integer version1 = getRequiredIntArg(properties, CommandOption.FLOW_VERSION_1); + final Integer version2 = getRequiredIntArg(properties, CommandOption.FLOW_VERSION_2); + + final FlowClient flowClient = client.getFlowClient(); + final VersionedFlowDifference flowDifference = flowClient.diff(bucketId, flowId, version1, version2); + return new VersionedFlowDifferenceResult(getResultType(properties), flowDifference); + } +} diff --git a/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/result/registry/VersionedFlowDifferenceResult.java b/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/result/registry/VersionedFlowDifferenceResult.java new file mode 100644 index 0000000000..00d1b8f120 --- /dev/null +++ b/nifi-toolkit/nifi-toolkit-cli/src/main/java/org/apache/nifi/toolkit/cli/impl/result/registry/VersionedFlowDifferenceResult.java @@ -0,0 +1,81 @@ +/* + * Licensed to the Apache Software Foundation (ASF) under one or more + * contributor license agreements. See the NOTICE file distributed with + * this work for additional information regarding copyright ownership. + * The ASF licenses this file to You under the Apache License, Version 2.0 + * (the "License"); you may not use this file except in compliance with + * the License. You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +package org.apache.nifi.toolkit.cli.impl.result.registry; + +import org.apache.commons.lang3.Validate; +import org.apache.nifi.registry.diff.ComponentDifference; +import org.apache.nifi.registry.diff.ComponentDifferenceGroup; +import org.apache.nifi.registry.diff.VersionedFlowDifference; +import org.apache.nifi.toolkit.cli.api.ResultType; +import org.apache.nifi.toolkit.cli.impl.result.AbstractWritableResult; +import org.apache.nifi.toolkit.cli.impl.result.writer.DynamicTableWriter; +import org.apache.nifi.toolkit.cli.impl.result.writer.Table; +import org.apache.nifi.toolkit.cli.impl.result.writer.TableWriter; + +import java.io.IOException; +import java.io.PrintStream; +import java.util.ArrayList; +import java.util.Collections; +import java.util.Comparator; +import java.util.List; + +public class VersionedFlowDifferenceResult extends AbstractWritableResult { + + private final VersionedFlowDifference flowDifference; + + public VersionedFlowDifferenceResult(final ResultType resultType, final VersionedFlowDifference flowDifference) { + super(resultType); + this.flowDifference = Validate.notNull(flowDifference); + } + + @Override + protected void writeSimpleResult(final PrintStream output) throws IOException { + final Table table = new Table.Builder() + .column("#", 3, 3, false) + .column("Component Name", 20, 40, false) + .column("Change Type", 20, 40, true) + .column("Difference", 40, 60, true) + .build(); + + final List differenceGroups = new ArrayList<>( + flowDifference.getComponentDifferenceGroups() == null + ? Collections.emptyList() : flowDifference.getComponentDifferenceGroups()); + differenceGroups.sort(Comparator.comparing(ComponentDifferenceGroup::getComponentName)); + + int differenceCount = 1; + for (final ComponentDifferenceGroup differenceGroup : differenceGroups) { + final String componentName = differenceGroup.getComponentName(); + + final List componentDifferences = new ArrayList<>(differenceGroup.getDifferences()); + componentDifferences.sort(Comparator.comparing(ComponentDifference::getDifferenceType)); + + for (final ComponentDifference componentDifference : componentDifferences) { + final String changeType = componentDifference.getDifferenceType(); + final String changeDescription = componentDifference.getChangeDescription(); + table.addRow(String.valueOf(differenceCount++), componentName, changeType, changeDescription); + } + } + + final TableWriter tableWriter = new DynamicTableWriter(); + tableWriter.write(table, output); + } + + @Override + public VersionedFlowDifference getResult() { + return flowDifference; + } +}