🐛 Set new Hubspot granular scopes (#2531)

* Hubspot Developer API Credentials: Use granular scopes as contacts scope is no longer available for new apps

*  Add new scopes to regular node

*  Small fix

*  Load contacts, companies and deals from API

Co-authored-by: that-one-tom <19203795+that-one-tom@users.noreply.github.com>
This commit is contained in:
Ricardo Espinoza 2021-12-10 14:28:59 -05:00 committed by GitHub
parent 8e2191b633
commit 1854d505b8
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
4 changed files with 54 additions and 30 deletions

View file

@ -4,7 +4,12 @@ import {
} from 'n8n-workflow';
const scopes = [
'contacts',
'crm.objects.contacts.read',
'crm.schemas.contacts.read',
'crm.objects.companies.read',
'crm.schemas.companies.read',
'crm.objects.deals.read',
'crm.schemas.deals.read',
];
export class HubspotDeveloperApi implements ICredentialType {

View file

@ -4,7 +4,16 @@ import {
} from 'n8n-workflow';
const scopes = [
'contacts',
'crm.schemas.deals.read',
'crm.objects.owners.read',
'crm.objects.contacts.write',
'crm.objects.companies.write',
'crm.objects.companies.read',
'crm.objects.deals.read',
'crm.schemas.contacts.read',
'crm.objects.deals.write',
'crm.objects.contacts.read',
'crm.schemas.companies.read',
'forms',
'tickets',
];

View file

@ -39,12 +39,16 @@ export async function hubspotApiRequest(this: IHookFunctions | IExecuteFunctions
return await this.helpers.request!(options);
} else if (authenticationMethod === 'developerApi') {
const credentials = await this.getCredentials('hubspotDeveloperApi');
if (endpoint.includes('webhooks')) {
const credentials = await this.getCredentials('hubspotDeveloperApi');
options.qs.hapikey = credentials!.apiKey as string;
return await this.helpers.request!(options);
} else {
return await this.helpers.requestOAuth2!.call(this, 'hubspotDeveloperApi', options, { tokenType: 'Bearer', includeCredentialsOnRefreshOnBody: true });
}
} else {
// @ts-ignore
return await this.helpers.requestOAuth2!.call(this, 'hubspotOAuth2Api', options, { tokenType: 'Bearer', includeCredentialsOnRefreshOnBody: true });
}
} catch (error) {

View file

@ -143,6 +143,9 @@ export class HubspotTrigger implements INodeType {
name: 'property',
type: 'options',
typeOptions: {
loadOptionsDependsOn: [
'contact.propertyChange',
],
loadOptionsMethod: 'getContactProperties',
},
displayOptions: {
@ -160,6 +163,9 @@ export class HubspotTrigger implements INodeType {
name: 'property',
type: 'options',
typeOptions: {
loadOptionsDependsOn: [
'company.propertyChange',
],
loadOptionsMethod: 'getCompanyProperties',
},
displayOptions: {
@ -177,6 +183,9 @@ export class HubspotTrigger implements INodeType {
name: 'property',
type: 'options',
typeOptions: {
loadOptionsDependsOn: [
'deal.propertyChange',
],
loadOptionsMethod: 'getDealProperties',
},
displayOptions: {
@ -220,51 +229,48 @@ export class HubspotTrigger implements INodeType {
// select them easily
async getContactProperties(this: ILoadOptionsFunctions): Promise<INodePropertyOptions[]> {
const returnData: INodePropertyOptions[] = [];
for (const field of contactFields) {
const endpoint = '/properties/v2/contacts/properties';
const properties = await hubspotApiRequest.call(this, 'GET', endpoint, {});
for (const property of properties) {
const propertyName = property.label;
const propertyId = property.name;
returnData.push({
name: capitalCase(field.label),
value: field.id,
name: propertyName,
value: propertyId,
});
}
returnData.sort((a, b) => {
if (a.name < b.name) { return -1; }
if (a.name > b.name) { return 1; }
return 0;
});
return returnData;
},
// Get all the available companies to display them to user so that he can
// select them easily
async getCompanyProperties(this: ILoadOptionsFunctions): Promise<INodePropertyOptions[]> {
const returnData: INodePropertyOptions[] = [];
for (const field of companyFields) {
const endpoint = '/properties/v2/companies/properties';
const properties = await hubspotApiRequest.call(this, 'GET', endpoint, {});
for (const property of properties) {
const propertyName = property.label;
const propertyId = property.name;
returnData.push({
name: capitalCase(field.label),
value: field.id,
name: propertyName,
value: propertyId,
});
}
returnData.sort((a, b) => {
if (a.name < b.name) { return -1; }
if (a.name > b.name) { return 1; }
return 0;
});
return returnData;
},
// Get all the available deals to display them to user so that he can
// select them easily
async getDealProperties(this: ILoadOptionsFunctions): Promise<INodePropertyOptions[]> {
const returnData: INodePropertyOptions[] = [];
for (const field of dealFields) {
const endpoint = '/properties/v2/deals/properties';
const properties = await hubspotApiRequest.call(this, 'GET', endpoint, {});
for (const property of properties) {
const propertyName = property.label;
const propertyId = property.name;
returnData.push({
name: capitalCase(field.label),
value: field.id,
name: propertyName,
value: propertyId,
});
}
returnData.sort((a, b) => {
if (a.name < b.name) { return -1; }
if (a.name > b.name) { return 1; }
return 0;
});
return returnData;
},
},