Access Control Best Practices
Strategies for controlling who can use your plugins — from launch rules to runtime eligibility checks.
Your plugin calls APIs, reads data, and takes actions on behalf of users. Not every user should have access to every plugin. Access control is how you ensure the right people reach the right capabilities — and get a clear explanation when they don’t.
There are three strategies, and they aren’t mutually exclusive. Most production plugins combine at least two.
Secure the Underlying Action
This is not optional. Regardless of what you do at the plugin layer, the downstream system should enforce its own permissions. Moveworks supports this through connector-level authentication that ties actions to the requesting user’s identity.
OAuth 2.0 Authorization Code — The user grants consent to a third-party system. Moveworks runs a preflight check before the plugin executes. If the user hasn’t authorized the connector, the assistant prompts them to grant access. The plugin only runs after all required connectors are authorized.
JWT User Claims — The user’s identity is passed in JWT claims to the target system. Every API call executes as that user, preserving the target system’s audit trail and permission model.
RPA — When API integrations aren’t available, browser-based RPA logs into applications on behalf of the user, inheriting their session-level permissions.
Connector-level auth is the only strategy that truly secures the action. Launch rules and eligibility checks control who can start a conversation — they don’t prevent a determined user from reaching the underlying API if the connector uses a shared service account. Always pair plugin-layer access control with per-user authentication on the connector.
DSL Launch Rules
Launch rules determine who can trigger a plugin. They are evaluated before the conversation starts, so there is zero latency impact on the user experience. If a user doesn’t match the rules, the reasoning engine won’t even consider the plugin when interpreting their request.
There are two modes:
- List Mode — Allow or deny specific email addresses. Good for testing or small, fixed audiences.
- Advanced Mode — Write DSL expressions that evaluate against user attributes. This is where attribute-based access control happens.
See Launch Permissions for the full configuration reference.
Sync Attributes for Fast Evaluation
DSL launch rules evaluate against the user record in Moveworks. If the attributes you need aren’t there yet, sync them from your identity provider through the Identity Gateway.
For example, if your organization tracks admin access eligibility in an Active Directory group:
This approach works well when:
- Latency matters — No API call happens at conversation time. The evaluation is instant.
- Attributes don’t change frequently — Group memberships, department, role, and license assignments are typically stable enough that syncing on a schedule is acceptable.
- You want to hide the plugin entirely — Users who don’t match the rules never see the plugin surface in the assistant. There’s no “you don’t have access” message because they never encounter it.
Check the User Attribute Reference for the full list of attributes available in DSL expressions.
Common DSL Patterns
Runtime Eligibility Checks
Sometimes you can’t determine access from static attributes alone. The eligibility decision requires live data — a ServiceNow group membership, an approval status in a ticketing system, or a calculation that spans multiple systems. In these cases, you run the access check inside the conversation process at runtime.
The pattern is:
- Action Activity — Call an API to check the user’s eligibility. Store the result in the data bank.
- Decision Policy — Evaluate the result with DSL. Branch based on whether the user passes.
- Content Activity (denial path) — If the user fails the check, display a clear explanation of why they don’t have access and what they can do next.
- Continue (success path) — If the user passes, proceed with the plugin’s main flow.
Worked Example: Local Admin Access
A user asks to elevate their local admin privileges. Before running the provisioning action, the plugin needs to verify the user is eligible by checking their department, role, and whether they’ve completed the required security training — data that spans ServiceNow and a compliance system.
Build the eligibility check action
Create an HTTP action (or compound action) that queries the relevant systems and returns an eligibility result. The output should include a clear boolean and a reason for denial.
Add the action as the first activity
In the conversation process, add the eligibility check as the first action activity. Map the user’s identity into the request and store the result:
Configure the denial path
On the Not eligible branch, add a content activity that explains the denial. Use the reason and next step from the API response so the user gets a specific, actionable explanation — not a generic “access denied.”
The reasoning engine reads the content activity’s data and can incorporate data.eligibility.reason and data.eligibility.next_step into its response, giving the user a natural-language explanation of what happened and what to do next.
The eligibility check action runs as an activity inside the conversation process, so the user has already triggered the plugin. Unlike DSL launch rules, they will see the plugin — they just receive a clear explanation if they don’t qualify. Design your denial message to be helpful, not just a dead end.
When to Use Runtime Checks
Runtime eligibility checks add latency (one or more API calls before the main flow starts), so only use them when the data can’t be synced ahead of time:
- Data changes frequently — Real-time group memberships, approval statuses, or certification expirations.
- Data spans multiple systems — Eligibility requires joining data from ServiceNow, an HR system, and a compliance tool.
- Complex evaluation logic — Department hierarchy lookups, org-chart traversals, or custom business rules that don’t fit into a DSL expression.
Choosing the Right Strategy
Use this decision flow to pick your approach:
Most production plugins combine strategies:
- OAuth connector + DSL launch rule — The connector secures the action; the launch rule prevents unlicensed users from even starting the conversation.
- DSL launch rule + runtime check — The launch rule filters out obviously ineligible users fast; the runtime check handles edge cases that require live data.
- All three — OAuth secures the action, a launch rule gates on department/role, and a runtime check verifies training certification before executing.
Start with the simplest strategy that meets your requirements. Add complexity only when the simpler approach doesn’t cover your use case. DSL launch rules handle the majority of access control needs without any runtime cost.