release-foundry provides two things:
-
Reusable GitHub Actions workflows β a workflow library that any repo can call to build and publish a multi-arch Docker image to
ghcr.io/bluefunda/<repo>, run CI, enforce Conventional Commits, manage releases, and more. -
A Go binary β collects merged pull requests from one or more GitHub repositories, filters by label, and renders structured output (JSON + Markdown) ready to feed to an LLM to produce social media posts, blog intros, and newsletter copy.
Repos in the bluefunda org call release-foundry's reusable workflows from their
own workflow.yml files. The docker-deploy.yml workflow handles the full
multi-arch build and push to ghcr.io/bluefunda/<repo> β no per-repo
Dockerfile boilerplate required beyond the Dockerfile itself.
After a release, the release-foundry binary collects merged PRs, filters them
by label, and writes structured JSON and Markdown files. Feed those files to an
LLM to generate LinkedIn posts, tweet threads, blog intros, or newsletters.
git tag v1.2.0
ββ release-foundry binary runs
ββ GitHub release body (Markdown, grouped by label)
ββ release-summary.json (structured feed for LLM consumption)
brew install <your-tap>/release-foundrySee docs/homebrew.md for tap setup.
go install github.com/release-foundry/cmd/release-foundry@latestDownload a pre-built binary from the Releases page.
# macOS arm64
curl -L https://github.com/<org>/release-foundry/releases/latest/download/release-foundry_macOS_arm64.tar.gz \
| tar xz && mv release-foundry /usr/local/bin/# Debian/Ubuntu
curl -L https://github.com/<org>/release-foundry/releases/latest/download/release-foundry_linux_amd64.deb \
-o release-foundry.deb && sudo dpkg -i release-foundry.deb
# Fedora/RHEL
curl -L https://github.com/<org>/release-foundry/releases/latest/download/release-foundry_linux_amd64.rpm \
-o release-foundry.rpm && sudo rpm -i release-foundry.rpm# Set your GitHub token (or use the gh CLI β it's auto-detected)
export GITHUB_TOKEN=ghp_...
# Single repo, last 7 days
release-foundry -owner myorg -repo myrepo -render github-release -out ./out
# Single repo since a specific date
release-foundry -owner myorg -repo myrepo -since 2024-04-01T00:00:00Z \
-render github-release -out ./out
# Batch mode β multiple repos from a config file
release-foundry -config repos.yml -days 14 -render github-release -out ./out
# Topic discovery β auto-discover repos tagged "active" in an org
release-foundry -topic active -owner myorg -render github-release -out ./out
# Print version
release-foundry version| Flag | Env var | Default | Description |
|---|---|---|---|
-token |
GITHUB_TOKEN |
gh CLI / prompt | GitHub personal access token |
-owner |
GITHUB_OWNER |
prompt | Repository owner or org |
-repo |
GITHUB_REPO |
prompt | Repository name |
-days |
7 |
Number of days to look back | |
-since |
RFC3339 timestamp (overrides -days) |
||
-output |
release-summary.json |
Output JSON file path | |
-render |
Comma-separated renderer names | ||
-out |
. |
Output directory for rendered files | |
-config |
YAML config file for batch mode | ||
-topic |
GitHub topic to auto-discover repos |
Create a repos.yml (based on repos.example.yml):
defaults:
owner: myorg
baseBranch: main
repos:
- repo: api-server
edition: enterprise
- repo: web-ui
edition: free
- repo: cli-tool
includeLabels: [feature, fix, plugin]
excludeLabels: [internal]Run:
release-foundry -config repos.yml -days 7 -render github-release -out ./outrelease-foundry collects PRs with these labels by default:
| Label | Rendered as |
|---|---|
feature |
β¨ Features |
fix |
π Bug Fixes |
performance |
β‘ Performance |
security |
π Security |
infrastructure |
ποΈ Infrastructure |
PRs without a matching label fall back to conventional commit prefix inference
(feat: β feature, fix: β fix, etc.). PRs labeled internal, refactor,
or chore are excluded by default.
Override per-repo in repos.yml via includeLabels / excludeLabels.
release-foundry extracts structured fields from PR bodies. Add to your
.github/PULL_REQUEST_TEMPLATE.md:
## Customer Impact
<!-- Who benefits and how? Required for feature / perf / security PRs. -->
## Marketing Notes
<!-- Optional. Anything noteworthy for release notes, blog posts, or customer comms? -->The marketing_notes field is included in the JSON output and can be used by
downstream LLM renderers to produce better-quality social content.
The github-release renderer produces structured Markdown. Feed that to an LLM
to generate blog posts, social media posts, or newsletters:
# 1. Generate structured release notes
release-foundry -owner myorg -repo myrepo -since 2024-04-01T00:00:00Z \
-render github-release -out ./out
# 2. Feed to Claude for social content
claude -p "$(cat <<'EOF'
You are a developer relations writer. Given these release notes, produce:
1. A LinkedIn post (3-4 sentences, professional tone)
2. A tweet thread (3 tweets, punchy, with hashtags)
3. A short blog intro paragraph (5-6 sentences)
Release notes:
$(cat ./out/*-github-release.md)
EOF
)"Tips:
- Label PRs consistently β well-labeled PRs produce more structured notes
- Fill in Marketing Notes β that context flows into the JSON output and gives the LLM better material
- Batch across repos β use
-config repos.ymlfor a cross-repo sprint summary
release-foundry ships generic, reusable workflows for Go projects.
# .github/workflows/ci.yml
on: [pull_request, push]
jobs:
ci:
uses: bluefunda/release-foundry/.github/workflows/go-ci.yml@mainInputs: go-version, build-command, test-command, golangci-lint-version,
run-codecov, runner.
goreleaser:
needs: release-please
if: needs.release-please.outputs.release_created == 'true'
uses: bluefunda/release-foundry/.github/workflows/go-binary-release.yml@main
with:
tag: ${{ needs.release-please.outputs.tag_name }}
secrets:
GH_PAT: ${{ secrets.GH_PAT }}
HOMEBREW_TAP_TOKEN: ${{ secrets.HOMEBREW_TAP_TOKEN }}Supports macOS code signing and notarization. See docs/macos-notarization.md.
release-please:
uses: bluefunda/release-foundry/.github/workflows/release-please.yml@main
secrets:
GH_PAT: ${{ secrets.GH_PAT }}Outputs: release_created, tag_name.
release-notes:
needs: release-please
if: needs.release-please.outputs.release_created == 'true'
uses: bluefunda/release-foundry/.github/workflows/github-release-notes.yml@main
with:
tag: ${{ needs.release-please.outputs.tag_name }}
release-foundry-repo: bluefunda/release-foundry
secrets:
GH_PAT: ${{ secrets.GH_PAT }}Builds a linux/amd64 + linux/arm64 image and pushes to
ghcr.io/<org>/<repo>:<tag> and ghcr.io/<org>/<repo>:latest.
deploy:
needs: release-please
if: needs.release-please.outputs.release_created == 'true'
uses: bluefunda/release-foundry/.github/workflows/docker-deploy.yml@main
with:
tag: ${{ needs.release-please.outputs.tag_name }}
secrets:
GH_PAT: ${{ secrets.GH_PAT }} # only needed for private Go module dependenciesInputs: tag (required), image-name (defaults to repo name), build-args, runner.
pr-title:
uses: bluefunda/release-foundry/.github/workflows/pr-title-check.yml@mainRenderers are registered via init() and selected at runtime by name. Adding
a new renderer requires no changes to the CLI β only a new file in
internal/renderers/ that calls Register("name", renderer).
release-foundry -render github-release,my-custom-renderer -out ./out
See CONTRIBUTING.md for how to write a renderer.
cmd/release-foundry/ Binary entrypoint, flag parsing, mode dispatch
internal/
config/ Multi-repo batch config loader (repos.yml)
domain/ Core types, label rules, PR classification
github/ GitHub REST API client (paginated, rate-limit aware)
renderers/ Pluggable output renderers + registry
service/ Collect β filter β render orchestration
.github/workflows/ Reusable GitHub Actions workflows
docs/
cli-reference.md Full CLI flags, batch config, output schema
macos-notarization.md macOS code signing + notarization setup
homebrew.md Homebrew tap setup guide
repos.example.yml Example batch config
.goreleaser.yml GoReleaser config for binary distribution
See CONTRIBUTING.md. All PRs require:
make testpassing (race detector enabled)make lintpassing- PR title following Conventional Commits
Apache 2.0 β see LICENSE.