Skip to content

02 Authentication

RemyDuijkeren edited this page Jul 18, 2026 · 14 revisions

Authentication

Flowline delegates all auth to PAC CLI — no credentials stored in Flowline config files, ever. Set up a PAC auth profile once and Flowline picks it up automatically from then on.

Don't have PAC CLI yet? → Install Power Platform CLI


Developer setup — one command

pac auth create --environment https://yourorg-dev.crm4.dynamics.com

Done. A browser opens, you sign in, and Flowline can connect to that environment from now on. Tokens are cached and refreshed automatically — you won't be asked to sign in again.


Multiple environments

One profile per environment, one name each:

pac auth create --environment https://yourorg-dev.crm4.dynamics.com --name "Dev"
pac auth create --environment https://yourorg-test.crm4.dynamics.com --name "Test"
pac auth create --environment https://yourorg.crm4.dynamics.com --name "Prod"

See all profiles and switch the active one:

pac auth list
pac auth select --index 2

Flowline always shows which profile it resolved before connecting:

Resolved PAC auth profile 'Dev' (UNIVERSAL)

For the full PAC auth reference → pac auth commands


CI/CD — service principal

Add PAC CLI to your pipeline image, then authenticate with a service principal before running any Flowline command:

pac auth create \
  --applicationId $CLIENT_ID \
  --clientSecret $CLIENT_SECRET \
  --tenant $TENANT_ID \
  --environment $ENV_URL

After that, any Flowline command just works — no extra config needed.

Replace the placeholder values with yours. The one called CLIENT_SECRET — keep that a secret ;-).

# GitHub Actions
- name: Authenticate
  run: |
    pac auth create \
      --applicationId 00000000-0000-0000-0000-000000000000 \
      --clientSecret "$PAC_CLIENT_SECRET" \
      --tenant 00000000-0000-0000-0000-000000000000 \
      --environment https://yourorg.crm4.dynamics.com
  env:
    PAC_CLIENT_SECRET: ${{ secrets.PAC_CLIENT_SECRET }}

- name: Run Flowline
  run: flowline sync   # or push, deploy, generate — any command
# Azure Pipelines
- task: Bash@3
  displayName: Authenticate
  inputs:
    script: |
      pac auth create \
        --applicationId 00000000-0000-0000-0000-000000000000 \
        --clientSecret $(PacClientSecret) \
        --tenant 00000000-0000-0000-0000-000000000000 \
        --environment https://yourorg.crm4.dynamics.com

- task: Bash@3
  displayName: Run Flowline
  inputs:
    script: flowline sync   # or push, deploy, generate — any command

Note for Managed Identity / Azure DevOps Federation: PAC CLI also supports --managedIdentity and --azureDevOpsFederated for keyless auth. See pac auth create.

Run via dnx (no install step)

Both PAC CLI and Flowline are .NET tools, so on a runner with .NET 10 already present, dnx can run either one on demand — no dotnet tool install step, no tool cache to restore. For CI images that are rebuilt or torn down every run, that's one less thing to set up and keep up to date.

dnx microsoft.powerapps.cli.tool --yes auth create \
  --applicationId $CLIENT_ID \
  --clientSecret $CLIENT_SECRET \
  --tenant $TENANT_ID \
  --environment $ENV_URL

dnx flowline --yes sync   # or push, deploy, generate — any command

Auth still persists the same way — dnx runs the same PAC CLI, so the profile created here is picked up whether later commands go through dnx, an installed pac, or Flowline's own internal fallback.


How Flowline selects a profile

When you run a Flowline command, it finds the right PAC auth profile automatically:

  1. Match profiles whose environment URL matches the target
  2. Prefer the one PAC has marked active (pac auth select)
  3. Fall back to the active UNIVERSAL profile if no URL-specific match exists
  4. Multiple matches, none active → interactive: a picker lists candidates; CI: error with a candidate list and pac auth select instructions
  5. No match at all → error with a pac auth create hint

Keeping PAC CLI's active profile in sync

pac.exe always operates on whichever profile is currently active — it has no way to scope a single call to a different one. So once Flowline has resolved the right profile for the target environment, it also checks that this profile is the one PAC CLI actually has active, before running any pac.exe call that depends on it (solution list/sync/version, publisher-prefix lookup, admin backup).

