Skip to content

03 Command Reference

RemyDuijkeren edited this page Jul 21, 2026 · 43 revisions

Command Reference

Run commands from any directory inside your project — Flowline walks up to find .flowline. Cancel anytime with Ctrl+C (graceful) or Ctrl+Break (immediate, Windows). If cancelled mid-run, re-running is safe.


Global flags

Available on every command:

Flag Description
-h, --help Show help for the command. Works on every subcommand: flowline push --help, flowline deploy --help, etc.
-v, --verbose Show detailed command output
-f, --force <specifier> Approve a specific hazard by name; repeatable (--force x --force y). Each command accepts only the values it actually gates — passing one that doesn't apply fails with an error naming the values that do; status gates nothing, so passing --force there is always an error. all approves everything a command gates. config approves a .flowline config overwrite and is accepted by every command except status and deploy (deploy never writes .flowline — see its own section for its first-import hazard instead). See each command's own section for its command-specific hazards.
--no-cache Re-run all pre-flight checks instead of using cached results. Flowline caches tool version probes, environment info, and solution metadata (TTLs: 7 days / 12 hours / 4 hours) so commands start instantly. Use this when the cache is stale but the TTL hasn't expired yet — e.g. you just created a new solution or switched PAC auth profiles.
-a, --auto-select-auth-profile Automatically switch PAC CLI's active auth profile to match the one Flowline resolved, without asking — the switch is not restored afterward. See 02-Authentication#keeping-pac-clis-active-profile-in-sync.

clone

Bootstraps an existing Dataverse solution into a new Git repo. Creates .flowline, unpacks the solution XML into Solution/src/, scaffolds the Plugins and WebResources projects, creates the solution file (*.slnx) and wires them up, writes AGENTS.md and CLAUDE.md, and generates the initial DATAVERSE_CONTEXT.md.

flowline clone ContosoSales --prod https://contoso.crm4.dynamics.com
Argument / Option Description
<solution> Solution to clone
--prod <url> Production environment URL — saved to .flowline. Required on first run; omit once set.
--uat <url> UAT environment URL — saved to .flowline when provided. Typically set via flowline provision uat instead.
--test <url> Test environment URL — saved to .flowline when provided. Typically set via flowline provision test instead.
--dev <url> Development environment URL — saved to .flowline when provided. Typically set via flowline provision dev instead.
--managed Also clone the managed solution (saved to .flowline)

