Agency & White-Label Services
Is There a Read-Only Scope for HubSpot Workflows?
No. The automation scope covers the whole Workflows API in both directions, so any tool that can read a client's workflows can also delete them.

Key Takeaways
- There is no automation.workflows.read. The automation scope grants read and write across the whole Workflows API, so permission to read a client's automation is permission to delete it.
- Sequences have a read-only scope, automation.sequences.read, and CRM objects were split into per-object read and write scopes years ago. Workflows are the unfinished part of that migration, not a deliberate design.
- You can read a private app token's scope list. POST /oauth/v2/private-apps/get/access-token-info with the token in the body returns its hub id, app id and granted scopes.
- The scope list cannot answer 'is this tool safe'. Ask the vendor to state their write behaviour in writing instead, and prefer tools whose source you can check.
- Across the 113 workflows in the portal we tested this against, 12 pairs of enabled workflows enrolled on the same trigger, which is the usual cause of a contact receiving the same email twice.
Somebody on the client side asks whether the tool you want to connect can break anything. You go looking for the narrow scope that reads workflows and nothing else, because that is how the rest of HubSpot's permission model works.
It is not there. This post is what we found when we went looking, and what we did instead.
Is there a read-only scope for HubSpot workflows?
No. HubSpot exposes one scope for workflows, automation, described in its own documentation as "This includes workflows." It covers the entire Workflows API in both directions. There is no automation.workflows.read.
So the moment you let any integration list a client's workflows, you have also let it rewrite or delete every one of them. There is no narrower option to grant, and no combination of other scopes that gets you read access on its own.
That is worth saying plainly to anyone evaluating an integration, because "it only needs the automation scope" sounds modest and reads as read-only to most people. It is delete rights on every workflow in the portal.
Checked against HubSpot's scope reference and confirmed against a live portal on 3 August 2026. HubSpot changes its permission model, so re-check before you rely on it.
Why does HubSpot have read-only scopes everywhere else?
Because it built them, and then stopped. The tell is inside the automation family itself.
automation.sequences.read exists. Sequences got a read-only scope. Workflows did not.
The CRM went further. The old monolithic contacts scope was split years ago into per-object, per-direction scopes, so today you can grant crm.objects.contacts.read without granting crm.objects.contacts.write, and the same holds for companies, deals, lists, owners and property schemas.
| Area | Read-only scope available |
|---|---|
| CRM objects, schemas, lists, owners | Yes |
| Sequences | Yes, automation.sequences.read |
| Workflows | No |
| Content: site pages, blog, marketing email | No |
| Forms | No |
The pattern exists, it shipped, and workflows never received it. This is an unfinished migration rather than a considered decision, which is a more useful way to think about it: it is the kind of gap that gets closed if enough people ask. There is an open request on HubSpot's own ideas board for granular workflow permissions.
What does this mean when a client asks whether a tool is safe?
It means the scope list cannot answer the question, and you should stop treating it as if it can.
For CRM data you can genuinely say "the token is read-only" and be right. For workflows you cannot, so the honest sentence changes shape. It moves from a claim about the client's configuration to a claim about the tool's own behaviour.
The version that survives scrutiny sounds like this: this tool issues GET requests only, every request goes through one function that refuses any other verb, and there is a test that fails the build if that changes. It is a smaller claim. It is also the one somebody can check without trusting you.
Three practical consequences for agency work.
Your own scripts are in scope too. Every internal automation, every one-off script somebody wrote against the Workflows API, every contractor's utility is holding delete rights on a client's automation. The exposure is not limited to third-party vendors.
One private app per tool. When you cannot narrow what a token is permitted to do, the remaining control is how many things hold it. A shared token means revoking one integration breaks the others, so nobody revokes anything.
Ask vendors to write it down. "This tool issues only GET requests" is a sentence a vendor can put in a README and be held to. It is worth considerably more than a scope list, and a vendor who will not put it in writing has told you something.
How do you see what a token can actually do?
You can read the scope list, and most people never have. It is one request:
POST https://api.hubapi.com/oauth/v2/private-apps/get/access-token-info
{ "tokenKey": "pat-na1-..." }
It returns the hub id, the private app id and the full list of granted scopes. Two things trip people up. It is a POST with the token in the body, not the URL, and the introspection endpoint HubSpot documents more prominently, GET /oauth/v1/access-tokens/{token}, only accepts OAuth tokens and returns 400 for a private app token. Tokens beginning pat-eu also need the Bearer header.
We ran that check across our own tokens before writing any of this. One of them, named for read-only use, turned out to hold 117 scopes, 63 of them write-capable, including bulk import and export. Nobody had granted that deliberately. It had simply accumulated, and its name had stopped being true years earlier.
That is the failure mode to look for in your own estate. Not a dramatic breach: a token whose name nobody has re-read since it was created. Run the check on every private app in every portal you manage, and read the list rather than the label.
What did we do about it in our own tool?
We were building a read-only workflow documenter, and the original plan was the obvious one: check the token's scopes on startup and refuse to run if any of them could write.
That plan does not survive contact with the scope model. Since automation is write-capable and mandatory, a refuse-if-writable check refuses on every portal, every time. It would never once have allowed a legitimate run.
So the guarantee moved into the code. One module opens a network connection, and it raises on any HTTP method except GET, with a single named exception for the token introspection call above, which reads nothing but the token's own scope list. A test parses the source and asserts that no other module can issue a write or even import a networking library. Anyone evaluating it can run that one test in about a minute rather than reading the whole codebase.
The tool is public and the test is the first thing the README points at, because the claim is only worth making if somebody else can check it. This is the same reasoning we applied to proving a tool cannot write to a client portal, from the other direction.
What did we find once we could read the workflows?
The reason this matters commercially, rather than only philosophically, is what turns up once a portal's automation is actually documented.
We ran the finished tool against a portal with 113 workflows and 305 actions. Some of what it found:
- 12 pairs of enabled workflows enrolling on the same trigger. A contact meeting that trigger enters both. This is the usual cause of somebody receiving the same email twice, and it is invisible in the HubSpot UI, which shows you one workflow at a time.
- Dead references. Steps pointing at marketing emails that no longer exist, in workflows that are still switched on.
- 8 workflows with no meaningful name, which is what makes a portal unauditable in the first place.
- 44 of the 305 actions carried no action type id at all. They are branches and webhooks, not defects, but any tool that keys on that field silently drops every branch in the portal, and with it all the logic. We nearly shipped exactly that bug.
None of those findings needed a name resolved or a fancy scope. They came out of structure alone, which means even a deliberately minimal token produces them.
Should you go and look at your own portals?
Yes, and the first pass costs almost nothing.
Read the scope list on every private app token you hold, using the request above. Look at what the token can do rather than what it is called. Then take the narrowest useful step: one app per tool, and a written statement from every vendor about their write behaviour.
If you want the workflow side documented, the tool is free and open source and runs on your machine with no server in the path. If what it turns up is bigger than a tidy-up, that is the point at which we take portal work off your plate.
The broader lesson is smaller than it sounds. HubSpot's scope model is good, and the CRM half of it is the standard the rest should meet. Workflows are just the part that has not caught up yet, and knowing that is the difference between a security conversation you can answer and one you cannot.
Sources
Frequently Asked Questions
Is there a read-only scope for HubSpot workflows?
No. HubSpot exposes a single automation scope covering the entire Workflows API for both reading and writing, and there is no automation.workflows.read variant. Any private app or integration granted enough access to list your workflows also holds enough access to modify or delete them.
Which HubSpot scopes have a read-only version and which do not?
CRM objects, schemas, lists and owners all have explicit .read scopes, such as crm.objects.contacts.read and crm.lists.read. Automation, content and forms do not. Sequences are the exception inside automation, with a genuine automation.sequences.read scope that workflows never received.
How do I see what a HubSpot private app token is allowed to do?
Send a POST to /oauth/v2/private-apps/get/access-token-info with the token in the request body. It returns the hub id, the private app id and the full scope list. The documented GET introspection endpoint only works for OAuth tokens and returns 400 for private app tokens.
How can an agency check a HubSpot tool is really read-only?
The scope list will not tell you, so ask the vendor to state in writing that the tool issues only GET requests. With an open source tool you can confirm it: check that every request goes through one function refusing other verbs, and that a test enforces it.
Should agencies use one HubSpot private app for several tools?
No. Create one private app per tool. When you cannot narrow what a token is permitted to do, the remaining control is limiting how many things hold it and how quickly you can revoke one without disrupting the others.
HubSpot Portal Audits
What's Hiding in Your Clients' Portals?
A meticulous white-label audit turns messy portals into a prioritized roadmap, and into your next retainer conversation.
Related Articles

Do You Need HubSpot Enterprise for Custom Objects?
You need one Enterprise subscription on the account, not Enterprise across every hub. What that single upgrade unlocks, and when you don't need it.

