GitHub Actions Runners with Local SSD Storage
WarpBuild BYOC Linux runners detect local NVMe SSDs at boot, RAID-0 them, and mount them to the work directory. Support matrix, instance types, and rates.
A GitHub Actions runner with local SSD storage runs its job on a machine that has NVMe disks attached to the instance itself, with the runner work directory mounted on those disks rather than on a network attached volume. On WarpBuild this is a BYOC behavior: choose an instance type that bundles local NVMe, and the runner detects, formats, and mounts the disks during boot with no label, no action, and no workflow change.
This page covers the three things that decide whether a job gets local SSD at all: which placements support the auto-mount, which instance families carry the disks, and what the arrangement bills. Mechanics come from the WarpBuild local SSD documentation and were re-checked on 2026-08-13.
Catalog
WarpBuild provides Linux x64, Linux ARM64, macOS, and Windows runners. BYOC runs on AWS, GCP, and Azure, and the local SSD auto-mount is documented on the Linux images of all three.
| Placement | Local SSD auto-mount |
|---|---|
| BYOC on AWS, Linux image | Supported |
| BYOC on GCP, Linux image | Supported |
| BYOC on Azure, Linux image | Supported |
| Windows runners | Not supported |
| macOS runners | Not supported |
Auto-mount is available on Linux based images only. A Windows or macOS runner set keeps its normal storage layout whatever instance type sits underneath it.
What the auto-mount changes for a build
During VM boot the runner detects every local NVMe device on the instance, creates a RAID-0 array when it finds more than one, formats the device or array with ext4, and mounts it to the runner work directory, for example /home/runner/work. The whole sequence finishes before any job starts.
Four consequences follow from that.
- One filesystem, whatever the disk count. Several local SSDs are striped into a single RAID-0 volume with the combined capacity of the members. RAID-0 carries no redundancy, which is the right trade for storage that is destroyed at the end of every job anyway.
- Only the work directory moves. Paths outside the work directory stay on the boot volume, so a build that writes its heavy output into
$HOMEor/tmpsees none of the change. - The storage is ephemeral. Local SSDs are tied to the instance lifecycle and every byte is lost when the runner terminates.
- Custom images are handled. For BYOC custom VM images the
mdadmpackage that RAID-0 needs is installed automatically when it is missing, across Ubuntu, Amazon Linux, and other common distributions.
WarpBuild Cloud runners take the other approach: the disk is fixed by the label and comes with the size in the catalog. Rates below are WarpBuild list prices per minute, verified on 2026-08-13 and published on the pricing page.
| Label family | Image | Storage | Per minute |
|---|---|---|---|
warp-ubuntu-latest-x64-2x to -32x | Ubuntu 24.04 | 150GB SSD | $0.004 to $0.064 |
warp-ubuntu-latest-arm64-2x to -32x | Ubuntu 24.04 | 150GB SSD | $0.003 to $0.048 |
warp-windows-latest-x64-4x to -32x | Windows Server 2022 | 256GB SSD | $0.016 to $0.128 |
warp-macos-26-arm64-6x | macOS 26 | 120GB SSD | $0.08 |
warp-macos-26-arm64-12x | macOS 26 | 270GB SSD | $0.16 |
Instance families that carry local NVMe
Local SSDs exist only on specific instance types, so the runner set configuration is where this feature is switched on in practice.
| Cloud provider | Instance types with bundled local NVMe |
|---|---|
| AWS | c5d, m5d, r5d, i3, c6id, m6id, r6id families |
| GCP | machine types ending in -lssd, such as c3-standard-88-lssd and c4a-standard-4-lssd |
| Azure | VM sizes with local NVMe temp storage, such as the Lsv3 and Lasv3 families |
A runner set accepts several instance types in priority order, and the runner picks one by availability at launch. Put local NVMe types in every slot of that list. A fallback type without local disks still runs the job, and the only visible effect is a job duration that moves around for a reason the workflow file does not explain.
Pricing
Pricing is purely usage based. There is no base subscription fee, no platform fee, and no seat fee. Local SSD has no line item of its own, because the disks ship with the instance your own cloud account is already paying for.
| Line item | Billed by | Rate |
|---|---|---|
| BYOC Linux runner minutes | WarpBuild | $0.002 per minute |
| BYOC Windows runner minutes (AWS and Azure) | WarpBuild | $0.002 per minute |
| BYOC add-ons, including cache | WarpBuild | Free |
| Instance time and its bundled local NVMe | Your cloud provider | Provider list price for the instance type |
Two figures fall out of that split. The WarpBuild fee on BYOC is flat at $0.002 per runner minute regardless of instance size, so moving from a small local-NVMe shape to a large one changes only the provider half of the bill. And a local-NVMe instance family usually lists above the general purpose family of the same core count, so the comparison to run is the provider price delta against the minutes the job stops spending on disk work, measured in your own account. Every WarpBuild rate quoted here comes from the pricing page and was verified on 2026-08-13.
Signup includes $10 free credits, which is 5,000 BYOC runner minutes at $0.002 per minute while you measure a shape against your workloads.
Configuration
There is nothing to configure in the workflow. The setup happens once, on the runner set.
- Create the runner set on your stack and choose instance types from the families above, listing several in priority order so a job does not sit in queue when one family is short on capacity in a region.
- Set the disk configuration. The documented minimum is 100GB and the documented best practice is 150GB. This is the boot volume, and it still holds everything outside the work directory.
- Reference the runner by its Runner ID, which is the full name with the
warp-custom-prefix.
name: build
on: push
jobs:
build:
runs-on: warp-custom-linux-lssd-16x
steps:
- name: Show where the work directory lives
run: |
df -h "$GITHUB_WORKSPACE"
lsblk -o NAME,SIZE,TYPE,MOUNTPOINT
cat /proc/mdstat || true
- uses: actions/checkout@v5
with:
fetch-depth: 0
- name: Build
run: ./gradlew build --no-daemonRun that first step once on a new runner set. lsblk shows the NVMe devices and where they are mounted, /proc/mdstat shows the RAID-0 array when the instance carries more than one disk, and df -h on $GITHUB_WORKSPACE shows the capacity the job actually has. If the work directory reports the boot volume size, the instance type in that runner set has no local NVMe.
On GCP the boot disk type is a separate decision from local SSD, and the runner creation UI exposes it. pd-balanced is the default, hyperdisk-balanced takes provisioned IOPS from 3,000 to 160,000 and throughput from 140 to 2,400 MiB/s, and hyperdisk-extreme takes provisioned IOPS from 300 to 350,000. Full field list and quota notes are in the BYOC GCP configuration documentation, and the choice between them is worked through on disk types for BYOC runners on GCP.
Which jobs gain the most
The work directory is the mount point, so the jobs that benefit are the ones whose disk work happens inside the workspace.
| Workload shape | Disk work inside the job | Signal to look for first |
|---|---|---|
| Full-history checkout of a large repository | Writing the object database and materializing the working tree | Checkout time that scales with repository size after the fetch has finished |
| Container image builds and pulls | Unpacking and writing layers into the local image store | Long gaps between layer progress lines with the network idle |
| Cache and artifact restore | Expanding a compressed archive into the workspace | Restore time longer than the download it followed |
| Test suites with large fixtures or heavy temporary output | Many small writes under the workspace | IO wait visible in the job system metrics |
Checkout-heavy repositories have other levers worth pulling first, and those are covered in the large repository GitHub Actions guide. To confirm that storage is the constraint before changing instance families, start from why does my job show high IO wait. The term itself is defined on local SSD.
FAQ
Do I need a runner label or a workflow change to use local SSD storage?
No. Local SSD auto-mount is decided by the instance type in your BYOC runner set. If the instance type carries local NVMe, the runner detects, formats, and mounts it to the work directory during boot, before the first step runs. The workflow file stays the same.
What happens if the instance type does not have local SSDs?
The runner uses the regular boot disk as usual. There is no error and no warning, so the only symptom is a job that takes as long as it did before. Check the instance families in your runner set, including the fallback types, when a change to disk behavior does not show up.
Does anything written to a local SSD survive to the next job?
No. Local SSDs are tied to the instance lifecycle and all data is lost when the runner terminates, which is expected because WarpBuild runners are ephemeral. State that has to cross jobs belongs in the cache or in object storage.
Start with $10 in free credits
Change the runner label in your workflow and keep the rest of your GitHub Actions setup. Runner time is billed per minute.