Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat: add generate from latest tag #372

Open
wants to merge 3 commits into
base: master
Choose a base branch
from
Open
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Next Next commit
feat: add generate from latest tag
  • Loading branch information
pocesar committed Jul 11, 2023
commit 4a08b319dffafe2ed56896d5411ff05b609ee3bd
11 changes: 11 additions & 0 deletions __tests__/util.test.ts
Original file line number Diff line number Diff line change
@@ -52,6 +52,7 @@ describe("util", () => {
input_target_commitish: undefined,
input_discussion_category_name: undefined,
input_generate_release_notes: false,
input_previous_tag: undefined,
})
);
});
@@ -72,6 +73,7 @@ describe("util", () => {
input_target_commitish: undefined,
input_discussion_category_name: undefined,
input_generate_release_notes: false,
input_previous_tag: undefined,
})
);
});
@@ -92,6 +94,7 @@ describe("util", () => {
input_target_commitish: undefined,
input_discussion_category_name: undefined,
input_generate_release_notes: false,
input_previous_tag: undefined,
})
);
});
@@ -125,6 +128,7 @@ describe("util", () => {
input_target_commitish: undefined,
input_discussion_category_name: undefined,
input_generate_release_notes: false,
input_previous_tag: undefined,
}
);
});
@@ -150,6 +154,7 @@ describe("util", () => {
input_target_commitish: "affa18ef97bc9db20076945705aba8c516139abd",
input_discussion_category_name: undefined,
input_generate_release_notes: false,
input_previous_tag: undefined,
}
);
});
@@ -174,6 +179,7 @@ describe("util", () => {
input_target_commitish: undefined,
input_discussion_category_name: "releases",
input_generate_release_notes: false,
input_previous_tag: undefined,
}
);
});
@@ -199,6 +205,7 @@ describe("util", () => {
input_target_commitish: undefined,
input_discussion_category_name: undefined,
input_generate_release_notes: true,
input_previous_tag: undefined,
}
);
});
@@ -227,6 +234,7 @@ describe("util", () => {
input_target_commitish: undefined,
input_discussion_category_name: undefined,
input_generate_release_notes: false,
input_previous_tag: undefined,
}
);
});
@@ -253,6 +261,7 @@ describe("util", () => {
input_target_commitish: undefined,
input_discussion_category_name: undefined,
input_generate_release_notes: false,
input_previous_tag: undefined,
}
);
});
@@ -278,6 +287,7 @@ describe("util", () => {
input_target_commitish: undefined,
input_discussion_category_name: undefined,
input_generate_release_notes: false,
input_previous_tag: undefined,
}
);
});
@@ -302,6 +312,7 @@ describe("util", () => {
input_target_commitish: undefined,
input_discussion_category_name: undefined,
input_generate_release_notes: false,
input_previous_tag: undefined,
}
);
});
4 changes: 4 additions & 0 deletions action.yml
Original file line number Diff line number Diff line change
@@ -43,6 +43,10 @@ inputs:
generate_release_notes:
description: "Whether to automatically generate the name and body for this release. If name is specified, the specified name will be used; otherwise, a name will be automatically generated. If body is specified, the body will be pre-pended to the automatically generated notes."
required: false
previous_tag:
description: "The tag name of the previous release. If not specified, the previous tag will be detected automatically."
required: false
default: ""
append_body:
description: "Append to existing body instead of overwriting it. Default is false."
required: false
2 changes: 1 addition & 1 deletion dist/index.js

Large diffs are not rendered by default.

109 changes: 96 additions & 13 deletions src/github.ts
Original file line number Diff line number Diff line change
@@ -44,7 +44,6 @@ export interface Releaser {
prerelease: boolean | undefined;
target_commitish: string | undefined;
discussion_category_name: string | undefined;
generate_release_notes: boolean | undefined;
}): Promise<{ data: Release }>;

updateRelease(params: {
@@ -58,13 +57,21 @@ export interface Releaser {
draft: boolean | undefined;
prerelease: boolean | undefined;
discussion_category_name: string | undefined;
generate_release_notes: boolean | undefined;
}): Promise<{ data: Release }>;

allReleases(params: {
owner: string;
repo: string;
}): AsyncIterableIterator<{ data: Release[] }>;

getLatestTag(params: {
owner: string;
repo: string;
}): Promise<undefined | string>;

generateReleaseBody(
params: Parameters<GitHub["rest"]["repos"]["generateReleaseNotes"]>[0]
): Promise<string>;
}

export class GitHubReleaser implements Releaser {
@@ -91,9 +98,11 @@ export class GitHubReleaser implements Releaser {
prerelease: boolean | undefined;
target_commitish: string | undefined;
discussion_category_name: string | undefined;
generate_release_notes: boolean | undefined;
}): Promise<{ data: Release }> {
return this.github.rest.repos.createRelease(params);
return this.github.rest.repos.createRelease({
...params,
generate_release_notes: false,
});
}

