Skip to content

Commit

Permalink
Minor Updates (#304)
Browse files Browse the repository at this point in the history
* > Bamboo v7+ Support
> Historical Fixes
> Allure binary download, unzip, and so on was updated
> All libraries was updated to newer versions
> Removed the error when you add the allure task to any plan (only a log message is shown)

Signed-off-by: Manuel Lara <[email protected]>

* > AllureArtifactsManager: Ensure the path URL, avoiding having two backslashes together when filePath is concatenated
> AllureBuildCompleteAction: Fixing Report URL in the executor.json file.
> AllureCommandLineSupport: Increasing timeout to 5 minutes
> AllureReportServlet: Rollback URL Pattern

Signed-off-by: Manuel Lara <[email protected]>

* > AllureBuildCompleteAction: Adding more historical info (trends and so on).

Signed-off-by: Manuel Lara <[email protected]>

* > Customize the logo of each report from each build from the bamboo UI
> Bug: When you try to uncheck an option from Bamboo UI the option is not saved.
> Download Util class we created to download logo and allure binary
> The deprecated logo was changed due to it being confused. (It is not deprecated, it is just not necessary)
> The task description was changed
> Bug: If you add an allure task to your plan the build fails due to API incompatibility

Signed-off-by: Manuel Lara <[email protected]>

* > Bug-fixed: If a plan execution fails the history is missing for the next execution.

Signed-off-by: Manuel Lara <[email protected]>

* > Plan Titles customization
> Allure removed from the title. (it's not customizable)
> A link was created to download the report for evidence in other systems.
> The logo can have other types not only SVG.
> Fix some dependencies conflicts

Signed-off-by: Manuel Lara <[email protected]>

* > Change Version: 2.0, because the change in this version is major.

Signed-off-by: Manuel Lara <[email protected]>

* Revert "> Change Version: 2.0, because the change in this version is major."

This reverts commit d873df7.

* Revert "Revert "> Change Version: 2.0, because the change in this version is major.""

This reverts commit e143ff0.

* > Change Version: 2.0 to 2.0-SNAPSHOT
> amps.version to 8.0.3-89c970d65

Signed-off-by: Manuel Lara <[email protected]>

* update license

Signed-off-by: Manuel Lara <[email protected]>

* > Fixes

Signed-off-by: Manuel Lara <[email protected]>

* > Fixes:
  - Fixed custom logo error with multiple plans same agent.
  - Improved logo customization options with support for base64 URLs and various file extensions.

Signed-off-by: Manuel Lara <[email protected]>

* > Fixes:
  - Fixed custom logo error with multiple plans same agent.
  - Improved logo customization options with support for base64 URLs and various file extensions.

Signed-off-by: Manuel Lara <[email protected]>

* > Fixes:
  - Fixed custom logo error with multiple plans same agent.
  - Improved logo customization options with support for base64 URLs and various file extensions.

Signed-off-by: Manuel Lara <[email protected]>

---------

Signed-off-by: Manuel Lara <[email protected]>
Co-authored-by: Dmitry Baev <[email protected]>
  • Loading branch information
lararojasmr and baev authored Oct 23, 2023
1 parent 6a6dd09 commit 9c8036b
Show file tree
Hide file tree
Showing 24 changed files with 173 additions and 146 deletions.
2 changes: 1 addition & 1 deletion .github/workflows/release.yml
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ name: Release

on:
release:
types: [published]
types: [ published ]

jobs:
build:
Expand Down
14 changes: 7 additions & 7 deletions .mvn/quality-configs/checkstyle/checkstyle.xml
Original file line number Diff line number Diff line change
Expand Up @@ -104,10 +104,10 @@
<module name="PackageDeclaration"/>
<module name="ParameterAssignment"/> <!-- more strict version is FinalParameters -->
<!--<module name="RequireThis"/>-->
<!-- <module name="ReturnCount">-->
<!-- <property name="max" value="5"/>-->
<!-- <property name="maxForVoid" value="3"/>-->
<!-- </module>-->
<!-- <module name="ReturnCount">-->
<!-- <property name="max" value="5"/>-->
<!-- <property name="maxForVoid" value="3"/>-->
<!-- </module>-->
<module name="SimplifyBooleanExpression"/>
<module name="SimplifyBooleanReturn"/>
<module name="StringLiteralEquality"/>
Expand Down Expand Up @@ -136,9 +136,9 @@
<!-- org.springframework.data.util"-->
<!-- />-->
<!-- </module>-->
<!-- <module name="ImportControl">-->
<!-- <property name="file" value="${config_loc}/import-control.xml"/>-->
<!-- </module>-->
<!-- <module name="ImportControl">-->
<!-- <property name="file" value="${config_loc}/import-control.xml"/>-->
<!-- </module>-->
<!--<module name="ImportOrder"/>-->
<module name="RedundantImport"/>
<module name="UnusedImports"/>
Expand Down
3 changes: 2 additions & 1 deletion .mvn/quality-configs/pmd/pmd.xml
Original file line number Diff line number Diff line change
Expand Up @@ -112,7 +112,8 @@
<exclude name="JUnitStaticSuite"/>
<exclude name="LoggerIsNotStaticFinal"/>
<exclude name="MissingSerialVersionUID"/>
<exclude name="NullAssignment"/> <!-- disabled due to false positive for initialization with ternary operator -->
<exclude
name="NullAssignment"/> <!-- disabled due to false positive for initialization with ternary operator -->
<exclude name="StaticEJBFieldShouldBeFinal"/> <!-- earlier j2ee group-->
<exclude name="UseCorrectExceptionLogging"/>
<exclude name="UseLocaleWithCaseConversions"/>
Expand Down
2 changes: 1 addition & 1 deletion .mvn/quality-configs/spotbugs/exclude.xml
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@
you will have to use @NotNull annotation, which contradict with original contract
(actually not, because guava intend weaker semantics). So disable this check to be able to properly
use nullability annotations -->
<Bug pattern="NP_METHOD_PARAMETER_TIGHTENS_ANNOTATION" />
<Bug pattern="NP_METHOD_PARAMETER_TIGHTENS_ANNOTATION"/>
</Match>
<Match>
<!-- Disabled as confusing check (very misleading description) and also not so useful -->
Expand Down
20 changes: 16 additions & 4 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,17 +1,29 @@
## Allure Bamboo Plugin

This repository contains source code of Allure plugin for [Atlassian Bamboo CI](https://www.atlassian.com/software/bamboo). It allows you to generate Allure report from [existing Allure XML files](https://github.com/allure-framework/allure-core/wiki#gathering-information-about-tests).
This repository contains source code of Allure plugin
for [Atlassian Bamboo CI](https://www.atlassian.com/software/bamboo). It allows you to generate Allure report
from [existing Allure XML files](https://github.com/allure-framework/allure-core/wiki#gathering-information-about-tests).

### Building and Installing

#### Short way
Download precompiled JAR from [releases page](https://github.com/allure-framework/allure-bamboo-plugin/releases) and install it manually as described [here](https://confluence.atlassian.com/display/UPM/Installing+add-ons#Installingadd-ons-Installingbyfileupload). We use JDK 1.7+ to compile the plugin so be sure to use Java 1.7+ for running Bamboo.

Download precompiled JAR from [releases page](https://github.com/allure-framework/allure-bamboo-plugin/releases) and
install it manually as
described [here](https://confluence.atlassian.com/display/UPM/Installing+add-ons#Installingadd-ons-Installingbyfileupload).
We use JDK 1.7+ to compile the plugin so be sure to use Java 1.7+ for running Bamboo.

#### Long way
1. Set up Atlassian plugin SDK as described [here](https://developer.atlassian.com/display/DOCS/Set+up+the+Atlassian+Plugin+SDK+and+Build+a+Project).

1. Set up Atlassian plugin SDK as
described [here](https://developer.atlassian.com/display/DOCS/Set+up+the+Atlassian+Plugin+SDK+and+Build+a+Project).
2. Clone this repository
3. Run `$ atlas-run`
4. Access http://localhost:6990/bamboo/ to view development instance of Bamboo
5. Verify that plugin is working as expected
6. Install **target/allure-bamboo-plugin-VERSION.jar** manually as described [here](https://confluence.atlassian.com/display/UPM/Installing+add-ons#Installingadd-ons-Installingbyfileupload).
6. Install **target/allure-bamboo-plugin-VERSION.jar** manually as
described [here](https://confluence.atlassian.com/display/UPM/Installing+add-ons#Installingadd-ons-Installingbyfileupload).

### Configuration and Usage

Please follow the guide on the official Allure docs: https://docs.qameta.io/allure/#_bamboo
3 changes: 2 additions & 1 deletion pom.xml
Original file line number Diff line number Diff line change
Expand Up @@ -234,6 +234,7 @@
<version>${spotless.version}</version>
<configuration>
<encoding>UTF-8</encoding>
<lineEndings>UNIX</lineEndings>
<!-- optional: limit format enforcement to just the files changed by this feature branch -->
<formats>
<!-- you can define as many formats as you want, each is independent -->
Expand Down Expand Up @@ -263,7 +264,7 @@
</includes>
<!-- <removeUnusedImports/> Some bug exists with it-->
<importOrder> <!-- or a custom ordering -->
<order> ,jakarta,javax,java,\#</order>
<order>,jakarta,javax,java,\#</order>
</importOrder>
<licenseHeader>
<file>.mvn/quality-configs/spotless/allure.java.license</file>
Expand Down
56 changes: 28 additions & 28 deletions src/main/java/io/qameta/allure/bamboo/AllureArtifactsManager.java
Original file line number Diff line number Diff line change
Expand Up @@ -147,7 +147,7 @@ Optional<String> getArtifactUrl(final String planKeyString,
.flatMap(rs -> getArtifactHandlerByClassName(
fromCustomData(rs.getCustomBuildData()).getArtifactHandlerClass())
.map(handler -> getArtifactUrl(planKeyString, buildNumber,
filePath, artifactConfig, planResultKey, handler)
filePath, artifactConfig, planResultKey, handler)
)
);
}
Expand All @@ -164,10 +164,10 @@ private String getArtifactUrl(final String planKeyString,
final ArtifactDefinitionContextImpl artifactDef = getAllureArtifactDef();

return Optional.ofNullable(
artifactHandler.getArtifactLinkDataProvider(
mutableArtifact(planResultKey, artifactDef.getName()),
configProvider(artifactConfig)
))
artifactHandler.getArtifactLinkDataProvider(
mutableArtifact(planResultKey, artifactDef.getName()),
configProvider(artifactConfig)
))
.map(lp -> getArtifactUrl(filePath, planResultKey, artifactDef, lp))
.orElse(null);
}
Expand Down Expand Up @@ -326,19 +326,19 @@ Optional<AllureBuildResult> uploadReportArtifacts(final @NotNull ImmutableChain
final String errorMessage = "Unable to publish artifact via " + artifactHandler;
final ArtifactHandlerPublishingResult publishingResult = BambooPluginUtils.callUnsafeCode(
new BambooPluginUtils.NoThrowCallable<ArtifactHandlerPublishingResult>(errorMessage) {
@NotNull
@Override
public ArtifactHandlerPublishingResult call() {
try {
return artifactHandler.publish(
summary.getPlanResultKey(), artifact, artifactPublishingConfig);
} catch (final Exception e) {
LOGGER.error("Failed to publish Allure Report using handler "
+ artifactHandler.getClass().getName(), e);
return ArtifactHandlerPublishingResultImpl.failure();
}
}
});
@NotNull
@Override
public ArtifactHandlerPublishingResult call() {
try {
return artifactHandler.publish(
summary.getPlanResultKey(), artifact, artifactPublishingConfig);
} catch (final Exception e) {
LOGGER.error("Failed to publish Allure Report using handler "
+ artifactHandler.getClass().getName(), e);
return ArtifactHandlerPublishingResultImpl.failure();
}
}
});
if (publishingResult != null) {
publishingResult.setArtifactHandlerKey(artifactHandler.getModuleDescriptor().getCompleteKey());
return Optional.of(allureBuildResult(publishingResult.isSuccessful(), null)
Expand Down Expand Up @@ -451,17 +451,17 @@ private <T extends ArtifactHandler> Optional<T> getArtifactHandlerByClassName(fi
final AtomicReference<Predicate<ModuleDescriptor<T>>> predicate = new AtomicReference<>();
return Optional.ofNullable(className)
.map(clazz -> {
final Class<T> aClass;
try {
aClass = (Class<T>) Class.forName(clazz);
predicate.set(new ModuleOfClassPredicate<>(aClass).and(new EnabledModulePredicate()));

return pluginAccessor.getModules(predicate.get()).stream().findAny().orElse(null);
} catch (ClassNotFoundException e) {
LOGGER.error("Failed to find artifact handler for class name " + className, e);
final Class<T> aClass;
try {
aClass = (Class<T>) Class.forName(clazz);
predicate.set(new ModuleOfClassPredicate<>(aClass).and(new EnabledModulePredicate()));

return pluginAccessor.getModules(predicate.get()).stream().findAny().orElse(null);
} catch (ClassNotFoundException e) {
LOGGER.error("Failed to find artifact handler for class name " + className, e);
}
return null;
}
return null;
}
);
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -125,6 +125,9 @@ public void execute(final @NotNull ImmutableChain chain,
final AllureExecutable allure = allureExecutable.provide(globalConfig, executable)
.orElseThrow(() -> new RuntimeException("Failed to find Allure executable by name " + executable));

// Creating a copy for customize report
final AllureExecutable allureTmp = allure.getCopy();

LOGGER.info("Starting artifacts downloading into {} for {}", artifactsTempDir.getPath(), chain.getName());
final Collection<Path> artifactsPaths = artifactsManager.downloadAllArtifactsTo(
chainResultsSummary, artifactsTempDir, buildConfig.getArtifactName());
Expand All @@ -137,9 +140,9 @@ public void execute(final @NotNull ImmutableChain chain,

// Setting the new logo in the allure libraries before generate the report.
if (globalConfig.isCustomLogoEnabled()) {
allure.setCustomLogo(buildConfig.getCustomLogoUrl());
allureTmp.setCustomLogo(buildConfig.getCustomLogoUrl());
}
allure.generate(artifactsPaths, allureReportDir.toPath());
allureTmp.generate(artifactsPaths, allureReportDir.toPath());
// Setting report name
this.finalizeReport(allureReportDir,
chainExecution.getPlanResultKey().getBuildNumber(), chain.getBuildName());
Expand Down
5 changes: 1 addition & 4 deletions src/main/java/io/qameta/allure/bamboo/AllureBuildConfig.java
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,6 @@
package io.qameta.allure.bamboo;

import org.apache.commons.lang3.StringUtils;
import org.apache.commons.validator.routines.UrlValidator;

import javax.annotation.Nullable;
import java.io.Serializable;
Expand Down Expand Up @@ -49,9 +48,7 @@ private AllureBuildConfig(final String executable,
this.enabled = StringUtils.isEmpty(enabled) ? FALSE : Boolean.parseBoolean(enabled);
this.executable = executable;
this.artifactName = artifactName;
// If the URL is not a valid URL it will be omitted
final UrlValidator urlValidator = new UrlValidator();
this.logoUrl = urlValidator.isValid(logoUrl) ? logoUrl : AllureBuildConfig.DEFAULT_CUSTOM_LOGO_URL;
this.logoUrl = !logoUrl.isEmpty() ? logoUrl : AllureBuildConfig.DEFAULT_CUSTOM_LOGO_URL;
}

static AllureBuildConfig fromContext(final Map<String, String> context) {
Expand Down
12 changes: 6 additions & 6 deletions src/main/java/io/qameta/allure/bamboo/AllureDownloader.java
Original file line number Diff line number Diff line change
Expand Up @@ -79,8 +79,8 @@ private Optional<Path> downloadAllure(final String version) {
return Downloader.download(url, downloadToFile);
} catch (Exception e) {
LOGGER
.warn("Failed to download from {}. Root cause : {}.",
url, e.toString());
.warn("Failed to download from {}. Root cause : {}.",
url, e.toString());
}
}
} catch (Exception e) {
Expand All @@ -91,11 +91,11 @@ private Optional<Path> downloadAllure(final String version) {

private URL[] buildAllureDownloadUrls(final String version) throws MalformedURLException {
final URL gitUrl = fromPath(settingsManager.getSettings().getDownloadBaseUrl())
.path(String.format("%s/allure-%s.zip", version, version))
.build().toURL();
.path(String.format("%s/allure-%s.zip", version, version))
.build().toURL();
final URL mavenUrl = fromPath(settingsManager.getSettings().getDownloadCliBaseUrl())
.path(String.format("allure-commandline/%s/allure-commandline-%s.zip", version, version))
.build().toURL();
.path(String.format("allure-commandline/%s/allure-commandline-%s.zip", version, version))
.build().toURL();
return new URL[]{gitUrl, mavenUrl};
}
}
29 changes: 25 additions & 4 deletions src/main/java/io/qameta/allure/bamboo/AllureExecutable.java
Original file line number Diff line number Diff line change
Expand Up @@ -25,15 +25,15 @@
import javax.annotation.Nonnull;
import java.io.File;
import java.io.IOException;
import java.net.URL;
import java.nio.file.Path;
import java.util.Collection;
import java.util.LinkedList;
import java.util.regex.Pattern;

import static java.nio.file.Files.createTempDirectory;
import static java.util.Arrays.asList;
import static java.util.stream.Collectors.toList;
import static javax.ws.rs.core.UriBuilder.fromPath;
import static org.apache.commons.io.FileUtils.copyDirectoryToDirectory;

class AllureExecutable {

Expand Down Expand Up @@ -87,11 +87,10 @@ public void setCustomLogo(final String logoUrl) {
objectMapper.writeValue(configFile, ap);
}
//Setting new Logo
final URL srcLogoUrl = fromPath(logoUrl).build().toURL();
FileStringReplacer.replaceInFile(logoPluginFolder.resolve(cssFileName),
Pattern.compile("url\\('.+'\\)",
Pattern.CASE_INSENSITIVE | Pattern.MULTILINE | Pattern.COMMENTS),
"url(" + srcLogoUrl.toString() + ")"
"url(" + logoUrl + ")"
);

// aligning logo to center
Expand All @@ -100,6 +99,12 @@ public void setCustomLogo(final String logoUrl) {
Pattern.CASE_INSENSITIVE | Pattern.MULTILINE | Pattern.COMMENTS),
"center"
);
// fit logo to area
FileStringReplacer.replaceInFile(logoPluginFolder.resolve(cssFileName),
Pattern.compile("(?<=\\s )!important;",
Pattern.CASE_INSENSITIVE | Pattern.MULTILINE | Pattern.COMMENTS),
"!important; background-size: contain !important;"
);
// removing margin
FileStringReplacer.replaceInFile(logoPluginFolder.resolve(cssFileName),
Pattern.compile("10px",
Expand All @@ -113,6 +118,22 @@ public void setCustomLogo(final String logoUrl) {
}
}

public AllureExecutable getCopy() throws IOException {
final String binary = this.cmdPath.getFileName().toString();
final String binFolder = this.cmdPath.getParent().getFileName().toString();
final Path rootPath = this.cmdPath.getParent().getParent();
final Path rootFolderName = rootPath.getFileName();
final Path copyPath = createTempDirectory(rootFolderName.toString());
copyDirectoryToDirectory(rootPath.toFile(), copyPath.toFile());

return new AllureExecutable(copyPath
.resolve(rootFolderName.toString())
.resolve(binFolder)
.resolve(binary),
this.cmdLine
);
}

Path getCmdPath() {
return cmdPath;
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -70,7 +70,7 @@ Optional<AllureExecutable> provide(final boolean isDownloadEnabled, final String
} else if (isDownloadEnabled) {
final Matcher nameMatcher = EXEC_NAME_PATTERN.matcher(executableName);
return allureDownloader.downloadAndExtractAllureTo(allureHomeSubDir,
nameMatcher.matches() ? nameMatcher.group(1) : DEFAULT_VERSION)
nameMatcher.matches() ? nameMatcher.group(1) : DEFAULT_VERSION)
.map(path -> executable).orElse(null);
}
return null;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -100,7 +100,7 @@ private void setResponseHeaders(final HttpServletResponse response,
final URI file = new URL(fileUrl).toURI();
final String mimeType = Optional.ofNullable(getServletContext().getMimeType(fileUrl))
.orElse(Files.probeContentType(Paths.get(file.getPath()))
);
);
final String charsetPostfix = Stream.of("application", "text")
.anyMatch(mimeType::contains) ? ";charset=utf-8" : "";
response.setHeader(CONTENT_TYPE, mimeType + charsetPostfix);
Expand Down Expand Up @@ -152,7 +152,7 @@ private void uploadResultWasNotSuccess(final HttpServletResponse response,
final String errorMessage = isEmpty(uploadResult.getFailureDetails())
? "Unknown error has occurred during Allure Build. Please refer the server logs for details."
: "Something went wrong with Allure Report generation. Here are some details: \n"
+ uploadResult.getFailureDetails();
+ uploadResult.getFailureDetails();
try {
response.setHeader(CONTENT_TYPE, "text/plain");
response.setHeader("Content-Length", String.valueOf(errorMessage.length()));
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -84,7 +84,7 @@ void addDefaultAllureExecutableCapability() {
final CapabilityImpl capability = new CapabilityImpl(key, DEFAULT_PATH);
capSet.addCapability(capability);
capabilitySetManager.saveCapabilitySet(capSet);
});
});
}

@NotNull
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,6 @@ public class Statistic extends AbstractSummary {

/**
* No args constructor for use in serialization.
*
*/
public Statistic() {
// empty
Expand Down
Loading

0 comments on commit 9c8036b

Please sign in to comment.