Build and deploy modules with the CLI | Viam Documentation

Build and deploy modules with the CLI

Scaffold a new module, iterate on it locally with hot-reload, upload it to the registry, and manage versions and cloud builds.

Prerequisites

You need the Viam CLI installed and authenticated. See Viam CLI overview for installation and authentication instructions.

Find your IDs

To find the part ID for a running machine (needed for reload and restart):

viam machines list --organization=<org-id> --location=<location-id>

Copy

viam machines part list --machine=<machine-id>

Copy

To find your organization and location IDs:

viam organizations list

Copy

viam locations list

Copy

Scaffold a new module

Generate a module project with boilerplate code, a meta.json manifest, and a build script. This command does not require authentication, so you can scaffold a module before logging in.

viam module generate

Copy

The generator first asks whether you want to generate a module or an app. Choose Module, then follow the interactive prompts to choose:

To generate a hosted web application instead of a module, choose App or see Deploy a Viam application.

You can also pass flags to skip the interactive prompts:

viam module generate \
  --generate-type=module \
  --name=my-sensor-module \
  --language=python \
  --visibility=public

Copy

To add a new resource model to an existing module, use viam module add-model from within the module directory. To add a web application to an existing Go module, use viam module add-app.

Iterate during development

After making code changes, reload your module on a running machine without restarting the entire machine. By default, the CLI builds the module in the cloud and syncs the new binary to the target:

viam module reload --part-id=<part-id>

Copy

If your development machine is also running the module (for example, developing a macOS module on the Mac that runs viam-server), use reload-local to build and reload without a cloud build:

viam module reload-local --part-id=<part-id>

Copy

If a reload is not sufficient, restart the module process:

viam module restart --part-id=<part-id>

Copy

Update model definitions

After adding or changing models in your module, update the model definitions in meta.json. This command runs the module’s executable (binary or script) in a sandbox, queries it for the API-model pairs it advertises, and updates the manifest. It also auto-detects markdown documentation files named namespace_module_model.md.

If you omit --binary, the CLI uses the entrypoint declared in meta.json:

viam module update-models

Copy

To point at a specific executable, pass --binary:

viam module update-models --binary=./bin/module

Copy

Then push the updated meta.json to the registry:

viam module update

Copy

Upload to the registry

Upload a module version for a specific platform. The CLI validates the tarball before uploading: it checks for an executable at the declared entrypoint, verifies file permissions, and warns about platform mismatches or symlinks escaping the archive. Pass --force to skip validation.

viam module upload \
  --version=1.0.0 \
  --platform=linux/amd64 \
  dist/archive.tar.gz

Copy

On success, the CLI prints a link to your module in the registry:

Version successfully uploaded! you can view your changes online here: https://app.viam.com/module/my-org/my-module

Copy

Upload for multiple platforms by running the command once per platform:

viam module upload --version=1.0.0 --platform=linux/amd64 dist/archive-amd64.tar.gz

Copy

viam module upload --version=1.0.0 --platform=linux/arm64 dist/archive-arm64.tar.gz

Copy

Cloud builds

For CI/CD workflows, use cloud builds to compile your module on Viam’s build infrastructure.

Start a cloud build:

viam module build start --version=1.0.0

Copy

Build for multiple platforms in one command:

viam module build start --version=1.0.0 --platforms=linux/amd64,linux/arm64

Copy

Build from a specific git ref:

viam module build start --version=1.0.0 --ref=main

Copy

Build locally to test before pushing:

viam module build local

Copy

List recent builds (the output includes build IDs you need for build logs):

viam module build list

Copy

View build logs:

viam module build logs --id=<build-id>

Copy

Wait for a build to complete and stream logs:

viam module build logs --id=<build-id> --wait

Copy

Download a module

Download a module from the registry for local testing or inspection. The --id flag takes the format org-namespace:module-name:

viam module download \
  --id=my-org:my-sensor-module \
  --version=1.0.0 \
  --platform=linux/amd64 \
  --destination=./downloaded-module

Copy

Create a module

If you need to register a module in the registry before uploading (for example, to reserve a name), use create:

viam module create --name=my-new-module

Copy

Most users should use viam module generate instead, which handles both creation and scaffolding.

Convert xacro files to URDF

If your module works with a robot described in xacro format (the ROS XML macro language), convert it to URDF with the CLI. The conversion runs in a Docker container with the specified ROS distribution.

viam xacro convert \
  --input-file=./robot.xacro \
  --output-file=./robot.urdf

Copy

If the xacro file uses <xacro:arg> tags, pass the required arguments:

viam xacro convert \
  --input-file=./robot.xacro \
  --output-file=./robot.urdf \
  --args name:=ur20

Copy

To collapse fixed joint chains (useful when the URDF must have a single end-effector):

viam xacro convert \
  --input-file=./robot.xacro \
  --output-file=./robot.urdf \
  --collapse-fixed-joints

Copy

By default, the conversion uses the osrf/ros:humble-desktop Docker image. To use a different ROS distribution or a custom image:

viam xacro convert \
  --input-file=./robot.xacro \
  --output-file=./robot.urdf \
  --docker-image=osrf/ros:jazzy-desktop

Copy

Use --dry-run to print the Docker command without running it.