Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
35 commits
Select commit Hold shift + click to select a range
13c70ba
fix naming error
frequency403 Mar 24, 2026
01162ec
fix icon name
frequency403 Mar 24, 2026
fe3ef20
Fix startup error when files are not readable. (#18)
frequency403 Mar 24, 2026
b3e8a9c
remove warnings as error in csproj
frequency403 Mar 24, 2026
bbbe8ea
remove warnings as error in csproj
frequency403 Mar 24, 2026
f536d95
Merge branch 'master' into development
frequency403 Mar 24, 2026
e4807aa
Merge branch 'development' into release/v3.0.1
frequency403 Mar 24, 2026
d99e92f
Fix and Optimize Configuration, SSH Key Handling, and UI (#21)
frequency403 Jun 9, 2026
8ee5e98
Introduce new workflows: auto-tag refinement, unit tests, build-and-p…
frequency403 Jun 9, 2026
5fbbd39
Bump version to 3.1.0, improve PKGBUILD formatting, and fix SSH key f…
frequency403 Jun 9, 2026
cdff101
Add `build-and-package.yml` and `test.yml` workflows; refine asset pr…
frequency403 Jun 9, 2026
1431a2d
Refactor workflows: streamline asset preparation, reorganize director…
frequency403 Jun 9, 2026
638c3b8
Update `staging.yml`: adjust dependencies for `deploy-aur-nightly` an…
frequency403 Jun 9, 2026
d7f6b4b
Refactor GitHub Actions workflows: improve artifact handling and enha…
frequency403 Jun 9, 2026
ec44535
Update `staging.yml`: add `build` dependency for `deploy-aur-nightly`…
frequency403 Jun 9, 2026
08afa89
Revamp README: overhaul content structure, include new features, upda…
frequency403 Jun 9, 2026
f9f6e48
Bump version to 3.1.1; update PKGBUILD, normalize version logic in wo…
frequency403 Jun 9, 2026
107d24e
Merge branch 'master' into release/v3.1.1
frequency403 Jun 9, 2026
4a91f0a
Bump version to 3.1.2; update PKGBUILD, enhance version normalization…
frequency403 Jun 10, 2026
2ba45d1
Merge branch 'master' into release/v3.1.2
frequency403 Jun 10, 2026
75c82ec
Enhance Komac installation in workflow: dynamically fetch latest rele…
frequency403 Jun 10, 2026
2ae51bf
Refactor GitHub Actions: modularize workflows, add custom composite a…
frequency403 Jun 10, 2026
36859b5
Merge remote-tracking branch 'origin/master' into release/v3.1.3
frequency403 Jun 10, 2026
e4f25b4
Add `actions/checkout@v4` to workflows for consistent repository access.
frequency403 Jun 10, 2026
1180366
Refactor `install-komac` action: enhance reliability with `gh` CLI in…
frequency403 Jun 10, 2026
07e469a
Remove `install-komac` action, update GitHub Actions to latest versio…
frequency403 Jun 11, 2026
56c683e
Remove unused `needs: detect-tfm` property from `.github/actions/dotn…
frequency403 Jun 11, 2026
237e273
Remove nightly GitHub Release action from staging workflow
frequency403 Jun 11, 2026
c38234b
resolve warning IL3000
frequency403 Jun 11, 2026
f0c32b2
Remove nightly support and update workflows to reflect changes
frequency403 Jun 11, 2026
0ac2a6f
Update PKGBUILD to include date and commit hash in versioning
frequency403 Jun 11, 2026
d131b9b
Sync auto-tag workflow with development process:
frequency403 Jun 11, 2026
37cc849
Simplify test workflow by removing conditional triggers based on even…
frequency403 Jun 11, 2026
b81f1fd
Bump version to 3.1.4 in PKGBUILD and project properties
frequency403 Jun 11, 2026
bd6236f
Merge remote-tracking branch 'origin/master' into release/v3.1.4
frequency403 Jun 11, 2026
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
56 changes: 46 additions & 10 deletions .github/workflows/auto-tag.yml
Original file line number Diff line number Diff line change
Expand Up @@ -9,18 +9,18 @@ on:

permissions:
contents: write
pull-requests: write

concurrency:
group: auto-tag-${{ github.ref }}
cancel-in-progress: false

jobs:
create-tag:
name: Create and Push Tag
# Only run when a release/* branch was actually merged (not just closed)
name: Create Tag and Sync Development
if: github.event.pull_request.merged == true && startsWith(github.event.pull_request.head.ref, 'release/')
runs-on: ubuntu-latest
timeout-minutes: 5
timeout-minutes: 10

steps:
- name: Checkout repository
Expand All @@ -29,17 +29,17 @@ jobs:
fetch-depth: 0
token: ${{ secrets.PAT_TOKEN }}

- name: Extract and validate version from branch name
- name: Extract and validate version
id: version
uses: ./.github/actions/determine-version

- name: Check if tag already exists
id: check
run: |
set -euo pipefail
if git rev-parse "refs/tags/${{ steps.version.outputs.TAG }}" >/dev/null 2>&1; then
if git rev-parse "refs/tags/${{ steps.version.outputs.tag }}" >/dev/null 2>&1; then
echo "exists=true" >> "$GITHUB_OUTPUT"
echo "::warning::Tag ${{ steps.version.outputs.TAG }} already exists, skipping."
echo "::warning::Tag ${{ steps.version.outputs.tag }} already exists, skipping."
else
echo "exists=false" >> "$GITHUB_OUTPUT"
fi
Expand All @@ -50,7 +50,43 @@ jobs:
set -euo pipefail
git config user.name "github-actions[bot]"
git config user.email "github-actions[bot]@users.noreply.github.com"
git tag -a "${{ steps.version.outputs.TAG }}" \
-m "Release ${{ steps.version.outputs.VERSION }}"
git push origin "${{ steps.version.outputs.TAG }}"
echo "::notice::Tag ${{ steps.version.outputs.TAG }} pushed successfully."
git tag -a "${{ steps.version.outputs.tag }}" \
-m "Release ${{ steps.version.outputs.version }}"
git push origin "${{ steps.version.outputs.tag }}"
echo "::notice::Tag ${{ steps.version.outputs.tag }} pushed successfully."

- name: Cherry-pick release commit into development
if: steps.check.outputs.exists == 'false'
env:
GH_TOKEN: ${{ secrets.PAT_TOKEN }}
run: |
set -euo pipefail

RELEASE_SHA="${{ github.event.pull_request.head.sha }}"
VERSION="${{ steps.version.outputs.version }}"

git config user.name "github-actions[bot]"
git config user.email "github-actions[bot]@users.noreply.github.com"

git fetch origin development
git checkout -B development origin/development

if git cherry-pick "$RELEASE_SHA"; then
git push origin development
echo "::notice::Cherry-pick of $RELEASE_SHA into development succeeded."
else
git cherry-pick --abort

SYNC_BRANCH="chore/sync-release-${VERSION}-to-development"
git checkout -B "$SYNC_BRANCH" origin/development
git push origin "$SYNC_BRANCH"

gh pr create \
--base development \
--head "$SYNC_BRANCH" \
--title "chore: sync release ${VERSION} into development" \
--body "$(printf 'Automatic cherry-pick of release \`%s\` (commit \`%s\`) into \`development\` failed due to conflicts.\n\nPlease apply and resolve manually:\n\n```\ngit fetch origin\ngit checkout %s\ngit cherry-pick %s\n# resolve conflicts\ngit push origin %s\n```' \
"$VERSION" "$RELEASE_SHA" "$SYNC_BRANCH" "$RELEASE_SHA" "$SYNC_BRANCH")"

echo "::warning::Cherry-pick conflict. PR created: $SYNC_BRANCH → development."
fi
50 changes: 29 additions & 21 deletions .github/workflows/build.yml
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
name: Build and Release
name: Build and Release

on:
push:
Expand All @@ -13,9 +13,15 @@ concurrency:
cancel-in-progress: false # Never cancel an in-flight release

jobs:
test:
name: Run Tests
uses: ./.github/workflows/test.yml

prepare:
name: Prepare Metadata
runs-on: ubuntu-latest
timeout-minutes: 5
needs: test
outputs:
version: ${{ steps.version.outputs.version }}
tag: ${{ steps.version.outputs.tag }}
Expand All @@ -28,7 +34,7 @@ jobs:
uses: ./.github/actions/determine-version

build:
needs: prepare
needs: [ test, prepare ]
uses: ./.github/workflows/build-and-package.yml
with:
version: ${{ needs.prepare.outputs.version }}
Expand All @@ -39,7 +45,7 @@ jobs:
name: Create GitHub Release
runs-on: ubuntu-latest
timeout-minutes: 15
needs: [ prepare, build ]
needs: [ test, prepare, build ]

steps:
- name: Checkout repository
Expand Down Expand Up @@ -68,12 +74,15 @@ jobs:

cp LICENSE release-assets/LICENSE

# Assert all expected files are present before creating the release
# Assert all expected files are present before creating the release.
# appicon.png and .desktop are required by openssh-gui-bin PKGBUILD source URLs.
for EXPECTED in \
"OpenSSH-GUI-linux-x64" \
"OpenSSH-GUI-win-x64.exe" \
"OpenSSH-GUI-osx-x64" \
"OpenSSH-GUI-x86_64.AppImage"
"OpenSSH-GUI-x86_64.AppImage" \
"appicon.png" \
"io.github.frequency403.openssh_gui.desktop"
do
if [[ ! -f "release-assets/$EXPECTED" ]]; then
echo "::error::Expected release asset missing: $EXPECTED"
Expand All @@ -95,13 +104,13 @@ jobs:
name: Update AUR Packages
runs-on: ubuntu-latest
timeout-minutes: 15
needs: [ prepare, release ]
needs: [ test, prepare, release ]

steps:
- name: Checkout repository
uses: actions/checkout@v4
with:
fetch-depth: 0
fetch-depth: 1

- name: Download build artifacts
uses: actions/download-artifact@v4
Expand Down Expand Up @@ -140,12 +149,15 @@ jobs:
SHA_LICENSE=$(sha256sum LICENSE | cut -d' ' -f1)

sed -i "s/^pkgver=.*/pkgver=$VERSION/" openssh-gui-bin/PKGBUILD
sed -i "s/^pkgrel=.*/pkgrel=1/" openssh-gui-bin/PKGBUILD
sed -i "s/^sha256sums=.*/sha256sums=('$SHA_BIN' '$SHA_ICON' '$SHA_DESKTOP' '$SHA_LICENSE')/" \
openssh-gui-bin/PKGBUILD

sed -i "s/^pkgver=.*/pkgver=$VERSION/" openssh-gui-git/PKGBUILD
sed -i "s/^pkgrel=.*/pkgrel=1/" openssh-gui-git/PKGBUILD

echo "Updated PKGBUILDs:"
grep -E '^(pkgver=|sha256sums=)' openssh-gui-bin/PKGBUILD
grep -E '^(pkgver=|pkgrel=|sha256sums=)' openssh-gui-bin/PKGBUILD

- name: Publish AUR (openssh-gui-bin)
uses: KSXGitHub/github-actions-deploy-aur@v4.1.1
Expand All @@ -169,23 +181,19 @@ jobs:

winget:
name: Update Winget Package
runs-on: ubuntu-latest
runs-on: ubuntu-slim
timeout-minutes: 10
needs: [ prepare, release ]
needs: [ test, prepare, release ]

steps:
- name: Checkout Repository
uses: actions/checkout@v4

- name: Install Komac
id: komac
uses: ./.github/actions/install-komac

- name: Update Winget manifest
run: |
set -euo pipefail
"${{ steps.komac.outputs.komac-path }}" update "frequency403.OpenSSHGUI" \
--version "${{ needs.prepare.outputs.version }}" \
--urls "https://github.com/${{ github.repository }}/releases/download/${{ needs.prepare.outputs.tag }}/OpenSSH-GUI-win-x64.exe" \
--submit \
--token "${{ secrets.WINGET_GITHUB_TOKEN }}"
uses: vedantmgoyal9/winget-releaser@main
with:
identifier: frequency403.OpenSSHGUI
version: ${{ needs.prepare.outputs.version }}
release-tag: ${{ needs.prepare.outputs.tag }}
installers-regex: 'win-x64\.exe$'
token: ${{ secrets.WINGET_GITHUB_TOKEN }}
101 changes: 25 additions & 76 deletions .github/workflows/staging.yml
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
name: Staging / Nightly Build
name: Staging / Development Build

on:
push:
Expand All @@ -9,19 +9,22 @@ permissions:
contents: write

concurrency:
group: nightly-${{ github.ref }}
cancel-in-progress: true # Supersede previous nightly on rapid pushes
group: staging-${{ github.ref }}
cancel-in-progress: true # Supersede previous run on rapid pushes

jobs:
test:
name: Run Tests
uses: ./.github/workflows/test.yml

prepare:
name: Prepare Metadata
runs-on: ubuntu-latest
timeout-minutes: 5
needs: test
outputs:
version: ${{ steps.meta.outputs.version }}
base_version: ${{ steps.meta.outputs.base_version }}
git_hash: ${{ steps.meta.outputs.git_hash }}
build_date: ${{ steps.meta.outputs.build_date }}
version: ${{ steps.version.outputs.version }}
tag: ${{ steps.version.outputs.tag }}

steps:
- name: Checkout repository
Expand All @@ -31,92 +34,38 @@ jobs:
id: version
uses: ./.github/actions/determine-version

- name: Resolve build metadata
id: meta
run: |
set -euo pipefail
HASH=$(git rev-parse --short HEAD)
DATE=$(date +%Y-%m-%d)
BASE_VERSION="${{ steps.version.outputs.version }}"

VERSION="${BASE_VERSION}+${HASH}"
echo "version=$VERSION" >> "$GITHUB_OUTPUT"
echo "base_version=$BASE_VERSION" >> "$GITHUB_OUTPUT"
echo "git_hash=$HASH" >> "$GITHUB_OUTPUT"
echo "build_date=$DATE" >> "$GITHUB_OUTPUT"
echo "::notice::Nightly version: $VERSION"

build:
needs: prepare
uses: ./.github/workflows/build-and-package.yml
with:
version: ${{ needs.prepare.outputs.version }}
is_nightly: true
asset_name_prefix: OpenSSH-GUI-nightly

deploy-aur-nightly:
name: Update AUR Nightly Package
deploy-aur-git:
name: Update AUR Git Package
runs-on: ubuntu-latest
timeout-minutes: 15
needs: [ prepare, build ]
needs: [ test, prepare ]

steps:
- name: Checkout repository
uses: actions/checkout@v4
with:
fetch-depth: 0
fetch-depth: 1

- name: Download build artifacts
uses: actions/download-artifact@v4
with:
path: artifacts/

- name: Prepare and update nightly PKGBUILD
- name: Update openssh-gui-git PKGBUILD
run: |
set -euo pipefail
rm -rf aur-assets
mkdir -p aur-assets

find artifacts -type f | while read -r FILE; do
DEST="aur-assets/$(basename "$FILE")"
if [[ -f "$DEST" ]]; then
echo "::error::AUR artifact name collision: $(basename "$FILE")"
exit 1
fi
cp "$FILE" "$DEST"
done

test -f aur-assets/OpenSSH-GUI-nightly-linux-x64 \
|| { echo "::error::Missing nightly linux binary"; exit 1; }
test -f aur-assets/appicon.png \
|| { echo "::error::Missing appicon.png"; exit 1; }
test -f "aur-assets/io.github.frequency403.openssh_gui.desktop" \
|| { echo "::error::Missing .desktop file"; exit 1; }
test -f LICENSE \
|| { echo "::error::Missing LICENSE"; exit 1; }

DATE=$(date +%Y%m%d)
AUR_VERSION="${{ needs.prepare.outputs.base_version }}.${DATE}.${{ needs.prepare.outputs.git_hash }}"
echo "AUR_VERSION=$AUR_VERSION" >> "$GITHUB_ENV"

SHA_BIN=$(sha256sum aur-assets/OpenSSH-GUI-nightly-linux-x64 | cut -d' ' -f1)
SHA_ICON=$(sha256sum aur-assets/appicon.png | cut -d' ' -f1)
SHA_DESKTOP=$(sha256sum "aur-assets/io.github.frequency403.openssh_gui.desktop" | cut -d' ' -f1)
SHA_LICENSE=$(sha256sum LICENSE | cut -d' ' -f1)
HASH=$(git rev-parse --short HEAD)
# pkgver must only contain [a-zA-Z0-9._] — no + or -
AUR_VERSION="${{ needs.prepare.outputs.version }}.${DATE}.${HASH}"

sed -i "s/^pkgver=.*/pkgver=$AUR_VERSION/" openssh-gui-nightly/PKGBUILD
sed -i "s/^sha256sums=.*/sha256sums=('$SHA_BIN' '$SHA_ICON' '$SHA_DESKTOP' '$SHA_LICENSE')/" \
openssh-gui-nightly/PKGBUILD
sed -i "s/^pkgver=.*/pkgver=$AUR_VERSION/" openssh-gui-git/PKGBUILD
sed -i "s/^pkgrel=.*/pkgrel=1/" openssh-gui-git/PKGBUILD

echo "Updated PKGBUILD:"
grep -E '^(pkgver=|sha256sums=)' openssh-gui-nightly/PKGBUILD
grep -E '^(pkgver=|pkgrel=)' openssh-gui-git/PKGBUILD

- name: Publish AUR (openssh-gui-nightly)
- name: Publish AUR (openssh-gui-git)
uses: KSXGitHub/github-actions-deploy-aur@v4.1.1
with:
pkgname: openssh-gui-nightly
pkgbuild: ./openssh-gui-nightly/PKGBUILD
pkgname: openssh-gui-git
pkgbuild: ./openssh-gui-git/PKGBUILD
commit_username: ${{ github.repository_owner }}
commit_email: ${{ github.repository_owner }}@users.noreply.github.com
ssh_private_key: ${{ secrets.AUR_SSH_PRIVATE_KEY }}
commit_message: "Nightly update ${{ env.AUR_VERSION }}"
commit_message: "Development update ${{ needs.prepare.outputs.tag }}"
14 changes: 10 additions & 4 deletions .github/workflows/test.yml
Original file line number Diff line number Diff line change
Expand Up @@ -2,9 +2,15 @@ name: Unit Tests

on:
push:
branches: [ main, master, development ]
branches:
- master
- main
pull_request:
branches: [ main, master, development ]
branches:
- master
- main
- development
workflow_call:

concurrency:
group: tests-${{ github.ref }}-${{ github.event_name }}
Expand All @@ -19,7 +25,7 @@ jobs:
steps:
- name: Checkout repository
uses: actions/checkout@v4

- name: Setup .NET environment
uses: ./.github/actions/dotnet-setup

Expand All @@ -30,4 +36,4 @@ jobs:
run: dotnet build OpenSSH_GUI.slnx --configuration Release --no-restore

- name: Run tests
run: dotnet test OpenSSH_GUI.slnx --configuration Release --no-build --verbosity normal
run: dotnet test OpenSSH_GUI.slnx --configuration Release --no-build --verbosity normal
Loading
Loading