From 14b3e10d0ab035364559fd83e10736a772d60c23 Mon Sep 17 00:00:00 2001 From: ehsantg Date: Mon, 1 Jun 2026 10:00:00 +0330 Subject: [PATCH 1/2] =?UTF-8?q?chore:=20publish=20to=20PyPI=20=E2=80=94=20?= =?UTF-8?q?CI,=20Trusted=20Publishing=20workflow,=20Dependabot,=20live=20b?= =?UTF-8?q?adges?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .github/dependabot.yml | 29 +++++++ .github/workflows/ci.yml | 41 +++++++++ .github/workflows/publish.yml | 155 ++++++++++++++++++++++++++++++++++ README.md | 8 +- pyproject.toml | 13 ++- 5 files changed, 242 insertions(+), 4 deletions(-) create mode 100644 .github/dependabot.yml create mode 100644 .github/workflows/ci.yml create mode 100644 .github/workflows/publish.yml diff --git a/.github/dependabot.yml b/.github/dependabot.yml new file mode 100644 index 0000000..b617446 --- /dev/null +++ b/.github/dependabot.yml @@ -0,0 +1,29 @@ +version: 2 + +updates: + - package-ecosystem: pip + directory: "/" + schedule: + interval: weekly + day: monday + groups: + minor-and-patch: + update-types: + - minor + - patch + labels: + - dependencies + + - package-ecosystem: github-actions + directory: "/" + schedule: + interval: weekly + day: monday + groups: + actions-minor-patch: + update-types: + - minor + - patch + labels: + - dependencies + - github-actions diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml new file mode 100644 index 0000000..e021b59 --- /dev/null +++ b/.github/workflows/ci.yml @@ -0,0 +1,41 @@ +name: CI + +on: + push: + branches: [main] + pull_request: + branches: [main] + +jobs: + test: + name: Test (Python ${{ matrix.python-version }}) + runs-on: ubuntu-latest + strategy: + fail-fast: false + matrix: + python-version: ["3.11", "3.12", "3.13"] + + steps: + - uses: actions/checkout@v4 + + - name: Install uv + uses: astral-sh/setup-uv@v4 + with: + version: "latest" + + - name: Set up Python ${{ matrix.python-version }} + run: uv python install ${{ matrix.python-version }} + + - name: Install dependencies + run: uv sync --extra dev + + - name: Run tests with coverage + run: uv run pytest --cov=src/foreman --cov-report=xml --cov-report=term-missing + + - name: Upload coverage to Codecov + uses: codecov/codecov-action@v4 + if: matrix.python-version == '3.11' + with: + token: ${{ secrets.CODECOV_TOKEN }} + files: ./coverage.xml + fail_ci_if_error: false diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml new file mode 100644 index 0000000..5753120 --- /dev/null +++ b/.github/workflows/publish.yml @@ -0,0 +1,155 @@ +name: Publish to PyPI + +on: + push: + tags: + - "v[0-9]+.[0-9]+.[0-9]+" + - "v[0-9]+.[0-9]+.[0-9]+a[0-9]+" + - "v[0-9]+.[0-9]+.[0-9]+b[0-9]+" + - "v[0-9]+.[0-9]+.[0-9]+rc[0-9]+" + workflow_dispatch: + inputs: + target: + description: "Publish target" + required: true + default: "testpypi" + type: choice + options: + - testpypi + - pypi + +jobs: + test: + name: Test before publish + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v4 + + - name: Install uv + uses: astral-sh/setup-uv@v4 + with: + version: "latest" + + - name: Run tests + run: | + uv python install 3.11 + uv sync --extra dev + uv run pytest + + build: + name: Build distribution + runs-on: ubuntu-latest + needs: test + outputs: + version: ${{ steps.version.outputs.version }} + is_prerelease: ${{ steps.version.outputs.is_prerelease }} + steps: + - uses: actions/checkout@v4 + + - name: Install uv + uses: astral-sh/setup-uv@v4 + with: + version: "latest" + + - name: Extract version + id: version + run: | + VERSION=$(uv run python -c "import tomllib; d=tomllib.loads(open('pyproject.toml').read()); print(d['project']['version'])") + echo "version=$VERSION" >> "$GITHUB_OUTPUT" + if [[ "$VERSION" =~ (a|b|rc)[0-9]+ ]]; then + echo "is_prerelease=true" >> "$GITHUB_OUTPUT" + else + echo "is_prerelease=false" >> "$GITHUB_OUTPUT" + fi + + - name: Assert tag matches pyproject.toml version + if: startsWith(github.ref, 'refs/tags/') + run: | + TAG="${GITHUB_REF_NAME#v}" + PKG="${{ steps.version.outputs.version }}" + if [ "$TAG" != "$PKG" ]; then + echo "Tag $TAG does not match pyproject.toml version $PKG" >&2 + exit 1 + fi + + - name: Build sdist and wheel + run: uv build + + - name: Validate with twine + run: | + uv run --with twine twine check dist/* + + - name: Upload dist artifacts + uses: actions/upload-artifact@v4 + with: + name: dist + path: dist/ + + publish-testpypi: + name: Publish to TestPyPI + runs-on: ubuntu-latest + needs: build + if: | + needs.build.outputs.is_prerelease == 'true' || + github.event_name == 'workflow_dispatch' && github.event.inputs.target == 'testpypi' + environment: + name: testpypi + url: https://test.pypi.org/p/foreman-orchestrator + permissions: + id-token: write + steps: + - uses: actions/download-artifact@v4 + with: + name: dist + path: dist/ + + - name: Publish to TestPyPI + uses: pypa/gh-action-pypi-publish@release/v1 + with: + repository-url: https://test.pypi.org/legacy/ + + publish-pypi: + name: Publish to PyPI + runs-on: ubuntu-latest + needs: build + if: | + startsWith(github.ref, 'refs/tags/') && + needs.build.outputs.is_prerelease == 'false' + environment: + name: pypi + url: https://pypi.org/p/foreman-orchestrator + permissions: + id-token: write + steps: + - uses: actions/download-artifact@v4 + with: + name: dist + path: dist/ + + - name: Publish to PyPI + uses: pypa/gh-action-pypi-publish@release/v1 + + release: + name: Create GitHub Release + runs-on: ubuntu-latest + needs: [build, publish-pypi] + if: startsWith(github.ref, 'refs/tags/') && needs.build.outputs.is_prerelease == 'false' + permissions: + contents: write + steps: + - uses: actions/checkout@v4 + with: + fetch-depth: 0 + + - uses: actions/download-artifact@v4 + with: + name: dist + path: dist/ + + - name: Create GitHub Release + uses: softprops/action-gh-release@v2 + with: + name: "v${{ needs.build.outputs.version }}" + generate_release_notes: true + files: dist/* + prerelease: false diff --git a/README.md b/README.md index 6a6847b..d1cbc51 100644 --- a/README.md +++ b/README.md @@ -6,11 +6,13 @@ `plan → ADR/PRD → issues → TDD build → e2e` +[![CI](https://github.com/VisionForge-OU/foreman/actions/workflows/ci.yml/badge.svg)](https://github.com/VisionForge-OU/foreman/actions/workflows/ci.yml) +[![Coverage](https://codecov.io/gh/VisionForge-OU/foreman/branch/main/graph/badge.svg)](https://codecov.io/gh/VisionForge-OU/foreman) +[![PyPI version](https://img.shields.io/pypi/v/foreman-orchestrator.svg)](https://pypi.org/project/foreman-orchestrator/) +[![PyPI - Python Version](https://img.shields.io/pypi/pyversions/foreman-orchestrator.svg)](https://pypi.org/project/foreman-orchestrator/) +[![PyPI - Downloads](https://img.shields.io/pypi/dm/foreman-orchestrator.svg)](https://pypi.org/project/foreman-orchestrator/) [![License: MIT](https://img.shields.io/badge/License-MIT-yellow.svg)](./LICENSE) -[![Python 3.11+](https://img.shields.io/badge/python-3.11%2B-blue.svg)](https://www.python.org/) -[![Version](https://img.shields.io/badge/version-0.6.0-blueviolet.svg)](./CHANGELOG.md) [![TUI: Textual](https://img.shields.io/badge/TUI-Textual-5a3fd6.svg)](https://textual.textualize.io/) -[![No database](https://img.shields.io/badge/database-none-lightgrey.svg)](#how-it-works) [![PRs welcome](https://img.shields.io/badge/PRs-welcome-brightgreen.svg)](#contributing) [Why Foreman?](#why-foreman) · [Demo](#demo) · [Quickstart](#5-minute-quickstart) · [Guide](#guide--driving-the-tui) · [How it works](#how-it-works) · [Roadmap](#roadmap) · [Contributing](#contributing) diff --git a/pyproject.toml b/pyproject.toml index 760ea91..0a4aaca 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -9,15 +9,25 @@ description = "A Boris-style agentic orchestrator TUI that supervises headless C readme = "README.md" requires-python = ">=3.11" license = { text = "MIT" } -authors = [{ name = "Foreman" }] +authors = [{ name = "ehsantg", email = "me@ehsan.ee" }] keywords = ["claude", "claude-code", "tui", "agents", "orchestrator", "textual", "tdd"] classifiers = [ + "Development Status :: 4 - Beta", "Environment :: Console", "Intended Audience :: Developers", "License :: OSI Approved :: MIT License", + "Programming Language :: Python :: 3", "Programming Language :: Python :: 3.11", + "Programming Language :: Python :: 3.12", + "Programming Language :: Python :: 3.13", "Topic :: Software Development :: Build Tools", ] + +[project.urls] +Homepage = "https://github.com/VisionForge-OU/foreman" +Repository = "https://github.com/VisionForge-OU/foreman" +Issues = "https://github.com/VisionForge-OU/foreman/issues" +Changelog = "https://github.com/VisionForge-OU/foreman/blob/main/CHANGELOG.md" dependencies = [ "textual>=0.79", "pyyaml>=6.0", @@ -27,6 +37,7 @@ dependencies = [ dev = [ "pytest>=8.0", "pytest-asyncio>=0.23", + "pytest-cov>=5.0", "pytest-textual-snapshot>=1.0", "textual-dev>=1.5", ] From 6c375a01a3aa623628afa961595ea6229e5e0c9a Mon Sep 17 00:00:00 2001 From: "dependabot[bot]" <49699333+dependabot[bot]@users.noreply.github.com> Date: Sun, 21 Jun 2026 09:43:00 +0000 Subject: [PATCH 2/2] chore(deps): bump actions/checkout from 4 to 7 Bumps [actions/checkout](https://github.com/actions/checkout) from 4 to 7. - [Release notes](https://github.com/actions/checkout/releases) - [Changelog](https://github.com/actions/checkout/blob/main/CHANGELOG.md) - [Commits](https://github.com/actions/checkout/compare/v4...v7) --- updated-dependencies: - dependency-name: actions/checkout dependency-version: '7' dependency-type: direct:production update-type: version-update:semver-major ... Signed-off-by: dependabot[bot] --- .github/workflows/ci.yml | 2 +- .github/workflows/publish.yml | 6 +++--- 2 files changed, 4 insertions(+), 4 deletions(-) diff --git a/.github/workflows/ci.yml b/.github/workflows/ci.yml index e021b59..0097c72 100644 --- a/.github/workflows/ci.yml +++ b/.github/workflows/ci.yml @@ -16,7 +16,7 @@ jobs: python-version: ["3.11", "3.12", "3.13"] steps: - - uses: actions/checkout@v4 + - uses: actions/checkout@v7 - name: Install uv uses: astral-sh/setup-uv@v4 diff --git a/.github/workflows/publish.yml b/.github/workflows/publish.yml index 5753120..6cf3a8f 100644 --- a/.github/workflows/publish.yml +++ b/.github/workflows/publish.yml @@ -23,7 +23,7 @@ jobs: name: Test before publish runs-on: ubuntu-latest steps: - - uses: actions/checkout@v4 + - uses: actions/checkout@v7 - name: Install uv uses: astral-sh/setup-uv@v4 @@ -44,7 +44,7 @@ jobs: version: ${{ steps.version.outputs.version }} is_prerelease: ${{ steps.version.outputs.is_prerelease }} steps: - - uses: actions/checkout@v4 + - uses: actions/checkout@v7 - name: Install uv uses: astral-sh/setup-uv@v4 @@ -137,7 +137,7 @@ jobs: permissions: contents: write steps: - - uses: actions/checkout@v4 + - uses: actions/checkout@v7 with: fetch-depth: 0