{"id":50765510,"url":"https://github.com/mackysoft/actions","last_synced_at":"2026-06-11T13:30:41.960Z","repository":{"id":359374367,"uuid":"1245777312","full_name":"mackysoft/actions","owner":"mackysoft","description":"Reusable GitHub Actions","archived":false,"fork":false,"pushed_at":"2026-05-21T17:58:25.000Z","size":53,"stargazers_count":0,"open_issues_count":0,"forks_count":0,"subscribers_count":0,"default_branch":"master","last_synced_at":"2026-05-22T00:11:36.298Z","etag":null,"topics":["actions","ci"],"latest_commit_sha":null,"homepage":"","language":"Shell","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/mackysoft.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null},"funding":{"github":"mackysoft"}},"created_at":"2026-05-21T14:45:00.000Z","updated_at":"2026-05-21T17:58:19.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/mackysoft/actions","commit_stats":null,"previous_names":["mackysoft/actions"],"tags_count":1,"template":false,"template_full_name":null,"purl":"pkg:github/mackysoft/actions","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mackysoft%2Factions","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mackysoft%2Factions/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mackysoft%2Factions/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mackysoft%2Factions/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/mackysoft","download_url":"https://codeload.github.com/mackysoft/actions/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/mackysoft%2Factions/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":34201839,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-05-26T15:22:16.424Z","status":"online","status_checked_at":"2026-06-11T02:00:06.485Z","response_time":57,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["actions","ci"],"created_at":"2026-06-11T13:30:40.999Z","updated_at":"2026-06-11T13:30:41.952Z","avatar_url":"https://github.com/mackysoft.png","language":"Shell","funding_links":["https://github.com/sponsors/mackysoft"],"categories":[],"sub_categories":[],"readme":"# MackySoft Actions\n\nSmall GitHub Actions for CI-only external boundaries.\n\nThis repository only keeps actions that behave as single-purpose modules:\n\n- one action owns one external operation\n- repository verification policy stays in the consuming repository\n- local scripts stay the source of truth for build, test, format, package, and smoke checks\n- duplicate publish policy, release note policy, and package contract checks stay in each repository\n\n## Actions\n\n### `release/source-guard`\n\nValidates that the current checkout exactly matches a SemVer release tag and\nthat the release commit is reachable from the repository default branch.\n\n```yaml\n- name: Guard release source\n  id: release-source\n  uses: mackysoft/actions/release/source-guard@v1\n  with:\n    tag-name: ${{ github.ref_name }}\n    default-branch: ${{ github.event.repository.default_branch }}\n```\n\nInputs:\n\n| Name | Required | Default | Description |\n| --- | --- | --- | --- |\n| `tag-name` | Yes | None | Release tag name to fetch and validate. |\n| `default-branch` | Yes | None | Default branch name used for reachability validation. |\n| `remote` | No | `origin` | Git remote name. |\n| `expected-release-sha` | No | `\"\"` | Optional expected release commit SHA. |\n| `tag-prefix` | No | `\"\"` | Optional prefix to strip from the tag before SemVer package version validation. |\n\nOutputs:\n\n| Name | Description |\n| --- | --- |\n| `tag-name` | Validated release tag name. |\n| `package-version` | SemVer package version resolved from the release tag. |\n| `release-sha` | Validated release commit SHA. |\n\nThe guard always fetches the release tag and default branch, validates that the\nchecked-out `HEAD` is the release tag commit, and verifies that the release\ncommit is reachable from the default branch. It does not create tags.\n\n### `nuget/trusted-publish`\n\nPublishes one or more `.nupkg` files to NuGet.org using NuGet Trusted Publishing.\n\n```yaml\npermissions:\n  contents: read\n  id-token: write\n\nsteps:\n  - name: Publish to NuGet.org\n    uses: mackysoft/actions/nuget/trusted-publish@v1\n    with:\n      package-glob: artifacts/packages/*.nupkg\n      nuget-user: ${{ vars.NUGET_USER }}\n```\n\nThe caller job must grant `id-token: write`.\n\nInputs:\n\n| Name | Required | Default | Description |\n| --- | --- | --- | --- |\n| `package-glob` | Yes | None | Glob or path for NuGet package artifacts. Matched files are pushed in sorted order. |\n| `nuget-user` | Yes | None | NuGet.org account name configured for Trusted Publishing. |\n| `source` | No | `https://api.nuget.org/v3/index.json` | NuGet package source URL passed to `dotnet nuget push`. |\n\nThis action only performs Trusted Publishing login and `dotnet nuget push`.\nIt does not decide whether publishing is required, and it does not pass\n`--skip-duplicate`.\n\n### `nuget/package-state`\n\nInspects or waits for NuGet package availability through the NuGet flat\ncontainer feed.\n\nInspect before publishing:\n\n```yaml\n- name: Inspect NuGet package state\n  id: package-state\n  uses: mackysoft/actions/nuget/package-state@v1\n  with:\n    mode: inspect\n    package-version: ${{ needs.prepare-release.outputs.package_version }}\n    package-ids: |\n      MackySoft.Ucli\n      MackySoft.Ucli.Contracts\n```\n\nWait after publishing:\n\n```yaml\n- name: Wait for NuGet package availability\n  uses: mackysoft/actions/nuget/package-state@v1\n  with:\n    mode: wait\n    package-version: ${{ needs.prepare-release.outputs.package_version }}\n    package-ids: |\n      MackySoft.Ucli\n      MackySoft.Ucli.Contracts\n    max-attempts: 30\n    interval-seconds: 10\n```\n\nInputs:\n\n| Name | Required | Default | Description |\n| --- | --- | --- | --- |\n| `mode` | No | `inspect` | Operation mode. Use `inspect` to classify publication state, or `wait` to block until every package exists. |\n| `package-version` | Yes | None | NuGet package version to inspect. |\n| `package-ids` | Yes | None | Newline-separated NuGet package IDs. |\n| `flat-container-base-url` | No | `https://api.nuget.org/v3-flatcontainer` | NuGet flat container base URL. |\n| `max-attempts` | No | `30` | Maximum number of checks in `wait` mode. |\n| `interval-seconds` | No | `10` | Seconds to wait between checks in `wait` mode. |\n\nOutputs:\n\n| Name | Description |\n| --- | --- |\n| `all-packages-exist` | `true` when every requested package exists. |\n| `publish-required` | `true` when none of the requested packages exist and publishing should proceed. |\n| `existing-package-ids-json` | JSON array of package IDs that already exist. |\n| `missing-package-ids-json` | JSON array of package IDs that do not exist. |\n\nIn `inspect` mode, partial publication state fails closed. That means all\npackages existing is safe to skip, all packages missing is safe to publish, and\nmixed existing/missing state fails.\n\n## Non-Goals\n\nThese responsibilities intentionally stay out of this repository:\n\n- .NET SDK setup, restore, build, test, and format\n- repository verification policy\n- package version resolution\n- package content or command contract smoke tests\n- GitHub Release asset policy\n- path-based verification scope detection\n\n## Validation\n\nRun the repository validation locally:\n\n```bash\nbash tests/run.sh\n```\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmackysoft%2Factions","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fmackysoft%2Factions","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fmackysoft%2Factions/lists"}