Every --prod/--uat/--test/--dev URL you pass is saved to .flowline, regardless of which environment the solution actually gets cloned from. So you can use clone to register any environment, not just the source. Re-run it later with just the flag for a new one (e.g. flowline clone ContosoSales --uat https://contoso-uat.crm4.dynamics.com) to add it without repeating the rest of the setup.

Clone source: the solution is unpacked from the first unmanaged match among the environments you've configured, checked in produattestdev order — it doesn't always come from prod.

This mirrors Flowline's promotion ladder in reverse: PROD is the canonical baseline, so its solution state is preferred; UAT is checked next as the highest-fidelity environment below it, ahead of Test/Dev, which are short-lived and more likely to have diverged.

If prod's solution is managed, clone falls through to uat, then test, then dev; it fails if none of the configured environments has an unmanaged copy.

Solution file: a new project gets a .slnx. A project that already has a .sln keeps it — clone writes the .cdsproj entry into whichever solution file is there and never converts one to the other. (dotnet sln migrate does that, if you want it.)

What it scaffolds: Solution/ContosoSales.cdsproj plus Solution/src/, Plugins/ContosoSales.Plugins.csproj, and WebResources/ContosoSales.WebResources.csproj. Folders are the same in every Flowline repo; the project files are named after your solution, so the built assembly is ContosoSales.Plugins.dll rather than an anonymous Plugins.dll. Clone places what pac generates and never renames a project file — for the plugins project it runs pac plugin init in a directory named after the solution and then renames only that directory to Plugins/. Underscores in the solution name are kept verbatim.

Safe to re-run: if the solution hasn't been cloned yet, clone fetches it fresh. If it has (ContosoSales.cdsproj already exists under Solution/), clone normally skips the fetch — except when you've switched to --managed and the local source doesn't have the managed layer yet, in which case it re-syncs Solution/src/ from Dataverse to pick it up, then continues as usual. Re-syncing overwrites Solution/src/ with the current Dataverse state, so commit any local edits there first. Everything else (solution file, Plugins/WebResources projects, AGENTS.md, CLAUDE.md) is left alone if already present — remove the specific part you want to recreate and re-run clone.

.flowline is always re-saved (merging in any new URLs), and DATAVERSE_CONTEXT.md is always regenerated from the current solution state.


push

Builds the solution and syncs plugin assemblies and web resources to DEV. Files under WebResources/dist/ are synced.

flowline push
Argument / Option Description
[solution] Solution to push — required outside a Flowline project; optional in project mode, where a passed value is validated against the configured solution (error on mismatch)
-s, --scope <scope> Limit scope: all, webresources, formevents, plugins, or assemblyonly. Can be specified multiple times.
-p, --pluginFile <path> Prebuilt plugin assembly (.dll) or plugin package (.nupkg) — for standalone use
-w, --webresources <path> Web resource folder — for standalone use
--dev <url> Dev environment URL — read from .flowline. Only needed to override or in standalone mode.
--no-delete Push without deleting Dataverse assets missing from source
--no-build Skip dotnet build and push the existing Release artifacts. Every discovered plugin project must already have output in its bin/Release — with nothing to reflect, Flowline can't tell whether a project is a plugin project, and it fails rather than guess. Build first, or drop --no-build. No effect in standalone mode (--pluginFile/--webresources), which doesn't require building.
--no-publish Skip publishing web resources and Form Event Handlers after sync. Useful when pushing several solutions and publishing once at the end.
--dry-run Preview changes without touching Dataverse
-f, --force <specifier> Approves delete-orphans (delete an orphaned assembly/step), recreate-assembly (delete-and-recreate an assembly whose identity changed), delete-form-handlers (remove an unrecognized Form Event Handler), config, or all — see Global flags

Plugin packaging: push supports both the classic .dll and NuGet plugin packages (.nupkg), auto-detected from the build output. Override via .flowline's PluginPackageMode key (Auto/Nupkg/Dll).

--scope assemblyonly: Updates only the assembly bytes, skipping step/Custom API registration — useful for fast iteration when registrations haven't changed.

Full guide: 04-Push-Plugins-and-Custom-APIs · 05-Push-WebResources

Standalone push

push works outside a Flowline project — no .flowline, Git repo, or project structure required:

flowline push ContosoSales --pluginFile ./bin/Release/MyPlugins.dll --dev https://contoso-dev.crm4.dynamics.com
flowline push ContosoSales --webresources ./dist --dev https://contoso-dev.crm4.dynamics.com
flowline push ContosoSales --pluginFile ./bin/Release/MyPlugins.dll --webresources ./dist --dev https://contoso-dev.crm4.dynamics.com

Standalone rules:

  • --pluginFile must point to an already-built assembly (.dll) or plugin package (.nupkg).
  • --webresources points at the folder whose files should be synced.
  • If .flowline exists in the current folder, standalone mode stops — project mode and standalone mode cannot be mixed.
  • The target solution must be unmanaged.

sync

Pulls the current solution state from DEV and unpacks it into the repo. Run this after making changes in the maker portal to capture them in source control.

Full guide: 06-Sync

flowline sync
Argument / Option Description
--dev <url> Dev environment URL — read from .flowline. Only needed to override.
--managed Export and unpack the managed solution in addition to unmanaged
--bump <component> Version component to increment: patch, minor, major, or none to skip bumping (default: patch)
--no-build Skip the dotnet build validation step after syncing
-f, --force <specifier> Approves dirty (overwrite uncommitted local Solution/src/ changes), config, or all — see Global flags

By default, Flowline syncs only the unmanaged solution. Pass --managed once to also export the managed package; the flag is saved to .flowline so all subsequent syncs include it automatically. Pass --managed false to revert.

Warning

You need --managed if you intend to deploy to other environments (test, UAT, prod) as a managed solution.


deploy

Packs the solution from the repo and imports it into the target environment.

Full guide: 07-Deploy

flowline deploy test
flowline deploy prod
flowline deploy https://contoso-uat.crm4.dynamics.com
Argument / Option Description
<target> Target environment: prod, uat, test, dev, or a URL
--path <zip> Import this pre-built solution zip instead of packing from source
--skip-dtap-check Skip DTAP promotion checks (existence and version)
--skip-solution-check Skip the solution checker gate
--no-backup Skip the pre-deploy environment backup
--no-delete Report orphan components without deleting them
-f, --force <specifier> Approves drift (skip drift validation for local-only or plugin-size-mismatch changes), first-import (skip the first-import confirmation), or allconfig is not one of deploy's values; see Global flags

By default, deploy imports the unmanaged solution — managed/unmanaged mode is configured via clone --managed/sync --managed, not a deploy flag. deploy enforces promotion order (DTAP gate), confirms before a solution's first import to a target, runs the solution checker, takes a pre-deploy backup, and cleans up orphaned components. See 07-Deploy for details on all of that.

When --path is omitted, repeated deploys of unchanged source reuse the last packed artifact instead of repacking (build once, promote through test/uat/prod); pass --path explicitly for CI pipelines that promote across separate jobs/runners. See 07-Deploy#artifacts for details. Pass --no-cache to bust this reuse cache and force a fresh pack even when the source commit hasn't changed.


provision

Provisions a DEV, TEST, or UAT environment by copying an entire Dataverse environment from production via the Power Platform admin API (pac admin create + pac admin copy) — this is a real environment copy, not just a solution clone. If the target doesn't exist yet, provision creates it first, then copies prod into it.

This is a long-running operation — full Dataverse environment copies commonly take tens of minutes, and the underlying pac CLI enforces a 60-minute limit on the operation. Use it once when setting up a new environment, or again later to refresh an existing one back to a clean copy of prod.

Why it exists: Flowline treats PROD as the canonical baseline and Git as the delivery source — dev, test, and UAT are meant to be short-lived workspaces provisioned from PROD, not permanent environments maintained by hand. provision is what makes that practical: one command instead of manually creating and refreshing environments in the admin center.

flowline provision dev --prod https://contoso.crm4.dynamics.com
flowline provision test --prod https://contoso.crm4.dynamics.com
flowline provision uat --prod https://contoso.crm4.dynamics.com
Argument / Option Description
[role] Target role: dev, test, or uat (default: dev)
--prod <url> Production environment URL to copy from — read from .flowline. Only needed to override.
--copy <type> Copy type for dev: minimal (no data, default) or full (with data). test and uat always copy with data, regardless of this flag.
--suffix <text> Target URL/display-name suffix (default: role name, e.g. Dev/Test/UAT)
--allow-overwrite Overwrite an existing target environment. Without it, an existing target is left untouched — provision warns and exits instead of copying.

The resulting environment URL is saved to .flowline, same as --dev/--test/--uat on clone.


generate

Generates early-bound C# entity types via pac modelbuilder build with opinionated defaults. Output lands in Plugins/Models/ — no separate assembly, no ILMerge. Running generate again fully replaces the folder.

Full guide: 09-Generate-Early-Bound-Types

flowline generate
flowline generate --namespace Contoso.Plugins.Models --extra-tables account,contact
Argument / Option Description
[solution] Solution to generate types for — required outside a Flowline project; optional in project mode, where a passed value is validated against the configured solution (error on mismatch)
--namespace <ns> Model namespace — saved to .flowline for future runs
--extra-tables <tables> Comma-separated extra tables to include that are not in the solution
--dev <url> Dev environment URL — read from .flowline. Only needed to override or in standalone mode.
-o, --output <path> Output folder (required outside a Flowline project)
--generator {pac|xrmcontext3|xrmcontext} Generator to use — pac (default) uses pac modelbuilder build; xrmcontext3 uses Delegate.XrmContext v3 F# exe (Windows only, bridge); xrmcontext uses XrmContext v4 dotnet tool (cross-platform). Saved to .flowline.

Standalone generate

Use outside a Flowline project by supplying -o, --dev, and the solution name:

flowline generate ContosoSales --dev https://contoso.crm4.dynamics.com --namespace Contoso.Plugins.Models -o ./src/Models

status

Shows DTAP status, environment info, Flowline version, .NET SDK, PAC CLI, and Git versions, plus authentication status.

flowline status

The output looks like this:

╭─╴╷  ╭─╮╷ ╷╷  ╷╭╮╷╭─╴
├╴ │  │ ││╷││  ││╰┤├╴
╵  ╰─╴╰─╯╰┴╯╰─╴╵╵ ╵╰─╴
Flowline CLI v0.7.1.0 (NT 10.0.26200.0, CLR:10.0.9, 64-bit)
.NET SDK version: 10.0.301
Power Platform CLI version: 2.8.1+ga4eb71c (.NET 10.0.9)
Git version: 2.54.0.windows.1

Configuration
  Dev: https://contoso-dev.crm4.dynamics.com/
    ✓ remy@contoso.com
  Test: https://contoso-test.crm4.dynamics.com/
    ✗ Not authenticated
  UAT: Not configured
  Prod: https://contoso.crm4.dynamics.com/
    ✓ remy@contoso.com

─────────────────────────────────────────────────────────────────────
  Solution        Dev          Repo             Test         Prod
─────────────────────────────────────────────────────────────────────
  ContosoSales    1.0.36  ──▶  1.0.37 ⚠ ●  ┈┈▶  ✗ auth  ┈┈▶  1.0.36 ↑
─────────────────────────────────────────────────────────────────────
— not deployed   ✗ auth failed   ↑ behind   ⚠ ahead   ● uncommitted

Warning: an environment is ahead of an earlier stage — check the grid above.

The grid shows the project's solution — always exactly one row — with its version across your pipeline, left to right in promotion order (Dev → Repo → Test → UAT → Prod). The arrows show how each stage compares to the one before it: green means caught up, cyan means behind (normal — just not promoted yet), red means ahead (unexpected — usually something deployed out of band). A means not deployed there yet, means the environment is configured but not authenticated, and flags uncommitted changes in the repo folder. Environments without a configured URL are skipped entirely.

The line below the grid sums it up: a warning if something's out of order, a nudge to promote if environments are just behind, or All environments in sync. when everything matches.


sln add

Adds a .cdsproj to the project's solution file. dotnet sln add refuses a .cdsproj — and exits 0 while doing it, so a script can't even tell it failed (dotnet/sdk#47638) — so Flowline writes the entry itself.

flowline sln add Solution/ContosoSales.cdsproj
Argument Description
<path> Path to the .cdsproj to add. A .csproj is refused — use dotnet sln add for those, which handles them fine.

clone already wires up the .cdsproj it creates, so you only need this for a project that didn't come from clone: a repo migrating off spkl, Daxif, or PACX, or one assembled by hand.

Runs standalone. No .flowline, no git repo, no PAC login needed — it only edits a local file. That's deliberate: the repos that need it are usually the ones not yet set up for Flowline.

It finds the solution file by walking up from where you're standing, so running it from inside Solution/ works fine.

Re-running is safe: a project already in the solution file is reported and skipped, not duplicated.


drift

A preview command: it shows what a deploy to the target would delete as orphans, without actually deploying. Compares committed source against a live environment and reports components that are present there but not declared in source — i.e. exactly the components deploy's orphan cleanup would remove if you deployed now. Read-only — never deletes or modifies anything itself.

flowline drift prod
flowline drift dev
flowline drift test
flowline drift https://contoso-test.crm4.dynamics.com/
Argument / Option Description
<target> Environment to compare against: prod, uat, test, dev, or a URL

Run it against prod/test as a standalone drift check, or against dev before sync/deploy as a preview of what the next run would flag. It reuses the same comparison deploy's orphan cleanup runs internally, just pointed at whichever environment you name and always in report-only mode.

Exit codes: 0 when the comparison ran and found nothing, 15 (Validation Failed) when drift is found, 19 (Inconclusive) when the comparison couldn't run at all (e.g. the solution has no components locally or in the target — investigate the printed reason before trusting the result), or the same connection/config codes deploy uses.

Current scope: this is the first, narrower half of drift detection — it only detects components present in the target but not declared in your committed source (created directly there, or added since your last sync), which is the orphan-deletion direction. It does not yet detect the opposite — something your source declares that was deleted directly in the target. Extending drift to cover that direction too is a planned future improvement.

Clone this wiki locally