/** * * Copyright (C) norad.fr * * 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 fr.norad.visuwall.plugin.bamboo; import java.util.ArrayList; import java.util.Arrays; import java.util.Date; import java.util.HashMap; import java.util.List; import java.util.Map; import org.apache.commons.lang.StringUtils; import org.slf4j.Logger; import org.slf4j.LoggerFactory; import com.google.common.annotations.VisibleForTesting; import com.google.common.base.Preconditions; import fr.norad.visuwall.providers.bamboo.Bamboo; import fr.norad.visuwall.providers.bamboo.exception.BambooBuildNotFoundException; import fr.norad.visuwall.providers.bamboo.exception.BambooBuildNumberNotFoundException; import fr.norad.visuwall.providers.bamboo.exception.BambooEstimatedFinishTimeNotFoundException; import fr.norad.visuwall.providers.bamboo.exception.BambooPlanNotFoundException; import fr.norad.visuwall.providers.bamboo.exception.BambooStateNotFoundException; import fr.norad.visuwall.providers.bamboo.resource.Plan; import fr.norad.visuwall.providers.bamboo.resource.Result; import fr.norad.visuwall.api.domain.BuildState; import fr.norad.visuwall.api.domain.BuildTime; import fr.norad.visuwall.api.domain.Commiter; import fr.norad.visuwall.api.domain.ProjectKey; import fr.norad.visuwall.api.domain.SoftwareProjectId; import fr.norad.visuwall.api.domain.TestResult; import fr.norad.visuwall.api.exception.BuildIdNotFoundException; import fr.norad.visuwall.api.exception.BuildNotFoundException; import fr.norad.visuwall.api.exception.MavenIdNotFoundException; import fr.norad.visuwall.api.exception.ProjectNotFoundException; import fr.norad.visuwall.api.plugin.capability.BuildCapability; import fr.norad.visuwall.api.plugin.capability.TestCapability; public class BambooConnection implements BuildCapability, TestCapability { @VisibleForTesting Bamboo bamboo; private boolean connected; private static final Logger LOG = LoggerFactory.getLogger(BambooConnection.class); @Override public void connect(String url, String login, String password) { Preconditions.checkNotNull(url, "url is mandatory"); if (StringUtils.isBlank(url)) { throw new IllegalArgumentException("url can't be null."); } if (StringUtils.isNotBlank(login)) { bamboo = new Bamboo(url, login, password); } else { bamboo = new Bamboo(url); } connected = true; } @Override public boolean isBuilding(SoftwareProjectId softwareProjectId, String buildId) throws ProjectNotFoundException, BuildNotFoundException { checkConnected(); checkSoftwareProjectId(softwareProjectId); checkBuildId(buildId); try { String projectName = getProjectKey(softwareProjectId); return bamboo.isBuilding(projectName, Integer.valueOf(buildId)); } catch (BambooPlanNotFoundException e) { throw new ProjectNotFoundException("Can't find project with software project id:" + softwareProjectId, e); } } @Override public BuildState getBuildState(SoftwareProjectId projectId, String buildId) throws ProjectNotFoundException, BuildNotFoundException { checkConnected(); checkSoftwareProjectId(projectId); checkBuildId(buildId); try { String projectName = getProjectKey(projectId); String bambooState = bamboo.getState(projectName); return States.asVisuwallState(bambooState); } catch (BambooStateNotFoundException e) { throw new ProjectNotFoundException(e); } } @Override public String getLastBuildId(SoftwareProjectId projectId) throws ProjectNotFoundException, BuildIdNotFoundException { checkConnected(); checkSoftwareProjectId(projectId); try { String id = getProjectKey(projectId); return String.valueOf(bamboo.getLastResultNumber(id)); } catch (BambooBuildNumberNotFoundException e) { throw new BuildIdNotFoundException(e); } } @Override public void close() { connected = false; } @Override public String getDescription(SoftwareProjectId softwareProjectId) throws ProjectNotFoundException { checkConnected(); checkSoftwareProjectId(softwareProjectId); return ""; } @Override public SoftwareProjectId identify(ProjectKey projectKey) throws ProjectNotFoundException { checkConnected(); Preconditions.checkNotNull(projectKey, "projectKey is mandatory"); String name = projectKey.getName(); List<Plan> plans = bamboo.findAllPlans(); for (Plan plan : plans) { String planName = plan.getName(); if (name.equals(planName)) { SoftwareProjectId softwareProjectId = new SoftwareProjectId(plan.getKey()); return softwareProjectId; } } throw new ProjectNotFoundException("Can't identify project with projectKey:" + projectKey); } @Override public Date getEstimatedFinishTime(SoftwareProjectId projectId, String buildId) throws ProjectNotFoundException, BuildNotFoundException { checkConnected(); checkBuildId(buildId); String projectName = getProjectKey(projectId); try { return bamboo.getEstimatedFinishTime(projectName); } catch (BambooPlanNotFoundException e) { throw new ProjectNotFoundException(e); } catch (BambooEstimatedFinishTimeNotFoundException e) { return new Date(); } } private String getProjectKey(SoftwareProjectId projectId) { return projectId.getProjectId(); } private void checkConnected() { Preconditions.checkState(connected, "You must connect your plugin"); } @Override public Map<SoftwareProjectId, String> listSoftwareProjectIds() { checkConnected(); Map<SoftwareProjectId, String> projects = new HashMap<SoftwareProjectId, String>(); List<Plan> plans = bamboo.findAllPlans(); for (Plan plan : plans) { String key = plan.getKey(); SoftwareProjectId softwareProjectId = new SoftwareProjectId(key); projects.put(softwareProjectId, plan.getName()); } return projects; } @Override public List<String> getBuildIds(SoftwareProjectId softwareProjectId) throws ProjectNotFoundException { checkConnected(); checkSoftwareProjectId(softwareProjectId); String planKey = softwareProjectId.getProjectId(); String lastResultNumber; try { lastResultNumber = String.valueOf(bamboo.getLastResultNumber(planKey)); } catch (BambooBuildNumberNotFoundException e) { if (LOG.isDebugEnabled()) { LOG.debug("Can't find builds numbers of software project id : " + softwareProjectId, e); } return new ArrayList<String>(); } return Arrays.asList(lastResultNumber); } @Override public String getMavenId(SoftwareProjectId softwareProjectId) throws ProjectNotFoundException, MavenIdNotFoundException { checkConnected(); throw new MavenIdNotFoundException("Not implemented!"); } @Override public String getName(SoftwareProjectId softwareProjectId) throws ProjectNotFoundException { checkConnected(); checkSoftwareProjectId(softwareProjectId); try { String projectKey = softwareProjectId.getProjectId(); Plan plan = bamboo.findPlan(projectKey); String name = plan.getBuildName(); return name; } catch (BambooPlanNotFoundException e) { throw new ProjectNotFoundException("Can't find name of software project id: " + softwareProjectId); } } @Override public boolean isClosed() { return !connected; } @Override public BuildTime getBuildTime(SoftwareProjectId softwareProjectId, String buildId) throws BuildNotFoundException { checkConnected(); checkSoftwareProjectId(softwareProjectId); checkBuildId(buildId); try { String projectKey = softwareProjectId.getProjectId(); Result bambooResult = bamboo.findResult(projectKey, Integer.valueOf(buildId)); BuildTime buildTime = new BuildTime(); buildTime.setDuration(bambooResult.getBuildDuration()); buildTime.setStartTime(bambooResult.getBuildStartedTime()); return buildTime; } catch (BambooBuildNotFoundException e) { throw new BuildNotFoundException("Can't find build #" + buildId + " of project " + softwareProjectId, e); } } @Override public boolean isProjectDisabled(SoftwareProjectId softwareProjectId) throws ProjectNotFoundException { checkConnected(); checkSoftwareProjectId(softwareProjectId); String planKey = softwareProjectId.getProjectId(); try { Plan plan = bamboo.findPlan(planKey); return !plan.isEnabled(); } catch (BambooPlanNotFoundException e) { throw new ProjectNotFoundException("Can't find plan with software project id: " + softwareProjectId, e); } } @Override public List<Commiter> getBuildCommiters(SoftwareProjectId softwareProjectId, String buildId) throws BuildNotFoundException, ProjectNotFoundException { checkConnected(); checkSoftwareProjectId(softwareProjectId); checkBuildId(buildId); return new ArrayList<Commiter>(); } private void checkBuildId(String buildId) { Preconditions.checkNotNull(buildId, "buildId is mandatory"); } private void checkSoftwareProjectId(SoftwareProjectId softwareProjectId) { Preconditions.checkNotNull(softwareProjectId, "softwareProjectId is mandatory"); } @Override public TestResult analyzeUnitTests(SoftwareProjectId projectId) { checkConnected(); TestResult result = new TestResult(); try { String planKey = projectId.getProjectId(); int buildId = bamboo.getLastResultNumber(planKey); Result findResult = bamboo.findResult(planKey, buildId); int successfulTestCount = findResult.getSuccessfulTestCount(); int failedTestCount = findResult.getFailedTestCount(); result.setFailCount(failedTestCount); result.setPassCount(successfulTestCount); } catch (BambooBuildNumberNotFoundException e) { LOG.warn("Can't analyze unit tests for projectId:" + projectId, e); } catch (BambooBuildNotFoundException e) { LOG.warn("Can't analyze unit tests for projectId:" + projectId, e); } return result; } @Override public TestResult analyzeIntegrationTests(SoftwareProjectId projectId) { checkConnected(); return new TestResult(); } }