> ## Documentation Index
> Fetch the complete documentation index at: https://docs.flowdeck.studio/llms.txt
> Use this file to discover all available pages before exploring further.

# Xcodebuild Arguments

> Pass custom arguments and environment variables to xcodebuild

FlowDeck provides full access to xcodebuild's capabilities through custom arguments and environment variables. You can configure builds using three methods.

## Methods Overview

| Method                                                      | Best For                                | Priority |
| ----------------------------------------------------------- | --------------------------------------- | -------- |
| [CLI Options](#cli-options)                                 | Quick one-off builds, testing flags     | Highest  |
| [Legacy Local Build Settings](#legacy-local-build-settings) | Compatibility with older project setups | Medium   |
| [Config File](#config-file)                                 | CI/CD, reproducible builds              | Lowest   |

When multiple sources provide arguments, they're merged with CLI taking highest priority.

## Preferred Project Settings Format

For shared project settings, prefer storing xcodebuild passthrough values in:

* `.flowdeck/config.json`
* `.flowdeck/config.local.json`

Example:

```json theme={null}
{
  "xcodebuild": {
    "args": ["-enableCodeCoverage", "YES"],
    "env": {
      "CI": "true"
    }
  },
  "schemes": {
    "MyApp": {
      "xcodebuild": {
        "args": ["-quiet"],
        "env": {}
      }
    }
  }
}
```

Use the top-level `xcodebuild` block for project-wide defaults, and `schemes.<scheme>.xcodebuild` for per-scheme overrides.

## CLI Options

### Xcodebuild Arguments

Use `--xcodebuild-options` to pass arguments to xcodebuild:

```bash theme={null}
# Single argument
flowdeck build -w App.xcworkspace -s MyApp -S "iPhone 16" \
  --xcodebuild-options='-enableCodeCoverage YES'

# Multiple arguments
flowdeck build -w App.xcworkspace -s MyApp -S "iPhone 16" \
  --xcodebuild-options='-enableCodeCoverage YES ONLY_ACTIVE_ARCH=NO GCC_TREAT_WARNINGS_AS_ERRORS=YES'

# Build settings (KEY=VALUE format)
flowdeck run -w App.xcworkspace -s MyApp -S "iPhone 16" \
  --xcodebuild-options='CODE_SIGN_IDENTITY=- CODE_SIGNING_REQUIRED=NO'
```

<Tip>
  Use `=` syntax (e.g., `--xcodebuild-options='...'`) when values start with `-` to avoid argument parsing issues.
</Tip>

### Xcodebuild Environment

Use `--xcodebuild-env` to set environment variables for the build:

```bash theme={null}
flowdeck build -w App.xcworkspace -s MyApp -S "iPhone 16" \
  --xcodebuild-env='CI=true DEVELOPER_DIR=/Applications/Xcode-15.4.app/Contents/Developer'
```

### Combining Options

All options can be combined:

```bash theme={null}
flowdeck build -w App.xcworkspace -s MyApp -S "iPhone 16" \
  --xcodebuild-options='-quiet -enableCodeCoverage YES' \
  --xcodebuild-env='CI=true'
```

### Works with All Commands

```bash theme={null}
# Build
flowdeck build -w App.xcworkspace -s MyApp -S "iPhone 16" \
  --xcodebuild-options='-enableCodeCoverage YES'

# Run
flowdeck run -w App.xcworkspace -s MyApp -S "iPhone 16" \
  --xcodebuild-options='ONLY_ACTIVE_ARCH=YES'

# Test
flowdeck test -w App.xcworkspace -s MyApp -S "iPhone 16" \
  --xcodebuild-options='-parallel-testing-enabled YES'
```

### Test Result Bundle Routing

`flowdeck test` owns one result bundle per xcodebuild phase so each bundle is finalized exactly once:

* `build-for-testing` writes `~/.flowdeck/logs/<project-hash>/build-test.xcresult`.
* `test-without-building` writes `~/.flowdeck/logs/<project-hash>/test.xcresult` by default.
* A caller-supplied `-resultBundlePath` overrides only the test-phase path.

Both `-resultBundlePath <path>` and `-resultBundlePath=<path>` are accepted. When arguments from multiple sources contain the flag, the last valid value wins. FlowDeck removes the duplicates before invoking xcodebuild and normalizes the selected result to an absolute path. The final `flowdeck.test` JSON snapshot reports that same path as `resultBundlePath`.

## Legacy Local Build Settings

Create `.flowdeck/build-settings.json` in your project root for settings that apply to all FlowDeck commands automatically:

```json theme={null}
{
  "args": [
    "ONLY_ACTIVE_ARCH=YES",
    "GCC_TREAT_WARNINGS_AS_ERRORS=YES",
    "-enableCodeCoverage", "YES"
  ],
  "env": {
    "CUSTOM_BUILD_VAR": "value"
  }
}
```

This file is a legacy compatibility format and is still auto-loaded by current CLI runtime paths.

<Info>
  Prefer `.flowdeck/config.json` or `.flowdeck/config.local.json` for new setup. Keep `.flowdeck/build-settings.json` only when you need compatibility with older workflows.
</Info>

### Structure

| Field  | Type   | Description                                      |
| ------ | ------ | ------------------------------------------------ |
| `args` | array  | Arguments appended to xcodebuild command line    |
| `env`  | object | Environment variables set for xcodebuild process |

## Config File

Include xcodebuild settings in your `--config` JSON file:

```json theme={null}
{
  "workspace": "MyApp.xcworkspace",
  "scheme": "MyApp",
  "platform": "iOS",
  "xcodebuild": {
    "args": [
      "-enableCodeCoverage", "YES",
      "-resultBundlePath", "./build/results.xcresult"
    ],
    "env": {
      "CI": "true"
    }
  }
}
```

Use with:

```bash theme={null}
flowdeck test --config path/to/config.json
```

<Info>
  `--config` uses the explicit command config format, which is separate from `.flowdeck/config.json` and `.flowdeck/config.local.json`. See [Configuration File](/cli/configuration-file) for the difference.
</Info>

## Priority and Merging

When arguments come from multiple sources, they're combined in this order:

1. **Config file** (lowest priority) - base configuration
2. **Local build-settings.json** - compatibility override for current CLI auto-load behavior
3. **CLI options** (highest priority) - appended last, takes effect

**Example:**

```bash theme={null}
# Config file has: ONLY_ACTIVE_ARCH=YES
# Local settings has: GCC_TREAT_WARNINGS_AS_ERRORS=YES
# CLI: --xcodebuild-options='ONLY_ACTIVE_ARCH=NO'

# Final xcodebuild args include:
# ONLY_ACTIVE_ARCH=YES (from config, overridden)
# GCC_TREAT_WARNINGS_AS_ERRORS=YES (from local)
# ONLY_ACTIVE_ARCH=NO (from CLI, takes effect because it's last)
```

## Common Arguments Reference

### Build Settings

| Argument                             | Description                                              |
| ------------------------------------ | -------------------------------------------------------- |
| `ONLY_ACTIVE_ARCH=YES`               | Build only for active architecture (faster debug builds) |
| `ONLY_ACTIVE_ARCH=NO`                | Build for all architectures (required for distribution)  |
| `CODE_SIGN_IDENTITY=-`               | Disable code signing                                     |
| `CODE_SIGNING_REQUIRED=NO`           | Skip code signing requirement                            |
| `GCC_TREAT_WARNINGS_AS_ERRORS=YES`   | Fail build on C/Obj-C warnings                           |
| `SWIFT_TREAT_WARNINGS_AS_ERRORS=YES` | Fail build on Swift warnings                             |

### Xcodebuild Flags

| Flag                                   | Description                                                                                       |
| -------------------------------------- | ------------------------------------------------------------------------------------------------- |
| `-quiet`                               | Suppress most xcodebuild output                                                                   |
| `-enableCodeCoverage YES`              | Enable code coverage collection                                                                   |
| `-resultBundlePath <path>`             | Override the finalized test-phase xcresult path during `flowdeck test`; the last valid value wins |
| `-allowProvisioningUpdates`            | Allow automatic provisioning updates                                                              |
| `-allowProvisioningDeviceRegistration` | Allow automatic device registration                                                               |
| `-parallel-testing-enabled YES`        | Enable parallel test execution                                                                    |
| `-parallel-testing-worker-count <n>`   | Number of parallel test workers                                                                   |

### Compiler Flags

| Argument                    | Description                     |
| --------------------------- | ------------------------------- |
| `OTHER_SWIFT_FLAGS=<flags>` | Additional Swift compiler flags |
| `OTHER_CFLAGS=<flags>`      | Additional C compiler flags     |
| `OTHER_LDFLAGS=<flags>`     | Additional linker flags         |

## Environment Variables

Set environment variables for the xcodebuild process:

### Via CLI

```bash theme={null}
flowdeck build -w App.xcworkspace -s MyApp -S "iPhone 16" \
  --xcodebuild-env='CI=true DEVELOPER_DIR=/Applications/Xcode-15.4.app/Contents/Developer'
```

### In Local Settings

```json theme={null}
{
  "args": [],
  "env": {
    "CI": "true",
    "DEVELOPER_DIR": "/Applications/Xcode-15.4.app/Contents/Developer"
  }
}
```

### In Config File

```json theme={null}
{
  "workspace": "MyApp.xcworkspace",
  "scheme": "MyApp",
  "xcodebuild": {
    "env": {
      "DEVELOPER_DIR": "/Applications/Xcode-15.4.app/Contents/Developer"
    }
  }
}
```

### Common Environment Variables

| Variable              | Description                                             |
| --------------------- | ------------------------------------------------------- |
| `CI`                  | Indicates CI environment (affects some Xcode behaviors) |
| `DEVELOPER_DIR`       | Override Xcode installation path                        |
| `XCODE_XCCONFIG_FILE` | Path to custom xcconfig file                            |

<Note>
  The canonical shared project-settings format is `xcodebuild` inside `.flowdeck/config.json` or `.flowdeck/config.local.json`. The separate `build-settings.json` file remains a legacy compatibility input.
</Note>

## Use Cases

<AccordionGroup>
  <Accordion title="Code Coverage">
    ```bash theme={null}
    flowdeck test -w App.xcworkspace -s MyApp -S "iPhone 16" \
      --xcodebuild-options='-enableCodeCoverage YES -resultBundlePath ./coverage/results.xcresult'
    ```

    Extract coverage after tests:

    ```bash theme={null}
    xcrun xccov view --report ./coverage/results.xcresult
    ```
  </Accordion>

  <Accordion title="Parallel Testing">
    ```bash theme={null}
    flowdeck test -w App.xcworkspace -s MyApp -S "iPhone 16" \
      --xcodebuild-options='-parallel-testing-enabled YES -parallel-testing-worker-count 4'
    ```
  </Accordion>

  <Accordion title="CI Build (No Code Signing)">
    ```bash theme={null}
    flowdeck build -w App.xcworkspace -s MyApp -S "iPhone 16" \
      --xcodebuild-options='CODE_SIGN_IDENTITY=- CODE_SIGNING_REQUIRED=NO'
    ```
  </Accordion>

  <Accordion title="Use Different Xcode Version">
    ```bash theme={null}
    flowdeck build -w App.xcworkspace -s MyApp -S "iPhone 16" \
      --xcodebuild-env='DEVELOPER_DIR=/Applications/Xcode-15.4.app/Contents/Developer'
    ```

    Or create `.flowdeck/build-settings.json`:

    ```json theme={null}
    {
      "args": [],
      "env": {
        "DEVELOPER_DIR": "/Applications/Xcode-15.4.app/Contents/Developer"
      }
    }
    ```
  </Accordion>

  <Accordion title="Strict Warnings">
    ```bash theme={null}
    flowdeck build -w App.xcworkspace -s MyApp -S "iPhone 16" \
      --xcodebuild-options='GCC_TREAT_WARNINGS_AS_ERRORS=YES SWIFT_TREAT_WARNINGS_AS_ERRORS=YES'
    ```
  </Accordion>

  <Accordion title="Address Sanitizer">
    ```bash theme={null}
    flowdeck build -w App.xcworkspace -s MyApp -S "iPhone 16" \
      --xcodebuild-options='"OTHER_SWIFT_FLAGS=-sanitize=address" "OTHER_CFLAGS=-fsanitize=address" "OTHER_LDFLAGS=-fsanitize=address"'
    ```
  </Accordion>

  <Accordion title="Quiet Build with Coverage (CI)">
    ```bash theme={null}
    flowdeck test -w App.xcworkspace -s MyApp -S "iPhone 16" \
      --xcodebuild-options='-quiet -enableCodeCoverage YES' \
      --xcodebuild-env='CI=true'
    ```
  </Accordion>
</AccordionGroup>

## Viewing the Final Command

Use `--dry-run` to see the complete xcodebuild command with all arguments without executing:

```bash theme={null}
flowdeck build -w App.xcworkspace -s MyApp -S "iPhone 16" --dry-run \
  --xcodebuild-options='-enableCodeCoverage YES'
```

Use `--verbose` to see the command during actual execution:

```bash theme={null}
flowdeck build -w App.xcworkspace -s MyApp -S "iPhone 16" --verbose \
  --xcodebuild-options='-enableCodeCoverage YES'
```

## Troubleshooting

### Values Starting with Dash

Use `=` syntax when values start with `-`:

```bash theme={null}
# Won't work - ArgumentParser sees -quiet as a new option
flowdeck build ... --xcodebuild-options -quiet

# Works - use = syntax
flowdeck build ... --xcodebuild-options='-quiet -enableCodeCoverage YES'
```

### Build Settings Format

Use `KEY=VALUE` format (no spaces around `=`):

```bash theme={null}
# Correct
flowdeck build ... --xcodebuild-options='ONLY_ACTIVE_ARCH=YES'

# Wrong
flowdeck build ... --xcodebuild-options='ONLY_ACTIVE_ARCH = YES'
```

### JSON Array Format

In config files, each argument is a separate array element:

```json theme={null}
{
  "xcodebuild": {
    "args": ["-enableCodeCoverage", "YES"]
  }
}
```

Not:

```json theme={null}
{
  "xcodebuild": {
    "args": ["-enableCodeCoverage YES"]
  }
}
```
