From cdc09e1cf1efdaf96dca341700433f94789537cb Mon Sep 17 00:00:00 2001 From: twobiers <22715034+twobiers@users.noreply.github.com> Date: Thu, 29 Aug 2024 17:57:48 +0200 Subject: [PATCH] Enable customization of the publication step --- README.md | 18 ++++++++++++++++++ src/config.ts | 17 +++++++++++++++++ src/definition.ts | 5 +++++ src/gradle.ts | 4 ++-- src/index.ts | 2 +- src/publish.ts | 22 +++++++++++++++++----- src/verify-conditions.ts | 21 +++++++++++++++------ test/src/config.test.ts | 39 +++++++++++++++++++++++++++++++++++++++ test/src/gradle.test.ts | 21 +++++++++++---------- test/src/publish.test.ts | 16 ++++++++++++++++ 10 files changed, 141 insertions(+), 24 deletions(-) create mode 100644 src/config.ts create mode 100644 test/src/config.test.ts create mode 100644 test/src/publish.test.ts diff --git a/README.md b/README.md index 314b455c..b4de3f6c 100644 --- a/README.md +++ b/README.md @@ -46,6 +46,24 @@ This plugin updates `gradle.properties` to bump up project version. If you want }, ``` +## Configure `gradle-semantic-release-plugin` + +The plugin offers some configuration options to customize its default behavior. You can configure your `package.json` like below: + +```json +"release": { + "plugins": [ + [ + "gradle-semantic-release-plugin", + { + "skipPublishing": true, // Decide whether the publication task should run during the execution + "publicationTask": "jib" // Configure a custom publication task + } + ] + ] +}, +``` + # Gradle Properties ## Publish Properties diff --git a/src/config.ts b/src/config.ts new file mode 100644 index 00000000..29e8686f --- /dev/null +++ b/src/config.ts @@ -0,0 +1,17 @@ +import { Signale } from "signale"; +import { PluginConfig } from "./definition"; +import { autoDetectPublicationTask } from "./gradle"; + +export async function getTaskToPublish( + pluginConfig: PluginConfig, + cwd: string, + env: NodeJS.ProcessEnv, + logger: Signale, +) { + const customTask = pluginConfig.publicationTask; + if (customTask) { + return [customTask]; + } + + return autoDetectPublicationTask(cwd, env, logger); +} diff --git a/src/definition.ts b/src/definition.ts index 29708c73..a30d299f 100644 --- a/src/definition.ts +++ b/src/definition.ts @@ -28,3 +28,8 @@ export interface IContext { nextRelease: INextRelease; logger: Signale; } + +export type PluginConfig = { + publicationTask?: string; + skipPublishing?: boolean; +}; diff --git a/src/gradle.ts b/src/gradle.ts index 2e75f7d9..82b03cfe 100644 --- a/src/gradle.ts +++ b/src/gradle.ts @@ -36,7 +36,7 @@ export function getCommand(cwd: string): Promise { * @param {string} cwd the path of current working directory * @return A promise that resolves name of task to publish artifact */ -export function getTaskToPublish( +export function autoDetectPublicationTask( cwd: string, env: NodeJS.ProcessEnv, logger: Signale, @@ -186,12 +186,12 @@ export function buildOptions(env: NodeJS.ProcessEnv): string[] { export function publishArtifact( cwd: string, + task: string[], env: NodeJS.ProcessEnv, logger: Signale, ) { return new Promise(async (resolve, reject) => { const command = getCommand(cwd); - const task = await getTaskToPublish(cwd, env, logger); const options = [...task, "-q"].concat(buildOptions(env)); logger.info(`launching child process with options: ${options.join(" ")}`); const child = spawn(await command, options, { cwd, env }); diff --git a/src/index.ts b/src/index.ts index 8d7f3945..0b3c75b8 100644 --- a/src/index.ts +++ b/src/index.ts @@ -1,5 +1,5 @@ module.exports = { prepare: require("./prepare").default, - publish: require("./publish"), + publish: require("./publish").default, verifyConditions: require("./verify-conditions"), }; diff --git a/src/publish.ts b/src/publish.ts index 87532ea4..1c983c27 100644 --- a/src/publish.ts +++ b/src/publish.ts @@ -1,10 +1,22 @@ -import { IContext } from "./definition"; +import { getTaskToPublish } from "./config"; +import { IContext, PluginConfig } from "./definition"; import { publishArtifact } from "./gradle"; -module.exports = async function publish( - pluginConfig: object, +export default async function publish( + pluginConfig: PluginConfig, context: IContext, ) { const { cwd, env, logger } = context; - await publishArtifact(cwd, env as NodeJS.ProcessEnv, logger); -}; + + if (pluginConfig.skipPublishing) { + return; + } + + const task = await getTaskToPublish( + pluginConfig, + cwd, + env as NodeJS.ProcessEnv, + logger, + ); + await publishArtifact(cwd, task, env as NodeJS.ProcessEnv, logger); +} diff --git a/src/verify-conditions.ts b/src/verify-conditions.ts index 56892db7..93182c1a 100644 --- a/src/verify-conditions.ts +++ b/src/verify-conditions.ts @@ -1,8 +1,9 @@ -import { IContext } from "./definition"; -import { getCommand, getTaskToPublish } from "./gradle"; +import { getTaskToPublish } from "./config"; +import { IContext, PluginConfig } from "./definition"; +import { getCommand } from "./gradle"; module.exports = async function verifyConditions( - pluginConfig: object, + pluginConfig: PluginConfig, context: IContext, ) { const { cwd, env, logger } = context; @@ -10,9 +11,17 @@ module.exports = async function verifyConditions( if (command !== "./gradlew") { throw new Error(`Gradle wrapper not found at ${cwd}`); } - const task = await getTaskToPublish(cwd, env as NodeJS.ProcessEnv, logger); - if (task.length === 0) { - throw new Error("No task found that can publish artifacts"); + + if (!pluginConfig.skipPublishing) { + const task = await getTaskToPublish( + pluginConfig, + cwd, + env as NodeJS.ProcessEnv, + logger, + ); + if (task.length === 0) { + throw new Error("No task found that can publish artifacts"); + } } logger.debug("Verified conditions, and found no problem"); }; diff --git a/test/src/config.test.ts b/test/src/config.test.ts new file mode 100644 index 00000000..027854af --- /dev/null +++ b/test/src/config.test.ts @@ -0,0 +1,39 @@ +import { join } from "path"; +import { cwd } from "process"; +import { Signale } from "signale"; +import { getTaskToPublish } from "../../src/config"; +import { describe, expect, it, jest } from "@jest/globals"; + +describe("Test for config handling", function () { + jest.setTimeout(60000); + describe("getTaskToPublish()", () => { + it("returns 'jib' when custom task is set", async () => { + const gradleProject = join( + cwd(), + "test/project/with-maven-publish-plugin", + ); + const task = await getTaskToPublish( + { + publicationTask: "jib", + }, + gradleProject, + process.env, + new Signale(), + ); + expect(task).toEqual(["jib"]); + }); + it("returns 'publish' when it should auto detect", async () => { + const gradleProject = join( + cwd(), + "test/project/with-maven-publish-plugin", + ); + const task = await getTaskToPublish( + {}, + gradleProject, + process.env, + new Signale(), + ); + expect(task).toEqual(["publish"]); + }); + }); +}); diff --git a/test/src/gradle.test.ts b/test/src/gradle.test.ts index d43c235d..d86b941a 100644 --- a/test/src/gradle.test.ts +++ b/test/src/gradle.test.ts @@ -4,9 +4,9 @@ import { cwd } from "process"; import { sync as rmdir } from "rimraf"; import { Signale } from "signale"; import { + autoDetectPublicationTask, buildOptions, getCommand, - getTaskToPublish, getVersion, publishArtifact, } from "../../src/gradle"; @@ -26,10 +26,10 @@ describe("Test for gradle handling", function () { }); }); - describe("getTaskToPublish()", () => { + describe("autoDetectPublicationTask()", () => { it("returns empty array when there is no task to publish", async () => { const gradleProject = join(cwd(), "test/project/without-plugin"); - const task = await getTaskToPublish( + const task = await autoDetectPublicationTask( gradleProject, process.env, new Signale(), @@ -41,7 +41,7 @@ describe("Test for gradle handling", function () { cwd(), "test/project/with-maven-publish-plugin", ); - const task = await getTaskToPublish( + const task = await autoDetectPublicationTask( gradleProject, process.env, new Signale(), @@ -50,7 +50,7 @@ describe("Test for gradle handling", function () { }); it.skip("returns 'uploadArchives' when there is available legacy publishing method", async () => { const gradleProject = join(cwd(), "test/project/with-legacy-publishing"); - const task = await getTaskToPublish( + const task = await autoDetectPublicationTask( gradleProject, process.env, new Signale(), @@ -59,7 +59,7 @@ describe("Test for gradle handling", function () { }); it("returns 'artifactoryDeploy' when there is available artifactory-plugin", async () => { const gradleProject = join(cwd(), "test/project/with-artifactory-plugin"); - const task = await getTaskToPublish( + const task = await autoDetectPublicationTask( gradleProject, process.env, new Signale(), @@ -71,7 +71,7 @@ describe("Test for gradle handling", function () { cwd(), "test/project/with-plugin-publish-plugin", ); - const task = await getTaskToPublish( + const task = await autoDetectPublicationTask( gradleProject, process.env, new Signale(), @@ -83,7 +83,7 @@ describe("Test for gradle handling", function () { cwd(), "test/project/with-plugin-publish-and-maven-publish", ); - const task = await getTaskToPublish( + const task = await autoDetectPublicationTask( gradleProject, process.env, new Signale(), @@ -92,7 +92,7 @@ describe("Test for gradle handling", function () { }); it("returns 'publishToSonatype' when there is available gradle-nexus", async () => { const gradleProject = join(cwd(), "test/project/with-gradle-nexus"); - const task = await getTaskToPublish( + const task = await autoDetectPublicationTask( gradleProject, process.env, new Signale(), @@ -124,7 +124,8 @@ describe("Test for gradle handling", function () { it("runs 'publish' task", async () => { const gradleProject = join(cwd(), "test/project/with-publish"); - await publishArtifact(gradleProject, process.env, new Signale()); + const task = ["publish"]; + await publishArtifact(gradleProject, task, process.env, new Signale()); const file = join( gradleProject, "build/repo/com/example/project/1.0/project-1.0.jar", diff --git a/test/src/publish.test.ts b/test/src/publish.test.ts new file mode 100644 index 00000000..2b8f6807 --- /dev/null +++ b/test/src/publish.test.ts @@ -0,0 +1,16 @@ +import { describe, expect, it, jest } from "@jest/globals"; +import * as gradle from "../../src/gradle"; +import * as publish from "../../src/publish"; + +describe("publish()", () => { + const publishSpy = jest.spyOn(gradle, "publishArtifact"); + it("will skip publication if configured", () => { + publish.default( + { + skipPublishing: true, + }, + {} as any, + ); + expect(publishSpy).not.toBeCalled(); + }); +});