One workflow per platform. Steps are shell scripts, so existing build scripts work unchanged. Unknown keys are errors; validate locally with bakery recipe validate or against the JSON Schema.
workflows:
ios:
platform: ios # macOS oven, VM per job
xcode: "26"
code_signing: { distribution: app_store, bundle_id: com.acme.app }
steps:
- name: Pods
script: cd ios && pod install
- name: Archive
script: ./scripts/archive-ios.sh
artifacts: [build/ios/ipa/*.ipa]
publish: { app_store_connect: { submit_to_testflight: true } }
android:
platform: android # Linux oven, container
android_signing: { keystore: release }
verify_signing: { keystore: release }
steps:
- ./gradlew bundleRelease -PversionCode=$CB_BUILD_NUMBER
artifacts: ["app/build/outputs/bundle/release/*.aab"]platform and labels; jobs in a batch run in parallel.$CB_BUILD_NUMBER increases with every batch, for version codes and build numbers.tools: ({ node: 22, python: "3.12" }) and are installed with mise.$CB_ARTIFACTS_DIR, kept with the batch, and passed to deliveries.bakery bake (pushed branch or the local working tree).Reference: every recipe field, the platforms and preinstalled tools, and ready-made recipes for Android, iOS, Flutter, React Native, macOS, Linux and web. Running builds from a terminal or CI: the bakery CLI.
What happens between a push and a release.
push / pull request ─▶ webhook ─▶ batch #482 ─▶ scheduler
│
┌───────────────────────────┬───────────┴──────────────┐
▼ ▼ ▼
ios → macOS oven android → Linux oven windows → Windows oven
(Tart VM, cloned per job) (container per job) (WSL/Podman or native)
│ │ │
└──────────── artifacts + signing check ───────────────┘
│
┌──────────────────────┼─────────────────────────┐
▼ ▼ ▼
commit status PR comment with QR deliveries: TestFlight,
install link Google Play, Firebase,
S3/R2, SFTP, GitHub
Releases, webhook