HubSpot – Configuration Guide
HubSpot is your all-in-one stop for all of your marketing software needs.
How to create an OAuth app in HubSpot
This guide is for the application owner — the team that ships an integration on Apideck. You will create a HubSpot app, register Apideck's redirect URL and the connector's scopes, and paste the resulting Client ID and Client Secret into the Apideck Dashboard. Once that is done, your consumers can authorize their own HubSpot accounts without any further work from you.
The same app covers both unified APIs this connector serves — CRM and Lead — so scopes, redirect URL and webhooks are configured once.
Before you start
- A HubSpot account. Any edition works, including the free CRM. Legacy developer accounts were converted to standard HubSpot accounts on March 9, 2026, so the account you already sign in with is the one you use — there is no separate developer portal login to create.
- The HubSpot CLI, installed and authenticated (
npm install -g @hubspot/cli@latest, thenhs account auth). HubSpot documents a minimum CLI version on the create-an-app page — update before you start rather than debugging an old client. - Access to your Apideck HubSpot connector settings. That page is filed under CRM and configures the connector for both the CRM and Lead APIs.
Already have a HubSpot app? Existing public apps built on the legacy flow continue to function as-is — you do not need to rebuild anything. Skip to steps 4 (Redirect URL) and 5 (Scopes) below, which are the only two settings Apideck depends on. Migrating an existing app to the current platform is optional; see Migrate an app if you want the newer tooling.
1. Create your app
New HubSpot apps are built on the Projects-based developer platform, driven from the CLI. The older "Create an app" button in the developer UI no longer creates public apps: HubSpot disabled legacy public app creation on May 26, 2026 for accounts created on or after that date, and on June 23, 2026 for all older accounts. If you are looking for that button, this is why it is gone — the flow below replaces it.
At the prompts:
| Prompt | Choose |
|---|---|
| Base contents | App |
| Distribution | Marketplace — see step 2 |
| Auth | OAuth |
| Features | Include Webhooks if you want event delivery (step 7) |
Then upload the project so HubSpot creates the app and issues credentials:
The app-level settings in steps 2–6 are configured in the project's app-hsmeta.json file and
applied by re-running hs project upload. Webhook subscriptions are the exception: they live in
their own *-hsmeta.json file under src/app/webhooks/, covered in step 7. HubSpot's
Create a new app using the CLI
and App configuration
pages are the authoritative reference for the file's full shape.
2. Distribution mode
Choose Marketplace distribution ("distribution": "marketplace") with "type": "oauth". This
is the mode that lets other companies install your app in their HubSpot accounts, which is what
an Apideck integration does. (Listing on the App Marketplace is a separate, optional step — see
step 9. Choosing marketplace distribution does not publish anything.)
Distribution mode also decides which rate-limit regime you run under, so it is worth getting right the first time:
- Marketplace / public distribution — each connected HubSpot account carries its own request allowance, so one busy consumer cannot starve the others. This is the regime the Overview's At a Glance rate-limit figure describes.
- Private distribution (a single-account app) — requests are billed against that one HubSpot account's tier instead: Free and Starter get 100 requests/10s and 250,000/day, Professional 190 requests/10s and 625,000/day, Enterprise 190 requests/10s and 1,000,000/day. HubSpot's API Limit Increase add-on raises these. A private app cannot serve multiple consumers, so pick this only for a genuinely single-tenant integration.
Full detail lives in HubSpot's usage guidelines.
3. Basic information
Set the app's name, description, logo and support contact. Your consumers see these on the HubSpot authorization screen when they connect, so use the branding of your product — this is the screen that tells them who is asking for access to their CRM.
4. Redirect URL
Register Apideck's callback as a valid OAuth redirect URL. It must be exactly:
https://unify.apideck.com/vault/callback
In app-hsmeta.json this goes in the auth.redirectUrls array:
Any other value — a localhost URL from a scaffold template, your own backend, a trailing slash —
makes HubSpot reject the authorization with a redirect URI mismatch. Run hs project upload after
editing.
5. Scopes — these must match exactly
This is the step that most often breaks a first connection. The scopes configured on your HubSpot
app must exactly match the scopes Apideck requests during OAuth. Any mismatch — a missing scope,
or a scope Apideck requests that your app does not declare — fails consumer authorization with an
insufficient scopes error rather than degrading gracefully.
The connector currently requests the following set (identical for CRM and Lead):
crm.schemas.companies.read
crm.schemas.companies.write
crm.schemas.contacts.read
crm.schemas.contacts.write
crm.schemas.deals.read
crm.schemas.deals.write
crm.objects.owners.read
crm.objects.contacts.read
crm.objects.contacts.write
crm.objects.companies.read
crm.objects.companies.write
crm.objects.deals.read
crm.objects.deals.write
crm.lists.read
crm.lists.write
sales-email-read
Add these to auth.requiredScopes in app-hsmeta.json and upload.
This list is current as of writing, not a contract. Before you configure the app, check the scope list shown on your Apideck HubSpot connector settings page — that is the authoritative source for what Apideck will actually request, and it is what your app has to match. If you override the scopes on the Apideck side, match your override, not the list above.
Two additions to consider:
- If you call HubSpot endpoints through the Proxy API that fall outside the connector's own operations, add the scopes those endpoints need as well.
- HubSpot's scopes reference documents what each scope grants and which HubSpot editions include it.
6. Copy your Client ID and Secret into Apideck
After hs project upload, retrieve the credentials HubSpot issued:
- Run
hs project opento open the project page in HubSpot. - Under Project Components, click your app's name.
- Open the Auth tab and copy the Client ID and Client secret from the Client credentials section.
Paste both into the Apideck HubSpot connector settings under Use your own client credentials, and save.

