Skip to main content
This guide is for Aspect Workflows customers moving from the legacy Rosetta task runner (.aspect/workflows/config.yaml, rosetta run <task>) to Aspect CLI AXL tasks (aspect <task>). New to Aspect CLI tasks? See Tasks for the general overview.

Why migrate

AXL tasks are where Aspect Workflows is going. Moving off the legacy Rosetta YAML task runner unlocks capabilities the YAML-configured tasks can’t reach — and the biggest one changes how you receive every future improvement. The big one: fixes and features reach you on a version.axl bump, not an infrastructure upgrade. AXL tasks ship inside the Aspect CLI and are pinned per-repo in .aspect/version.axl. With legacy Rosetta, task behavior was baked into the Workflows CI runners, so picking up a fix or a new capability meant a coordinated infrastructure upgrade. With AXL, the same improvement is a one-line version() bump in your own repo — you pull it the day it lands, at your own pace, and every developer and CI runner gets identical, reproducible behavior. This is also why we can ship to AXL tasks much faster than we ever could to Rosetta. Beyond that, AXL tasks bring genuinely new capabilities:
  • New status checks. Dedicated per-task status checks surface results right on the commit — including a lint status check carrying the lint findings and a delivery status check carrying the delivery results. The aggregate PR/MR task-summary comment (GithubStatusComments / GitlabStatusComments) is substantially improved over the legacy comment.
  • Clearer CLI output. Every task’s terminal output is improved, with clearly delineated phases for multi-phase tasks like lint and delivery and a timing summary at the end of each run.
  • Faster selective delivery. Selective delivery’s change detection now uses an optimized, remote-cache-based hash check — it reads the action digest straight from the remote cache instead of downloading each target’s artifacts to hash them locally.
  • Customize the product in AXL. AXL opens up extension points the YAML runner never had:
  • Self-contained and portable. Each aspect <task> runs directly from your CI config — the Workflows Environment setup and Agent Health Check steps fold into the invocation, removing boilerplate from your CI YAML. Migrate one task at a time: flip lint to aspect lint while build and test stay on rosetta run, so the blast radius of any surprise is a single CI step.
More is on the way — customizable status check and PR-summary templates and Bazel output filtering are coming soon.
Legacy Rosetta YAML-configured tasks are being wound down. No new features are being added to them, and support is being removed entirely:
  • Workflows 5.19 — support for Rosetta YAML-configured tasks becomes opt-in.
  • Workflows 5.20 — support is removed entirely.
Migrating to AXL tasks now keeps you ahead of these changes and on the supported path.

Per-task guides

Each task has a dedicated migration guide covering the flag mapping, config.axl configuration, and CI YAML.
TaskGuide
aspect build / aspect testaspect build & test
aspect formataspect format
aspect buildifieraspect buildifier
aspect lintaspect lint
aspect gazelleaspect gazelle
aspect deliveryaspect delivery
aspect ci warmingaspect ci warming
The rest of this page covers shared setup that applies to all tasks.

Migrating from Rosetta

This section is for Aspect Workflows customers moving from the legacy YAML-configured Rosetta task runner. New Aspect CLI users can skip this section entirely.
The Aspect CLI replaces the legacy Aspect Workflows task runner (“Rosetta”) and its YAML-configured .aspect/workflows/config.yaml. Each Rosetta task has a corresponding aspect <task> command that you invoke directly from your CI config — task logic now lives entirely inside the aspect invocation, so Aspect Workflows is no longer opinionated about how your CI is structured around it.

Breaking changes

.aspect/workflows/bazelrc is not loaded by AXL tasks

Rosetta automatically passed —bazelrc=.aspect/workflows/bazelrc to every Bazel invocation when that file existed. AXL tasks do not do this. If you have CI-only Bazel flags in .aspect/workflows/bazelrc, they will be silently ignored after you migrate.
Move those flags into your workspace .bazelrc under a named config group:
.bazelrc
# flags only active when --config=ci is passed
build:ci --remote_download_minimal
Then activate --config=ci automatically on CI runners via .aspect/config.axl:
.aspect/config.axl
load("@aspect//traits.axl", "BazelTrait")

def config(ctx: ConfigContext):
    is_ci = bool(ctx.std.env.var("CI"))
    if is_ci:
        ctx.traits[BazelTrait].extra_flags.extend([
            "--config=ci",
        ])
This activates --config=ci for all AXL tasks on any runner where the CI environment variable is set (all major CI providers set it by default). Because .aspect/config.axl is evaluated for both CI and local invocations, CI-only flags stay isolated from developer machines without needing a separate file.