If the active profile already matches, nothing changes — no extra output, no prompt.

If it doesn't match:

  • CI (non-interactive): the command stops immediately with an error naming the exact fix:
    PAC auth profile 'Dev' isn't the active PAC CLI profile — run: pac auth select --name 'Dev'
    
    (Unnamed profiles get pac auth select --index <n> instead.)
  • Interactive: Flowline shows a table of local PAC auth profiles (Index, Kind, Name, User, Environment) — the currently-active profile's index gets a trailing *, and the row Flowline wants to switch to is highlighted — then asks to confirm switching to the resolved one. A bare Enter declines — declining aborts with the same error shown above.

Pass -a/--auto-select-auth-profile to skip the block/prompt and switch automatically, in both interactive and non-interactive runs:

flowline push -a

When the switch happens — whether you confirmed the prompt or passed -a — Flowline prints a line naming it, separate from the usual "Resolved PAC auth profile '...'" line:

Resolved PAC auth profile 'Dev' (UNIVERSAL)
Switched active PAC auth profile to 'Dev'

The switch is not restored afterward — PAC CLI's active profile stays on whatever Flowline just switched to, for any follow-up pac/flowline commands you run by hand. It only ever runs pac auth select; it never creates, renames, or deletes a profile.

flowline status is the one exception: since it reports on up to 4 environments in a single run, it never blocks or prompts on a mismatch — it just shows an informational line per environment and always completes. provision's checks against a brand-new target environment are unaffected too, since there's no local profile yet to compare against.


XrmContext generators — one extra step

The default --generator pac needs nothing beyond the PAC auth profile above. The xrmcontext and xrmcontext3 generators are separate external tools that authenticate independently — they can't read from PAC's token cache.

Local dev (personal account)

Flowline still picks up your PAC auth profile for the environment URL, but XrmContext opens its own browser session to authenticate independently. It happens once — the token is cached and subsequent runs are silent. Nothing extra to configure.

Local dev (service principal)

Flowline picks up your PAC auth profile for the environment URL and client ID, but XrmContext can't read PAC's token cache so it needs the secret separately. Pass it with --client-secret:

flowline generate --generator xrmcontext --client-secret <your-secret>

No --client-secret? Flowline will prompt you interactively instead.

CI/CD (service principal)

Pass the secret with --client-secret on the generate step:

# GitHub Actions
- name: Generate types
  run: flowline generate --generator xrmcontext --client-secret "$PAC_CLIENT_SECRET"
  env:
    PAC_CLIENT_SECRET: ${{ secrets.PAC_CLIENT_SECRET }}
# Azure Pipelines
- task: Bash@3
  displayName: Generate types
  inputs:
    script: flowline generate --generator xrmcontext --client-secret $(PacClientSecret)

Flowline also reads the secret from the AZURE_CLIENT_SECRET environment variable if it's already set in your pipeline — useful if other tools share the same credential.

Override credentials on the fly

Use --client-id and --client-secret to pass credentials directly, bypassing whatever is in the PAC auth profile:

flowline generate --generator xrmcontext --client-id <app-id> --client-secret <secret>

Generator comparison and XrmContext setup


Troubleshooting

No PAC auth profile found for <url>

No PAC auth profile matches the target environment. Create one:

pac auth create --environment https://yourorg-dev.crm4.dynamics.com --name "Dev"

Multiple PAC auth profiles match <url> (non-interactive)

Multiple profiles are registered for that URL and none is active. Set one as active:

pac auth list
pac auth select --index <n>

PAC auth profile '...' isn't the active PAC CLI profile

Flowline resolved the right profile for this environment, but PAC CLI's globally active profile is a different one — pac.exe calls would run under the wrong identity. Switch to the named profile:

pac auth select --name 'Dev'

Or re-run the command with -a/--auto-select-auth-profile to switch automatically. See Keeping PAC CLI's active profile in sync.

Client secret required for '...'

Using an XrmContext generator with a service principal profile but no secret was provided. Pass it with --client-secret:

flowline generate --generator xrmcontext --client-secret <your-secret>

PAC CLI version error (profile file missing or corrupt)

Flowline shows the PAC CLI version and asks you to update:

dotnet tool update --global Microsoft.PowerApps.CLI.Tool
# or
winget upgrade Microsoft.PowerAppsCLI

See also

Clone this wiki locally