That completes the credential handoff: from this point Apideck runs the OAuth flow against your app, and your consumers never see or handle the Client Secret. Apideck also handles token refresh — HubSpot access tokens are short-lived (30 minutes) and are renewed automatically.
7. Register webhook subscriptions (optional)
Webhook subscriptions on HubSpot are app-level, not per-connection: you register one subscription set in your app, and it delivers events for every consumer who has connected. You do this once, manually — it is not created for you when a consumer connects, and it is not repeated per customer.
Step 1 — get the target URL. Open your Apideck HubSpot connector settings and copy the full Webhook Execute URL from the bottom of the page.

Step 2 — configure the subscriptions. In your project, add a *-hsmeta.json file under
src/app/webhooks/ with the Apideck Webhook Execute URL as targetUrl. HubSpot's
Configure a webhook subscription
page documents the file's exact shape — and one detail on that page matters more than any other
here: subscriptions is not one flat list. It splits into three arrays, and only two of them
work with Apideck:
legacyCrmObjects— the classic event names (contact.creation,deal.propertyChange, …). Use this array for the contact, company and deal events in the table below.hubEvents— holdscontact.privacyDeletion. Use this array for that one event.crmObjects— HubSpot's newerobject.*event format, which that page recommends as the standard. Do not use it for this connector: HubSpot accepts the subscription, but Apideck dispatches on the classic event names, so everything delivered in theobject.*format is dropped silently — no error on either side, just no events arriving.
Then hs project upload.
Subscribe using the classic event names below — these are the subscription types the connector recognizes, and each maps to a unified Apideck event:
| HubSpot subscription type | Apideck unified event |
|---|---|
contact.creation | contact.created |
contact.propertyChange | contact.updated |
contact.deletion | contact.deleted |
contact.privacyDeletion | contact.deletion_requested |
company.creation | company.created |
company.propertyChange | company.updated |
company.deletion | company.deleted |
deal.creation | opportunity.created |
deal.propertyChange | opportunity.updated |
deal.deletion | opportunity.deleted |
Contacts, companies and deals are the full extent of the connector's event coverage. There are no engagement events — activities, notes, calls, meetings and tasks are not delivered by webhook, so poll those resources instead if you need to track changes to them.
Step 3 — subscribe your own application to the Apideck events. Registering the HubSpot side only gets events as far as Apideck; you still need a subscription on the Apideck side to receive them. Follow How to subscribe to webhook events.

