DEV Community

Pravinraj Vincent
Pravinraj Vincent

Posted on Edited on

An Operating Model for Reliable UiPath Unattended Automation

Pravinraj Vincent, UiPath Solutions Engineer

Who this is for

This paper is for platform leads, solution architects and COE owners who already run unattended robots in production. It isn't a build guide. It covers the decisions above individual workflows: machines and folders, runtime capacity, where retries live, what you measure, and how changes reach production.

Every product behavior below is taken from UiPath documentation, linked inline. Where I give an opinion, I mark it as my recommendation and say which facts it rests on.

Thesis

Most unattended failures I see on the forum aren't bugs in the business logic. They come from the platform around it: a session that can't be created after patching, a browser policy pushed by another team, a runtime pool sized for the average day, a retry policy that counts the same invoice twice. Reliability at scale is mostly an operating model problem. The platform team's job is to name the failure domains, give each an owner, and design so a failure in one domain stays there.

The failure domains

Domain What breaks Documented example
Windows session The robot can't log on or can't reach the desktop Logon policies such as "Display information about previous logons during user logon" block session creation with error 0x80070520 (session troubleshooting)
Host configuration Same package behaves differently per machine Resolution and scaling differ between an RDP session and a local one (execution troubleshooting)
Browser policy Extension or selectors stop working after a policy change ProcessIsolationEnabled affects selectors outside the HTML content; DeveloperToolsAvailability settings limit the extension (Chrome group policies)
Office dependency Excel steps fail where Excel isn't installed or set up Modern and classic Excel activities need Excel installed; Workbook activities don't (Excel package)
Capacity Jobs sit in Pending Runtimes are drawn from the tenant pool per connected host (unattended concepts)
Work distribution Items processed late, twice, or never Queue trigger scheduling can over- or under-schedule depending on a tenant setting (queue triggers)
Change A new version breaks production Pending jobs pick up an edited process version, running jobs don't (managing processes)

My recommendation: give each row a named owner. The session and browser rows usually belong to the desktop or VDI team, not the RPA team, and the fastest fix is a shared change calendar with them.

Machine and folder strategy

Machine templates are UiPath's recommended machine type for unattended work. One template lets many hosts connect with a single key or client credential pair, regardless of hostname (unattended concepts). The docs attach conditions to that: hosts under one template should share the same applications, installed at the same paths and versions, and every robot account in a folder needs a matching account on every machine in that template, because Orchestrator can start a job on any valid account and machine pair.

That turns template design into a blast-radius decision.

Option Choose it when Trade-off
One broad template for a pool Hosts are built from one image and all processes need the same apps Simplest capacity math; one bad image change affects every process on the pool
Templates split by application stack (for example SAP hosts vs browser-only hosts) Processes need different software or different access rights Smaller blast radius; runtimes are split across pools, so idle capacity in one can't help another
Templates split by environment (non-production vs production) You want image changes to land somewhere safe first Needs a second set of hosts; gives you a natural canary

UiPath also recommends non-persistent VDI to keep host configuration consistent, and installing the Robot in Service Mode for unattended work (how unattended automation is performed). A User Mode robot can't run unattended automations (execution troubleshooting). For images, the CLI supports UiRobot.exe connect with --url plus either --key or --clientID and --clientSecret (Robot CLI). My recommendation is to run that at first boot rather than baking a connected robot into the golden image, so each clone registers under its own final hostname.

Robot accounts assigned to a parent folder inherit access to its subfolders, and inherited roles can't be removed lower down (unattended concepts). I'd design the folder tree around ownership and access boundaries first and around org charts second, because that inheritance rule makes over-broad parent assignments hard to undo.

Capacity and licensing

The runtime rules, from unattended concepts:

  • Runtimes are assigned to a machine object, and that number applies to each host connected to it. Three runtimes on a template with three connected hosts means up to nine concurrent automations.
  • Runtimes come from the tenant pool when a host connects and go back when it disconnects.
  • A host can run many background processes but only one foreground process at a time. UiPath's own example: 10 background processes plus 1 foreground process need 11 runtimes but only one host. A second simultaneous foreground process needs a second host.

So capacity has two dimensions: runtimes and foreground slots. My recommendation is to model them separately. Background-heavy portfolios are runtime-bound; UI-heavy portfolios are host-bound, and adding runtimes alone won't clear the queue.

