Skip to content

Commit

Permalink
feat(core): Add SpEL helper to get all resolved stage artifacts (#3998)
Browse files Browse the repository at this point in the history
* feat(core): Add SpEL helper to get all resolved stage artifacts

This commit adds a spell helper called resolvedArtifacts which will
return all the resolved stage artifacts. Further selection of artifacts
can be done with '.?' or other SpEL built-in features.

* Apply suggestions from code review

Co-authored-by: David Byron <dbyron@dbyron.com>

Co-authored-by: Aufar Gilbran <aufar.gilbran@grabtaxi.com>
Co-authored-by: David Byron <dbyron@dbyron.com>
Co-authored-by: mergify[bot] <37929162+mergify[bot]@users.noreply.github.com>
  • Loading branch information
4 people committed Jan 4, 2021
1 parent ca398bf commit 2b91f74
Show file tree
Hide file tree
Showing 2 changed files with 63 additions and 3 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,10 @@
import com.netflix.spinnaker.kork.expressions.ExpressionFunctionProvider;
import com.netflix.spinnaker.kork.expressions.SpelHelperFunctionException;
import com.netflix.spinnaker.orca.api.pipeline.models.PipelineExecution;
import java.util.Collections;
import java.util.List;
import java.util.function.Predicate;
import java.util.stream.Collectors;
import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable;
import org.springframework.stereotype.Component;
Expand All @@ -42,16 +45,21 @@ public Functions getFunctions() {
return new Functions(
new FunctionDefinition(
"triggerResolvedArtifact",
"Looks up the an artifact in current execution given its name. If multiple artifacts are found, only 1 will be returned.",
"Looks up a resolved artifact in the current execution trigger given its name. If multiple artifacts are found, only 1 will be returned.",
new FunctionParameter(
PipelineExecution.class, "execution", "The execution to search for artifacts"),
new FunctionParameter(String.class, "name", "The name of the resolved artifact")),
new FunctionDefinition(
"triggerResolvedArtifactByType",
"Looks up the an artifact in current execution given its type. If multiple artifacts are found, only 1 will be returned.",
"Looks up a resolved artifact in the current execution trigger given its type. If multiple artifacts are found, only 1 will be returned.",
new FunctionParameter(
PipelineExecution.class, "execution", "The execution to search for artifacts"),
new FunctionParameter(String.class, "type", "The type of the resolved artifact")));
new FunctionParameter(String.class, "type", "The type of the resolved artifact")),
new FunctionDefinition(
"resolvedArtifacts",
"Looks up resolved artifacts in the current execution.",
new FunctionParameter(
PipelineExecution.class, "execution", "The execution to search for artifacts")));
}

public static Artifact triggerResolvedArtifact(PipelineExecution execution, String name) {
Expand All @@ -78,4 +86,16 @@ private static Artifact triggerResolvedArtifactBy(
"Unable to locate resolved artifact %s in trigger execution %s.",
nameOrType, execution.getId())));
}

private static List<Artifact> resolvedArtifacts(PipelineExecution execution) {
return execution.getStages().stream()
.flatMap(
stageExecution ->
((List<Artifact>)
stageExecution
.getOutputs()
.getOrDefault("artifacts", Collections.emptyList()))
.stream())
.collect(Collectors.toList());
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -25,7 +25,9 @@ import spock.lang.Specification

import static com.netflix.spinnaker.orca.pipeline.expressions.functions.ArtifactExpressionFunctionProvider.triggerResolvedArtifact
import static com.netflix.spinnaker.orca.pipeline.expressions.functions.ArtifactExpressionFunctionProvider.triggerResolvedArtifactByType
import static com.netflix.spinnaker.orca.pipeline.expressions.functions.ArtifactExpressionFunctionProvider.resolvedArtifacts
import static com.netflix.spinnaker.orca.test.model.ExecutionBuilder.pipeline
import static com.netflix.spinnaker.orca.test.model.ExecutionBuilder.stage


class ArtifactExpressionFunctionProviderSpec extends Specification {
Expand All @@ -38,6 +40,34 @@ class ArtifactExpressionFunctionProviderSpec extends Specification {
trigger.resolvedExpectedArtifacts = [
ExpectedArtifact.builder().matchArtifact(matchArtifact1).boundArtifact(boundArtifact).build()
]

stage {
id = "1"
refId = "1"
name = "Stage 1"
outputs = [artifacts: [Artifact.builder().type("type1").name("name1").reference("ref1").build()] ]
}

stage {
id = "2"
refId = "2"
name = "Stage 2"
outputs = [artifacts: [Artifact.builder().type("type2").name("name2").reference("ref2").build()] ]
}

stage {
id = "3"
refId = "3"
name = "Stage 3"
outputs = [artifacts: [Artifact.builder().type("type3").name("name3").reference("ref3").build()] ]
}

stage {
id = "4"
refId = "4"
name = "Stage 4"
outputs = [artifacts: [Artifact.builder().type("type4").name("name4").reference("ref4").build()] ]
}
}

def "triggerResolvedArtifact returns resolved trigger artifact by name"() {
Expand Down Expand Up @@ -74,4 +104,14 @@ class ArtifactExpressionFunctionProviderSpec extends Specification {
then:
thrown(SpelHelperFunctionException)
}

def "resolvedArtifacts returns artifacts in execution"() {
when:
def artifacts = resolvedArtifacts(pipeline1)

then:
artifacts.collect { it.name } == [ "name1", "name2", "name3", "name4" ]
artifacts.collect { it.type } == [ "type1", "type2", "type3", "type4" ]
artifacts.collect { it.reference } == [ "ref1", "ref2", "ref3", "ref4" ]
}
}

0 comments on commit 2b91f74

Please sign in to comment.