From a6c10301ef153417f4f03aaff99d0afeb14704e5 Mon Sep 17 00:00:00 2001 From: John McCall Date: Sat, 11 Apr 2026 22:11:39 -0400 Subject: [PATCH 1/4] Add Galaxy overwrite check and use gh for release Add a new boolean workflow input overwrite_existing (default false) and expose it as OVERWRITE_EXISTING. Add a step that checks whether the specified VERSION tarball already exists on Ansible Galaxy (sets step output exists) and a conditional step that aborts the run unless overwrite_existing=true. Replace the softprops/action-gh-release step with a gh CLI release create invocation that uses VERSION and RELEASE_DESCRIPTION. These changes prevent accidental duplicate Galaxy publishes and allow explicit overwriting while simplifying release creation. --- .github/workflows/release.yml | 34 +++++++++++++++++++++++++++------- 1 file changed, 27 insertions(+), 7 deletions(-) diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 2191c5fc..ff8f9daf 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -5,6 +5,11 @@ on: version: description: "Version number to release" required: true + overwrite_existing: + description: "Overwrite version if already published to Galaxy" + required: false + type: boolean + default: false concurrency: group: release-${{ github.ref }} @@ -24,6 +29,7 @@ jobs: contents: write # Required for creating releases and tags env: VERSION: ${{ github.event.inputs.version }} # zizmor: ignore[template-injection] -- User input is required for this workflow + OVERWRITE_EXISTING: ${{ github.event.inputs.overwrite_existing }} # zizmor: ignore[template-injection] -- Boolean input is safe for this comparison GHP_BASE_URL: https://${{ github.repository_owner }}.github.io/${{ github.event.repository.name }} GALAXY_API_KEY: ${{ secrets.GALAXY_API_KEY }} # zizmor: ignore[secrets-outside-env] -- Galaxy API key needed for publishing; workflow_dispatch only GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} # zizmor: ignore[secrets-outside-env] -- GitHub token needed for release creation; workflow_dispatch only @@ -41,6 +47,23 @@ jobs: - name: Install PyYaml run: pip install pyyaml + - name: Check if version exists on Galaxy + id: check_galaxy_version + run: | + if curl --head -s -f -o /dev/null "https://galaxy.ansible.com/download/lowlydba-sqlserver-${VERSION}.tar.gz"; then + echo "exists=true" >> "$GITHUB_OUTPUT" + echo "Version ${VERSION} already exists on Galaxy" + else + echo "exists=false" >> "$GITHUB_OUTPUT" + echo "Version ${VERSION} does not yet exist on Galaxy" + fi + + - name: Abort if version exists and overwrite not enabled + if: steps.check_galaxy_version.outputs.exists == 'true' && env.OVERWRITE_EXISTING != 'true' + run: | + echo "::error::Version ${VERSION} already exists on Galaxy. Set overwrite_existing=true to overwrite." + exit 1 + - name: Publish to Galaxy uses: artis3n/ansible_galaxy_collection@ffbca2460a5a1c600b941bbf1536bd61de1c2227 # v3.0.0 with: @@ -87,10 +110,7 @@ jobs: e.write("RELEASE_DESCRIPTION< Date: Sat, 11 Apr 2026 22:13:47 -0400 Subject: [PATCH 2/4] Update release.yml --- .github/workflows/release.yml | 9 +++++++++ 1 file changed, 9 insertions(+) diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index ff8f9daf..9779d7a8 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -47,6 +47,15 @@ jobs: - name: Install PyYaml run: pip install pyyaml + - name: Validate version matches galaxy.yml + run: | + GALAXY_VERSION=$(python -c "import yaml; print(yaml.safe_load(open('galaxy.yml'))['version'])") + if [ "${GALAXY_VERSION}" != "${VERSION}" ]; then + echo "::error::Input version '${VERSION}' does not match galaxy.yml version '${GALAXY_VERSION}'." + exit 1 + fi + echo "Version ${VERSION} matches galaxy.yml" + - name: Check if version exists on Galaxy id: check_galaxy_version run: | From 8e0b2a3c1fb2cc25bf4e7c8970cead1b4926b41b Mon Sep 17 00:00:00 2001 From: John McCall Date: Sat, 11 Apr 2026 22:26:29 -0400 Subject: [PATCH 3/4] Update release.yml --- .github/workflows/release.yml | 6 ++++++ 1 file changed, 6 insertions(+) diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index 9779d7a8..917408b9 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -78,6 +78,12 @@ jobs: with: api_key: ${{ env.GALAXY_API_KEY }} + - name: Upload collection artifact + uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1 + with: + name: lowlydba-sqlserver-${{ env.VERSION }} + path: ${{ github.workspace }}/lowlydba-sqlserver-${{ env.VERSION }}.tar.gz + - name: Validate version is published to Galaxy run: curl --head -s -f -o /dev/null "https://galaxy.ansible.com/download/lowlydba-sqlserver-${VERSION}.tar.gz" From 80635a0186258b7c05b5bb42a13d1e4741999add Mon Sep 17 00:00:00 2001 From: John McCall Date: Sat, 11 Apr 2026 22:37:45 -0400 Subject: [PATCH 4/4] Prefer shutil.which to locate pwsh Use shutil.which('pwsh') to locate the pwsh executable dynamically, falling back to platform-specific defaults (/usr/local/bin/pwsh on macOS, /usr/bin/pwsh otherwise) if not found. This improves portability across different environments and CI runners where pwsh may be installed in non-standard locations. --- .../connection_plugins/local_pwsh.py | 13 +++++++------ 1 file changed, 7 insertions(+), 6 deletions(-) diff --git a/tests/integration/targets/setup_sqlserver_test_plugins/connection_plugins/local_pwsh.py b/tests/integration/targets/setup_sqlserver_test_plugins/connection_plugins/local_pwsh.py index b78d2ade..26c48608 100644 --- a/tests/integration/targets/setup_sqlserver_test_plugins/connection_plugins/local_pwsh.py +++ b/tests/integration/targets/setup_sqlserver_test_plugins/connection_plugins/local_pwsh.py @@ -68,12 +68,13 @@ def exec_command(self, cmd, in_data=None, sudoable=True): display.debug("in local_pwsh.exec_command()") - # mac (darwin) has different pwsh install location than linux - if sys.platform.startswith('darwin'): - executable = '/usr/local/bin/pwsh' - else: - executable = '/usr/bin/pwsh' - # executable = C.DEFAULT_EXECUTABLE.split()[0] if C.DEFAULT_EXECUTABLE else None + # Locate pwsh dynamically; fall back to platform-specific defaults + executable = shutil.which('pwsh') + if executable is None: + if sys.platform.startswith('darwin'): + executable = '/usr/local/bin/pwsh' + else: + executable = '/usr/bin/pwsh' if not os.path.exists(to_bytes(executable, errors='surrogate_or_strict')): raise AnsibleError("failed to find the executable specified %s."