/* * Copyright 2017 ThoughtWorks, Inc. * * Licensed 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 com.thoughtworks.go.server.valuestreammap; import com.thoughtworks.go.domain.MaterialInstance; import com.thoughtworks.go.domain.PipelineIdentifier; import com.thoughtworks.go.domain.valuestreammap.Node; import com.thoughtworks.go.domain.valuestreammap.PipelineRevision; import com.thoughtworks.go.domain.valuestreammap.Revision; import com.thoughtworks.go.domain.valuestreammap.ValueStreamMap; import com.thoughtworks.go.server.dao.PipelineDao; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Component; import java.util.HashSet; import java.util.List; import java.util.Set; @Component public class DownstreamInstancePopulator { private PipelineDao pipelineDao; @Autowired public DownstreamInstancePopulator(PipelineDao pipelineDao) { this.pipelineDao = pipelineDao; } public void apply(ValueStreamMap valueStreamMap) { if (valueStreamMap.getCurrentPipeline() != null) { Node currentPipeline = valueStreamMap.getCurrentPipeline(); populateRevisionsForAllChildrenOf(currentPipeline, new HashSet<>()); } else { Node currentMaterial = valueStreamMap.getCurrentMaterial(); MaterialInstance currentMaterialInstance = valueStreamMap.getCurrentMaterialInstance(); populateRevisionsFor(currentMaterial, currentMaterialInstance, new HashSet<>()); } } private void populateRevisionsFor(Node currentMaterial, MaterialInstance currentMaterialInstance, HashSet<Revision> visitedRevisions) { String revision = currentMaterial.revisions().get(0).getRevisionString(); List<Node> downstreamPipelines = currentMaterial.getChildren(); for (Node downstreamPipeline : downstreamPipelines) { List<PipelineIdentifier> pipelineIdentifiers = pipelineDao.getPipelineInstancesTriggeredWithDependencyMaterial(downstreamPipeline.getName(), currentMaterialInstance, revision); addRevisionsToNode(downstreamPipeline, pipelineIdentifiers); populateRevisionsForAllChildrenOf(downstreamPipeline, visitedRevisions); } } private void populateRevisionsForAllChildrenOf(Node node, Set<Revision> visitedRevisions) { for (Revision revision : node.revisions()) { if (visitedRevisions.contains(revision)) { continue; } visitedRevisions.add(revision); for (Node child : node.getChildren()) { List<PipelineIdentifier> pipelineIdentifiers = pipelineDao.getPipelineInstancesTriggeredWithDependencyMaterial(child.getName(), ((PipelineRevision) revision).getPipelineIdentifier()); addRevisionsToNode(child, pipelineIdentifiers); populateRevisionsForAllChildrenOf(child, visitedRevisions); } } } private void addRevisionsToNode(Node node, List<PipelineIdentifier> pipelineIdentifiers) { for (PipelineIdentifier pipelineIdentifier : pipelineIdentifiers) { node.addRevision(new PipelineRevision(pipelineIdentifier)); } } }