For Cloud Robot - Serverless, consumption is per minute by machine size (Small 1 RU per minute, Standard 2, Medium 4, Large 10), and if the size is too small the process times out but still consumes robot units for the time it ran (managing processes). Undersizing to save units can cost more.

Queue and retry design

Queues are where reliability is either designed in or bolted on. A few documented behaviors drive the design:

  • Auto retry has separate options for Failed items and Abandoned items, with a Max # of retries field that takes a value from 1 to 50. Manual retries don't count toward that maximum (managing queues).
  • Only items failed with an Application exception are retried (automation best practices). Business exceptions aren't.
  • An item that stays In Progress for a long time (approx. 24 hours) without being processed becomes Abandoned (queue item statuses).
  • Each retry is a new item. The Key field holds the GUID of the first item in the chain, RetryNumber counts automatic retries, and manual retries are tracked separately in ManualRetryNumber (managing queues).
  • Retried and deleted items don't take part in unique reference checks, so UiPath advises against deleting the first item in a retry chain.
Retry layer Scope Use it for
Activity-level retry in a Global Exception Handler (result = Retry) One activity Rare, attended or simple linear processes. Not available in libraries (GEH)
Framework retry inside the job One transaction Transient system errors you can recover from in-session
Queue auto retry One item, new job possible Failures that need a fresh session or machine
Manual retry by a reviewer One item Failures that need a human decision

My recommendation: pick one automated layer per failure type and write it down. The layers multiply. A GEH that retries an activity, inside a framework that retries the transaction, on a queue that retries the item, can turn one bad record into many attempts, and each queue retry shows up as a new item in reporting.

On triggers, the docs say queue triggers are optimized for processes that loop through all available items before exiting, there's one queue trigger per queue, and a periodic check (30 minutes by default, configurable down to 10) restarts work for postponed or unprocessed items. They also warn that this check can tie up resources outside business hours if items are left over (queue triggers). The "Enable pending jobs strategy" tenant setting changes the capacity formula: on, it may over-schedule; off, it may under-schedule, with the periodic check catching up. I'd treat that setting as an architecture decision, not a default, and record why you chose it.

Graceful control

Orchestrator's Stop is a soft stop. The job is marked Stopping and the robot is notified, but execution continues. The workflow has to check for it with Should Stop and exit on its own; if it never acts on the signal, the job runs to the end and finishes as Successful. Kill forcefully stops the job and marks it Stopped (managing jobs). The Robot guide adds that Kill first sends a Cancel request, which lets Finally blocks run cleanup, before it forces termination (stopping a process, Robot 2023.10). UiPath recommends Stop over Kill (automation best practices). The same Robot page notes that a stopped or cancelled transaction can be recorded as successful if status is set in the wrong block, and advises setting Successful only in the Try block and Failed only in the Catch block.

This matters because machine maintenance mode offers three choices: wait for running jobs to finish (the default, which issues no stop command), stop all running jobs and wait, or kill them now. UiPath notes that jobs only shut down gracefully if the automation is built to handle stop requests. Maintenance is set per session (machine plus hostname), and pending jobs keep their status until another machine, or the same one once it's back, picks them up (managing machines). If your processes honor Should Stop, "stop and wait" becomes a safe patch-night tool. If they don't, you're left choosing between waiting indefinitely and killing.

Observability and SLOs

Orchestrator gives you several building blocks:

  • Queue SLAs. SLA predictions per queue, with an optional Risk SLA buffer, up to 90 days (managing queues).
  • Notifications. Subscribable events include unattended robot unresponsive or disconnected, trigger automatically disabled, job execution failed, jobs pending, transaction failed with application exception, and queue SLA error (notifications).
  • Job recording. Recording of failed jobs, failed queue transactions, or all jobs. The maximum duration depends on the plan: 3 minutes for non-entitled cloud tenants, up to 15 on Enterprise or Advanced (managing processes).

Two documented limits shape how far you can lean on these. Transaction-failure notifications are deduplicated to 10 per queue per 60 minutes, with an hourly summary (notifications). And by default a trigger is disabled automatically after 10 failed launches if it hadn't launched successfully in the last day (managing triggers). That second one is quiet: work just stops arriving.

My recommendation is to define SLOs on business outcomes, not job status: share of business items finished inside the queue SLA, counted once per Key, plus time from item creation to final status. Job success rate alone hides the stopped-but-successful case above and double counts retries. Treat "trigger automatically disabled" and "unattended robot disconnected" as page-worthy, since both stop throughput without a failed job to show for it.

Governance and change control

