-
Notifications
You must be signed in to change notification settings - Fork 10
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #262 from modeseven-lfit/github-list-releases-action
Feat: action to list GitHub releases
- Loading branch information
Showing
2 changed files
with
218 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,54 @@ | ||
<!-- | ||
SPDX-License-Identifier: Apache-2.0 | ||
SPDX-FileCopyrightText: 2025 The Linux Foundation | ||
--> | ||
|
||
# 📦 GitHub List Releases | ||
|
||
Lists the GitHub releases for a given repository | ||
|
||
## github-list-releases-action | ||
|
||
## Usage Example | ||
|
||
When provided with a tag/version as input, will check if a release for that | ||
tag/version exists in the repository. Provides the list of releases as an | ||
output variable for other actions/workflows to consume. | ||
|
||
```yaml | ||
steps: | ||
- name: "Check if tag/version already released" | ||
id: release-check | ||
# yamllint disable-line rule:line-length | ||
uses: lfit/releng-reusable-workflows/.github/actions/github-list-releases-action@main | ||
with: | ||
tag: "v0.1.23" | ||
``` | ||
## Inputs | ||
<!-- markdownlint-disable MD013 --> | ||
| Variable Name | Required | Default | Description | | ||
| --------------- | -------- | --------- | -------------------------------------------- | | ||
| TAG | False | N/A | Checks if this tag/version has released | | ||
| SUMMARY_OUTPUT | False | N/A | Display summary output | | ||
| PRODUCTION_ONLY | False | See Below | Do not list pre-release or draft releases | | ||
| RETURN_TYPE | False | text | Return type set to either: text/json | | ||
| JSON_FIELDS | False | False | Fields to return as JSON | | ||
| ORDER | False | False | Sort order set to either: asc/desc | | ||
<!-- markdownlint-enable MD013 --> | ||
Note: Specification of JSON fields is mandatory when JSON return type requested | ||
## Outputs | ||
<!-- markdownlint-disable MD013 --> | ||
| Variable Name | Mandatory | Description | | ||
| ------------- | --------- | ---------------------------------------------- | | ||
| RELEASES | True | List of releases as either text or JSON | | ||
| RELEASED | False | Set true when tag/version has already released | | ||
<!-- markdownlint-enable MD013 --> |
164 changes: 164 additions & 0 deletions
164
.github/actions/github-list-releases-action/action.yaml
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,164 @@ | ||
--- | ||
# SPDX-License-Identifier: Apache-2.0 | ||
# SPDX-FileCopyrightText: 2024 The Linux Foundation | ||
|
||
# github-list-releases-action | ||
name: "📦 List GitHub Releases" | ||
description: "Returns a list of releases for the current repository" | ||
# Limited to 1000 records due to GitHub API query limits | ||
# 640K ought to be enough for anybody | ||
# ToDo: investigate support for API query pagination | ||
|
||
inputs: | ||
# Optional | ||
TAG: | ||
description: "Check if this tag/version has been released" | ||
required: false | ||
type: string | ||
SUMMARY_OUTPUT: | ||
description: "Displays summary output" | ||
required: false | ||
default: "false" | ||
type: string | ||
PRODUCTION_ONLY: | ||
description: "Pre-release and draft releases are included" | ||
required: false | ||
default: "false" | ||
type: string | ||
RETURN_TYPE: | ||
description: "Set to either: text|json" | ||
required: false | ||
default: "text" | ||
type: string | ||
JSON_FIELDS: | ||
# Mandatory when return type (above) is set to JSON | ||
description: "Fields to return when return type set to JSON" | ||
required: false | ||
default: "tagName" | ||
type: string | ||
ORDER: | ||
description: "Sort order: asc|desc" | ||
required: false | ||
default: "desc" | ||
type: string | ||
|
||
outputs: | ||
# Mandatory | ||
RELEASES: | ||
description: "List of releases in specified output format" | ||
value: ${{ steps.releases.outputs.releases }} | ||
# Optional | ||
RELEASED: | ||
description: "Has provided tag/version already been released" | ||
value: ${{ steps.releases.outputs.tag }} | ||
|
||
runs: | ||
using: "composite" | ||
steps: | ||
- name: "List GitHub Releases" | ||
id: releases | ||
shell: bash | ||
run: | | ||
# List GitHub Releases | ||
# Check GitHub CLI is available | ||
GH_CLI=$(which gh) | ||
if [ ! -x "$GH_CLI" ]; then | ||
echo "Error: GitHub CLI was NOT found in PATH ❌" | ||
exit 1 | ||
fi | ||
# Function to check releases | ||
checkReleases() { | ||
while IFS= read -r RELEASE ; do | ||
if [ "$RELEASE" = "$TAG" ]; then | ||
RELEASED="true" | ||
fi | ||
done <<< "$RELEASES" | ||
} | ||
# Case-insensitive matching of inputs | ||
SUMMARY_OUTPUT=$(echo ${{ inputs.summary_output }} |\ | ||
tr '[:upper:]' '[:lower:]') | ||
PRODUCTION_ONLY=$(echo ${{ inputs.PRODUCTION_ONLY }} |\ | ||
tr '[:upper:]' '[:lower:]') | ||
RETURN_TYPE=$(echo ${{ inputs.return_type }} |\ | ||
tr '[:upper:]' '[:lower:]') | ||
ORDER=$(echo ${{ inputs.order }} |\ | ||
tr '[:upper:]' '[:lower:]') | ||
TAG="${{ inputs.tag }}" | ||
# Set baseline flags for the CLI command | ||
# Note: limit MUST be provided numerically to GH CLI | ||
CLI_FLAGS="release list --limit 1000 -O \ | ||
${{ inputs.ORDER }} --limit 1000" | ||
if [ "f$PRODUCTION_ONLY" = "ffalse" ]; then | ||
CLI_FLAGS="$CLI_FLAGS --exclude-drafts --exclude-pre-releases" | ||
fi | ||
# Check dependent input parameters are coherent | ||
if [ "$RETURN_TYPE" = "json" ] && [ -z "$JSON_FIELDS" ]; then | ||
echo "Error: fields MUST be specified when return type is JSON ❌" | ||
exit 1 | ||
elif [ "$RETURN_TYPE" = "json" ]; then | ||
CLI_FLAGS="$CLI_FLAGS --json ${{ inputs.JSON_FIELDS }}" | ||
fi | ||
echo "Fetching GitHub Releases 📦" | ||
if [ "f$SUMMARY_OUTPUT" = "ftrue" ]; then | ||
echo "### 📦 GitHub List Releases" >> "$GITHUB_STEP_SUMMARY" | ||
fi | ||
# Run and capture GitHub CLI Command | ||
if [ "$RETURN_TYPE" = "text" ]; then | ||
# Text output is actually a JSON query processed with fixed arguments | ||
echo "Running: $GH_CLI $CLI_FLAGS" | ||
RELEASES=$($GH_CLI $CLI_FLAGS --json tagName -q '.[] | .tagName') | ||
else | ||
echo "Running: $GH_CLI $CLI_FLAGS" | ||
RELEASES=$($GH_CLI $CLI_FLAGS) | ||
fi | ||
# Only list releases if/when values are returned | ||
if [ -n "$RELEASES" ]; then | ||
echo "Releases in this repository:" | ||
echo "$RELEASES" | ||
fi | ||
if [ -z "$TAG" ]; then | ||
# Exit early if no tag/version to check in releases | ||
exit 0 | ||
fi | ||
# Check with leading character in place | ||
echo "Checking for: $TAG" | ||
checkReleases | ||
if [ "$RELEASED" != "true" ]; then | ||
if [[ "$TAG" == v* ]]; then | ||
TAG="${TAG:1}" | ||
# Check again with leading 'v' character stripped | ||
echo "Checking for: $TAG" | ||
checkReleases | ||
fi | ||
fi | ||
# Set output value | ||
echo "RELEASED=$RELEASED" >> "$GITHUB_ENV" | ||
echo "RELEASED=$RELEASED" >> "$GITHUB_OUTPUT" | ||
if [ "$RELEASED" = "true" ]; then | ||
echo "${{ inputs.tag }} HAS already been release ⚠️" | ||
else | ||
echo "${{ inputs.tag }} has not previously been released ✅" | ||
fi | ||
if [ "f$SUMMARY_OUTPUT" = "ftrue" ]; then | ||
if [ "$RELEASED" = "true" ]; then | ||
echo "Release already published: $TAG ⚠️" \ | ||
>> "$GITHUB_STEP_SUMMARY" | ||
else | ||
echo "Release not published yet: $TAG ✅" \ | ||
>> "$GITHUB_STEP_SUMMARY" | ||
fi | ||
fi |