When I worked at an Atlassian Partner, one of the most common gotchas I came across was the “simple workflow” problem. Take a typically simple workflow: five statuses, seven transitions, clean diagram. The kind of workflow you'd use as the poster-child for a "keep it simple" presentation.
Then you look at the workflow with a magnifying glass. One of those seven transitions carries three conditions, four validators, and six post-functions. One of the post-functions was a script nobody could really explain. Another reassigned issues to a user who is no longer a member of the team.
At a glance, the diagram showed none of that complexity.
The workflow diagram answers exactly one question: where can an issue go? That's navigational complexity, and it's the easiest to assess. Count statuses, count arrows, judge accordingly.
Behavioural complexity is a different question: what happens when an issue moves? Who's allowed to trigger it, what gets checked, what fires afterward. That's where the friction lives, and Jira gives you no immediate visual for it. On the surface, a transition carrying ten hidden rules looks identical to an empty one.
Users can learn to navigate a big workflow. What they can't do is understand why a button is missing, why a transition failed, or why a field changed on its own. Invisible friction hurts more than visible size.
Three mechanisms, firing at three different moments:
Conditions run before the click. They control whether the user can see or use the transition at all. Permission checks, role restrictions, field-based logic. Here's the cruel part: when a condition blocks someone, there is no error. The button is greyed out or just absent. The user has nothing to work with, so they file a ticket that says "Jira is broken." And where does the ticket land? In your lap as the admin.
Validators run at the click. The user attempts the transition and validators judge the attempt. Required fields, resolution checks, permission verification. Validators at least fail visibly. But a validator without a custom error message produces a cryptic message, and the difference between "helpful guardrail" and "mystery" is entirely dependent on whether someone took time to write a helpful prompt.
Post-functions run after. Once the transition succeeds, they execute in sequence: set a field, change the assignee, fire an event, call a webhook, trigger additional automation. Users don't know they exist. When someone says "Jira changed my ticket by itself," a post-function did it.
So, user thinks they move their ticket, but in reality, one transition = three potentially hidden results.
Counting post-functions tells you little. What they do is what matters:
A set-field post-function is predictable and usually intentional. A notification is visible but may contribute to alert fatigue. An assignee change is an ownership decision the user didn't make but people notice. A webhook has its effects in another system entirely, so when that system changes, Jira doesn’t give you any feedback. An automation trigger can cascade: one transition fires a rule that edits ten issues that trigger further rules. And a script is arbitrary code, capable of many actions, including those its author no longer remembers writing.
One script post-function outweighs five set-field ones. Audit accordingly.
Manual route: open the workflow in edit view (not the diagram) and inventory each transition. Atlassian's advanced workflow configuration docs explain what each rule type can do. Keep in mind that the manual approach doesn't scale well.
API route: everything is exposed. GET /rest/api/3/workflow/search?expand=transitions returns every transition with its conditions, validators, and post-functions (actions in the payload), each carrying a ruleKey. System rules read like system:update-field or system:change-assignee. App rules arrive as connect:remote-workflow-function with an appKey identifying the app responsible. One afternoon of scripting gets you a behavioral inventory of every workflow in the instance. Reference: workflow search API.
Either way, what you're hunting for:
Overloaded transitions. Measure load per transition, never per workflow. Averaging across the workflow hides the one transition making everyone’s life harder.
Ordering dependencies. If post-function two reads a field that post-function one sets, maintaining that order is key. Reordering during a well-intentioned cleanup is an easy way to create a bug that rears its head again in three months.
External pointers. Webhooks, automation triggers, app functions. They break silently when the target changes. The breakage never gets connected back to the workflow because it happens in a different tool.
Orphaned app rules. Uninstalled apps and expired trials can leave dead rules behind. Some fail silently on every single transition.
For every transition, ask: if this blocks someone or does something surprising, would they understand why?
If the answer is no, that transition is generating friction for users and support tickets for you. Undocumented conditions, validators without error messages, and invisible post-functions are exactly where an admin’s time goes to die.
Tidy diagram, complex transitions. That’s the kind of config that eats your time.
What's the most complex workflow you've inherited?
Thanks @Peter Kerrigan for bringing attention to this aspect of tech debt hiding in Jira workflows.
A few comments:
I often find that teams who have been using Jira for some years will be deeply entrenched in the current configuration of their Space. Change is often resisted or feared.
I find success by partnering strongly with individual teams when they ask for help. But even then their focus is delivering business value of their product or service, and Jira details are a much lower priority.
Really insightful article. I particularly like the distinction between navigational and behavioural complexity.
One thing I’d add is that behavioural complexity isn’t static. Every workflow change, new automation, app installation or process adjustment can gradually increase it. The real challenge isn’t just auditing workflows once, but continuously knowing where complexity is accumulating before users start reporting issues.
As Co-Founder of MetaFrazo, that’s exactly the problem we’re focused on. Visibility into behavioural complexity at scale helps admins identify where attention is needed instead of waiting until operational friction becomes visible through support tickets.
I’d also love to see Atlassian surface more of this directly in the workflow UI.
What enlarges complexity is when several teams work on a single work item. Typical example: task is made from requirements and system analytic takes it to work, then passes to product owner to add it to plan, then developer investigates possible solutions, then he develops the code and passes to code review, then code is deployed by devops and passed to QA, then QA finds bugs and possibly returns to analytic or developer, then final deployment.
This means literally dozens of statuses with conditions and cross links here and there. And it completely overthrows idea of agile when a task should be completed during one sprint. Consequently jira reports do not work, we have issues migrating from sprint to sprint and total mess for managers who cannot control team quality.
What I would do is have special issue types for Designers, QA, Developers, Analytics and so on with each workflow having 3-4 steps. Then we can have separate sprints for each team and they can work in parralel without blocking each other. When a story is taken into work Product owner creates 5-6 work items like "Analyze requirements", "Develop and review code", "Test", "Deploy to UAT", "Deploy to Prod" and link them all. If a task is blocked by another task it cannot be taken into sprint. If a task was not completed during the sprint team discusses and takes extra time to finish it before starting next sprint or puts it and related tasks to technical debt.
I worked with the process like this and it was very cool - our manager sold product to the client and client new for sure when the product will be delivered and how much time it took to finish this functionality. Naturaly USD per feature.
My rule of a thumb. If workflow has intersecting lines then something is wrong. If any status has more than 3 outgoing transactions something is wrong. If there are conditions like "Only people in Design role can move issue to this status" then something is wrong.
@Peter Kerrigan A couple of points.
You're using the terminology of conditions, validators and post-functions from the old workflow editor which is due to be fully deprecated in two days' time! https://community.atlassian.com/forums/Jira-Cloud-Admins-articles/Final-notice-old-workflow-editor-deprecation-in-July-2026/ba-p/3247499
They are all now 'rules' which 'restrict transition', 'validate details' or 'perform actions'. This page has a useful comparison table https://support.atlassian.com/jira-cloud-administration/docs/what-is-the-new-workflow-editor/
It looks like Atlassian have updated some of their doc pages (example) but not others (example).
You talked about friction for users, and @s_gridnevskii mentioned a role-based condition being wrong. I have a different perspective from having worked in regulated industries where the Jira tickets' history was used as evidence to show auditors that the correct processes were followed. And the auditors would literally pore over every step in the history, in conjunction with the org chart, and there'd be trouble if the 'wrong person' had done certain transitions. I had to ensure that the workflows were absolutely robust so that eg an approval/review transition could not be skipped, or that certain steps were performed by different people (four eyes principle). It could be experienced as friction by new users, but it's actually a way of protecting them - so they don't accidentally leave themselves and the company open to audit pain down the line.
That's the beauty of Jira - we can configure our workflows for our different companies' needs, simple for some, complex and robust for others.
@Julia Foden maybe I used improper wording. It is not wrong, it is the source of problems as any restriction. Many times users come to me and ask "Why I cannot transit the work item to next step". It takes time to find out and explain giving I have 150 spaces in my Jira.
I think it is better to explain to user why he should not do it rather than forbid it. If someone does something wrong history of a work item will keep it for audit.
But a validator without a custom error message produces a cryptic message, and the difference between "helpful guardrail" and "mystery" is entirely dependent on whether someone took time to write a helpful prompt.
In a previous company we had an old legacy program (it's old enough that it's a program not an app, and the person who originally wrote it had to develop his own programming language to write it because nothing else available at the time could do what he wanted), that basically controlled a specific piece of equipment to capture background noise over a certain frequency range and compare it against a radio signal (for example).
Someone put in an error code for if a certain background noise value was ever measured, and the error message was something like "Data collected from environment 'Sky' is incorrect, please remove 'cloud' from 'Sky', if 'cloud' is not present in 'Sky' recalibrate 'weather'".
It was rarely used internal only software, written in a non standard programming language, and it was too much hassle at the time to work out where the error was raised so it got left in.
In the same program there was a hidden random number generator that raised an error "User {specific_user} detected, user is invalid, please replace user with valid user".
I never found out why that specific user was chosen, but both these errors codes were documented as being real errors
Recommended Learning For You
Level up your skills with Atlassian learning
Learning Path
Improve user experience across Jira with global settings
Learn how to set up and configure a Jira site, manage Jira permissions, and configure Jira apps and integrations.
Learning Path
Streamline projects across Jira with shared configurations
Build Jira work items with reusable configurations called schemes, and reduce administrative work with automation.
Learning Path
Become an effective Jira software project admin
Set up software projects and configure tools and agile boards to meet your team's needs.