Post

#PowerPlatformTip 175: 'Force-Sync Per-App-Licensed Users into Dataverse with Power Automate'

#PowerPlatformTip 175: 'Force-Sync Per-App-Licensed Users into Dataverse with Power Automate'

TL;DR: With per-app (app-pass) licensing, the background sync does not add users to the Dataverse SystemUser table automatically – they are only added on demand. Trigger a flow when a user is added to the environment’s Microsoft Entra security group and call Force Sync user (Power Platform for Admins connector) so the user record exists before they first open the app.

Managed production environments licensed with per-app plans (app-pass) behave differently from Dynamics 365 / Power Apps Premium seats. A licensed Premium user is picked up by the periodic background sync and lands in Dataverse automatically. An app-pass user is not – Microsoft only adds them on demand: at their first sign-in (just-in-time), via an admin action, or via the API. That gap causes “You are not a member of the organization” errors and missing security-role assignments right when a new user tries to start. This tip automates the fill so the SystemUser record is provisioned in advance.

💡 Challenge

You run a managed production environment and license makers/users with per-app (app-pass) plans, scoped by a Microsoft Entra security group on the environment. Per Microsoft’s documented rules, users in “an environment with a Dataverse database and environment-level app-pass license type” are not added automatically to the Dataverse SystemUser table – they are added on demand only. The symptoms: a freshly added user isn’t visible under Users + permissions, has no security role, and hits access errors on first launch. Manually clicking Refresh in the Power Platform admin center for every new joiner doesn’t scale.

✅ Solution

Automate the on-demand provisioning. Microsoft exposes a Force Sync user action in the Power Platform for Admins connector (described there as “Used to sync user to CRM”). It adds the user to the environment’s Dataverse on demand. Its inputs are the environment and the user’s object ID. Combine it with a trigger that fires when a user is added to the environment’s associated Entra security group, and the Dataverse SystemUser record is created before the user ever signs in. Use an Environment Group to consistently govern the managed production environments you want this to cover (grouped policies, security-group requirements, sharing limits), so your automation targets a well-defined, governed set of environments.

🔧 How It’s Done

1. Confirm the license/sync gap.

🔸 In the Power Platform admin center, open the environment → Settings → Users + permissions → Users. If a licensed user is missing right after assignment, you are in the app-pass on-demand scenario (not a bug).

2. Govern the target environments with an Environment Group.

🔸 Admin center → Manage → Environment groups → create/assign a group for your managed production environments. Enforce “environment must be associated with a security group” so membership is the single source of truth for who belongs.

🔸 Add users to the environment’s security group directly. Nested security groups inside the associated group are ignored for environment access.

3. Trigger: Office 365 Groups → When a group member is added or removed.

🔸 Group Id: the object ID of the security group associated with the environment.

🔸 The trigger returns User Id (id), which is the Microsoft Entra object ID that the sync action needs. It polls every two minutes and fires for removals as well, so add this trigger condition to start only for additions:

1
@empty(triggerBody()?['@removed'])

🔸 Role-assignable groups (isAssignableToRole) are not supported by this trigger. Use a regular security group for the environment.

4. Call the Force Sync user admin action.

🔸 Add Power Platform for Admins → Force Sync user. The connection must belong to a Power Platform admin or to an environment admin of the target environment.

🔸 Map the parameters:

1
2
Environment : <environment ID, the GUID from the admin center>
ObjectId    : triggerBody()?['id']

🔸 For multiple governed environments, wrap this in an Apply to each over your environment IDs so one new joiner is synced into every relevant environment.

5. Assign the security role right after.

Syncing the user does not grant privileges. Pick one of two ways:

🔸 Group team (recommended): in the environment, create a Dataverse team of type Microsoft Entra ID Security Group for the same security group and assign the security role to that team. Every group member gets the team’s role, without any role action in the flow.

🔸 Direct role assignment in the flow: Dataverse List rows on Users with the filter azureactivedirectoryobjectid eq '@{triggerBody()?['id']}' to get the systemuserid, then Dataverse Relate rows: table Users, the systemuserid as Row ID, relationship systemuserroles_association, and as Relate with the OData URL of the role row (https://<org>.crm.dynamics.com/api/data/v9.2/roles(<role id>)). Role IDs differ per environment, so read them per environment.

6. Handle timing and replays.

🔸 The sync is not always instant. Put the List rows from step 5 into a Do until that waits until the user row exists (with a Delay of one minute per round and a limit of, for example, 10 rounds) before you relate the role.

🔸 The trigger can deliver the same change twice. Force Sync user on a user who already exists only updates the record. Relate rows on a role the user already has fails, so set Configure run after on the next step to also run after has failed, and the duplicate run ends cleanly.

🎉 Result

New per-app-licensed users are provisioned into the Dataverse SystemUser table proactively, the moment they join the environment’s security group – no manual Refresh, no first-login errors, and roles can be assigned immediately after. Onboarding into managed production environments becomes a hands-off, governed process.

🌟 Key Advantages

🔸 Fixes the app-pass blind spot: targets exactly the license type Microsoft excludes from automatic sync.

🔸 Proactive, not reactive: users are ready before their first login instead of erroring on it.

🔸 Governed at scale: Environment Groups + a single associated security group keep membership authoritative across many environments.

🔸 Standard connectors for the core: Force Sync user (Power Platform for Admins) and the group trigger (Office 365 Groups) are standard connectors. The direct role assignment in step 5 uses the Dataverse connector, which is premium.

🛠️ FAQ

1. Why aren’t per-app-licensed users synced automatically like Premium users?

Microsoft’s documented rule: users in an environment with a Dataverse database and environment-level app-pass license type are added to Dataverse on demand only (first access, API, or admin center), not by the periodic background sync. Dataverse-for-Teams and free-Dataverse-plan (Office) users fall in the same on-demand bucket.

2. What exactly does “Force Sync user” do?

The connector describes it as “Used to sync user to CRM”. It syncs a single user (by object ID) into a specific environment’s Dataverse. It does not assign security roles.

3. Does syncing give the user access to apps and data?

No. Adding the SystemUser record only makes the user present in the environment. You still must assign the appropriate security role (directly or via a team) for actual privileges.

4. Which trigger should fire the flow?

When a group member is added or removed from the Office 365 Groups connector, on the Microsoft Entra security group that is associated with the environment, with the trigger condition @empty(triggerBody()?['@removed']). A user must be in that group to be added to Dataverse anyway, so group membership is the natural signal.

5. Can I cover several environments at once?

Yes. Keep your managed production environments in an Environment Group and loop the Force Sync user action over that environment list, so one new joiner is provisioned everywhere they belong.

This tip is by Marcel Lehmann, Microsoft MVP (Business Applications) and founder of the Power Platform Academy – live Power Platform workshops, free or CHF 49. Join the workshop waitlist to get notified about new dates. For companies that want this implemented for them, see KMUpower – Power Platform consulting & automation for SMEs (DACH).

This post is licensed under CC BY 4.0 by the author.

Microsoft and the Power Platform product names (for example Power Apps, Power Automate, Copilot Studio) are trademarks of the Microsoft group of companies. This is an independent website. It is not operated, sponsored or endorsed by Microsoft.