Docs/Provisioning Profiles

Provisioning Profiles

Variant-keyed config templates with required tokens and provisioning scripts for the production line

Last updated: 2026-05-26

Provisioning Profiles define what data a device needs to be flashed with on the production line, scoped per variant. The same physical hardware can ship as multiple SKUs (US / EU / OEM, dev / prod, customer A / customer B) with different endpoint URLs, API keys, calibration values, or feature flags - the profile captures the per-variant configuration so the operator on the line doesn't have to type it by hand.

Open it from any project: sidebar -> Protocol -> Provisioning Profiles, or visit /projects//protocol/profiles.


When you need it

You need a Provisioning Profile when:

  • You manufacture more than one variant of the same hardware and each variant gets a different runtime config.
  • Your devices need secrets (API keys, certificates, signed tokens) injected at flash time, not baked into the firmware binary.
  • Your line operators provision dozens to thousands of devices and you cannot afford typos.
If your product has exactly one configuration and no per-device secrets, you can skip Provisioning Profiles entirely - the firmware binary plus a serial number is enough.

Concepts

TermWhat it means
ProfileOne named provisioning recipe, attached to a specific Production Variant.
Config fieldOne key in the recipe: name + type + required flag + default value + description.
Field typesstring, number, boolean, url, secret. The secret type pulls its value from Security Tokens instead of being plaintext on the profile.
Required tokenA reference to a Security Token (e.g. API_KEY_PROD). The profile cannot be used unless this token is set on the project.
Provisioning scriptOptional shell or Python script the line tool runs to flash the device. Has access to the resolved config field values.
Active flagInactive profiles are hidden from the line tooling. Use to retire an old recipe without deleting it.

Quick start: define your first profile (10 minutes)

1. Make sure the variant exists

The profile is keyed by variant. Before creating a profile, the variant must exist:

  1. Open your project
  2. Go to Manufacturing -> Production Variants
  3. Confirm the variant you want to profile is there (e.g. "Mainboard Rev B - US")

2. Open Provisioning Profiles

  1. Sidebar -> Protocol -> Provisioning Profiles
  2. The page shows existing profiles for the project grouped by variant

3. Create the profile

  1. Click New Profile
  2. Fill in:
- Name - short and recognisable (e.g. "US Production v1") - Description - optional - Variant - pick from the list
  1. Add config fields one at a time:
- Key - the variable name your firmware or script will read (e.g. endpointUrl, apiKey, region) - Label - human-readable name shown to the line operator (e.g. "Cloud endpoint") - Type - one of: string, number, boolean, url, secret - Required - whether the field must be filled at provision time - Default value - optional default for the operator to accept or change - Description - hint shown next to the field in the line tool
  1. Add required tokens:
- Type the name of a Security Token on the project (e.g. API_KEY_PROD) - The profile will refuse to activate if the token isn't defined - this catches missing-secret mistakes early
  1. (Optional) Paste a provisioning script - the shell or Python the line tool runs after the operator confirms the config. The script reads the resolved config keys as environment variables or stdin JSON.
  2. Toggle Active when ready
  3. Click Create

4. Test it

Hand the profile to the line tooling (the desktop app picks up active profiles automatically) and walk through provisioning a test device. Verify:

  • All required fields show up
  • Defaults pre-fill correctly
  • The provisioning script runs and the device boots with the right config

Workflow: rotate a secret without re-deploying the profile

  1. Go to Settings -> Security Tokens (or your project's token panel)
  2. Update the token value (e.g. API_KEY_PROD gets rotated)
  3. The profile picks up the new value on the next provision - no changes needed on the profile itself
This is why secrets should always be required token references, never plaintext on the profile.

Workflow: ship a new variant with a different endpoint

  1. Create the new variant in Manufacturing -> Production Variants (e.g. "Mainboard Rev B - EU")
  2. Open Protocol -> Provisioning Profiles
  3. Click New Profile, scoped to the new variant
  4. Copy the config field list from your US profile (re-type or use the duplicate-from action if available)
  5. Change endpoint URL default, region code, any compliance flags
  6. Reference the EU-specific token (e.g. API_KEY_EU)
  7. Activate
Line operators flashing devices for the EU variant now see the EU profile automatically when they scan a barcode matching the variant.

Workflow: retire an old profile

You cannot delete a provisioning profile that has been used (audit trail). Retire by:

  1. Open the profile
  2. Toggle Active off
  3. The profile drops out of the line-tool selection but stays visible in the dashboard for audit

Reference

Field types

TypeUI in the line toolUse for
stringFree-text inputNames, identifiers, free-text config
numberNumeric inputQuantities, calibration values, port numbers
booleanToggleFeature flags, debug mode on/off
urlURL input with validationEndpoint URLs, OTA hosts
secretPulled from Security Token (operator does not see value)API keys, signing certs, anything sensitive

Required tokens

Provisioning profiles reference Security Tokens by name. Tokens themselves are stored encrypted at the project level (see Security & Access). The profile only stores the token name; the actual value is resolved at provision time from the project's token store. If a referenced token doesn't exist, the profile won't activate and the operator gets a clear error.

Provisioning script

If the script field is non-empty, the line tool runs it after the operator confirms config:

  • Available to the script: every config field as an environment variable (or as stdin JSON, depending on the script header).
  • The script's exit code is captured. Non-zero = provisioning failed; the device record is marked accordingly.
  • Logs from the script are saved alongside the device record so you can debug a stuck provision later.

Common pitfalls

  • "My field type is secret but the operator can see the value." Check that the field is referencing a token, not storing a literal. Plaintext on the profile defeats the purpose.
  • "The profile activated but no device receives the config." Confirm the device's lot is tied to the right variant - the profile is variant-keyed, not project-keyed.
  • "My required-token check passes but the script gets undefined." Token names are case-sensitive. API_KEY_PROD and api_key_prod are different tokens.

Related docs