8. Test the app
You do not need a separate set of credentials for testing — HubSpot uses the same app for test and production accounts, and the API host never changes. What varies is the account you connect:
- A developer test account is the cleanest option and is free. In your HubSpot account, go to Development > Testing > Test Accounts and click Create developer test account. You can create up to 10, each with a 90-day trial of many Enterprise features. A test account expires after 90 days with no API calls against it and can be renewed from the same page. See HubSpot account types.
- Apideck's temporary shared HubSpot test credentials let you exercise the connector before your own app exists — ask Apideck Support for access.
- Your own production HubSpot account works too, but the connector writes real records. Be deliberate about which account you point a test run at.
9. Listing and certification (optional)
Nothing in this guide requires an App Marketplace listing — your app can serve consumers on marketplace distribution without ever being listed. Both paths below are free, with no revenue share.
- Listing on the App Marketplace requires the app to have active installs in at least 3 HubSpot accounts, plus HubSpot's listing content requirements. "Active install" means a unique production account unaffiliated with your organization that has shown app activity recently — your own developer test accounts do not count toward either threshold.
- App Certification is requested after listing and requires substantially more traction — 60 active installs as of writing (raised from 6 in May 2024) — along with a minimum period listed and operational quality expectations such as a high API success rate and staying inside rate limits. It renews on a rolling two-year cycle.
Both thresholds are HubSpot policy and do change; confirm the current numbers on HubSpot's certification requirements and listing requirements pages before planning around them, and ask your HubSpot contact for an expected timeline on any review.
What your consumers do next
With credentials saved, scopes matched and the redirect URL registered, connecting is entirely self-service for your consumers: they authorize their HubSpot account through Apideck Vault and choose a default pipeline and stage for new opportunities. The authorizing user needs HubSpot's App Marketplace Access permission (super admins have it by default) when new scopes are being granted.
FAQ and troubleshooting
"Insufficient scopes were provided. Please contact the app developer"
The scopes on your HubSpot app do not match what Apideck requests. This is an exact-match check, not a subset check, so it fires both when your app is missing a scope Apideck requests and when the two lists simply differ.
To fix it, compare two lists side by side: the scope list on your
Apideck HubSpot connector settings page,
and auth.requiredScopes in your app's app-hsmeta.json (or the Auth tab of the app in
HubSpot). Reconcile them, run hs project upload, and have the consumer authorize again — the
error is raised at authorization time, so the retry has to be a fresh authorization.
Common causes:
- One or more CRM scopes from step 5 missing on the app.
- Scopes overridden on the Apideck side for one integration and never mirrored onto the app.
- Proxy API calls that need scopes beyond the connector's own set.
Authorization fails with a redirect URI mismatch
auth.redirectUrls must contain https://unify.apideck.com/vault/callback character for
character. Scaffolded projects ship with a localhost placeholder; replacing it and re-uploading is
easy to forget.
I can't find "Create an app" in HubSpot
That button created legacy public apps and no longer does — creation was disabled for all accounts by June 23, 2026. Use the CLI flow in step 1 instead. Apps you created before the cutoff are unaffected and keep working.
A consumer's connection stopped working
Access tokens are refreshed automatically, and HubSpot documents no scheduled expiry for refresh tokens. What does end a connection is action on the HubSpot side: if the consumer uninstalls your app from their HubSpot account or revokes access, the connection stops working and they have to authorize again. Uninstalling in HubSpot also removes them from your app's install count.
No webhook events for activities, notes or calls
Expected — see step 7. Contact, company and deal events are the whole set; poll for the rest.
HubSpot returns 429
You are over the rate limit for the regime your distribution mode puts you in (step 2). The CRM Search API has its own, lower limit and does not draw on the general allowance, so search-heavy traffic is the usual first suspect. Back off and retry; if a consumer legitimately needs more throughput, note that HubSpot's API Limit Increase add-on raises the tiered limits for private apps only — it does not lift the per-account allowance for a marketplace-distributed app. Reducing call volume (batch endpoints, caching, webhooks instead of polling) is the available lever there; HubSpot's usage guidelines cover the mitigation options and the response headers that let you track usage.