Gestern haben wir Cloud Mac vs. lokaler Mac veröffentlicht: Immer mehr Teams verlagern Claude Code, CodeGraph-Index und optional Ollama auf einen dauerhaft erreichbaren macOS-Knoten. Die verbreitete Annahme lautet dann: „Sobald wir in der Cloud sind, wird jeder git push grün.“ In der Praxis passiert oft das Gegenteil — der Agent feiert Erfolg in der SSH-Session, während GitHub Actions weiter auf ubuntu-latest läuft, xcodebuild fehlt oder macOS-Jobs eine halbe Stunde in der Warteschlange verbringen.
Dieser Artikel ist weder ein Wikipedia-Eintrag zu „GitHub Runner“ noch ein Registrierungs-Tutorial für actions/runner (das kommt in L1-Q02). Ziel ist eine erweiterbare Methode: den Cloud Mac AI Stack, in dem L1 beantwortet, warum eine Ausführungsschicht eigenständig existieren muss — und warum „Cloud Mac mieten“ ohne Runner nur eine Remote-Shell mit schöner Bandbreite bleibt.
Cloud Mac AI Stack · Slogan
Claude Code produziert Diff, GitHub Runner produziert Fact.
Statt nur „Agent / Tool / CI“ sprechen wir von Context → Diff → Fact → Workflow als Ergebnisarten. Diff = vorgeschlagene Änderungen; Fact = nachweisbare Builds und Checks. Inference (L2, optional) = private Modell-Tokens auf dem Knoten.
L1 im Stack
Claude Code (L3) beantwortet „wie ändere ich den Code?“ GitHub Runner (L1) beantwortet „darf die Organisation das mergen, signieren und ausliefern?“ Ohne L1 bleibt jeder Diff eine Meinung in einer Terminal-Session — kein Fact auf dem Merge-Button.
Stack-Sprache: Context → Diff → Fact → Workflow
Überall liest man von Claude Code, Cursor, MCP und OpenHands — selten davon, wer nach dem Edit die organisationale Wahrheit erzeugt. Im Cloud Mac AI Stack ordnen wir vier Ergebnisarten zu (L2 Inference ist separat):
Ergebniskette (≠ Laufzeit-Reihenfolge · siehe #stack-map)
Context → Diff → Fact → Workflow
(MCP) (Claude Code) (Runner) (OpenHands)
| Ebene | Rolle | Komponente | Stack-Ergebnis |
|---|---|---|---|
| L0 | Infrastruktur | Cloud Mac | macOS-Laufzeitfläche |
| L1 | Ausführung | GitHub Runner | Fact |
| L2 | Inferenz | Ollama | Inference (optional) |
| L3 | Kodierung | Claude Code | Diff |
| L4 | Werkzeugverbindung | MCP | Context |
| L5 | Autonome Ausführung | OpenHands | Workflow |
Die Frage ist nicht „ist das LLM schlau genug?“, sondern: Existiert L1 als eigene Schicht? Ohne Fact wird kein PR grün, egal wie brillant Context und Diff wirken.
Kodierung vs. Ausführung: warum „Cloud Mac“ die CI-Kette nicht automatisch schließt
In Cloud Mac vs. lokaler Mac trennen wir Modell-Inference (API) von Agent-Ausführung (Shell auf macOS). Eine zweite Trennung übersehen viele Teams: die CI-Kette nach dem Push — wiederholbar, auditierbar, unabhängig von der SSH-Session.
| Schicht | Typisch | Trigger | Frage |
|---|---|---|---|
| Kodierung / Agent | Claude Code, Cursor | Terminal, IDE | „Hilf mir, diesen PR fertigzustellen“ |
| Ausführung / CI | GitHub Actions + self-hosted Runner | push, PR, Cron | „Baut und testet dieser Commit in der definierten Umgebung?“ |
Die Kluft: Claude Code läuft auf dem Cloud Mac, lokale Tests sind grün — das Workflow-Ziel bleibt ubuntu-latest. Die offizielle Repo-Wahrheit bleibt rot. Für iOS-Teams startet keine TestFlight-Pipeline auf Linux. L1 braucht oft dieselbe Apple-Silicon-macOS-Klasse wie die Entwickler-Maschine.
In DACH-Projekten sehen wir das besonders nach Agent-Piloten: Compliance fragt nach reproduzierbaren Builds, nicht nach Screenshots aus der SSH-Session. Runner übersetzen „Agent sagt OK“ in Fact — Logs, Artefakte, grüne Checks.
Typischer Irrtum: „Alle Tests bestanden“ — PR trotzdem rot
Ein wiederkehrendes Muster aus Kunden-Repos (besser merkbar als ein Diagramm allein):
- Entwickler:in nutzt Claude Code per SSH auf dem Cloud Mac. Antwort: „Alle Tests bestanden.“
git push, Meeting mit gutem Gefühl.- Actions startet mit
runs-on: ubuntu-latest. - PR-Checks rot; Log oft:
xcodebuild: command not found— oder nur Node-Tests grün, kein iOS-Job.
Claude Code ist nicht „schuld“ — die Umgebung in der Session ≠ CI-Umgebung. Der Runner reproduziert die Session-Aussage als Fact auf derselben GitHub Actions self-hosted runner macOS-Linie. Optional auf demselben Knoten wie der Agent.
Runner ist nicht „noch ein Mac mieten“
- Kein reines Cloud-Mac-Produktblatt — Miete ist L0; Runner ist Prozess + Labels + Workspace-Policy auf L0.
- Kein Handbuch zu
macos-latest— Hosted und Self-Hosted sind verschiedene Warteschlangen- und Kostenmodelle. - Kein Ersatz für OpenClaw — dort geht es um Workflow-Orchestrierung und Quittungen; Runner führt
xcodebuildundfastlaneaus.
Cloud Mac liefert macOS und Netz; Runner koppelt diese Kapazität an GitHubs Event-Modell. Merksatz: Ohne Runner ist Cloud Mac ein Remote-Desktop; mit Runner wird er Infrastruktur.
Fünf Ebenen · Stack ≠ Aufrufreihenfolge (#stack-map)
Folgeartikel L2–L5 verlinken hierher. Das Diagramm zeigt Verantwortungsebenen, nicht „wer ruft wen zuerst auf“.
Wichtig
- Claude Code braucht kein Ollama — L3 oft per API; L2 Inference optional.
- MCP über L3 in der Grafik = Context-Schicht, nicht „MCP startet vor dem CLI“.
- Rollout siehe #stack-order — anders als die Traglast von unten nach oben.
Cloud Mac AI Stack (Verantwortung · unten → oben)
┌──────────────┐
│ OpenHands │ L5 · Workflow
└──────┬───────┘
│
┌──────▼───────┐
│ MCP │ L4 · Context
└──────┬───────┘
│
┌──────▼───────┐
│ Claude Code │ L3 · Diff
└──────┬───────┘
│
┌──────▼───────┐
│ Ollama │ L2 · Inference (optional)
└──────┬───────┘
│
┌──────▼───────┐
│ GitHub Runner│ L1 · Fact ← dieser Artikel
└──────┬───────┘
│
┌──────▼───────┐
│ Cloud Mac │ L0
└──────────────┘
L0 trägt Rechenleistung; L1 trägt Vertrauen der Organisation (Fact); darüber Diff, Context, Workflow.
Warum „Execution Engine“: Aufgaben und iOS-Kette
Als Execution Engine (Ausführungsmotor) übernimmt L1 drei wiederholbare Jobs:
- Repo-Events —
push,pull_request,workflow_dispatch→ Jobs mit Runner-Labels. - macOS-Toolchain —
xcodebuild,swift test,notarytool, Signing — auf Linux nicht ersetzbar. - Entkopplung von AI — Agent-Edit ≠ grüne CI; Runner liefert Artefakte und Reports.
L1-Kette (konzeptionell)
Claude Code (L3, SSH)
│ git push
▼
GitHub Actions
▼
Runner (L1 · self-hosted · macOS · ARM64)
├── xcodebuild
├── Tests
├── archive → .ipa
└── fastlane → TestFlight
Kodierung in L3; Binär-Auslieferung in L1. Fehlt L1, bleibt „Agent fertig“ ohne Paket in App Store Connect.
# .github/workflows/ios-ci.yml (Auszug) jobs: build-ios: runs-on: [self-hosted, macOS, ARM64, cloud-mac] steps: - uses: actions/checkout@v4 - run: xcodebuild -scheme MyApp -destination 'platform=iOS Simulator,name=iPhone 16' test
Suchintention: selten „GitHub Runner“, oft iOS CI / Mac mini
Entwickler:innen tippen eher:
- GitHub Actions self-hosted runner macOS / Apple Silicon runner
- GitHub Runner Mac mini / iOS CI/CD self-hosted
- GitHub Actions iOS build / TestFlight-Automatisierung
Gemeinsame Architekturfrage: Jobs auf eigenen M-Serie-Knoten statt Linux-Pool oder wartendem macos-latest. Cloud Mac oder Büro-Mac mini = Hardware; Runner-Registrierung + Labels = L1. Vergleich Hardware: Mac mini vs. Cloud Mac für iOS-Teams. Kosten-Topic L1-Q05 folgt.
Wenn Linux reicht — und wann nicht
| Dimension | ubuntu-latest | Cloud Mac self-hosted |
|---|---|---|
| Xcode / iOS | ❌ | ✅ nativ |
| ARM64-Konsistenz | abweichend | wie Dev-Maschine |
| Claude Code gleicher Knoten | ❌ | ✅ optional |
| Tages-CI | Minuten + Queue | fester Knoten |
Oft reicht Linux (kein Zwang zu Cloud Mac): Next.js-Static, Node/Python/Go-APIs in Docker, kleine Hobby-Repos mit seltenem CI. macOS Runner-Signal: Xcode, Signing, Simulator, TestFlight in Workflows — oder ihr evaluiert bereits Mac mini vs. Cloud Mac.
Hosted macos-latest vs. Self-Hosted auf Cloud Mac
| Hosted | Self-hosted Cloud Mac |
|---|---|
| selten archive, <5 macOS-Jobs/Monat | tägliche CI, feste Zertifikate |
| Queue + Minutenpreis akzeptabel | AI + CI gleicher Stack, eine Maschine beobachten |
| kein fixes Egress-IP | statische IP, Intranet-Artefakte, CodeGraph zeitversetzt |
Daumenregel (keine Garantie): >10 macOS-Jobs/Woche, davon viele Sign/Archive → L1 auf festem Knoten. Darunter: erst Hosted macOS, Pipeline validieren.
Rollout: zuerst Fact, dann Diff
Strukturdiagramm = Verantwortung; Deployment oft umgekehrt zur Hype-Reihenfolge:
- L0 — Cloud Mac (SSH, Egress).
- L1 — Runner, reproduzierbares
push → grün/rot(dieser Text). - L2–L3 — Ollama Inference, Claude Code Diff auf stabiler CI.
- L4–L5 — MCP Context, OpenHands Workflow.
CodeGraph + Agent kann 18 Dateien ändern — ohne macOS-CI wisst ihr nicht, ob Archive später explodiert. Ergänzend: Mac mini + Claude Code 2026 (L3-Erfahrung); hier L1 — nachts Runner, tags Agent, getrennte Verantwortung.
Entscheidung: L1 als Execution Engine
| L1 zuerst (self-hosted auf Cloud Mac) | optional |
|---|---|
| Native iOS/macOS-Apps | reine Static-Sites |
| Flutter mit iOS/Xcode-Pfad | nur Android/Web |
| Claude Code auf Cloud Mac, CI noch Linux | Node/Python nur Docker/Linux |
| TestFlight / Notarize automatisieren | seltene Hobby-Releases |
| feste IP, CodeGraph auf gleichem Host | seltenes macos-latest reicht |
Zwei Treffer links? Nächster Schritt: L1 betreiben, nicht noch ein MCP-Server. Tutorial: L1-Serie.
L1-Serie: von der Execution Engine zu betriebsfähigem macOS-CI
Grundstein L1-Q01 (dieser Artikel). Geplant:
| Teil | qid | Status |
|---|---|---|
| L1-Q01 · Warum Runner = Execution Engine | Diff → Fact | ✅ |
| L1-Q02 · Registrierung auf Cloud Mac | Schritt-für-Schritt | als Nächstes |
| L1-Q03 · Claude Code + CI auf einem Host | Zeitfenster | geplant |
| L1-Q04 · Workspace-Isolation | Sicherheit | geplant |
| L1-Q05 · Mac mini vs. Cloud Mac Kosten | Queue | geplant |
Google bündelt Cluster-Artikel; L2+ baut auf vorhandenem Fact auf — Rücklink #stack-map.
FAQ
Cloud Mac vs. Runner?
L0 vs. L1. Miete ≠ Runner automatisch.
Nur MacBook als Runner?
Möglich; Deckel zu, RAM-Kampf mit Agent, wechselnde IP. Tägliches macOS-CI → 24/7 Cloud Mac.
Runner und Claude Code gleicher Rechner?
Nicht Pflicht; gleicher Knoten reduziert SSH-grün / Actions-rot.
OpenClaw?
Runner = Steps; OpenClaw = Workflow-Trigger. Siehe OpenClaw Cloud Automation.
Diff vs. Fact?
Diff = Agent-Änderung; Fact = Checks, Logs, Artefakte. Merge nutzt Fact. MCP = Context; OpenHands = Workflow.
Ollama unter Claude Code im Diagramm — Pflicht?
Nein. L2 Inference optional; L3 oft API. Siehe #stack-map.
L1 · Als Nächstes L1-Q02
Self-hosted GitHub Actions Runner auf Cloud Mac (macOS)
Hier: warum L1. Danach: Labels, actions/runner, launchd, Token-Rotation — Diff und Fact auf einem Apple-Silicon-Knoten.
