Skip to content

Commit

Permalink
🚧Create release workflow (#240)
Browse files Browse the repository at this point in the history
* Start work for issue #201

* config: replace deno check with deno check command

* refactor: update code to meet coding standards

* ci: remove unnecessary env vars

* ci: create scripts for release workflow

* config: add item to gitignore for script output during dev testing

* ci: improve build status check workflow

* config: improve deno tasks

* ci: create release workflow

* ci: update all setup deno actions to version 2
  • Loading branch information
CalvinWilkinson committed Oct 10, 2024
1 parent ca3e15f commit f4afdd6
Show file tree
Hide file tree
Showing 42 changed files with 565 additions and 329 deletions.
96 changes: 0 additions & 96 deletions .github/internal-cicd/scripts/deno-check.ts

This file was deleted.

35 changes: 35 additions & 0 deletions .github/internal-cicd/scripts/get-validate-version.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
import getEnvVar from "../../../cicd/core/GetEnvVar.ts";
import { Utils } from "../../../cicd/core/Utils.ts";
import DenoConfig from "../../../deno.json" with { type: "json" };

const scriptFileName = new URL(import.meta.url).pathname.split("/").pop();

if (Utils.isNothing(DenoConfig.version)) {
Utils.printAsGitHubError(`The Deno version is not defined in the deno.json file.\n${scriptFileName}`);
Deno.exit(1);
}

const githubOutputFilePath = getEnvVar("GITHUB_OUTPUT", scriptFileName);

const version = (DenoConfig.version.startsWith("v")
? DenoConfig.version.trim().toLocaleLowerCase()
: `v${DenoConfig.version}`).trim().toLocaleLowerCase();

const versionRegex = /^v([1-9]\d*|0)\.([1-9]\d*|0)\.([1-9]\d*|0)(-preview\.([1-9]\d*))?$/gm;

if (!versionRegex.test(version)) {
Utils.printAsGitHubError(`The version '${version}' is not valid.\n\t\n${scriptFileName}`);
Deno.exit(1);
}

try {
Deno.writeTextFileSync(githubOutputFilePath, `version=${version}\n`, { append: true });
} catch (error) {
if (error instanceof Error) {
Utils.printAsGitHubError(`${error.message}\n${scriptFileName}`);
} else {
Utils.printAsGitHubError(`An unknown error occurred.\n${scriptFileName}`);
}

Deno.exit(1);
}
1 change: 0 additions & 1 deletion .github/internal-cicd/scripts/update-csharp-proj.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,4 +10,3 @@ const token = getEnvVar("GITHUB_TOKEN", scriptFileName);
const service = new CSharpVersionService("KinsonDigital", "Infrastructure", token);

await service.updateVersion(version, ReleaseType.preview);

21 changes: 11 additions & 10 deletions .github/internal-cicd/scripts/update-workflow-versions.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,4 @@
import {
TagClient, RepoClient, Directory, Input
} from "../../../deps.ts";
import { Directory, Input, RepoClient, TagClient } from "../../../deps.ts";
import chalk from "../../../deps.ts";
import { File } from "../../../cicd/core/File.ts";
import { Utils } from "../../../cicd/core/Utils.ts";
Expand Down Expand Up @@ -34,7 +32,7 @@ const newVersion = await Input.prompt({
value = value.trim().toLowerCase();

return value.startsWith("v") ? value : `v${value}`;
}
},
});

const ownerName = "KinsonDigital";
Expand All @@ -58,15 +56,15 @@ const updateMsgs: string[] = [];
let noFilesUpdated = true;