updateRelease(params: {
@@ -107,9 +116,11 @@ export class GitHubReleaser implements Releaser {
draft: boolean | undefined;
prerelease: boolean | undefined;
discussion_category_name: string | undefined;
generate_release_notes: boolean | undefined;
}): Promise<{ data: Release }> {
return this.github.rest.repos.updateRelease(params);
return this.github.rest.repos.updateRelease({
...params,
generate_release_notes: false,
});
}

allReleases(params: {
@@ -121,6 +132,41 @@ export class GitHubReleaser implements Releaser {
this.github.rest.repos.listReleases.endpoint.merge(updatedParams)
);
}

async getLatestTag(params: {
owner: string;
repo: string;
}): Promise<undefined | string> {
try {
const release = await this.github.rest.repos.getLatestRelease(params);

if (!release?.data) {
return;
}

return release.data.tag_name;
} catch (e) {
console.error(e);

return;
}
}

async generateReleaseBody(
params: Parameters<GitHub["rest"]["repos"]["generateReleaseNotes"]>[0]
): Promise<string> {
try {
const { data } = await this.github.rest.repos.generateReleaseNotes(params);

if (!data.body) {
throw new Error("No release body generated");
}

return data.body;
} catch (e) {
throw e;
}
}
}

export const asset = (path: string): ReleaseAsset => {
@@ -196,8 +242,40 @@ export const release = async (
? config.github_ref.replace("refs/tags/", "")
: "");

const previous_tag = config.input_previous_tag;
const discussion_category_name = config.input_discussion_category_name;
const generate_release_notes = config.input_generate_release_notes;

const latestTag: string | undefined = !previous_tag
? await releaser.getLatestTag({
owner,
repo,
})
: undefined;

if (latestTag) {
console.log(`🏷️ Latest tag related to a release is ${latestTag}`);
} else if (previous_tag) {
console.log(`🏷️ Previous tag is ${previous_tag}`);
}

const tag_name = tag;

let body: string = generate_release_notes
? await releaser.generateReleaseBody({
owner,
repo,
tag_name,
previous_tag_name: previous_tag || latestTag,
})
: "";

if (generate_release_notes && previous_tag || latestTag) {
console.log(`Will generate release notes using ${previous_tag || latestTag} as previous tag`);
}

body = body ? `${body}\n` : "";

try {
// you can't get a an existing draft by tag
// so we must find one in the list of all releases
@@ -232,19 +310,20 @@ export const release = async (
target_commitish = existingRelease.data.target_commitish;
}

const tag_name = tag;
const name = config.input_name || existingRelease.data.name || tag;
// revisit: support a new body-concat-strategy input for accumulating
// body parts as a release gets updated. some users will likely want this while
// others won't previously this was duplicating content for most which
// no one wants
const workflowBody = releaseBody(config) || "";
const existingReleaseBody = existingRelease.data.body || "";
let body: string;

if (config.input_append_body && workflowBody && existingReleaseBody) {
body = existingReleaseBody + "\n" + workflowBody;
console.log('➕ Appending existing release body');
body = body + existingReleaseBody + "\n" + workflowBody;
} else {
body = workflowBody || existingReleaseBody;
console.log(`➕ Using ${workflowBody ? 'workflow body' : 'existing release body'}`);
body = body + (workflowBody || existingReleaseBody);
}

const draft =
@@ -267,14 +346,19 @@ export const release = async (
draft,
prerelease,
discussion_category_name,
generate_release_notes,
});
return release.data;
} catch (error) {
if (error.status === 404) {
const tag_name = tag;
const name = config.input_name || tag;
const body = releaseBody(config);
const workflowBody = releaseBody(config) || "";

if (config.input_append_body && workflowBody) {
console.log('➕ Appending existing release body');
body = body + workflowBody;
}

const draft = config.input_draft;
const prerelease = config.input_prerelease;
const target_commitish = config.input_target_commitish;
@@ -296,7 +380,6 @@ export const release = async (
prerelease,
target_commitish,
discussion_category_name,
generate_release_notes,
});
return release.data;
} catch (error) {
2 changes: 2 additions & 0 deletions src/util.ts
Original file line number Diff line number Diff line change
@@ -19,6 +19,7 @@ export interface Config {
input_discussion_category_name?: string;
input_generate_release_notes?: boolean;
input_append_body?: boolean;
input_previous_tag?: string;
}

export const uploadUrl = (url: string): string => {
@@ -70,6 +71,7 @@ export const parseConfig = (env: Env): Config => {
env.INPUT_DISCUSSION_CATEGORY_NAME || undefined,
input_generate_release_notes: env.INPUT_GENERATE_RELEASE_NOTES == "true",
input_append_body: env.INPUT_APPEND_BODY == "true",
input_previous_tag: env.INPUT_PREVIOUS_TAG?.trim() || undefined,
};
};