Skip to content

chore(cli): release 5.66.1 #10543

chore(cli): release 5.66.1

chore(cli): release 5.66.1 #10543

Workflow file for this run

name: Update Seed
on:
push:
branches:
- main
workflow_dispatch:
inputs:
language:
description: 'Language to run seed for (leave as "all" to run all languages)'
required: false
default: "all"
type: choice
options:
- all
- typescript
- python
- java
- go
- csharp
- php
- swift
- rust
- openapi
- cli
commit-on-failure:
description: 'Commit successful seed changes even if some seed runs fail'
required: false
default: false
type: boolean
skip-scripts:
description: 'Skip running compile/test scripts during seed generation'
required: false
default: false
type: boolean
fixture:
description: 'Specific fixture to run'
required: false
default: "all"
type: string
# Cancel previous workflows on previous push
concurrency:
group: ${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: false
# These scope secrets.GITHUB_TOKEN
permissions:
pull-requests: write
contents: write
env:
DO_NOT_TRACK: "1"
DOCKER_BUILDKIT: 1
TURBO_TOKEN: ${{ secrets.TURBO_TOKEN }}
TURBO_TEAM: "buildwithfern"
TURBO_NO_UPDATE_NOTIFIER: "1"
TURBO_DAEMON: "false"
jobs:
setup:
if: github.repository == 'fern-api/fern'
runs-on: ubuntu-latest
timeout-minutes: 2
outputs:
skip-scripts: ${{ steps.set-update-options.outputs.skip-scripts }}
update-by-push: ${{ steps.set-update-options.outputs.update-by-push }}
update-by-pr: ${{ steps.set-update-options.outputs.update-by-pr }}
selected-language: ${{ steps.set-language-filter.outputs.selected-language }}
commit-on-failure: ${{ steps.set-commit-on-failure.outputs.commit-on-failure }}
selected-fixture: ${{ steps.set-fixture-filter.outputs.selected-fixture }}
steps:
# Apply by direct push for workflow_dispatches that aren't on main, apply by PR if running against main
- name: Set update options
id: set-update-options
shell: bash
run: |
if [[ "${{ github.event_name }}" == "workflow_dispatch" && "${{ github.ref }}" != "refs/heads/main" ]]; then
echo "skip-scripts=true" >> $GITHUB_OUTPUT
echo "update-by-push=true" >> $GITHUB_OUTPUT
echo "update-by-pr=false" >> $GITHUB_OUTPUT
else
# For workflow_dispatch, check if skip-scripts checkbox is checked
# For push events, default to false
if [[ "${{ github.event_name }}" == "workflow_dispatch" && "${{ github.event.inputs.skip-scripts }}" == "true" ]]; then
echo "skip-scripts=true" >> $GITHUB_OUTPUT
else
echo "skip-scripts=false" >> $GITHUB_OUTPUT
fi
echo "update-by-push=false" >> $GITHUB_OUTPUT
echo "update-by-pr=true" >> $GITHUB_OUTPUT
fi
- name: Set language filter
id: set-language-filter
shell: bash
run: |
# For workflow_dispatch events, use the input language filter
# For push events, default to 'all' to maintain existing behavior
if [[ "${{ github.event_name }}" == "workflow_dispatch" ]]; then
SELECTED_LANGUAGE="${{ github.event.inputs.language }}"
echo "Language filter from workflow_dispatch input: $SELECTED_LANGUAGE"
else
SELECTED_LANGUAGE="all"
echo "Push event detected, running all languages"
fi
echo "selected-language=$SELECTED_LANGUAGE" >> $GITHUB_OUTPUT
- name: Set commit-on-failure option
id: set-commit-on-failure
shell: bash
run: |
# For workflow_dispatch events, use the input commit-on-failure option
# For push events, default to 'false' to maintain existing behavior
if [[ "${{ github.event_name }}" == "workflow_dispatch" ]]; then
COMMIT_ON_FAILURE="${{ github.event.inputs.commit-on-failure }}"
echo "Commit on failure option from workflow_dispatch input: $COMMIT_ON_FAILURE"
else
COMMIT_ON_FAILURE="false"
echo "Push event detected, defaulting commit-on-failure to false"
fi
echo "commit-on-failure=$COMMIT_ON_FAILURE" >> $GITHUB_OUTPUT
- name: Set fixture filter
id: set-fixture-filter
shell: bash
run: |
# For workflow_dispatch events, use the input fixture filter
# For push events, default to 'all' to maintain existing behavior
if [[ "${{ github.event_name }}" == "workflow_dispatch" ]]; then
SELECTED_FIXTURE="${{ github.event.inputs.fixture }}"
echo "Fixture filter from workflow_dispatch input: $SELECTED_FIXTURE"
else
SELECTED_FIXTURE="all"
echo "Push event detected, running all fixtures"
fi
echo "selected-fixture=$SELECTED_FIXTURE" >> $GITHUB_OUTPUT
changes:
if: github.repository == 'fern-api/fern'
runs-on: ubuntu-latest
timeout-minutes: 5
strategy:
matrix:
generator-name: [seed, ruby-v2, openapi, python, java, typescript, go, csharp, php, swift, rust, cli]
include:
- files: |
packages/seed/
packages/ir-sdk/fern/apis/
packages/cli/generation/ir-generator/
test-definitions/
test-definitions-openapi/
generator-name: seed
- files: |
generators/ruby-v2/
seed/ruby-sdk-v2/
generator-name: ruby-v2
- files: |
generators/openapi/
seed/openapi/
generator-name: openapi
- files: |
generators/python/
generators/python-v2/
seed/pydantic/
seed/pydantic-v2/
seed/python-sdk/
generator-name: python
- files: |
generators/java/
generators/java-v2/
seed/java-sdk/
seed/java-model/
generator-name: java
- files: |
generators/typescript/
generators/typescript-v2/
seed/ts-sdk/
generator-name: typescript
- files: |
generators/go/
generators/go-v2/
seed/go-sdk/
seed/go-model/
generator-name: go
- files: |
generators/csharp/
seed/csharp-sdk/
seed/csharp-model/
generator-name: csharp
- files: |
generators/php/
seed/php-sdk/
seed/php-model/
generator-name: php
- files: |
generators/swift/
seed/swift-sdk/
generator-name: swift
- files: |
generators/rust/
seed/rust-model/
seed/rust-sdk/
generator-name: rust
- files: |
generators/cli/
seed/cli/
generator-name: cli
outputs:
seed: ${{ steps.set-output.outputs.seed-changes }}
ruby-v2: ${{ steps.set-output.outputs.ruby-v2-changes }}
openapi: ${{ steps.set-output.outputs.openapi-changes }}
python: ${{ steps.set-output.outputs.python-changes }}
java: ${{ steps.set-output.outputs.java-changes }}
typescript: ${{ steps.set-output.outputs.typescript-changes }}
go: ${{ steps.set-output.outputs.go-changes }}
csharp: ${{ steps.set-output.outputs.csharp-changes }}
php: ${{ steps.set-output.outputs.php-changes }}
swift: ${{ steps.set-output.outputs.swift-changes }}
rust: ${{ steps.set-output.outputs.rust-changes }}
cli: ${{ steps.set-output.outputs.cli-changes }}
steps:
- name: Checkout Files
uses: actions/checkout@v6
with:
sparse-checkout: |
${{ matrix.files }}
.github/
fetch-tags: false
- name: Setup Base SHA
id: setup-base-sha
env:
GH_TOKEN: ${{ github.token }}
run: |
BASE_SHA=""
if [[ "${{ github.event_name }}" == "workflow_dispatch" && "${{ github.ref }}" != "refs/heads/main" ]]; then
# Use GitHub API to get merge base - git merge-base doesn't work with shallow clones
CURRENT_SHA=$(git rev-parse HEAD)
MAIN_SHA=$(gh api "/repos/${{ github.repository }}/git/ref/heads/main" --jq '.object.sha')
MERGE_BASE=$(gh api \
"/repos/${{ github.repository }}/compare/${MAIN_SHA}...${CURRENT_SHA}" \
--jq '.merge_base_commit.sha')
echo "Merge base commit: $MERGE_BASE"
BASE_SHA=$MERGE_BASE
else
LAST_SUCCESS_SHA=$(gh api \
"/repos/${{ github.repository }}/actions/workflows/update-seed.yml/runs?branch=main&status=success&per_page=1" \
--jq '.workflow_runs[0].head_sha // empty' 2>/dev/null || echo "")
if [[ -n "$LAST_SUCCESS_SHA" ]]; then
echo "Last successful run SHA: $LAST_SUCCESS_SHA"
BASE_SHA=$LAST_SUCCESS_SHA
else
# Fetch 2 commits of main to get the previous commit
git fetch --no-tags --depth=2 origin main
PREVIOUS_SHA=$(git rev-parse origin/main~1)
echo "No successful run found, falling back to previous commit: $PREVIOUS_SHA"
BASE_SHA=$PREVIOUS_SHA
fi
fi
echo "base_sha=$BASE_SHA" >> $GITHUB_OUTPUT
- name: Get generator changes for ${{ matrix.generator-name }}
id: get-generator-changes
uses: ./.github/actions/check-for-changed-files
with:
base_sha: ${{ steps.setup-base-sha.outputs.base_sha }}
files: ${{ matrix.files }}
- name: Set output
id: set-output
run: |
echo "${{ matrix.generator-name }}-changes=${{ steps.get-generator-changes.outputs.any_changed }}" >> $GITHUB_OUTPUT
get-all-test-matrices:
runs-on: ubuntu-latest
timeout-minutes: 10
needs: [setup]
outputs:
ruby-sdk-v2: ${{ steps.create-dynamic-matrix.outputs.ruby-sdk-v2-test-matrix }}
pydantic: ${{ steps.create-dynamic-matrix.outputs.pydantic-test-matrix }}
python-sdk: ${{ steps.create-dynamic-matrix.outputs.python-sdk-test-matrix }}
openapi: ${{ steps.create-dynamic-matrix.outputs.openapi-test-matrix }}
java-sdk: ${{ steps.create-dynamic-matrix.outputs.java-sdk-test-matrix }}
java-model: ${{ steps.create-dynamic-matrix.outputs.java-model-test-matrix }}
ts-sdk: ${{ steps.create-dynamic-matrix.outputs.ts-sdk-test-matrix }}
go-model: ${{ steps.create-dynamic-matrix.outputs.go-model-test-matrix }}
go-sdk: ${{ steps.create-dynamic-matrix.outputs.go-sdk-test-matrix }}
csharp-model: ${{ steps.create-dynamic-matrix.outputs.csharp-model-test-matrix }}
csharp-sdk: ${{ steps.create-dynamic-matrix.outputs.csharp-sdk-test-matrix }}
php-model: ${{ steps.create-dynamic-matrix.outputs.php-model-test-matrix }}
php-sdk: ${{ steps.create-dynamic-matrix.outputs.php-sdk-test-matrix }}
swift-sdk: ${{ steps.create-dynamic-matrix.outputs.swift-sdk-test-matrix }}
rust-model: ${{ steps.create-dynamic-matrix.outputs.rust-model-test-matrix }}
rust-sdk: ${{ steps.create-dynamic-matrix.outputs.rust-sdk-test-matrix }}
cli: ${{ steps.create-dynamic-matrix.outputs.cli-test-matrix }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
- name: Install
uses: ./.github/actions/install
- name: Build Seed CLI
env:
FORCE_COLOR: "2"
run: pnpm seed:build
- name: Create Dynamic Matrix
id: create-dynamic-matrix
shell: bash
run: |
SELECTED_FIXTURE="${{ needs.setup.outputs.selected-fixture }}"
# List of all generators.
# Retired generators (pydantic v1 and the standalone *-model generators) are
# marked `disabled: true` in their seed.yml and are intentionally omitted here
# so the seed CLI does not error with "Generators X not found" when building
# the test matrix. Their per-generator seed-update jobs below are already
# gated with `if: false # generator not actively supported`.
GENERATORS="ruby-sdk-v2 python-sdk openapi java-sdk ts-sdk go-sdk csharp-sdk php-sdk swift-sdk rust-sdk cli"
# Process each generator and set its output
for GEN in $GENERATORS; do
# If a specific fixture is selected, use a single-item matrix with just that fixture
if [[ "$SELECTED_FIXTURE" != "all" ]]; then
echo "Specific fixture selected: $SELECTED_FIXTURE"
MATRIX="[{\"fixtures\":[\"$SELECTED_FIXTURE\"]}]"
else
# Query fixtures with auto-grouping (seed CLI calculates optimal group count)
MATRIX=$(node --enable-source-maps packages/seed/dist/cli.cjs list-test-fixtures --generator "$GEN" --groups auto)
fi
if [ -z "$MATRIX" ] || [ "$MATRIX" = "null" ] || [ "$MATRIX" = "undefined" ]; then
echo "Error: Failed to create matrix for $GEN"
exit 1
fi
echo "${GEN}-test-matrix=$MATRIX" >> $GITHUB_OUTPUT
echo "Set output for $GEN: $MATRIX"
done
ruby-sdk-v2-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
if: >-
${{
always() && !cancelled() &&
(needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'ruby') &&
(github.event_name == 'workflow_dispatch' || needs.changes.outputs.ruby-v2 == 'true' || needs.changes.outputs.seed == 'true') &&
needs.get-all-test-matrices.outputs.ruby-sdk-v2 != ''
}}
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.ruby-sdk-v2) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: ruby-sdk-v2
generator-path: generators/ruby-v2
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
pydantic-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
# if: >-
# ${{
# always() && !cancelled() &&
# (needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'python') &&
# (github.event_name == 'workflow_dispatch' || needs.changes.outputs.python == 'true' || needs.changes.outputs.seed == 'true') &&
# needs.get-all-test-matrices.outputs.pydantic != ''
# }}
if: false # generator not actively supported
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.pydantic) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: pydantic
generator-path: generators/python generators/python-v2
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
python-sdk-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
if: >-
${{
always() && !cancelled() &&
(needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'python') &&
(github.event_name == 'workflow_dispatch' || needs.changes.outputs.python == 'true' || needs.changes.outputs.seed == 'true') &&
needs.get-all-test-matrices.outputs.python-sdk != ''
}}
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.python-sdk) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: python-sdk
generator-path: generators/python
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
openapi-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
if: >-
${{
always() && !cancelled() &&
(needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'openapi') &&
(github.event_name == 'workflow_dispatch' || needs.changes.outputs.openapi == 'true' || needs.changes.outputs.seed == 'true') &&
needs.get-all-test-matrices.outputs.openapi != ''
}}
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.openapi) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: openapi
generator-path: generators/openapi
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
java-sdk-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
if: >-
${{
always() && !cancelled() &&
(needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'java') &&
(github.event_name == 'workflow_dispatch' || needs.changes.outputs.java == 'true' || needs.changes.outputs.seed == 'true') &&
needs.get-all-test-matrices.outputs.java-sdk != ''
}}
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.java-sdk) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: java-sdk
generator-path: generators/java generators/java-v2
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
java-model-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
# if: >-
# ${{
# always() && !cancelled() &&
# (needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'java') &&
# (github.event_name == 'workflow_dispatch' || needs.changes.outputs.java == 'true' || needs.changes.outputs.seed == 'true') &&
# needs.get-all-test-matrices.outputs.java-model != ''
# }}
if: false # generator not actively supported
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.java-model) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: java-model
generator-path: generators/java generators/java-v2
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
typescript-sdk-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
if: >-
${{
always() && !cancelled() &&
(needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'typescript') &&
(github.event_name == 'workflow_dispatch' || needs.changes.outputs.typescript == 'true' || needs.changes.outputs.seed == 'true') &&
needs.get-all-test-matrices.outputs.ts-sdk != ''
}}
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.ts-sdk) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: ts-sdk
generator-path: generators/typescript generators/typescript-v2
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
go-model-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
# if: >-
# ${{
# always() && !cancelled() &&
# (needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'go') &&
# (github.event_name == 'workflow_dispatch' || needs.changes.outputs.go == 'true' || needs.changes.outputs.seed == 'true') &&
# needs.get-all-test-matrices.outputs.go-model != ''
# }}
if: false # generator not actively supported
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.go-model) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: go-model
generator-path: generators/go generators/go-v2
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
go-sdk-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
if: >-
${{
always() && !cancelled() &&
(needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'go') &&
(github.event_name == 'workflow_dispatch' || needs.changes.outputs.go == 'true' || needs.changes.outputs.seed == 'true') &&
needs.get-all-test-matrices.outputs.go-sdk != ''
}}
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.go-sdk) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: go-sdk
generator-path: generators/go generators/go-v2
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
csharp-model-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
# if: >-
# ${{
# always() && !cancelled() &&
# (needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'csharp') &&
# (github.event_name == 'workflow_dispatch' || needs.changes.outputs.csharp == 'true' || needs.changes.outputs.seed == 'true') &&
# needs.get-all-test-matrices.outputs.csharp-model != ''
# }}
if: false # generator not actively supported
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.csharp-model) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: csharp-model
generator-path: generators/csharp
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
csharp-sdk-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
if: >-
${{
always() && !cancelled() &&
(needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'csharp') &&
(github.event_name == 'workflow_dispatch' || needs.changes.outputs.csharp == 'true' || needs.changes.outputs.seed == 'true') &&
needs.get-all-test-matrices.outputs.csharp-sdk != ''
}}
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.csharp-sdk) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: csharp-sdk
generator-path: generators/csharp
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
php-model-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
# if: >-
# ${{
# always() && !cancelled() &&
# (needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'php') &&
# (github.event_name == 'workflow_dispatch' || needs.changes.outputs.php == 'true' || needs.changes.outputs.seed == 'true') &&
# needs.get-all-test-matrices.outputs.php-model != ''
# }}
if: false # generator not actively supported
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.php-model) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: php-model
generator-path: generators/php
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
php-sdk-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
if: >-
${{
always() && !cancelled() &&
(needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'php') &&
(github.event_name == 'workflow_dispatch' || needs.changes.outputs.php == 'true' || needs.changes.outputs.seed == 'true') &&
needs.get-all-test-matrices.outputs.php-sdk != ''
}}
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.php-sdk) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: php-sdk
generator-path: generators/php
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
swift-sdk-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
if: >-
${{
always() && !cancelled() &&
(needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'swift') &&
(github.event_name == 'workflow_dispatch' || needs.changes.outputs.swift == 'true' || needs.changes.outputs.seed == 'true') &&
needs.get-all-test-matrices.outputs.swift-sdk != ''
}}
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.swift-sdk) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: swift-sdk
generator-path: generators/swift
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
rust-model-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
# if: >-
# ${{
# always() && !cancelled() &&
# (needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'rust') &&
# (github.event_name == 'workflow_dispatch' || needs.changes.outputs.rust == 'true' || needs.changes.outputs.seed == 'true') &&
# needs.get-all-test-matrices.outputs.rust-model != ''
# }}
if: false # generator not actively supported
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.rust-model) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: rust-model
generator-path: generators/rust
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
rust-sdk-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
if: >-
${{
always() && !cancelled() &&
(needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'rust') &&
(github.event_name == 'workflow_dispatch' || needs.changes.outputs.rust == 'true' || needs.changes.outputs.seed == 'true') &&
needs.get-all-test-matrices.outputs.rust-sdk != ''
}}
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.rust-sdk) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: rust-sdk
generator-path: generators/rust
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
cli-seed-update:
runs-on: ubuntu-latest
timeout-minutes: 60
needs: [changes, setup, get-all-test-matrices]
if: >-
${{
always() && !cancelled() &&
(needs.setup.outputs.selected-language == 'all' || needs.setup.outputs.selected-language == 'cli') &&
(github.event_name == 'workflow_dispatch' || needs.changes.outputs.cli == 'true' || needs.changes.outputs.seed == 'true') &&
needs.get-all-test-matrices.outputs.cli != ''
}}
strategy:
fail-fast: false # Let all tests run for debug, won't end up applying changes with a failure
max-parallel: 15 # Limit the number of runners for this job
matrix:
include: ${{ fromJSON(needs.get-all-test-matrices.outputs.cli) }}
steps:
- name: Checkout repo
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/actions/
- name: Update seed
uses: ./.github/actions/auto-update-seed
with:
generator-name: cli
generator-path: generators/cli
allow-unexpected-failures: true
fixtures-to-run: ${{ toJson(matrix.fixtures) }}
index: ${{ strategy.job-index }}
skip-scripts: ${{ needs.setup.outputs.skip-scripts }}
dockerhub-username: ${{ secrets.DOCKER_USERNAME_PUBLIC_READONLY }}
dockerhub-token: ${{ secrets.DOCKER_PASSWORD_PUBLIC_READONLY }}
# Use always() to ensure this runs even if stages from needs are skipped.
# By default, block on failures. If commit-on-failure is true, continue even if some seed runs fail.
commit-seed-changes-by-push:
if: >-
${{
always() && !cancelled() && needs.setup.outputs.update-by-push == 'true' &&
(needs.setup.outputs.commit-on-failure == 'true' || (!contains(needs.*.result, 'failure') && !contains(needs.*.result, 'cancelled')))
}}
needs:
[
changes,
setup,
ruby-sdk-v2-seed-update,
pydantic-seed-update,
python-sdk-seed-update,
openapi-seed-update,
java-sdk-seed-update,
java-model-seed-update,
typescript-sdk-seed-update,
go-model-seed-update,
go-sdk-seed-update,
csharp-model-seed-update,
csharp-sdk-seed-update,
php-model-seed-update,
php-sdk-seed-update,
swift-sdk-seed-update,
rust-model-seed-update,
rust-sdk-seed-update,
cli-seed-update
]
runs-on: ubuntu-latest
timeout-minutes: 10
steps:
# Get running branch name
- name: Extract Branch Name
id: extract-branch
shell: bash
run: |
echo "branch=${GITHUB_HEAD_REF:-${GITHUB_REF#refs/heads/}}" >> $GITHUB_OUTPUT
echo $branch
# Get action file specific to the running branch
- name: Checkout Action File
uses: actions/checkout@v6
with:
ref: ${{ steps.extract-branch.outputs.branch }}
sparse-checkout: |
.github/
# Match to all patch files, since we are committing all generator changes at once
# Checkout the branch directly to avoid detaching the head so we can commit back changes
- name: Apply Patches
id: apply-patches
uses: ./.github/actions/apply-update-seed-patches
with:
patch-pattern: seed-*.patch
checkout-ref: ${{ steps.extract-branch.outputs.branch }}
- name: Install
if: steps.apply-patches.outputs.has-patches == 'true'
uses: ./.github/actions/install
- name: Clean orphaned seed folders
if: steps.apply-patches.outputs.has-patches == 'true'
shell: bash
env:
FORCE_COLOR: "2"
run: |
pnpm seed:local clean
# Commit all applied patches back to branch (will be checked out in apply-patches step)
- name: Add and Commit Changes
id: commit-changes
uses: EndBug/add-and-commit@v10
if: ${{ steps.apply-patches.outputs.has-patches == 'true' }}
with:
add: "seed/*"
push: true
fetch: false
message: "Automated update of seed files"
# Combine ALL generator seed patches into a single PR instead of one per generator.
# This reduces the number of main-branch pushes (and the resulting CI cascade) from
# up to 16 down to 1, dramatically cutting runner consumption and release latency.
commit-seed-changes-by-pr:
if: >-
${{
always() && !cancelled() &&
github.ref == 'refs/heads/main' &&
needs.setup.outputs.update-by-pr == 'true'
}}
needs:
[
changes,
setup,
ruby-sdk-v2-seed-update,
pydantic-seed-update,
python-sdk-seed-update,
openapi-seed-update,
java-sdk-seed-update,
java-model-seed-update,
typescript-sdk-seed-update,
go-model-seed-update,
go-sdk-seed-update,
csharp-model-seed-update,
csharp-sdk-seed-update,
php-model-seed-update,
php-sdk-seed-update,
swift-sdk-seed-update,
rust-model-seed-update,
rust-sdk-seed-update,
cli-seed-update
]
runs-on: ubuntu-latest
timeout-minutes: 10
steps:
- name: Checkout Action File
uses: actions/checkout@v6
with:
sparse-checkout: |
.github/
# Apply ALL seed patches at once (seed-*.patch matches every generator)
- name: Apply Patches
id: apply-patches
uses: ./.github/actions/apply-update-seed-patches
with:
patch-pattern: seed-*.patch
- name: Install
if: steps.apply-patches.outputs.has-patches == 'true'
uses: ./.github/actions/install
- name: Clean orphaned seed folders
if: steps.apply-patches.outputs.has-patches == 'true'
shell: bash
env:
FORCE_COLOR: "2"
run: |
pnpm seed:local clean
- name: Create Pull Request
if: steps.apply-patches.outputs.has-patches == 'true'
id: cpr
uses: peter-evans/create-pull-request@v8
with:
token: ${{ secrets.FERN_SUPPORT_GH_ACTIONS_PAT }}
commit-message: "chore(seed): update all seed snapshots"
title: "chore(seed): update all seed snapshots"
branch: update-all-seed
body: "Auto-generated combined seed update PR.\nTrigger: ${{ github.event_name }} from branch: ${{ github.ref_name }}.\nWorkflow run: ${{ github.server_url }}/${{ github.repository }}/actions/runs/${{ github.run_id }}"
delete-branch: true
add-paths: |
seed/**
labels: |
seed
- name: Log PR Creation Failure
if: steps.cpr.outputs.pull-request-operation != 'created' && steps.cpr.outputs.pull-request-operation != 'updated'
shell: bash
run: |
echo "PR was not created, likely due to no diff for the generated seed output"
- name: Log PR Creation Details
if: steps.cpr.outputs.pull-request-operation == 'created'
shell: bash
run: |
echo "PR Created: ${{ steps.cpr.outputs.pull-request-url }}"
- name: Enable Pull Request Automerge
if: steps.cpr.outputs.pull-request-operation == 'created' || steps.cpr.outputs.pull-request-operation == 'updated'
uses: peter-evans/enable-pull-request-automerge@v3
with:
token: ${{ secrets.FERN_SUPPORT_GH_ACTIONS_PAT }}
pull-request-number: ${{ steps.cpr.outputs.pull-request-number }}
merge-method: squash
- name: Approve PR
if: steps.cpr.outputs.pull-request-operation == 'created' || steps.cpr.outputs.pull-request-operation == 'updated'
uses: ./.github/actions/auto-approve
with:
approver-gh-token: ${{ secrets.GITHUB_TOKEN }}
pull-request-number: ${{ steps.cpr.outputs.pull-request-number }}