// Search for workflow references with a version that has not been updated
yamlFiles.forEach(yamlFile => {
yamlFiles.forEach((yamlFile) => {
let fileContent = File.LoadFile(yamlFile);

const possibleUpdates = fileContent.match(reusableWorkflowRegex)?.map((w) => w) ?? [];

let fileUpdated = false;

// Check each reusable workflow reference version
possibleUpdates.forEach(oldRef => {
// Check each reusable workflow reference version
possibleUpdates.forEach((oldRef) => {
const refPathSection = oldRef.split("uses:")[1].trim().split("@")[0];
const workflowRefVersion = oldRef.split("@")[1];

Expand All @@ -79,7 +77,8 @@ yamlFiles.forEach(yamlFile => {
// Update the reusable workflow reference version
fileContent = fileContent.replaceAll(oldRef, newRef);

const noticeMsg = `Updated reusable workflow reference '${refPathSection}' from version '${workflowRefVersion}' to '${newVersion}'.`;
const noticeMsg =
`Updated reusable workflow reference '${refPathSection}' from version '${workflowRefVersion}' to '${newVersion}'.`;
updateMsgs.push(noticeMsg);
}
});
Expand All @@ -96,7 +95,7 @@ if (noFilesUpdated) {
console.log(chalk.cyan("No files needed updating."));
} else {
updateMsgs.sort();
updateMsgs.forEach(updateMsg => {
updateMsgs.forEach((updateMsg) => {
console.log(chalk.cyan(updateMsg));
});
}
Expand All @@ -113,4 +112,6 @@ const scriptVersionVar = (await repoClient.getVariables()).find((v) => v.name ==

await repoClient.updateVariable(repoVarName, newVersion);

console.log(chalk.cyan(`Updated repository variable '${repoVarName}' from version '${scriptVersionVar?.value}' to '${newVersion}'.`));
console.log(
chalk.cyan(`Updated repository variable '${repoVarName}' from version '${scriptVersionVar?.value}' to '${newVersion}'.`),
);
101 changes: 1 addition & 100 deletions .github/internal-cicd/scripts/workflow-version-status-check.ts
Original file line number Diff line number Diff line change
@@ -1,100 +1 @@
import { walkSync } from "@std/fs/walk";
import { exists } from "@std/fs/exists";
import { basename } from "@std/path/basename";
import { TagClient } from "../../../deps.ts";
import { Utils } from "../../../cicd/core/Utils.ts";
import getEnvVar from "../../../cicd/core/GetEnvVar.ts";
import { validateOrgExists, validateRepoExists } from "../../../cicd/core/Validators.ts";

const scriptFileName = new URL(import.meta.url).pathname.split("/").pop();

const ownerName = getEnvVar("OWNER_NAME", scriptFileName);
const repoName = getEnvVar("REPO_NAME", scriptFileName);
let baseDirPath = getEnvVar("BASE_DIR_PATH", scriptFileName);
baseDirPath = Utils.normalizePath(baseDirPath);
const token = getEnvVar("GITHUB_TOKEN", scriptFileName);

await validateOrgExists(scriptFileName);
await validateRepoExists(scriptFileName);

if (!exists(baseDirPath)) {
Utils.printAsGitHubError(`Directory '${baseDirPath}' does not exist.`);
Deno.exit(1);
}

const yamlFiles = [...walkSync(baseDirPath, {
includeDirs: false,
includeFiles: true,
exts: [".yaml", ".yml"],
})].map((e) => e.path);

const tagClient: TagClient = new TagClient(ownerName, repoName, token);

const existingReleaseTags = (await tagClient.getAllTags()).map((t) => t.name);

const workflowsToUpdate: WorkflowToUpdate[] = [];

const reusableWorkflowRegex = /uses: .+.(yml|yaml)@v([1-9]\d*|0)\.([1-9]\d*|0)\.([1-9]\d*|0)(-preview\.([1-9]\d*))?/gm;

type WorkflowToUpdate = {
/**
* The file path to the workflow.
*/
filePath: string;

/**
* The reusable workflow references that need to be updated.
*/
workflowRefs: string[];
};

// Search for workflow references with a version that has not been updated
yamlFiles.forEach(yamlFile => {
const workflowToUpdate: WorkflowToUpdate = {
filePath: yamlFile,
workflowRefs: []
};

const fileContent = Deno.readTextFileSync(yamlFile);

const possibleUpdates = fileContent.match(reusableWorkflowRegex)?.map((w) => w) ?? [];

// Check each reusable workflow reference version
possibleUpdates.forEach(possibleUpdate => {
const fullRef = possibleUpdate.split("uses:")[1].trim();
const workflowRefVersion = possibleUpdate.split("@")[1];

// If the workflow version has not been updated
if (existingReleaseTags.includes(workflowRefVersion)) {
workflowToUpdate.workflowRefs.push(fullRef);
}
});

if (workflowToUpdate.workflowRefs.length > 0) {
workflowsToUpdate.push(workflowToUpdate);
}
});

// If there are no workflows to update, then exit
if (workflowsToUpdate.length === 0) {
Utils.printAsGitHubNotice("No workflows to update.");
Deno.exit(0);
}

const errorMsgs: string[] = [];

// Print out all of the workflows that need to be updated as an error
workflowsToUpdate.forEach(workflowToUpdate => {
const filePath = basename(workflowToUpdate.filePath);

const workflowErrors: string[] = workflowToUpdate.workflowRefs.map((workflowRef) => {
return `Workflow reference '${workflowRef}' in file '${filePath}' needs to be updated.`;
});

errorMsgs.push(...workflowErrors);
});

if (errorMsgs.length > 0) {
Utils.printAsGitHubErrors(errorMsgs);
Deno.exit(1);
}
import "../../../cicd/scripts/check-workflow-versions.ts";
2 changes: 1 addition & 1 deletion .github/workflows/add-item-to-project.yml
Original file line number Diff line number Diff line change
Expand Up @@ -62,7 +62,7 @@ jobs:
}
- name: Set Up Deno
uses: denoland/setup-deno@v1
uses: denoland/setup-deno@v2
with:
deno-version: ${{ vars.DENO_VERSION }}

Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/add-new-item-to-project.yml
Original file line number Diff line number Diff line change
Expand Up @@ -36,7 +36,7 @@ jobs:
add_new_item_to_project:
name: Add New Issue
needs: item_number
uses: KinsonDigital/Infrastructure/.github/workflows/add-item-to-project.yml@v13.6.3
uses: KinsonDigital/Infrastructure/.github/workflows/add-item-to-project.yml@v14.0.0
with:
org-name: "${{ vars.ORGANIZATION_NAME }}"
org-project-name: "${{ vars.ORG_PROJECT_NAME }}"
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/build-csharp-project.yml
Original file line number Diff line number Diff line change
Expand Up @@ -90,7 +90,7 @@ jobs:
resolve_proj_file_path:
name: Resolving ${{ inputs.project-name }} Project File Path
needs: print_validate_workflow
uses: KinsonDigital/Infrastructure/.github/workflows/resolve-csharp-proj-file.yml@v13.6.3
uses: KinsonDigital/Infrastructure/.github/workflows/resolve-csharp-proj-file.yml@v14.0.0
with:
project-name: ${{ inputs.project-name }}
base-path: ${{ inputs.base-path }}
Expand Down
9 changes: 4 additions & 5 deletions .github/workflows/build-status-check.yml
Original file line number Diff line number Diff line change
Expand Up @@ -23,11 +23,10 @@ jobs:
repository: ${{ github.event.pull_request.head.repo.full_name }}
ref: ${{ github.event.pull_request.head.ref }}

- name: Setup Deno
uses: denoland/setup-deno@v1
- name: Setup Deno (${{ vars.DENO_VERSION }})
uses: denoland/setup-deno@v2
with:
deno-version: ${{ vars.DENO_VERSION }}

- name: Run Build
run: |
deno run --allow-read --allow-run --allow-sys "./.github/internal-cicd/scripts/deno-check.ts";
- name: Run Check
run: deno check ./**/*.ts;
12 changes: 6 additions & 6 deletions .github/workflows/dotnet-action-release.yml
Original file line number Diff line number Diff line change
Expand Up @@ -157,7 +157,7 @@ jobs:
validate_version:
name: Validate Version
needs: [print_validate_workflow, validate_branch]
uses: KinsonDigital/Infrastructure/.github/workflows/validate-csharp-version.yml@v13.6.3
uses: KinsonDigital/Infrastructure/.github/workflows/validate-csharp-version.yml@v14.0.0
with:
project-name: "${{ inputs.project-name }}"
release-type: "${{ inputs.release-type }}"
Expand All @@ -168,7 +168,7 @@ jobs:
validate_tag:
name: Validate Tag
needs: validate_version
uses: KinsonDigital/Infrastructure/.github/workflows/validate-tag.yml@v13.6.3
uses: KinsonDigital/Infrastructure/.github/workflows/validate-tag.yml@v14.0.0
with:
project-name: "${{ inputs.project-name }}"
release-type: "${{ inputs.release-type }}"
Expand All @@ -180,7 +180,7 @@ jobs:
validate_sdk_setup:
name: Validate SDK Setup
needs: print_validate_workflow
uses: KinsonDigital/Infrastructure/.github/workflows/validate-sdk-versions.yml@v13.6.3
uses: KinsonDigital/Infrastructure/.github/workflows/validate-sdk-versions.yml@v14.0.0
with:
repo-name: "${{ inputs.project-name }}"
secrets:
Expand Down Expand Up @@ -216,7 +216,7 @@ jobs:
validate_github_release:
name: GitHub Release Does Not Exist
needs: validate_version
uses: KinsonDigital/Infrastructure/.github/workflows/validate-github-release.yml@v13.6.3
uses: KinsonDigital/Infrastructure/.github/workflows/validate-github-release.yml@v14.0.0
with:
project-name: "${{ inputs.project-name }}"
version: "${{ needs.validate_version.outputs.version }}"
Expand All @@ -227,7 +227,7 @@ jobs:
build_project:
name: Build Main Project (${{ inputs.project-name }})
needs: print_validate_workflow
uses: KinsonDigital/Infrastructure/.github/workflows/build-csharp-project.yml@v13.6.3
uses: KinsonDigital/Infrastructure/.github/workflows/build-csharp-project.yml@v14.0.0
with:
project-name: "${{ inputs.project-name }}"
runs-on: "${{ inputs.runs-on }}"
Expand All @@ -240,7 +240,7 @@ jobs:
run_tests:
name: Run Tests
needs: print_validate_workflow
uses: KinsonDigital/Infrastructure/.github/workflows/run-csharp-tests.yml@v13.6.3
uses: KinsonDigital/Infrastructure/.github/workflows/run-csharp-tests.yml@v14.0.0
with:
project-name: "${{ inputs.project-name }}Tests"
runs-on: "${{ inputs.runs-on }}"
Expand Down
Loading

0 comments on commit f4afdd6

Please sign in to comment.