Universal hooks
Universal hooksSupported in all extension points:
crm.record.tab, crm.record.sidebar, crm.preview, helpdesk.sidebar, settings, homeuseExtensionApi
TheuseExtensionApi hook provides access to available actions and contextual information from a single hook, for extension components that need access to both actions and context.
Otherwise, it’s best practice to use the more specific useExtensionActions or useExtensionContext, depending on your use case.
- For a complete list of available context properties, see the context reference documentation.
- For a complete list of available actions, see the actions reference documentation. The actions available depend on the extension point location.
useExtensionApi hook to display an alert (action) containing the user’s first name (context) when a button is clicked.
- Basic usage
- Typed usage
useExtensionContext
TheuseExtensionContext hook provides access to contextual information about the current extension environment, including location and other relevant data.
For a complete list of available context properties, see the context reference documentation.
The following example accesses the current extension location and renders it in a Text component:
- Basic usage
- Typed usage
useExtensionActions
TheuseExtensionActions hook provides access to various actions that can be performed within the HubSpot interface. It’s a generic hook that can be typed with specific extension point locations for better TypeScript support.
For a complete list of available actions, see the actions reference documentation. The actions available depend on the extension point location.
The following example displays an alert when a button is clicked:
- Basic usage
- Typed usage
useRecordProperties
TheuseRecordProperties hook fetches properties from the provided CRM record with optional formatting. It accepts an array of properties to fetch, the record ID/type, and an optional object of formatting options.
This hook was introduced in the latest version (v1) of the UI Extensions SDK.
- Call
- Response
- Example usage
useRecordAssociations
TheuseRecordAssociations hook fetches CRM records of a specific object type associated with the provided record. It accepts an object containing configuration details for the association fetch request.
This hook was introduced in the latest version (v1) of the UI Extensions SDK.
- Call
- Response
- Example usage
string
required
The object type of the record for which associations are being fetched.
integer
The ID of the record for which associations are being fetched.
String
The object type ID to fetch associations from (e.g., ‘0-1’ for contacts).
Array
An optional array of properties to fetch from associated records.
integer
An optional number of records per page (defaults to 10).
object
Contains formatting options for the values returned from date, datetime, and currency properties.
- The
propertiesToFormatproperties can be set to"all", or an array of property names to format. Defaults to"all". - The
dateanddateTimeobjects can includeformatandrelativesubfields:format(string): a date or datetime string likeMM-DD-YYYYorMM-DD-YYYY:mm:ss. Supports standard date time string formats.relative(boolean): set totrueto display the amount of time passed since the returned value (e.g.,(1 day ago)or(1 hour ago)).
- The
currencyobject can includeaddSymbol(boolean), which sets whether the currency symbol should display with the number. Set totrueto display the currency symbol.
useRecordSearch
TheuseRecordSearch hook searches CRM records of a given object type. The search is built using any combination of text query and structured filters, and returns record IDs, property values, and optional associations. Property values are returned unformatted unless the format option is provided.
This hook was introduced in the latest version (v1) of the UI Extensions SDK.
- Call
- Response
- Example usage
- Live search
- Filter by association
string
required
The object type to search. Accepts type IDs (
"0-1"), names ("contact", "deal"), or custom object names with a p_ prefix ("p_pets").array
An optional array of properties to return for each result.
string
An optional free-text search query matched against the object’s default searchable properties.
array
An optional array of filter groups. Groups in the array are OR’d together; filters within a single group are AND’d. Each filter includes a
propertyName, an operator (EQ, NEQ, LT, LTE, GT, GTE, BETWEEN, IN, NOT_IN, HAS_PROPERTY, NOT_HAS_PROPERTY, CONTAINS_TOKEN, NOT_CONTAINS_TOKEN), and a value, values, or highValue field depending on the operator. See search the CRM for more details.array
An optional array of sort configurations. Each item requires a
propertyName and a direction ("ASCENDING" or "DESCENDING").integer
An optional number of results per page. Default:
10. Max: 200.object
Contains formatting options for the values returned from date, datetime, and currency properties.
- The
propertiesToFormatproperties can be set to"all", or an array of property names to format. Defaults to"all". - The
dateanddateTimeobjects can includeformatandrelativesubfields:format(string): a date or datetime string likeMM-DD-YYYYorMM-DD-YYYY:mm:ss. Supports standard date time string formats.relative(boolean): set totrueto display the amount of time passed since the returned value (e.g.,(1 day ago)or(1 hour ago)).
- The
currencyobject can includeaddSymbol(boolean), which sets whether the currency symbol should display with the number. Set totrueto display the currency symbol.
useCrmSearch
TheuseCrmSearch hook searches CRM records of a given object type. The search is built using any combination of text query and structured filters, and returns record IDs, property values, and optional associations. Property values are returned unformatted unless propertiesToFormat is set.
- Call
- Response
- Example usage
- Live search
- Filter by association
object
required
Configures the search request with the following parameters:
objectTyperequired: the object type to search. Accepts type IDs ("0-1"), names ("contact","deal"), or custom object names with ap_prefix ("p_pets").properties: an optional array of properties to return for each result.query: an optional free-text search query matched against the object’s default searchable properties.filterGroups: an optional array of filter groups. Groups in the array are OR’d together; filters within a single group are AND’d. Each filter includes apropertyName, anoperator(EQ,NEQ,LT,LTE,GT,GTE,BETWEEN,IN,NOT_IN,HAS_PROPERTY,NOT_HAS_PROPERTY,CONTAINS_TOKEN,NOT_CONTAINS_TOKEN), and avalue,values, orhighValuefield depending on the operator. See search the CRM for more details.sorts: an optional array of sort configurations. Each item requires apropertyNameand adirection("ASCENDING"or"DESCENDING").pageLength: an optional number of results per page. Default:10. Max:200.
'all' | array
Either
'all' or an array of property names to format. When omitted, property values are returned unformatted.object
Contains formatting options for the values returned from date, datetime, and currency properties.
- The
dateanddateTimeobjects can includeformatandrelativesubfields:format(string): a date or datetime string likeMM-DD-YYYYorMM-DD-YYYY:mm:ss. Supports standard date time string formats.relative(boolean): set totrueto display the amount of time passed since the returned value (e.g.,(1 day ago)or(1 hour ago)).
- The
currencyobject can includeaddSymbol(boolean), which sets whether the currency symbol should display with the number. Set totrueto display the currency symbol.
useRecordAggregation (BETA)
TheuseRecordAggregation hook runs grouped counts and numeric metrics over CRM records, optionally across associated objects, and returns one row per group. HubSpot runs the aggregation server-side, so you don’t need to fetch every record with useCrmSearch and calculate totals in your extension. Use it for summary data like pipeline value by deal stage, revenue by month, or companies that have no deals.
A query starts from a root object (from), can join associated objects (joins), groups records by one or more properties (dimensions), and calculates values for each group (measures and calculatedMeasures). You can also filter, sort, and limit the results.
- Call
- Response
- Example usage
- Monthly trend
- Joined objects
- Calculated measures
object
required
The root object to aggregate:
objectTyperequired: the object type to aggregate. Accepts type IDs ("0-3"), names ("deal"), or custom object names with ap_prefix ("p_pets").alias: an optional name for the root object. You can reference it in thesourcefield of dimensions, measures, and filters, and in thejoinTofield of joins. Fields that omitsourcetarget the root object.
array
An optional array of up to three associated objects to bring into the query. Each join includes:
-
objectTyperequired: the object type to join. It must be associated with the object it joins to. -
aliasrequired: a name for the joined object, used insourcefields. -
joinTo: the alias of the object to join to. Must be the root object’saliasor thealiasof a join that appears earlier in the array. Defaults to the root object. -
on: the association type to join on, for when more than one association type exists between the two objects. When omitted, HubSpot selects the association automatically. The value is a string in the format"<categoryId>-<typeId>":categoryIdis0for HubSpot-defined association types,1for user-defined association labels, or2for integrator-defined association types.typeIdis the association type ID for the direction from thejoinToobject to the joined object. To find the ID of a custom association label, retrieve the association labels between the two objects.
"0-342"joins companies to deals using the default company to deal association. If the type ID is for the opposite direction, such as"0-341"(deal to company) on a join from companies to deals, the join finds no associated records instead of returning an error.
null for those records.array
required
The properties to group records by, up to 10. Each unique combination of dimension values produces one row. Pass an empty array to aggregate all matching records into a single row. The row is returned even when no records match, with values like a
COUNT of 0. Each dimension includes:propertyrequired: the property to group by.source: the alias of the object the property belongs to. Defaults to the root object.as: the key for this dimension in each row. Defaults to the value ofproperty. Setaswhen two objects in the query share a property name.dateTrunc: groups a date or datetime property into calendar buckets in the account’s time zone. AcceptsDAY,WEEK,MONTH,QUARTER, orYEAR. Each bucket’s value is the bucket’s start date as aYYYY-MM-DDstring (e.g.,"2026-08-01"for August 2026).WEEKbuckets start on Monday. Records with no value for the property are grouped into a bucket whose value isnull.
array
required
The values to calculate for each group. A query needs at least one entry in
measures (calculated measures alone aren’t enough), and can include up to 10 measures and calculated measures combined. Each measure includes:namerequired: the key for this measure in each row.metricrequired: the aggregation to perform. AcceptsCOUNT,SUM,AVERAGE,MIN,MAX,DISTINCT_COUNT, orMEDIAN. Without afield,COUNTcounts the root object’s records in each group. With afield, it counts the records where that property has a value.DISTINCT_COUNTreturns an exact count of unique values. To count unique records in a query with joins, useDISTINCT_COUNTon the object’shs_object_id.field: the property to aggregate, as an object with apropertyand an optionalsourcealias. Required for every metric exceptCOUNT.fixedBy: an array of dimension keys (each dimension’sasorpropertyvalue). The measure is calculated across only those dimensions, ignoring the query’s other dimensions. For example, in a query grouped by deal stage and owner, aSUMofamountwithfixedBy: ["dealstage"]returns each stage’s total on every row for that stage. An empty array behaves the same as omittingfixedBy.
array
An optional array of values derived from two other measures, such as a ratio. Calculated measures count toward the limit of 10 measures. Each calculated measure includes:
namerequired: the key for this value in each row.leftrequired andrightrequired: thenameof a measure or another calculated measure. Operands can’t reference dimensions or constant numbers, and calculated measures can’t reference themselves directly or indirectly. An operand that references a measure withfixedByuses that measure’s regular grouped value, not its fixed value.operatorrequired: the arithmetic to apply toleftandright. AcceptsADD,SUBTRACT,MULTIPLY, orDIVIDE.
array
An optional array of filter groups. Groups in the array are OR’d together; filters within a single group are AND’d. Each filter includes:
propertyNamerequired: the property to filter on.operatorrequired: the comparison to make. AcceptsEQ,NEQ,GT,GTE,LT,LTE,IN,NOT_IN,CONTAINS,NOT_CONTAINS,STARTS_WITH,ENDS_WITH,IS_KNOWN, orIS_UNKNOWN.value: the value to compare against, as a string. Used by every operator exceptIN,NOT_IN,IS_KNOWN, andIS_UNKNOWN.values: a non-empty array of string values, for theINandNOT_INoperators.source: the alias of the object the property belongs to. Defaults to the root object.
GT, GTE, LT, and LTE operators compare numeric values. To filter a date or datetime property, pass a millisecond timestamp as a string (e.g., String(date.getTime())). To find root records with no associated record of a joined type, filter the joined object’s hs_object_id with IS_UNKNOWN.object
Orders the rows:
byrequired: the key of a dimension, measure, or calculated measure.direction:"ASCENDING"or"DESCENDING". Default:"ASCENDING".
by value are then ordered by their dimension values in ascending order. Without sort, rows are ordered by their dimension values only.number
The maximum number of rows to return, as a positive integer. Requires
sort, so the rows returned are always the top results for that sort. Default: 100. Max: 1000. Larger values are treated as 1000.useRecordAggregation, keep the following in mind:
- Query limits: a query can include up to three joins, 10 dimensions, and 10 measures (including calculated measures). A query over these limits returns a
FAILEDerror. - Truncated results: results are capped rather than paginated. When
truncatedistrue, raise thelimit(up to 1,000), narrow your filters, or group by a broader dimension (e.g.,MONTHinstead ofDAY). - Timeouts: the hook waits up to 45 seconds for a query to complete, then returns a
TIMEOUTerror. A query that times out on HubSpot’s side returns aFAILEDerror. - Data freshness: results can come from a cache, so they may not reflect the latest changes to CRM data. Use
dataAgeto show when the data was last refreshed, andisStaleto flag older results. The hook has no refetch function. It runs a new query when its configuration changes or the component remounts, and a new query can still return cached results. - Stable configuration: because the hook runs a new query whenever its configuration changes, avoid values that change on every render, such as
Date.now(). Round dates to a fixed boundary, like the start of a day or month, instead. Changing the configuration also clears the currentrowsand setsisLoadingtotrueuntil the new results arrive. - Permissions: your app needs read scopes for the root object and every joined object. If a dimension, measure, or filter uses a sensitive data property and your app doesn’t have the matching sensitive data scope, the whole query fails. Results also respect the viewing user’s record and property permissions.
useDebounce
TheuseDebounce hook prevents a rapidly-changing value from propagating until it has stopped changing for a given number of milliseconds. Use it to avoid triggering expensive operations (like CRM search API requests) on every change, and instead wait until the user has paused.
null, arrays, and objects. Objects and arrays are compared by deep equality, so a new object reference with the same content won’t reset the debounce timer. Passing a non-serializable value (e.g., a function or a Date object) will result in incorrect deep equality comparisons.
The hook returns the debounced version of
value with the same type as the input. On the initial render, value is returned immediately without delay. The pending timer is cancelled when the component unmounts.
- Debouncing a search input
- Showing validation after pause
Pair
useDebounce with useCrmSearch (or any data-fetching hook) to avoid firing a request on every keystroke:CRM-specific hooks
These hooks are only available in CRM extension points (crm.record.tab, crm.record.sidebar, crm.preview, and helpdesk.sidebar). Ensure you’re on the latest version (v1) of the UI extensions SDK to use these hooks in your app:
useRecordPropertiesCurrent: fetch properties from the current CRM record.useRecordAssociationsCurrent: fetch records associated with the current CRM record.
useRecordPropertiesCurrent
As of version
v1 of the UI extensions SDK, the useRecordPropertiesCurrent hook has replaced the older useCrmProperties hook. Learn more in the UI extensions SDK versioning guide.useRecordPropertiesCurrent hook fetches properties from the current CRM record with optional formatting. It accepts an object that includes an array of properties to fetch, along with an optional object to format the returned data.
- Call
- Response
- Example usage
array
required
An array of property names to fetch.
object
Contains formatting options for the values returned from date, datetime, and currency properties.
- The
propertiesToFormatproperties can be set to"all", or an array of property names to format. Defaults to"all". - The
dateanddateTimeobjects can includeformatandrelativesubfields:format(string): a date or datetime string likeMM-DD-YYYYorMM-DD-YYYY:mm:ss. Supports standard date time string formats.relative(boolean): set totrueto display the amount of time passed since the returned value (e.g.,(1 day ago)or(1 hour ago)).
- The
currencyobject can includeaddSymbol(boolean), which sets whether the currency symbol should display with the number. Set totrueto display the currency symbol.
useCrmProperties
TheuseCrmProperties hook fetches properties from the current CRM record with optional formatting. It accepts an array of properties to fetch, along with an optional object to format the returned data.
- Call
- Response
- Example usage
'all' | array
required
Either
'all' or an array of property names to format.object
Contains formatting options for the values returned from date, datetime, and currency properties.
- The
dateanddateTimeobjects can includeformatandrelativesubfields:format(string): a date or datetime string likeMM-DD-YYYYorMM-DD-YYYY:mm:ss. Supports standard date time string formats.relative(boolean): set totrueto display the amount of time passed since the returned value (e.g.,(1 day ago)or(1 hour ago)).
- The
currencyobject can includeaddSymbol(boolean), which sets whether the currency symbol should display with the number. Set totrueto display the currency symbol.
useRecordAssociationsCurrent
TheuseRecordAssociationsCurrent hook fetches CRM records of a specific object type associated with the currently displaying record. It accepts an object containing the object type ID of the associated record, the properties to fetch from the associated object, an optional number of associated records to retrieve, and an optional object that formats returned property data.
This hook was introduced in the latest version (v1) of the UI Extensions SDK.
- Call
- Response
- Example usage
string
required
The object type ID to fetch associations from (e.g., ‘0-1’ for contacts).
properties:pageLength: an optional number of items per page (defaults to 10).
'all' | array
An optional array of properties to fetch from associated records.
integer
An optional number of records per page (defaults to 10).
object
Contains formatting options for the values returned from date, datetime, and currency properties.
- The
propertiesToFormatproperties can be set to"all", or an array of property names to format. Defaults to"all". - The
dateanddateTimeobjects can includeformatandrelativesubfields:format(string): a date or datetime string likeMM-DD-YYYYorMM-DD-YYYY:mm:ss. Supports standard date time string formats.relative(boolean): set totrueto display the amount of time passed since the returned value (e.g.,(1 day ago)or(1 hour ago)).
- The
currencyobject can includeaddSymbol(boolean), which sets whether the currency symbol should display with the number. Set totrueto display the currency symbol.
useAssociations
TheuseAssociations hook fetches CRM records of a specific object type associated with the currently displaying record. It accepts an object containing configuration details for the association fetch request, and an optional object that formats returned property data.
- Call
- Response
- Example usage
object
required
Configures the association data fetch request with:
toObjectType: the object type ID to fetch associations from (e.g., ‘0-1’ for contacts).properties: an optional array of properties to fetch from associated records.pageLength: an optional number of items per page (defaults to 10).
'all' | array
required
Either
'all' or an array of property names to format.object
Contains formatting options for the values returned from date, datetime, and currency properties.
- The
dateanddateTimeobjects can includeformatandrelativesubfields:format(string): a date or datetime string likeMM-DD-YYYYorMM-DD-YYYY:mm:ss. Supports standard date time string formats.relative(boolean): set totrueto display the amount of time passed since the returned value (e.g.,(1 day ago)or(1 hour ago)).
- The
currencyobject can includeaddSymbol(boolean), which sets whether the currency symbol should display with the number. Set totrueto display the currency symbol.