Revyl Documentation

Builds / Remote builds

Caching

Speed up remote builds with compilation and configured path caches

Every remote build runs in a clean, single-use VM. Revyl uses two kinds of caching to make repeat builds faster:

CacheDefaultBest for
Compilation cacheOnXcode, Gradle, and native C/C++ compilation
Configured path cacheOpt-inDependencies, generated files, and other project state

Automatic compilation caching

Revyl enables the right compilation caches for each platform without changing your build commands:

PlatformCaches
iOSXcode compilation cache
AndroidGradle build cache and ccache for native C/C++

The first compatible build warms the cache. Later builds on the same toolchain can reuse its compiler outputs across apps and branches in your organization.

The snippets below focus on cache fields. Keep the selected recipe's runnable app_id, build_commands, and output_path from your build configuration.

You can turn each cache off independently:

build:
  framework: react_native
  profiles:
    development:
      ios:
        build_commands: ["./scripts/build-ios"]
        env:
          REVYL_XCODE_COMPILATION_CACHE_ENABLED: "0"
      android:
        build_commands: ["./scripts/build-android"]
        env:
          REVYL_GRADLE_BUILD_CACHE_ENABLED: "0"
          REVYL_CCACHE_ENABLED: "0"

Each setting accepts "0" (off) or "1" (on) and defaults to "1".

Compilation caching is an optimization, not a build dependency. If it is unavailable, the build continues normally. It is also skipped when the build timeout is longer than 60 minutes.

Configured path caches

Declare defaults under build.caches and recipe-specific additions under build.profiles.<name>.<platform>.caches. Each cache has a key and a list of paths stored under it:

build:
  framework: react_native
  caches:
    - key: javascript-dependencies
      paths:
        - node_modules
  profiles:
    development:
      ios:
        build_commands: ["./scripts/build-ios"]
        caches:
          - key: ios-dependencies
            paths:
              - ios/Pods
      android:
        build_commands: ["./scripts/build-android"]
        caches:
          - key: android-dependencies
            paths:
              - .gradle-home

Paths can be project-relative or start with ~/ to cache files in the build user's home directory. Absolute paths and paths that escape either root are rejected.

How configured caches work

Build-level and recipe caches merge by key. For a matching key, build-level paths come first and recipe paths are appended with duplicates removed. Each effective key maps to one compressed archive that Revyl stores between builds:

  1. After checkout, Revyl restores the latest archive to its declared project or home locations. A new key starts empty.
  2. Your commands read and write the configured paths normally, such as node_modules, Pods, or DerivedData.
  3. If the build succeeds, Revyl archives those exact paths and saves them for the next build. Failed builds don't update caches, so a broken run can't poison them.

Compressed archives larger than 4 GiB are not saved. The build still succeeds, and the previous saved archive remains available for later builds.

Cache keys are scoped to your organization and platform. Builds using the same key share that archive across apps and branches. Concurrent builds work in private VMs; the last successful upload becomes the next saved state.

What to cache

WorkRecommended cache
Xcode or Gradle compilationAutomatic compilation cache
Android native compilationAutomatic ccache
JavaScript dependenciesConfigured path cache
CocoaPodsConfigured path cache
Gradle dependency downloadsConfigured path cache
DerivedData or generated filesOptional path cache; measure first

For example:

build:
  framework: android
  profiles:
    release:
      android:
        build_commands:
          - ./gradlew assembleRelease
        caches:
          - key: android-dependencies
            paths:
              - ~/.gradle/caches/modules-*/files-*
              - ~/.gradle/caches/modules-*/metadata-*
              - ~/.gradle/wrapper

If you cache a build-output directory, keep output_path specific enough that it cannot select a stale artifact.

Cold builds and clearing caches

# Bypass every cache for one build without deleting anything
revyl build --profile development --platform ios --remote --no-cache

# Inspect and delete configured caches
revyl cache list
revyl cache delete ios-dependencies

revyl cache list and delete manage configured caches only. Compilation caches are managed automatically and can be bypassed with --no-cache or the individual environment settings above.

Troubleshooting

  • The second build is still slow: make sure the first build completed successfully and compare builds using the same toolchain.
  • Dependency installation is still slow: add its download or install directory to a configured cache.
  • A configured cache looks stale: try --no-cache, then delete the cache if the cold build fixes the problem.
  • Compilation caching is missing: check the build logs for compilation-cache messages and confirm the timeout is 60 minutes or less.

On this page