From 2131efcdc4787af86e5e13078753215f3cb74117 Mon Sep 17 00:00:00 2001 From: Marcin Grzejszczak Date: Thu, 20 Apr 2017 14:51:46 +0200 Subject: [PATCH] Added the ability to run a single step without skipping fixes #9 --- README.adoc | 32 ++- .../asciidoc/spring-cloud-release-tools.adoc | 32 ++- .../cloud/release/internal/Releaser.java | 29 ++- .../cloud/release/internal/ReleaserTests.java | 15 ++ .../internal/spring/SpringReleaser.java | 206 +++++++++++++----- .../internal/spring/AcceptanceTests.java | 52 ++++- 6 files changed, 284 insertions(+), 82 deletions(-) diff --git a/README.adoc b/README.adoc index 2f118d67..745f876a 100644 --- a/README.adoc +++ b/README.adoc @@ -58,6 +58,32 @@ The application will start running from your working directory. TIP: It is important that you clone the repository you are going to release using SSH in order for the `releaser` to be able to push tags and commit changes automatically. +You will see text similar to this one + +[source] +---- +=== WHAT DO YOU WANT TO DO? === + +0) Perform a full release of this project without interruptions +1) Perform a full release of this project in a verbose mode (you'll be asked about skipping steps) +2) Update poms with versions from Spring Cloud Release +3) Build the project +4) Commit, tag and push the tag +5) Deploy the artifacts to Artifactory +6) Publish the docs +7) Go back to snapshots and bump originalVersion by patch +8) Push the commits +9) Close the milestone at Github +10) Create email / tweet etc. templates + + +You can press 'q' to quit +---- + +Just pick a number and continue! Pick either a full release or single steps. + +TIP: Read before picking a number cause it might have changed between tool releases ;) + === Project options - `releaser.fixed-versions` - A String to String mapping of manually set versions. E.g. `"spring-cloud-cli" -> "1.0.0.RELEASE"` will set @@ -88,11 +114,13 @@ folder and run your application like this: [source,bash] ---- -$ mkdir -p target -$ wget http://repo.spring.io/libs-milestone/org/springframework/cloud/internal/spring-cloud-release-tools-spring/1.0.0.M1/spring-cloud-release-tools-spring-1.0.0.M1.jar -O target/spring-cloud-release-tools-spring-1.0.0.M1.jar +$ wget http://repo.spring.io/libs-milestone/org/springframework/cloud/internal/spring-cloud-release-tools-spring/1.0.0.M1/spring-cloud-release-tools-spring-1.0.0.M1.jar -O ../spring-cloud-release-tools-spring-1.0.0.M1.jar $ java -jar target/spring-cloud-release-tools-spring-1.0.0.M1.jar --spring.config.name=releaser ---- +TIP: Notice that we're downloading the jar to a parent folder, not to `target`. That's because `target` get cleaned +during the build process + ==== Specifying A Branch By deafult the releaser will default to using the `master` branch of `spring-cloud-release`. diff --git a/docs/src/main/asciidoc/spring-cloud-release-tools.adoc b/docs/src/main/asciidoc/spring-cloud-release-tools.adoc index 5b7585b0..db023e1c 100644 --- a/docs/src/main/asciidoc/spring-cloud-release-tools.adoc +++ b/docs/src/main/asciidoc/spring-cloud-release-tools.adoc @@ -48,6 +48,32 @@ The application will start running from your working directory. TIP: It is important that you clone the repository you are going to release using SSH in order for the `releaser` to be able to push tags and commit changes automatically. +You will see text similar to this one + +[source] +---- +=== WHAT DO YOU WANT TO DO? === + +0) Perform a full release of this project without interruptions +1) Perform a full release of this project in a verbose mode (you'll be asked about skipping steps) +2) Update poms with versions from Spring Cloud Release +3) Build the project +4) Commit, tag and push the tag +5) Deploy the artifacts to Artifactory +6) Publish the docs +7) Go back to snapshots and bump originalVersion by patch +8) Push the commits +9) Close the milestone at Github +10) Create email / tweet etc. templates + + +You can press 'q' to quit +---- + +Just pick a number and continue! Pick either a full release or single steps. + +TIP: Read before picking a number cause it might have changed between tool releases ;) + === Project options - `releaser.fixed-versions` - A String to String mapping of manually set versions. E.g. `"spring-cloud-cli" -> "1.0.0.RELEASE"` will set @@ -78,11 +104,13 @@ folder and run your application like this: [source,bash] ---- -$ mkdir -p target -$ wget http://repo.spring.io/libs-milestone/org/springframework/cloud/internal/spring-cloud-release-tools-spring/1.0.0.M1/spring-cloud-release-tools-spring-1.0.0.M1.jar -O target/spring-cloud-release-tools-spring-1.0.0.M1.jar +$ wget http://repo.spring.io/libs-milestone/org/springframework/cloud/internal/spring-cloud-release-tools-spring/1.0.0.M1/spring-cloud-release-tools-spring-1.0.0.M1.jar -O ../spring-cloud-release-tools-spring-1.0.0.M1.jar $ java -jar target/spring-cloud-release-tools-spring-1.0.0.M1.jar --spring.config.name=releaser ---- +TIP: Notice that we're downloading the jar to a parent folder, not to `target`. That's because `target` get cleaned +during the build process + ==== Specifying A Branch By deafult the releaser will default to using the `master` branch of `spring-cloud-release`. diff --git a/spring-cloud-release-tools-core/src/main/java/org/springframework/cloud/release/internal/Releaser.java b/spring-cloud-release-tools-core/src/main/java/org/springframework/cloud/release/internal/Releaser.java index 7769e923..27020c47 100644 --- a/spring-cloud-release-tools-core/src/main/java/org/springframework/cloud/release/internal/Releaser.java +++ b/spring-cloud-release-tools-core/src/main/java/org/springframework/cloud/release/internal/Releaser.java @@ -35,11 +35,10 @@ public class Releaser { return this.projectPomUpdater.retrieveVersionsFromSCRelease(); } - public ProjectVersion updateProjectFromScRelease(File project, Projects versions) { + public void updateProjectFromScRelease(File project, Projects versions) { this.projectPomUpdater.updateProjectFromSCRelease(project, versions); ProjectVersion changedVersion = new ProjectVersion(project); log.info("\n\nProject was successfully updated to [{}]", changedVersion); - return changedVersion; } public void buildProject() { @@ -62,9 +61,13 @@ public class Releaser { log.info("\nThe docs were published successfully"); } - public void rollbackReleaseVersion(File project, ProjectVersion originalVersion, ProjectVersion changedVersion) { - this.projectGitUpdater.revertChangesIfApplicable(project, changedVersion); - if ((changedVersion.isRelease() || changedVersion.isServiceRelease()) && originalVersion.isSnapshot()) { + public void rollbackReleaseVersion(File project, ProjectVersion originalVersion, ProjectVersion scReleaseVersion) { + if (scReleaseVersion.isSnapshot()) { + log.info("\nWon't rollback a snapshot version"); + return; + } + this.projectGitUpdater.revertChangesIfApplicable(project, scReleaseVersion); + if ((scReleaseVersion.isRelease() || scReleaseVersion.isServiceRelease()) && originalVersion.isSnapshot()) { this.projectBuilder.bumpVersions(originalVersion.bumpedVersion()); this.projectGitUpdater.commitAfterBumpingVersions(project, originalVersion); log.info("\nSuccessfully reverted the commit and bumped snapshot versions"); @@ -79,6 +82,10 @@ public class Releaser { } public void closeMilestone(ProjectVersion releaseVersion) { + if (releaseVersion.isSnapshot()) { + log.info("\nWon't close a milestone for a SNAPSHOT version"); + return; + } this.projectGitUpdater.closeMilestone(releaseVersion); log.info("\nSuccessfully closed milestone"); } @@ -86,18 +93,18 @@ public class Releaser { public void createEmail(ProjectVersion releaseVersion) { if (releaseVersion.isSnapshot()) { log.info("\nWon't create email template for a SNAPSHOT version"); - } else { - File email = this.templateGenerator.email(); - log.info("\nSuccessfully created email template at location [{}]", email); + return; } + File email = this.templateGenerator.email(); + log.info("\nSuccessfully created email template at location [{}]", email); } public void createBlog(ProjectVersion releaseVersion, Projects projects) { if (releaseVersion.isSnapshot()) { log.info("\nWon't create blog template for a SNAPSHOT version"); - } else { - File blog = this.templateGenerator.blog(projects); - log.info("\nSuccessfully created blog template at location [{}]", blog); + return; } + File blog = this.templateGenerator.blog(projects); + log.info("\nSuccessfully created blog template at location [{}]", blog); } } diff --git a/spring-cloud-release-tools-core/src/test/java/org/springframework/cloud/release/internal/ReleaserTests.java b/spring-cloud-release-tools-core/src/test/java/org/springframework/cloud/release/internal/ReleaserTests.java index 52dea902..66014e73 100644 --- a/spring-cloud-release-tools-core/src/test/java/org/springframework/cloud/release/internal/ReleaserTests.java +++ b/spring-cloud-release-tools-core/src/test/java/org/springframework/cloud/release/internal/ReleaserTests.java @@ -17,6 +17,7 @@ import org.springframework.cloud.release.internal.pom.ProjectVersion; import org.springframework.cloud.release.internal.project.ProjectBuilder; import static org.mockito.BDDMockito.then; +import static org.mockito.Matchers.any; import static org.mockito.Matchers.anyString; import static org.mockito.Mockito.never; @@ -80,4 +81,18 @@ public class ReleaserTests { then(this.templateGenerator).should().email(); } + @Test + public void should_not_close_milestone_for_snapshots() throws Exception { + this.releaser.closeMilestone(new ProjectVersion("original", "1.0.0.BUILD-SNAPSHOT")); + + then(this.projectGitUpdater).should(never()).closeMilestone(any(ProjectVersion.class)); + } + + @Test + public void should_not_rollback_for_snapshots() throws Exception { + this.releaser.rollbackReleaseVersion(null, null, new ProjectVersion("original", "1.0.0.BUILD-SNAPSHOT")); + + then(this.projectGitUpdater).should(never()).revertChangesIfApplicable(any(File.class), any(ProjectVersion.class)); + } + } \ No newline at end of file diff --git a/spring-cloud-release-tools-spring/src/main/java/org/springframework/cloud/release/internal/spring/SpringReleaser.java b/spring-cloud-release-tools-spring/src/main/java/org/springframework/cloud/release/internal/spring/SpringReleaser.java index 34928dca..8ca3018b 100644 --- a/spring-cloud-release-tools-spring/src/main/java/org/springframework/cloud/release/internal/spring/SpringReleaser.java +++ b/spring-cloud-release-tools-spring/src/main/java/org/springframework/cloud/release/internal/spring/SpringReleaser.java @@ -2,6 +2,10 @@ package org.springframework.cloud.release.internal.spring; import java.io.File; import java.lang.invoke.MethodHandles; +import java.util.List; +import java.util.function.Consumer; +import java.util.stream.Collectors; +import java.util.stream.Stream; import org.slf4j.Logger; import org.slf4j.LoggerFactory; @@ -10,6 +14,8 @@ import org.springframework.cloud.release.internal.ReleaserProperties; import org.springframework.cloud.release.internal.pom.ProjectVersion; import org.springframework.cloud.release.internal.pom.Projects; +import static org.springframework.cloud.release.internal.spring.Task.task; + /** * Releaser that gets input from console * @@ -18,10 +24,6 @@ import org.springframework.cloud.release.internal.pom.Projects; public class SpringReleaser { private static final Logger log = LoggerFactory.getLogger(MethodHandles.lookup().lookupClass()); - private static final String MSG = "'q' to quit and 's' to skip\n\n"; - private static final String SKIP = "s"; - private static final String QUIT = "q"; - private final Releaser releaser; private final ReleaserProperties properties; @@ -30,80 +32,168 @@ public class SpringReleaser { this.properties = properties; } + private final List TASKS = Stream.of( + task("UPDATING POMS", + "Update poms with versions from Spring Cloud Release", + args -> args.releaser.updateProjectFromScRelease(args.project, args.projects)), + task("BUILD PROJECT", + "Build the project", + args -> args.releaser.buildProject()), + task("COMMITTING (ALL) AND PUSHING TAGS (NON-SNAPSHOTS)", + "Commit, tag and push the tag", + args -> args.releaser.commitAndPushTags(args.project, args.versionFromScRelease)), + task("ARTIFACT DEPLOYMENT", + "Deploy the artifacts to Artifactory", + args -> args.releaser.deploy()), + task("PUBLISHING DOCS", + "Publish the docs", + args -> args.releaser.publishDocs(args.versionFromScRelease)), + task("REVERTING CHANGES & BUMPING VERSION (RELEASE ONLY)", + "Go back to snapshots and bump originalVersion by patch", + args -> args.releaser.rollbackReleaseVersion(args.project, args.originalVersion, args.versionFromScRelease)), + task("PUSHING CHANGES", + "Push the commits", + args -> args.releaser.pushCurrentBranch(args.project)), + task("CLOSING MILESTONE", + "Close the milestone at Github", + args -> args.releaser.closeMilestone(args.versionFromScRelease)), + task("CREATING TEMPLATES", + "Create email / tweet etc. templates", + args -> { + args.releaser.createEmail(args.versionFromScRelease); + args.releaser.createBlog(args.versionFromScRelease, args.projects); + }) + ).collect(Collectors.toList()); + + private final List COMPOSITE_TASKS = Stream.of( + task("FULL RELEASE", + "Perform a full release of this project without interruptions", + args -> TASKS.forEach(task -> task.execute(args))), + task("FULL VERBOSE RELEASE", + "Perform a full release of this project in a verbose mode (you'll be asked about skipping steps)", + args -> TASKS.forEach(task -> task.execute(args))) + ).collect(Collectors.toList()); + + private final List ALL_TASKS = Stream.of( + COMPOSITE_TASKS, + TASKS + ).flatMap(List::stream).collect(Collectors.toList()); + public void release() { - log.info("\n\n\n=== RETRIEVING VERSIONS ===\n\nWill clone Spring Cloud Release" - + " to retrieve all versions for the branch [{}]", this.properties.getPom().getBranch()); + log.info(buildOptionsText().toString()); + printVersionRetreival(); String workingDir = this.properties.getWorkingDir(); File project = new File(workingDir); ProjectVersion originalVersion = new ProjectVersion(project); Projects projects = this.releaser.retrieveVersionsFromSCRelease(); ProjectVersion versionFromScRelease = projects.forFile(project); - log.info("\n\n\n=== UPDATING POMS ===\n\nWill run the application " - + "for root folder [{}]. \n\nPress ENTER to continue {}", workingDir, MSG); - boolean skipPoms = skipStep(); - if (!skipPoms) { - versionFromScRelease = this.releaser.updateProjectFromScRelease(project, projects); + int chosenOption = chosenOption(); + log.info("\n\n\nYou chose [{}]: [{}]\n\n\n", chosenOption, ALL_TASKS.get(chosenOption).description); + boolean verbose = chosenOption == 1; + Task task = taskFromOption(chosenOption); + Args args = new Args(this.releaser, project, projects, originalVersion, versionFromScRelease, + this.properties, verbose); + task.consumer.accept(args); + } + + private StringBuilder buildOptionsText() { + StringBuilder msg = new StringBuilder(); + msg.append("\n\n\n=== WHAT DO YOU WANT TO DO? ===\n\n"); + for (int i = 0; i < ALL_TASKS.size(); i++) { + msg.append(i).append(") ").append(ALL_TASKS.get(i).description).append("\n"); } - log.info("\n\n\n=== BUILD PROJECT ===\n\nPress ENTER to build the project {}", MSG); - boolean skipBuild = skipStep(); - if (!skipBuild) { - this.releaser.buildProject(); + msg.append("\n\n").append("You can press 'q' to quit\n\n"); + return msg; + } + + private void printVersionRetreival() { + log.info("\n\n\n=== RETRIEVING VERSIONS ===\n\nWill clone Spring Cloud Release" + + " to retrieve all versions for the branch [{}]", this.properties.getPom().getBranch()); + } + + private Task taskFromOption(int option) { + return ALL_TASKS.get(option); + } + + int chosenOption() { + String input = System.console().readLine(); + switch (input.toLowerCase()) { + case "q": + System.exit(0); + default: + return Integer.parseInt(input); } - log.info("\n\n\n=== COMMITTING (ALL) AND PUSHING TAGS (NON-SNAPSHOTS) ===\n\nPress ENTER to commit, tag and push the tag {}", MSG); - boolean skipCommit = skipStep(); - if (!skipCommit) { - this.releaser.commitAndPushTags(project, versionFromScRelease); - } - log.info("\n\n\n=== ARTIFACT DEPLOYMENT ===\n\nPress ENTER to deploy the artifacts {}", MSG); - boolean skipDeployment = skipStep(); - if (!skipDeployment) { - this.releaser.deploy(); - } - log.info("\n\n\n=== PUBLISHING DOCS ===\n\nPress ENTER to publish the docs {}", MSG); - boolean skipDocs = skipStep(); - if (!skipDocs) { - this.releaser.publishDocs(versionFromScRelease); - } - if (!versionFromScRelease.isSnapshot()) { - log.info("\n\n\n=== REVERTING CHANGES & BUMPING VERSION (RELEASE ONLY)===\n\nPress ENTER to go " - + "back to snapshots and bump originalVersion by patch {}", MSG); - boolean skipRevert = skipStep(); - if (!skipRevert) { - this.releaser.rollbackReleaseVersion(project, originalVersion, versionFromScRelease); - } - } - log.info("\n\n\n=== PUSHING CHANGES===\n\nPress ENTER to push the commits {}", MSG); - boolean skipPush = skipStep(); - if (!skipPush) { - this.releaser.pushCurrentBranch(project); - } - if (!versionFromScRelease.isSnapshot()) { - log.info("\n\n\n=== CLOSING MILESTONE===\n\nPress ENTER to close the milestone at Github {}", MSG); - boolean skipMilestone = skipStep(); - if (!skipMilestone) { - this.releaser.closeMilestone(versionFromScRelease); - } - } - if (!versionFromScRelease.isSnapshot()) { - log.info("\n\n\n=== CREATING TEMPLATES===\n\nPress ENTER to create email / tweet etc. templates {}", MSG); - boolean skipTemplates = skipStep(); - if (!skipTemplates) { - this.releaser.createEmail(versionFromScRelease); - this.releaser.createBlog(versionFromScRelease, projects); + } +} + +class Task { + + private static final Logger log = LoggerFactory.getLogger(MethodHandles.lookup().lookupClass()); + private static final String MSG = "'q' to quit and 's' to skip\n\n"; + + final String header; + final String description; + final Consumer consumer; + + Task(String header, String description, Consumer consumer) { + this.header = header; + this.description = description; + this.consumer = consumer; + } + + void execute(Args args) { + boolean verbose = args.verbose; + printLog(verbose); + if (verbose) { + boolean skipStep = skipStep(); + if (!skipStep) { + consumer.accept(args); } + } else { + consumer.accept(args); } } + private void printLog(boolean shouldSkip) { + log.info("\n\n\n=== {} ===\n\n{} {}\n\n", header, description, shouldSkip ? MSG : ""); + } + boolean skipStep() { String input = System.console().readLine(); switch (input.toLowerCase()) { - case SKIP: + case "s": return true; - case QUIT: + case "q": System.exit(0); return true; default: return false; } } + + static Task task(String header, String description, Consumer function) { + return new Task(header, description, function); + } } + +class Args { + final Releaser releaser; + final File project; + final Projects projects; + final ProjectVersion originalVersion; + final ProjectVersion versionFromScRelease; + final ReleaserProperties properties; + final boolean verbose; + + Args(Releaser releaser, File project, Projects projects, ProjectVersion originalVersion, + ProjectVersion versionFromScRelease, ReleaserProperties properties, + boolean verbose) { + this.releaser = releaser; + this.project = project; + this.projects = projects; + this.originalVersion = originalVersion; + this.versionFromScRelease = versionFromScRelease; + this.properties = properties; + this.verbose = verbose; + } +} \ No newline at end of file diff --git a/spring-cloud-release-tools-spring/src/test/java/org/springframework/cloud/release/internal/spring/AcceptanceTests.java b/spring-cloud-release-tools-spring/src/test/java/org/springframework/cloud/release/internal/spring/AcceptanceTests.java index a7d8ea7e..6daea1ac 100644 --- a/spring-cloud-release-tools-spring/src/test/java/org/springframework/cloud/release/internal/spring/AcceptanceTests.java +++ b/spring-cloud-release-tools-spring/src/test/java/org/springframework/cloud/release/internal/spring/AcceptanceTests.java @@ -7,7 +7,6 @@ import java.nio.file.Files; import java.util.Iterator; import org.apache.maven.model.Model; -import org.assertj.core.api.BDDAssertions; import org.eclipse.jgit.api.errors.GitAPIException; import org.eclipse.jgit.revwalk.RevCommit; import org.junit.Before; @@ -16,7 +15,6 @@ import org.junit.Test; import org.junit.rules.TemporaryFolder; import org.springframework.cloud.release.internal.Releaser; import org.springframework.cloud.release.internal.ReleaserProperties; -import org.springframework.cloud.release.internal.template.TemplateGenerator; import org.springframework.cloud.release.internal.git.GitTestUtils; import org.springframework.cloud.release.internal.git.ProjectGitUpdater; import org.springframework.cloud.release.internal.pom.ProjectPomUpdater; @@ -24,6 +22,7 @@ import org.springframework.cloud.release.internal.pom.ProjectVersion; import org.springframework.cloud.release.internal.pom.TestPomReader; import org.springframework.cloud.release.internal.pom.TestUtils; import org.springframework.cloud.release.internal.project.ProjectBuilder; +import org.springframework.cloud.release.internal.template.TemplateGenerator; import org.springframework.util.FileSystemUtils; import static org.assertj.core.api.BDDAssertions.then; @@ -105,6 +104,27 @@ public class AcceptanceTests { .contains("I am pleased to announce that the Release Candidate 1 (RC1)"); } + @Test + public void should_generate_templates_only() throws Exception { + File origin = GitTestUtils.clonedProject(this.tmp.newFolder(), this.springCloudConsulProject); + pomVersionIsEqualTo(origin, "1.2.0.BUILD-SNAPSHOT"); + pomParentVersionIsEqualTo(origin, "1.2.0.BUILD-SNAPSHOT"); + File project = GitTestUtils.clonedProject(this.tmp.newFolder(), tmpFile("spring-cloud-consul")); + GitTestUtils.setOriginOnProjectToTmp(origin, project); + SpringReleaser releaser = templateOnlyReleaser(project, "Dalston.RC1", "1.2.0.RC1"); + + releaser.release(); + + then(this.gitUpdater.executed).isFalse(); + then(emailTemplate()).exists(); + then(emailTemplateContents()) + .contains("Spring Cloud Dalston.RC1 available") + .contains("Spring Cloud Dalston RC1 Train release"); + then(blogTemplate()).exists(); + then(blogTemplateContents()) + .contains("I am pleased to announce that the Release Candidate 1 (RC1)"); + } + private Iterable listOfCommits(File project) throws GitAPIException { return GitTestUtils.openGitProject(project).log().call(); } @@ -132,8 +152,7 @@ public class AcceptanceTests { } private void tagIsPresentInOrigin(File origin, String expectedTag) throws GitAPIException { - BDDAssertions - .then(GitTestUtils.openGitProject(origin).tagList() + then(GitTestUtils.openGitProject(origin).tagList() .call().iterator().next().getName()).endsWith(expectedTag); } @@ -159,6 +178,25 @@ public class AcceptanceTests { private SpringReleaser releaser(File projectFile, String branch, String expectedVersion) throws Exception { ReleaserProperties properties = releaserProperties(projectFile, branch); + Releaser releaser = defaultReleaser(expectedVersion, properties); + return new SpringReleaser(releaser, properties) { + @Override int chosenOption() { + return 0; + } + }; + } + + private SpringReleaser templateOnlyReleaser(File projectFile, String branch, String expectedVersion) throws Exception { + ReleaserProperties properties = releaserProperties(projectFile, branch); + Releaser releaser = defaultReleaser(expectedVersion, properties); + return new SpringReleaser(releaser, properties) { + @Override int chosenOption() { + return 10; + } + }; + } + + private Releaser defaultReleaser(String expectedVersion, ReleaserProperties properties) throws Exception { ProjectPomUpdater pomUpdater = new ProjectPomUpdater(properties); ProjectBuilder projectBuilder = new ProjectBuilder(properties, pomUpdater); TestProjectGitUpdater gitUpdater = new TestProjectGitUpdater(properties, @@ -167,11 +205,7 @@ public class AcceptanceTests { Releaser releaser = new Releaser(pomUpdater, projectBuilder, gitUpdater, templateGenerator); this.gitUpdater = gitUpdater; - return new SpringReleaser(releaser, properties) { - @Override boolean skipStep() { - return false; - } - }; + return releaser; } private ReleaserProperties releaserProperties(File project, String branch) throws URISyntaxException {