checkout task

The legacy Rosetta checkout task ran a branch-freshness check after CI’s source checkout — fetching the target branch, computing the merge base, and posting a build annotation telling the developer how to rebase or merge when their branch was stale (update_strategy: rebase or merge). There’s no Aspect CLI equivalent and we don’t plan to add one. Source checkout (fetch depth, ref selection, submodules) is owned by your CI platform’s checkout action, and the rebase/merge behavior the legacy task provided is either built-in or trivially expressible in your CI YAML:
  • GitHub Actionsactions/checkout@v6 already checks out the synthetic merge ref for PR events (refs/pull/<n>/merge), which is the PR head pre-rebased onto the target. update_strategy: rebase was a no-op here.
  • Other CI hosts (Buildkite, GitLab, CircleCI) — customize your checkout step to fetch the target branch and rebases (or merges) before the rest of the build runs.

Requirements

Aspect CLI v2026.26.44 or newer, running on Aspect Workflows v5.17.31+ runners. v2026.26.44 has feature parity with the legacy Rosetta task runner. Every Rosetta task has an aspect <task> equivalent. Pin the CLI version in your repo’s .aspect/version.axl:
version("2026.26.44") # or newer
The new tasks are AXL-powered and ship inside the CLI itself, so bumping version() pulls in newer task behavior independent of any Aspect Workflows CI runner upgrade. See version pinning for the full set of source options (local builds, custom registries, etc.).

Authentication

Features that post to GitHub (GithubStatusChecks, GithubLintComments) authenticate via the Aspect Workflows GitHub App. If your migration enables either, authenticate the CLI once before the first task migrates — it’s a per-repo setup, not per-task. ArtifactUpload, where used, authenticates against your CI platform’s native artifact API — see the per-task migration guide for setup. Aspect Workflows ships with Setup Aspect Workflows, an integration that generates the CI configuration and invokes Rosetta tasks for you. We recommend a two-step migration:
  1. Eject from Setup Aspect Workflows. Invoke rosetta run <task> directly from your own CI config. Task behavior is identical to what the generated config did, so this step decouples the “where CI lives” change from the “what CI runs” change and de-risks the migration.
  2. Swap rosetta for aspect. Replace each rosetta run <task> call with the corresponding aspect <task> command. Per-task migration guides above cover the flag mapping. While you’re there, you can also drop the boilerplate that previously wrapped each rosetta run <task> call — the Workflows Environment setup and Agent Health Check steps are now self-contained inside the aspect <task> invocation and no longer need to be declared in your CI config.
If you already invoke rosetta directly today, skip straight to step 2.
Stage the migration per-task rather than all at once. Each aspect <task> is independent — you can flip lint to aspect lint while leaving build, test, etc. on rosetta run. That way the blast radius of any per-task surprise is limited to one CI step.

Top-level workspaces

Skip this section unless your legacy .aspect/workflows/config.yaml had a top-level workspaces: list. Most repos don’t.
Rosetta’s top-level workspaces: list ran every task once per directory it named, supporting both single-workspace and multi-workspace repos. There is no equivalent in the Aspect CLI: aspect <task> runs from the current working directory, so the choice of workspace moves into your CI config. To run a task in a sub-directory, cd first; to cover multiple workspaces, declare a separate CI step per directory. Before.aspect/workflows/config.yaml:
workspaces:
  - .
  - mobile/ios
tasks:
  build:
  test:
  format:
After — write one CI step per workspace, cd-ing first. Example with aspect test on Buildkite:
steps:
  - label: ":aspect: Test (root)"
    command: aspect test --task:name test-root //...

  - label: ":aspect: Test (mobile/ios)"
    command: |
      cd mobile/ios
      aspect test --task:name test-mobile-ios //...
The pattern generalizes to all five tasks and all four CI providers. A unique --task:name per workspace isn’t strictly required, but it’s recommended: features like GithubStatusChecks surface the task name in their output, so distinct names make it easy to tell which run came from which workspace.

Where to next

Pick the guide for the task you want to configure from the per-task guides table above, or work through them in order — each guide is self-contained and can be done independently.

Migration support

As an Aspect Workflows customer, you have direct access to Aspect platform support as part of your subscription — separate from the public community Slack open-source users land in. If you hit a snag during the migration, reach out:
  • Your shared customer Slack channel — fastest path; the team is already in the loop on your environment.
  • Email support@aspect.build — for issues you’d rather keep off Slack, or if a Slack channel isn’t set up yet.
We’re happy to pair-debug a stuck migration step, review your CI YAML before you flip a task over, or sanity-check a config.axl.