Automation Ops policies can restrict which package feeds Studio can use, enforce Workflow Analyzer rules, and require projects to pass analysis before running or publishing. Robot policies add Runtime Analyzer rules that block listed apps, URLs, or email recipients at runtime. Policies deploy at tenant, group, or user level (governance).

For infrastructure change, take the browser. UiPath documents that DeveloperToolsAvailability = 2 breaks the Chromium API input method unless the allowlist and blocklist policies are both set for the UiPath extension ID, and that DisableScreenshots on Chrome 154 and later breaks Chromium API input and Inject Js Script (Chrome group policies). Those are security team decisions. My recommendation is to register the robot pool as a stakeholder in browser and GPO change, and to route those changes through a non-production template first.

Release and rollback

Option Choose it when Trade-off
Manual publish and process update in Orchestrator Small estate, few releases No enforced tests or approval
Automation Ops Pipelines You want UiPath-native CI/CD from GitHub or Azure DevOps Pipeline jobs run on an unattended robot, so it needs a dedicated folder, a robot account, and a machine or serverless robot to run on (Pipelines)
UiPath CLI, Azure DevOps extension, or Jenkins plugin You already run an enterprise CI/CD system (CI/CD) You own the pipeline code

Built-in pipeline templates include "Update with tests" and "Build and promote with approval," which adds an approval step before promoting to a second environment (Pipelines).

Rollback is a process setting: Edit Process lets you pick a version or select Rollback to return to the previous one, and UiPath recommends keeping at least one old version for that purpose (managing processes, automation best practices). Running jobs keep the version they started with, while pending jobs and new triggers use the updated one. My recommendation: release when the queue is drained or the trigger is paused, so you know which version touched which items.

Cost and risk

The cheapest reliability work is usually removing a dependency rather than hardening it. Two examples from the docs. Workbook activities read and write Excel files without Excel installed (Excel package), which takes Office setup out of the robot's failure domain when you don't need the Excel UI. And the Microsoft 365 Download File activity fetches a OneDrive or SharePoint file through a connection into a local path, with an explicit "if a file already exists" choice (Download File). My recommendation is to stage inputs that way instead of relying on a per-user sync client being caught up when a robot session starts. With Sites.Selected, browsing lists nothing, so you enter the file URL or ID.

On risk, the trade-off to state openly is concentration: one big shared pool uses runtimes efficiently and also turns one image or policy change into a tenant-wide incident.

Maturity model

This is my own framing, not a UiPath model.

Level Characteristics
1. Reactive Per-VM machines, jobs on schedules, failures found by business users
2. Standardized Machine templates on a common image, Service Mode robots, queues with set statuses, one retry layer per failure type
3. Observed Queue SLAs, subscribed notifications for robot, trigger, and transaction events, outcome-based SLOs counted per Key
4. Governed Automation Ops policies, CI/CD with tests and approval, documented rollback, robot pool included in GPO and browser change
5. Engineered Non-production template as canary, capacity modeled on runtimes and foreground slots, dependencies removed where possible, maintenance via graceful stop

One-page checklist

Failure domains

  • [ ] Each domain (session, host, browser, Office, capacity, distribution, change) has a named owner
  • [ ] Logon and RDS session policies on robot hosts match UiPath's session troubleshooting guidance

Machines and folders

  • [ ] Unattended hosts use machine templates and Service Mode robots
  • [ ] Hosts under a template share apps, paths, and versions
  • [ ] Every robot account in a folder exists on every host in its templates

Capacity

  • [ ] Runtimes sized for peak overlap across all folders on a template
  • [ ] Foreground slots (hosts) modeled separately from runtimes

Queues

  • [ ] One automated retry layer per failure type, documented
  • [ ] Reporting counts business items by Key, not by queue item
  • [ ] First items in retry chains are never deleted
  • [ ] Pending jobs strategy chosen deliberately

Control and observability

  • [ ] Processes honor Should Stop; status set only in Try and Catch
  • [ ] Queue SLAs and Risk SLAs set
  • [ ] Alerts on robot disconnected, trigger auto-disabled, job failed, queue SLA error

Change

  • [ ] Automation Ops policies for feeds and analyzer rules
  • [ ] CI/CD with tests and approval
  • [ ] At least one previous process version kept for rollback
  • [ ] Browser and GPO changes tested on a non-production template first

I post short UiPath fixes from real forum questions on my YouTube channel, RPA Simplified.

Top comments (0)