🔀 Merge master

This commit is contained in:
Iván Ovejero 2021-11-29 10:05:37 +01:00
commit 563a852f47
166 changed files with 46944 additions and 728 deletions

View file

@ -34,10 +34,10 @@ jobs:
-
name: Install dependencies
run: |
apt update -y
echo 'tzdata tzdata/Areas select Europe' | debconf-set-selections
echo 'tzdata tzdata/Zones/Europe select Paris' | debconf-set-selections
DEBIAN_FRONTEND="noninteractive" apt-get install -y graphicsmagick
sudo apt update -y
echo 'tzdata tzdata/Areas select Europe' | sudo debconf-set-selections
echo 'tzdata tzdata/Zones/Europe select Paris' | sudo debconf-set-selections
DEBIAN_FRONTEND="noninteractive" sudo apt-get install -y graphicsmagick
shell: bash
-
name: npm install and build
@ -75,19 +75,19 @@ jobs:
shell: bash
env:
N8N_ENCRYPTION_KEY: ${{secrets.ENCRYPTION_KEY}}
-
name: Export credentials
if: always()
run: n8n/packages/cli/bin/n8n export:credentials --output=test-workflows/credentials.json --all --pretty
shell: bash
env:
N8N_ENCRYPTION_KEY: ${{secrets.ENCRYPTION_KEY}}
-
name: Commit and push credential changes
if: always()
run: |
cd test-workflows
git config --global user.name 'n8n test bot'
git config --global user.email 'n8n-test-bot@users.noreply.github.com'
git commit -am "Automated credential update"
git push --force --quiet "https://janober:${{ secrets.TOKEN }}@github.com/n8n-io/test-workflows.git" main:main
# -
# name: Export credentials
# if: always()
# run: n8n/packages/cli/bin/n8n export:credentials --output=test-workflows/credentials.json --all --pretty
# shell: bash
# env:
# N8N_ENCRYPTION_KEY: ${{secrets.ENCRYPTION_KEY}}
# -
# name: Commit and push credential changes
# if: always()
# run: |
# cd test-workflows
# git config --global user.name 'n8n test bot'
# git config --global user.email 'n8n-test-bot@users.noreply.github.com'
# git commit -am "Automated credential update"
# git push --force --quiet "https://janober:${{ secrets.TOKEN }}@github.com/n8n-io/test-workflows.git" main:main

4
.gitignore vendored
View file

@ -5,7 +5,6 @@ tmp
dist
npm-debug.log*
lerna-debug.log
package-lock.json
yarn.lock
google-generated-credentials.json
_START_PACKAGE
@ -13,4 +12,5 @@ _START_PACKAGE
.vscode/*
!.vscode/extensions.json
.idea
nodelinter.config.json
nodelinter.config.json
packages/*/package-lock.json

44345
package-lock.json generated Normal file

File diff suppressed because it is too large Load diff

View file

@ -854,7 +854,8 @@ export class ExecuteBatch extends Command {
}
}
} catch (e) {
executionResult.error = 'Workflow failed to execute.';
// eslint-disable-next-line @typescript-eslint/restrict-template-expressions, @typescript-eslint/no-unsafe-member-access
executionResult.error = `Workflow failed to execute: ${e.message}`;
executionResult.executionStatus = 'error';
}
clearTimeout(timeoutTimer);

View file

@ -1,6 +1,6 @@
{
"name": "n8n",
"version": "0.150.0",
"version": "0.151.0",
"description": "n8n Workflow Automation Tool",
"license": "SEE LICENSE IN LICENSE.md",
"homepage": "https://n8n.io",
@ -111,10 +111,10 @@
"localtunnel": "^2.0.0",
"lodash.get": "^4.4.2",
"mysql2": "~2.3.0",
"n8n-core": "~0.94.0",
"n8n-editor-ui": "~0.117.0",
"n8n-nodes-base": "~0.147.0",
"n8n-workflow": "~0.77.0",
"n8n-core": "~0.95.0",
"n8n-editor-ui": "~0.118.0",
"n8n-nodes-base": "~0.148.0",
"n8n-workflow": "~0.78.0",
"oauth-1.0a": "^2.2.6",
"open": "^7.0.0",
"pg": "^8.3.0",
@ -123,7 +123,7 @@
"sqlite3": "^5.0.1",
"sse-channel": "^3.1.1",
"tslib": "1.14.1",
"typeorm": "^0.2.30",
"typeorm": "0.2.30",
"winston": "^3.3.3"
},
"jest": {

View file

@ -1611,8 +1611,7 @@ class App {
async (req: express.Request, res: express.Response): Promise<ICredentialsResponse[]> => {
const findQuery = {} as FindManyOptions;
if (req.query.filter) {
findQuery.where = JSON.parse(req.query.filter as string);
// @ts-ignore
findQuery.where = JSON.parse(req.query.filter as string) as IDataObject;
if (findQuery.where.id !== undefined) {
// No idea if multiple where parameters make db search
// slower but to be sure that that is not the case we

View file

@ -1,6 +1,6 @@
{
"name": "n8n-core",
"version": "0.94.0",
"version": "0.95.0",
"description": "Core functionality of n8n",
"license": "SEE LICENSE IN LICENSE.md",
"homepage": "https://n8n.io",
@ -50,7 +50,7 @@
"form-data": "^4.0.0",
"lodash.get": "^4.4.2",
"mime-types": "^2.1.27",
"n8n-workflow": "~0.77.0",
"n8n-workflow": "~0.78.0",
"oauth-1.0a": "^2.2.6",
"p-cancelable": "^2.0.0",
"qs": "^6.10.1",

View file

@ -616,10 +616,7 @@ class NodeTypesClass implements INodeTypes {
name: 'dotNotation',
type: 'boolean',
default: true,
description: `By default does dot-notation get used in property names..<br />
This means that "a.b" will set the property "b" underneath "a" so { "a": { "b": value} }.<br />
If that is not intended this can be deactivated, it will then set { "a.b": value } instead.
`,
description: `<p>By default, dot-notation is used in property names. This means that "a.b" will set the property "b" underneath "a" so { "a": { "b": value} }.</p><p>If that is not intended this can be deactivated, it will then set { "a.b": value } instead.</p>`,
},
],
},

View file

@ -1,6 +1,6 @@
{
"name": "n8n-design-system",
"version": "0.7.0",
"version": "0.8.0",
"license": "SEE LICENSE IN LICENSE.md",
"homepage": "https://n8n.io",
"author": {

View file

@ -135,5 +135,9 @@ export default {
.tooltipPopper {
max-width: 400px;
li {
margin-left: var(--spacing-s);
}
}
</style>

View file

@ -1,6 +1,6 @@
{
"name": "n8n-editor-ui",
"version": "0.117.0",
"version": "0.118.0",
"description": "Workflow Editor UI for n8n",
"license": "SEE LICENSE IN LICENSE.md",
"homepage": "https://n8n.io",
@ -26,7 +26,7 @@
},
"dependencies": {
"@fontsource/open-sans": "^4.5.0",
"n8n-design-system": "~0.7.0",
"n8n-design-system": "~0.8.0",
"timeago.js": "^4.0.2",
"v-click-outside": "^3.1.2",
"vue-fragment": "^1.5.2",
@ -74,7 +74,7 @@
"lodash.debounce": "^4.0.8",
"lodash.get": "^4.4.2",
"lodash.set": "^4.3.2",
"n8n-workflow": "~0.77.0",
"n8n-workflow": "~0.78.0",
"normalize-wheel": "^1.0.1",
"prismjs": "^1.17.1",
"quill": "^2.0.0-dev.3",

View file

@ -26,6 +26,13 @@
<font-awesome-icon icon="sync-alt" spin />
</div>
<div class="node-trigger-tooltip__wrapper">
<n8n-tooltip placement="top" :manual="true" :value="showTriggerNodeTooltip" popper-class="node-trigger-tooltip__wrapper--item">
<div slot="content" v-text="getTriggerNodeTooltip"></div>
<span />
</n8n-tooltip>
</div>
<NodeIcon class="node-icon" :nodeType="nodeType" :size="40" :shrink="false" :disabled="this.data.disabled"/>
</div>
@ -110,11 +117,41 @@ export default mixins(externalHooks, nodeBase, nodeHelpers, renderText, workflow
return workflowResultDataNode.length;
},
canvasOffsetPosition() {
return this.$store.getters.getNodeViewOffsetPosition;
},
getTriggerNodeTooltip (): string | undefined {
if (this.nodeType !== null && this.nodeType.hasOwnProperty('eventTriggerDescription')) {
return this.nodeType.eventTriggerDescription;
} else {
return `Waiting for you to create an event in ${this.nodeType && this.nodeType.displayName.replace(/Trigger/, "")}`;
}
},
isExecuting (): boolean {
return this.$store.getters.executingNode === this.data.name;
},
isSingleActiveTriggerNode (): boolean {
const nodes = this.$store.getters.workflowTriggerNodes.filter((node: INodeUi) => {
const nodeType = this.$store.getters.nodeType(node.type) as INodeTypeDescription | null;
return nodeType && nodeType.eventTriggerDescription !== '' && !node.disabled;
});
return nodes.length === 1;
},
isTriggerNode (): boolean {
return !!(this.nodeType && this.nodeType.group.includes('trigger'));
},
isTriggerNodeTooltipEmpty () : boolean {
return this.nodeType !== null ? this.nodeType.eventTriggerDescription === '' : false;
},
isNodeDisabled (): boolean | undefined {
return this.node && this.node.disabled;
},
nodeType (): INodeTypeDescription | null {
return this.$store.getters.nodeType(this.data.type);
return this.data && this.$store.getters.nodeType(this.data.type);
},
node (): INodeUi | undefined { // same as this.data but reactive..
return this.$store.getters.nodesByName[this.name] as INodeUi | undefined;
},
nodeClass (): object {
return {
@ -140,9 +177,7 @@ export default mixins(externalHooks, nodeBase, nodeHelpers, renderText, workflow
}
},
position (): XYPosition {
const node = this.$store.getters.nodesByName[this.name] as INodeUi; // position responsive to store changes
return node.position;
return this.node ? this.node.position : [0, 0];
},
showDisabledLinethrough(): boolean {
return !!(this.data.disabled && this.nodeType && this.nodeType.inputs.length === 1 && this.nodeType.outputs.length === 1);
@ -236,13 +271,33 @@ export default mixins(externalHooks, nodeBase, nodeHelpers, renderText, workflow
shiftOutputCount (): boolean {
return !!(this.nodeType && this.nodeType.outputs.length > 2);
},
},
shouldShowTriggerTooltip () : boolean {
return !!this.node && this.workflowRunning && this.workflowDataItems === 0 && this.isTriggerNode && this.isSingleActiveTriggerNode && !this.isTriggerNodeTooltipEmpty && !this.isNodeDisabled && !this.hasIssues && !this.dragging;
},
},
watch: {
isActive(newValue, oldValue) {
if (!newValue && oldValue) {
this.setSubtitle();
}
},
canvasOffsetPosition() {
if (this.showTriggerNodeTooltip) {
this.showTriggerNodeTooltip = false;
setTimeout(() => {
this.showTriggerNodeTooltip = this.shouldShowTriggerTooltip;
}, 200);
}
},
shouldShowTriggerTooltip(shouldShowTriggerTooltip) {
if (shouldShowTriggerTooltip) {
setTimeout(() => {
this.showTriggerNodeTooltip = this.shouldShowTriggerTooltip;
}, 2500);
} else {
this.showTriggerNodeTooltip = false;
}
},
nodeRunData(newValue) {
this.$emit('run', {name: this.data.name, data: newValue, waiting: !!this.waiting});
},
@ -257,6 +312,8 @@ export default mixins(externalHooks, nodeBase, nodeHelpers, renderText, workflow
return {
isTouchActive: false,
nodeSubtitle: '',
showTriggerNodeTooltip: false,
dragging: false,
};
},
methods: {
@ -517,7 +574,6 @@ export default mixins(externalHooks, nodeBase, nodeHelpers, renderText, workflow
border-color: var(--color-success-light);
}
}
</style>
<style lang="scss">
@ -526,6 +582,20 @@ export default mixins(externalHooks, nodeBase, nodeHelpers, renderText, workflow
z-index: 2;
}
.node-trigger-tooltip {
&__wrapper {
top: -22px;
left: 50px;
position: relative;
&--item {
max-width: 160px;
position: fixed;
z-index: 0!important;
}
}
}
/** connector */
.jtk-connector {
z-index: 3;

View file

@ -74,7 +74,7 @@ export const nodeBase = mixins(
type: inputName,
index,
},
enabled: !this.isReadOnly,
enabled: !this.isReadOnly && nodeTypeData.inputs.length > 1, // only enabled for nodes with multiple inputs.. otherwise attachment handled by connectionDrag event in NodeView
dragAllowedWhenFull: true,
dropOptions: {
tolerance: 'touch',
@ -170,6 +170,8 @@ export const nodeBase = mixins(
// Do not allow to move nodes in readOnly mode
return false;
}
// @ts-ignore
this.dragging = true;
if (params.e && !this.$store.getters.isNodeSelected(this.data.name)) {
// Only the node which gets dragged directly gets an event, for all others it is
@ -183,6 +185,8 @@ export const nodeBase = mixins(
return true;
},
stop: (params: { e: MouseEvent }) => {
// @ts-ignore
this.dragging = false;
if (this.$store.getters.isActionActive('dragActive')) {
const moveNodes = this.$store.getters.getSelectedNodes.slice();
const selectedNodeNames = moveNodes.map((node: INodeUi) => node.name);

View file

@ -676,12 +676,12 @@
const diffX = paintInfo.endStubX - paintInfo.startStubX;
const diffY = paintInfo.endStubY - paintInfo.startStubY;
const direction = diffY >= 0 ? 1 : -1; // vertical direction of loop, above or below source
const direction = -1; // vertical direction of loop, always below source
var midx = paintInfo.startStubX + ((paintInfo.endStubX - paintInfo.startStubX) * midpoint),
midy;
if (diffX < (-1 * loopbackMinimum)) {
if (diffY >= 0 || diffX < (-1 * loopbackMinimum)) {
// loop backward behavior
midy = paintInfo.startStubY - (diffX < 0 ? direction * loopbackVerticalLength : 0);
} else {

View file

@ -753,6 +753,11 @@ export const store = new Vuex.Store({
return state.activeWorkflows;
},
workflowTriggerNodes: (state, getters) => {
return state.workflow.nodes.filter(node => {
return getters.nodeType(node.type).group.includes('trigger');
});
},
// Node-Index
getNodeIndex: (state) => (nodeName: string): number => {
return state.nodeIndex.indexOf(nodeName);

View file

@ -1624,7 +1624,7 @@ export default mixins(
);
const nodes = [...document.querySelectorAll('.node-default')];
const onMouseMove = (e: MouseEvent) => {
const onMouseMove = (e: MouseEvent | TouchEvent) => {
if (!connection) {
return;
}
@ -1639,7 +1639,8 @@ export default mixins(
const inputMargin = 24;
const intersecting = nodes.find((element: Element) => {
const {top, left, right, bottom} = element.getBoundingClientRect();
if (top <= e.pageY && bottom >= e.pageY && (left - inputMargin) <= e.pageX && right >= e.pageX) {
const [x, y] = CanvasHelpers.getMousePosition(e);
if (top <= y && bottom >= y && (left - inputMargin) <= x && right >= x) {
const nodeName = (element as HTMLElement).dataset['name'] as string;
const node = this.$store.getters.getNodeByName(nodeName) as INodeUi | null;
if (node) {
@ -1664,7 +1665,7 @@ export default mixins(
}
};
const onMouseUp = (e: MouseEvent) => {
const onMouseUp = (e: MouseEvent | TouchEvent) => {
this.pullConnActive = false;
this.newNodeInsertPosition = this.getMousePositionWithinNodeView(e);
CanvasHelpers.resetConnectionAfterPull(connection);
@ -1673,7 +1674,9 @@ export default mixins(
};
window.addEventListener('mousemove', onMouseMove);
window.addEventListener('touchmove', onMouseMove);
window.addEventListener('mouseup', onMouseUp);
window.addEventListener('touchend', onMouseMove);
} catch (e) {
console.error(e); // eslint-disable-line no-console
}

View file

@ -52,7 +52,7 @@ export const CONNECTOR_FLOWCHART_TYPE = ['N8nCustom', {
stub: JSPLUMB_FLOWCHART_STUB + 10,
targetGap: 4,
alwaysRespectStubs: false,
loopbackVerticalLength: NODE_SIZE, // height of vertical segment when looping
loopbackVerticalLength: NODE_SIZE + GRID_SIZE, // height of vertical segment when looping
loopbackMinimum: LOOPBACK_MINIMUM, // minimum length before flowchart loops around
getEndpointOffset(endpoint: Endpoint) {
const indexOffset = 10; // stub offset between different endpoints of same node

View file

@ -1,6 +1,6 @@
{
"name": "n8n-node-dev",
"version": "0.34.0",
"version": "0.35.0",
"description": "CLI to simplify n8n credentials/node development",
"license": "SEE LICENSE IN LICENSE.md",
"homepage": "https://n8n.io",
@ -60,8 +60,8 @@
"change-case": "^4.1.1",
"copyfiles": "^2.1.1",
"inquirer": "^7.0.1",
"n8n-core": "~0.94.0",
"n8n-workflow": "~0.77.0",
"n8n-core": "~0.95.0",
"n8n-workflow": "~0.78.0",
"oauth-1.0a": "^2.2.6",
"replace-in-file": "^6.0.0",
"request": "^2.88.2",

View file

@ -0,0 +1,18 @@
import {
ICredentialType,
INodeProperties,
} from 'n8n-workflow';
export class DhlApi implements ICredentialType {
name = 'dhlApi';
displayName = 'DHL API';
documentationUrl = 'dhl';
properties: INodeProperties[] = [
{
displayName: 'API Key',
name: 'apiKey',
type: 'string',
default: '',
},
];
}

View file

@ -0,0 +1,28 @@
import {
ICredentialType,
INodeProperties,
} from 'n8n-workflow';
export class GrafanaApi implements ICredentialType {
name = 'grafanaApi';
displayName = 'Grafana API';
documentationUrl = 'grafana';
properties: INodeProperties[] = [
{
displayName: 'API Key',
name: 'apiKey',
type: 'string',
default: '',
required: true,
},
{
displayName: 'Base URL',
name: 'baseUrl',
type: 'string',
default: '',
description: 'Base URL of your Grafana instance',
placeholder: 'e.g. https://n8n.grafana.net/',
required: true,
},
];
}

View file

@ -63,8 +63,7 @@ export class Snowflake implements ICredentialType {
name: 'clientSessionKeepAlive',
type: 'boolean',
default: false,
description: `By default, client connections typically time out approximately 3-4 hours after the most recent query was executed.<br>
If the parameter clientSessionKeepAlive is set to true, the clients connection to the server will be kept alive indefinitely, even if no queries are executed.`,
description: `By default, client connections typically time out approximately 3-4 hours after the most recent query was executed. If the parameter clientSessionKeepAlive is set to true, the clients connection to the server will be kept alive indefinitely, even if no queries are executed.`,
},
];
}

View file

@ -13,13 +13,15 @@ export class SurveyMonkeyApi implements ICredentialType {
name: 'accessToken',
type: 'string',
default: '',
description: `The access token must have the following scopes:</br />
- Create/modify webhooks</br />
- View webhooks</br />
- View surveys</br />
- View collectors</br />
- View responses<br />
- View response details`,
description: `The access token must have the following scopes:
<ul>
<li>Create/modify webhooks</li>
<li>View webhooks</li>
<li>View surveys</li>
<li>View collectors</li>
<li>View responses</li>
<li>View response details</li>
</ul>`,
},
{
displayName: 'Client ID',

View file

@ -32,9 +32,7 @@ export class WooCommerceApi implements ICredentialType {
name: 'includeCredentialsInQuery',
type: 'boolean',
default: false,
description: `Occasionally, some servers may not parse the Authorization header correctly</br>
(if you see a Consumer key is missing error when authenticating over SSL, you have a server issue).</br>
In this case, you may provide the consumer key/secret as query string parameters instead.`,
description: `Occasionally, some servers may not parse the Authorization header correctly (if you see a “Consumer key is missing” error when authenticating over SSL, you have a server issue). In this case, you may provide the consumer key/secret as query string parameters instead.`,
},
];
}

View file

@ -117,7 +117,7 @@ export class AcuitySchedulingTrigger implements INodeType {
name: 'resolveData',
type: 'boolean',
default: true,
description: 'By default does the webhook-data only contain the ID of the object.<br />If this option gets activated, it will resolve the data automatically.',
description: 'By default does the webhook-data only contain the ID of the object. If this option gets activated, it will resolve the data automatically.',
},
],
};

View file

@ -107,8 +107,7 @@ export const listEntryFields = [
name: 'creator_id',
type: 'string',
default: '',
description: `The id of a Person resource who should be recorded as adding the entry to the list. <br/>
Must be a person who can access Affinity. If not provided the creator defaults to the owner of the API key.`,
description: `The id of a Person resource who should be recorded as adding the entry to the list. Must be a person who can access Affinity. If not provided the creator defaults to the owner of the API key.`,
},
],
},

View file

@ -61,9 +61,7 @@ export class AirtableTrigger implements INodeType {
name: 'triggerField',
type: 'string',
default: '',
description: `A Created Time or Last Modified Time field that will be used to sort records. <br>
If you do not have a Created Time or Last Modified Time field in your schema, please create one,<br>
because without this field trigger will not work correctly.`,
description: `A Created Time or Last Modified Time field that will be used to sort records. If you do not have a Created Time or Last Modified Time field in your schema, please create one, because without this field trigger will not work correctly.`,
required: true,
},
{
@ -100,9 +98,7 @@ export class AirtableTrigger implements INodeType {
name: 'fields',
type: 'string',
default: '',
description: `Fields to be included in the response.<br>
Multiple ones can be set separated by comma. Example: name,id.<br>
By default just the trigger field will be included.`,
description: `Fields to be included in the response. Multiple ones can be set separated by comma. Example: <code>name, id</code>. By default just the trigger field will be included.`,
},
{
displayName: 'Formula',

View file

@ -217,7 +217,7 @@ export const contactFields = [
name: 'notify',
type: 'boolean',
default: true,
description: `By default Autopilot notifies registered REST hook endpoints for contact_added/contact_updated events when</br> a new contact is added or an existing contact is updated via API. Disable to skip notifications.`,
description: `By default Autopilot notifies registered REST hook endpoints for contact_added/contact_updated events when a new contact is added or an existing contact is updated via API. Disable to skip notifications.`,
},
{
displayName: 'Number of Employees',

View file

@ -172,7 +172,7 @@ export const itemFields = [
{
displayName: 'Expression Attribute Values',
name: 'eavUi',
description: 'Substitution tokens for attribute names in an expression.<br>Only needed when the parameter "condition expression" is set',
description: 'Substitution tokens for attribute names in an expression. Only needed when the parameter "condition expression" is set',
placeholder: 'Add Attribute Value',
type: 'fixedCollection',
default: '',
@ -350,7 +350,7 @@ export const itemFields = [
],
},
],
description: 'Item\'s primary key. For example, with a simple primary key, you only need to provide a value for the partition key.<br>For a composite primary key, you must provide values for both the partition key and the sort key',
description: 'Item\'s primary key. For example, with a simple primary key, you only need to provide a value for the partition key. For a composite primary key, you must provide values for both the partition key and the sort key',
},
{
displayName: 'Simple',
@ -430,7 +430,7 @@ export const itemFields = [
{
displayName: 'Expression Attribute Values',
name: 'expressionAttributeUi',
description: 'Substitution tokens for attribute names in an expression.<br>Only needed when the parameter "condition expression" is set',
description: 'Substitution tokens for attribute names in an expression. Only needed when the parameter "condition expression" is set',
placeholder: 'Add Attribute Value',
type: 'fixedCollection',
default: '',
@ -593,7 +593,7 @@ export const itemFields = [
],
},
],
description: 'Item\'s primary key. For example, with a simple primary key, you only need to provide a value for the partition key.<br>For a composite primary key, you must provide values for both the partition key and the sort key',
description: 'Item\'s primary key. For example, with a simple primary key, you only need to provide a value for the partition key. For a composite primary key, you must provide values for both the partition key and the sort key',
},
{
displayName: 'Additional Fields',
@ -708,7 +708,7 @@ export const itemFields = [
{
displayName: 'Key Condition Expression',
name: 'keyConditionExpression',
description: 'Condition to determine the items to be retrieved. The condition must perform an equality test<br>on a single partition key value, in this format: <code>partitionKeyName = :partitionkeyval</code>',
description: 'Condition to determine the items to be retrieved. The condition must perform an equality test on a single partition key value, in this format: <code>partitionKeyName = :partitionkeyval</code>',
placeholder: 'id = :id',
default: '',
type: 'string',
@ -901,7 +901,7 @@ export const itemFields = [
{
displayName: 'Index Name',
name: 'indexName',
description: 'Name of the index to query. It can be any <br>secondary local or global index on the table.',
description: 'Name of the index to query. It can be any secondary local or global index on the table.',
type: 'string',
default: '',
},
@ -910,7 +910,7 @@ export const itemFields = [
name: 'projectionExpression',
type: 'string',
default: '',
description: 'Text that identifies one or more attributes to retrieve from the table.<br>These attributes can include scalars, sets, or elements of a JSON document. The attributes<br>in the expression must be separated by commas',
description: 'Text that identifies one or more attributes to retrieve from the table. These attributes can include scalars, sets, or elements of a JSON document. The attributes in the expression must be separated by commas',
},
{
displayName: 'Filter Expression',
@ -924,7 +924,7 @@ export const itemFields = [
},
},
default: '',
description: 'Text that contains conditions that DynamoDB applies after the Query operation,<br>but before the data is returned. Items that do not satisfy the FilterExpression criteria</br>are not returned',
description: 'Text that contains conditions that DynamoDB applies after the Query operation, but before the data is returned. Items that do not satisfy the FilterExpression criteria are not returned',
},
{
displayName: 'Expression Attribute Names',

View file

@ -203,10 +203,7 @@ export class AwsTranscribe implements INodeType {
name: 'channelIdentification',
type: 'boolean',
default: false,
description: `Instructs Amazon Transcribe to process each audiochannel separately</br>
and then merge the transcription output of each channel into a single transcription.
You can't set both Max Speaker Labels and Channel Identification in the same request.
If you set both, your request returns a BadRequestException.`,
description: `Instructs Amazon Transcribe to process each audiochannel separately and then merge the transcription output of each channel into a single transcription. You can't set both Max Speaker Labels and Channel Identification in the same request. If you set both, your request returns a BadRequestException.`,
},
{
displayName: 'Max Alternatives',
@ -228,9 +225,7 @@ export class AwsTranscribe implements INodeType {
minValue: 2,
maxValue: 10,
},
description: `The maximum number of speakers to identify in the input audio.</br>
If there are more speakers in the audio than this number, multiple speakers are</br>
identified as a single speaker.`,
description: `The maximum number of speakers to identify in the input audio. If there are more speakers in the audio than this number, multiple speakers are identified as a single speaker.`,
},
{
displayName: 'Vocabulary Name',
@ -244,8 +239,7 @@ export class AwsTranscribe implements INodeType {
name: 'vocabularyFilterName',
type: 'string',
default: '',
description: `The name of the vocabulary filter to use when transcribing the audio.</br>
The filter that you specify must have the same language code as the transcription job.`,
description: `The name of the vocabulary filter to use when transcribing the audio. The filter that you specify must have the same language code as the transcription job.`,
},
{
displayName: 'Vocabulary Filter Method',
@ -267,9 +261,7 @@ export class AwsTranscribe implements INodeType {
],
default: 'remove',
description: `Set to mask to remove filtered text from the transcript and replace it with three asterisks ("***") as placeholder text.</br>
Set to remove to remove filtered text from the transcript without using placeholder text. Set to tag to mark the word in the transcription</br>
output that matches the vocabulary filter. When you set the filter method to tag, the words matching your vocabulary filter are not masked or removed.`,
description: `<p>Set to mask to remove filtered text from the transcript and replace it with three asterisks ("***") as placeholder text.</p><p>Set to remove to remove filtered text from the transcript without using placeholder text. Set to tag to mark the word in the transcription output that matches the vocabulary filter. When you set the filter method to tag, the words matching your vocabulary filter are not masked or removed.</p>`,
},
],
},
@ -288,7 +280,7 @@ export class AwsTranscribe implements INodeType {
],
},
},
description: 'By default, the response only contains metadata about the transcript.<br>Enable this option to retrieve the transcript instead.',
description: 'By default, the response only contains metadata about the transcript. Enable this option to retrieve the transcript instead.',
},
{
displayName: 'Simple',
@ -444,7 +436,7 @@ export class AwsTranscribe implements INodeType {
ShowAlternatives: true,
MaxAlternatives: options.maxAlternatives,
});
}
}
if (options.maxSpeakerLabels) {
Object.assign(body.Settings, {

View file

@ -86,9 +86,7 @@ export const imageFields = [
name: 'waitForImage',
type: 'boolean',
default: false,
description: `Wait for the image to be proccesed before returning.<br />
If after three tries the images is not ready, an error will be thrown.<br />
Number of tries can be increased by setting "Wait Max Tries".`,
description: `Wait for the image to be proccesed before returning. If after three tries the images is not ready, an error will be thrown. Number of tries can be increased by setting "Wait Max Tries".`,
},
{
displayName: 'Wait Max Tries',

View file

@ -144,7 +144,7 @@ export const groupFields = [
name: 'accessAll',
type: 'boolean',
default: false,
description: 'Allow this group to access all collections within the organization, instead of only its associated collections.<br>If set to true, this option overrides any collection assignments.',
description: 'Allow this group to access all collections within the organization, instead of only its associated collections. If set to true, this option overrides any collection assignments.',
displayOptions: {
show: {
resource: [
@ -208,7 +208,7 @@ export const groupFields = [
name: 'accessAll',
type: 'boolean',
default: false,
description: 'Allow this group to access all collections within the organization, instead of only its associated collections.<br>If set to true, this option overrides any collection assignments.',
description: 'Allow this group to access all collections within the organization, instead of only its associated collections. If set to true, this option overrides any collection assignments.',
},
{
displayName: 'Collections',

View file

@ -327,8 +327,7 @@ export const fileFields = [
name: 'contet_types',
type: 'string',
default: '',
description: `Limits search results to items with the given content types.</br>
Content types are defined as a comma separated lists of Box recognized content types.`,
description: `Limits search results to items with the given content types. Content types are defined as a comma separated lists of Box recognized content types.`,
},
{
displayName: 'Created At Range',
@ -397,8 +396,7 @@ export const fileFields = [
name: 'ancestor_folder_ids',
type: 'string',
default: '',
description: `Limits search results to items within the given list of folders.</br>
Folders are defined as a comma separated lists of folder IDs.`,
description: `Limits search results to items within the given list of folders. Folders are defined as a comma separated lists of folder IDs.`,
},
{
displayName: 'Scope',
@ -423,8 +421,7 @@ export const fileFields = [
type: 'string',
default: '',
placeholder: '1000000,5000000',
description: `Limits search results to items within a given file size range.</br>
File size ranges are defined as comma separated byte sizes.`,
description: `Limits search results to items within a given file size range. File size ranges are defined as comma separated byte sizes.`,
},
{
displayName: 'Sort',
@ -495,8 +492,7 @@ export const fileFields = [
name: 'owner_user_ids',
type: 'string',
default: '',
description: `Limits search results to items owned by the given list of owners..</br>
Owners are defined as a comma separated list of user IDs.`,
description: `Limits search results to items owned by the given list of owners. Owners are defined as a comma separated list of user IDs.`,
},
],
},
@ -710,8 +706,7 @@ export const fileFields = [
name: 'can_view_path',
type: 'boolean',
default: false,
description: `Whether the invited users can see the entire parent path to the associated folder.</br>
The user will not gain privileges in any parent folder and therefore cannot see content the user is not collaborated on.`,
description: `Whether the invited users can see the entire parent path to the associated folder. The user will not gain privileges in any parent folder and therefore cannot see content the user is not collaborated on.`,
},
{
displayName: 'Expires At',

View file

@ -279,8 +279,7 @@ export const folderFields = [
name: 'contet_types',
type: 'string',
default: '',
description: `Limits search results to items with the given content types.</br>
Content types are defined as a comma separated lists of Box recognized content types.`,
description: `Limits search results to items with the given content types. Content types are defined as a comma separated lists of Box recognized content types.`,
},
{
displayName: 'Created At Range',
@ -349,8 +348,7 @@ export const folderFields = [
name: 'ancestor_folder_ids',
type: 'string',
default: '',
description: `Limits search results to items within the given list of folders.</br>
Folders are defined as a comma separated lists of folder IDs.`,
description: `Limits search results to items within the given list of folders. Folders are defined as a comma separated lists of folder IDs.`,
},
{
displayName: 'Scope',
@ -375,8 +373,7 @@ export const folderFields = [
type: 'string',
default: '',
placeholder: '1000000,5000000',
description: `Limits search results to items within a given file size range.</br>
File size ranges are defined as comma separated byte sizes.`,
description: `Limits search results to items within a given file size range. File size ranges are defined as comma separated byte sizes.`,
},
{
displayName: 'Sort',
@ -447,8 +444,7 @@ export const folderFields = [
name: 'owner_user_ids',
type: 'string',
default: '',
description: `Limits search results to items owned by the given list of owners..</br>
Owners are defined as a comma separated list of user IDs.`,
description: `Limits search results to items owned by the given list of owners. Owners are defined as a comma separated list of user IDs.`,
},
],
},
@ -662,8 +658,7 @@ export const folderFields = [
name: 'can_view_path',
type: 'boolean',
default: false,
description: `Whether the invited users can see the entire parent path to the associated folder.</br>
The user will not gain privileges in any parent folder and therefore cannot see content the user is not collaborated on.`,
description: `Whether the invited users can see the entire parent path to the associated folder. The user will not gain privileges in any parent folder and therefore cannot see content the user is not collaborated on.`,
},
{
displayName: 'Expires At',

View file

@ -492,8 +492,7 @@ export const objectFields = [
name: 'sort_field',
type: 'string',
default: '',
description: `Specify the field to use for sorting. Either use a fielddefined for</br>
the current typeor use _random_sorting to get the entries in a random order`,
description: `Specify the field to use for sorting. Either use a fielddefined for the current typeor use <code>_random_sorting</code> to get the entries in a random order`,
},
{
displayName: 'Descending',

View file

@ -211,18 +211,14 @@ export const pipelineFields = [
name: 'branch',
type: 'string',
default: '',
description: `The branch where the pipeline ran.<br/>
The HEAD commit on this branch was used for the pipeline.<br/>
Note that branch and tag are mutually exclusive.`,
description: `The branch where the pipeline ran. The HEAD commit on this branch was used for the pipeline. Note that branch and tag are mutually exclusive.`,
},
{
displayName: 'Tag',
name: 'tag',
type: 'string',
default: '',
description: `The tag used by the pipeline.<br/>
The commit that this tag points to was used for the pipeline.<br/>
Note that branch and tag are mutually exclusive`,
description: `The tag used by the pipeline. The commit that this tag points to was used for the pipeline. Note that branch and tag are mutually exclusive`,
},
],
},

View file

@ -848,8 +848,7 @@ export const meetingFields = [
name: 'password',
type: 'string',
default: '',
description: `Meeting password. Must conform to the site's password complexity settings.</br>
If not specified, a random password conforming to the site's password rules will be generated automatically`,
description: `Meeting password. Must conform to the site's password complexity settings. If not specified, a random password conforming to the site's password rules will be generated automatically`,
},
{
displayName: 'Public Meeting',

View file

@ -254,7 +254,7 @@ export const taskFields = [
alwaysOpenEditWindow: true,
},
default: '',
description: 'Custom fields to set as JSON in the format:<br />[{"id": "", "value": ""}]',
description: 'Custom fields to set as JSON in the format: <code>[ {"id": "", "value": ""} ]</code>',
},
{
displayName: 'Content',

View file

@ -237,9 +237,7 @@ export const tableFields = [
name: 'useColumnNames',
type: 'boolean',
default: false,
description: `Use column names instead of column IDs in the returned output.</br>
This is generally discouraged as it is fragile. If columns are renamed,</br>
code using original names may throw errors.`,
description: `Use column names instead of column IDs in the returned output. This is generally discouraged as it is fragile. If columns are renamed, code using original names may throw errors.`,
},
{
displayName: 'ValueFormat',
@ -378,9 +376,7 @@ export const tableFields = [
alwaysOpenEditWindow: true,
},
default: '',
description: `Query used to filter returned rows, specified as <column_id_or_name>:<value>. <br/>
If you'd like to use a column name instead of an ID, you must quote it (e.g., "My Column":123).<br/>
Also note that value is a JSON value; if you'd like to use a string, you must surround it in quotes (e.g., "groceries").`,
description: `Query used to filter returned rows, specified as &lt;column_id_or_name&gt;:&lt;value&gt;. If you'd like to use a column name instead of an ID, you must quote it (e.g., "My Column":123). Also note that value is a JSON value; if you'd like to use a string, you must surround it in quotes (e.g., "groceries").`,
},
{
displayName: 'RAW Data',
@ -404,17 +400,14 @@ export const tableFields = [
value: 'natural',
},
],
description: `Specifies the sort order of the rows returned.<br />
If left unspecified, rows are returned by creation time ascending.`,
description: `Specifies the sort order of the rows returned. If left unspecified, rows are returned by creation time ascending.`,
},
{
displayName: 'Use Column Names',
name: 'useColumnNames',
type: 'boolean',
default: false,
description: `Use column names instead of column IDs in the returned output.</br>
This is generally discouraged as it is fragile. If columns
are renamed, code using original names may throw errors.`,
description: `Use column names instead of column IDs in the returned output. This is generally discouraged as it is fragile. If columns are renamed, code using original names may throw errors.`,
},
{
displayName: 'ValueFormat',

View file

@ -277,18 +277,14 @@ export const viewFields = [
alwaysOpenEditWindow: true,
},
default: '',
description: `Query used to filter returned rows, specified as <column_id_or_name>:<value>. <br/>
If you'd like to use a column name instead of an ID, you must quote it (e.g., "My Column":123).<br/>
Also note that value is a JSON value; if you'd like to use a string, you must surround it in quotes (e.g., "groceries").`,
description: `Query used to filter returned rows, specified as &lt;column_id_or_name&gt;:&lt;value&gt;. If you'd like to use a column name instead of an ID, you must quote it (e.g., "My Column":123). Also note that value is a JSON value; if you'd like to use a string, you must surround it in quotes (e.g., "groceries").`,
},
{
displayName: 'Use Column Names',
name: 'useColumnNames',
type: 'boolean',
default: false,
description: `Use column names instead of column IDs in the returned output.</br>
This is generally discouraged as it is fragile. If columns are renamed,</br>
code using original names may throw errors.`,
description: `Use column names instead of column IDs in the returned output. This is generally discouraged as it is fragile. If columns are renamed, code using original names may throw errors.`,
},
{
displayName: 'ValueFormat',
@ -333,8 +329,7 @@ export const viewFields = [
value: 'natural',
},
],
description: `Specifies the sort order of the rows returned.<br />
If left unspecified, rows are returned by creation time ascending.`,
description: `Specifies the sort order of the rows returned. If left unspecified, rows are returned by creation time ascending.`,
},
],
},

View file

@ -229,11 +229,7 @@ export class CrateDb implements INodeType {
},
],
default: 'multiple',
description: [
'The way queries should be sent to database.',
'Can be used in conjunction with <b>Continue on Fail</b>.',
'See the docs for more examples',
].join('<br>'),
description: 'The way queries should be sent to database. Can be used in conjunction with <b>Continue on Fail</b>. See <a href="https://docs.n8n.io/nodes/n8n-nodes-base.crateDb/">the docs</a> for more examples.',
},
{
displayName: 'Query Parameters',

View file

@ -25,6 +25,7 @@ export class Cron implements INodeType {
group: ['trigger'],
version: 1,
description: 'Triggers the workflow at a specific time',
eventTriggerDescription: '',
defaults: {
name: 'Cron',
color: '#00FF00',

View file

@ -0,0 +1,162 @@
import {
IExecuteFunctions,
} from 'n8n-core';
import {
ICredentialDataDecryptedObject,
ICredentialsDecrypted,
ICredentialTestFunctions,
IDataObject,
INodeExecutionData,
INodeType,
INodeTypeDescription,
NodeCredentialTestResult,
} from 'n8n-workflow';
import {
dhlApiRequest,
validateCrendetials,
} from './GenericFunctions';
export class Dhl implements INodeType {
description: INodeTypeDescription = {
displayName: 'DHL',
name: 'dhl',
icon: 'file:dhl.svg',
group: ['input'],
version: 1,
subtitle: '={{$parameter["operation"] + ": " + $parameter["resource"]}}',
description: 'Consume DHL API',
defaults: {
name: 'DHL',
color: '#fecc00',
},
inputs: ['main'],
outputs: ['main'],
credentials: [
{
name: 'dhlApi',
required: true,
testedBy: 'dhlApiCredentialTest',
},
],
properties: [
{
displayName: 'Resource',
name: 'resource',
noDataExpression: true,
type: 'hidden',
options: [
{
name: 'Shipment',
value: 'shipment',
},
],
default: 'shipment',
},
{
displayName: 'Operation',
name: 'operation',
type: 'options',
noDataExpression: true,
displayOptions: {
show: {
resource: [
'shipment',
],
},
},
options: [
{
name: 'Get Tracking Details',
value: 'get',
},
],
default: 'get',
},
{
displayName: 'Tracking Number',
name: 'trackingNumber',
type: 'string',
required: true,
default: '',
},
{
displayName: 'Options',
name: 'options',
type: 'collection',
placeholder: 'Add Option',
default: {},
options: [
{
displayName: `Recipient's Postal Code`,
name: 'recipientPostalCode',
type: 'string',
default: '',
description: `DHL will return more detailed information on the shipment when you provide the Recipient's Postal Code - it acts as a verification step`,
},
],
},
],
};
methods = {
credentialTest: {
async dhlApiCredentialTest(this: ICredentialTestFunctions, credential: ICredentialsDecrypted): Promise<NodeCredentialTestResult> {
try {
await validateCrendetials.call(this, credential.data as ICredentialDataDecryptedObject);
} catch (error) {
if (error.statusCode === 401) {
return {
status: 'Error',
message: 'The API Key included in the request is invalid',
};
}
}
return {
status: 'OK',
message: 'Connection successful!',
};
},
},
};
async execute(this: IExecuteFunctions): Promise<INodeExecutionData[][]> {
const items = this.getInputData();
const returnData: IDataObject[] = [];
let qs: IDataObject = {};
let responseData;
const resource = this.getNodeParameter('resource', 0) as string;
const operation = this.getNodeParameter('operation', 0) as string;
for (let i = 0; i < items.length; i++) {
try {
if (resource === 'shipment') {
if (operation === 'get') {
const trackingNumber = this.getNodeParameter('trackingNumber', i) as string;
const options = this.getNodeParameter('options', i) as IDataObject;
qs = {
trackingNumber,
};
Object.assign(qs, options);
responseData = await dhlApiRequest.call(this, 'GET', `/track/shipments`, {}, qs);
returnData.push(...responseData.shipments);
}
}
} catch (error) {
if (this.continueOnFail()) {
returnData.push({ error: error.description });
continue;
}
throw error;
}
}
return [this.helpers.returnJsonArray(returnData)];
}
}

View file

@ -0,0 +1,65 @@
import {
OptionsWithUri,
} from 'request';
import {
IExecuteFunctions,
IExecuteSingleFunctions,
IHookFunctions,
ILoadOptionsFunctions,
} from 'n8n-core';
import {
ICredentialDataDecryptedObject,
ICredentialTestFunctions,
IDataObject,
NodeApiError,
} from 'n8n-workflow';
export async function dhlApiRequest(this: IHookFunctions | IExecuteFunctions | IExecuteSingleFunctions | ILoadOptionsFunctions, method: string, path: string, body: any = {}, qs: IDataObject = {}, uri?: string, option: IDataObject = {}): Promise<any> { // tslint:disable-line:no-any
const credentials = await this.getCredentials('dhlApi') as { apiKey: string };
let options: OptionsWithUri = {
headers: {
'DHL-API-Key': credentials.apiKey,
},
method,
qs,
body,
uri: uri || `https://api-eu.dhl.com${path}`,
json: true,
};
options = Object.assign({}, options, option);
if (Object.keys(options.body).length === 0) {
delete options.body;
}
try {
return await this.helpers.request!(options);
} catch (error) {
throw new NodeApiError(this.getNode(), error);
}
}
export async function validateCrendetials(this: ICredentialTestFunctions, decryptedCredentials: ICredentialDataDecryptedObject): Promise<any> { // tslint:disable-line:no-any
const credentials = decryptedCredentials;
const { apiKey } = credentials as {
apiKey: string,
};
const options: OptionsWithUri = {
headers: {
'DHL-API-Key': apiKey,
},
qs: {
trackingNumber: 123,
},
method: 'GET',
uri: `https://api-eu.dhl.com/track/shipments`,
json: true,
};
return this.helpers.request!(options);
}

View file

@ -0,0 +1,21 @@
<?xml version="1.0" encoding="utf-8"?>
<!-- Generator: Adobe Illustrator 24.2.1, SVG Export Plug-In . SVG Version: 6.00 Build 0) -->
<svg version="1.1" id="Layer_1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink" x="0px" y="0px"
viewBox="0 0 60 60" style="enable-background:new 0 0 60 60;" xml:space="preserve">
<style type="text/css">
.st0{fill:#FFCC00;}
.st1{fill:#D40511;}
</style>
<path class="st0" d="M56,60H4c-2.2,0-4-1.8-4-4V4c0-2.2,1.8-4,4-4h52c2.2,0,4,1.8,4,4v52C60,58.2,58.2,60,56,60z"/>
<g>
<g>
<g>
<path class="st1" d="M16.2,32.3H6v2h8.7L16.2,32.3z M18.9,28.6H6v2h11.4L18.9,28.6z M36.1,27.9c-0.5,0.7-1.3,1.8-1.8,2.5
c-0.3,0.3-0.7,1,0.8,1h7.8c0,0,1.3-1.8,2.4-3.2c1.5-2,0.1-6.2-5.2-6.2H19.2l-3.6,4.9h20C36.6,26.9,36.6,27.3,36.1,27.9z M6,38h6
l1.5-2H6V38z M40.2,38H54v-2H41.6L40.2,38z M47.1,28.6l-1.5,2H54v-2H47.1z M41.6,33.1h-8.9l-3.4,0c-1.5,0-1.1-0.6-0.8-1
c0.5-0.7,1.4-1.8,1.8-2.5c0.5-0.7,0.8-1-0.2-1h-9L14.2,38h17.7C37.1,38,40.3,34.8,41.6,33.1z M42.9,34.3H54v-2h-9.6L42.9,34.3z"
/>
</g>
</g>
</g>
</svg>

After

Width:  |  Height:  |  Size: 1.1 KiB

View file

@ -387,7 +387,6 @@ export class Discourse implements INodeType {
// if (simple === true) {
// const response = [];
// for (const key of Object.keys(responseData)) {
// console.log(key)
// for (const data of responseData[key]) {
// response.push(Object.assign(data, { __type: key }));
// }

View file

@ -621,7 +621,7 @@ export class Dropbox implements INodeType {
name: 'file_extensions',
type: 'string',
default: '',
description: 'Multiple can be set separated by comma. Example: jpg,pdf',
description: 'Multiple file extensions can be set separated by comma. Example: jpg,pdf',
},
{
displayName: 'Folder',

View file

@ -243,8 +243,7 @@ export class Dropcontact implements INodeType {
name: 'siren',
type: 'boolean',
default: false,
description: `Whether you want the <a href="https://en.wikipedia.org/wiki/SIREN_code" target="_blank">SIREN number</a>, NAF code, TVA number, company address and informations about the company leader.</br>
Only applies to french companies`,
description: `Whether you want the <a href="https://en.wikipedia.org/wiki/SIREN_code" target="_blank">SIREN number</a>, NAF code, TVA number, company address and informations about the company leader. Only applies to french companies`,
},
{
displayName: 'Language',

View file

@ -1109,6 +1109,7 @@ export class EditImage implements INodeType {
],
composite: [
'dataPropertyNameComposite',
'operator',
'positionX',
'positionY',
],

View file

@ -291,7 +291,7 @@ export const documentFields = [
{
displayName: 'Allow Partial Search Results',
name: 'allow_partial_search_results',
description: 'If true, return partial results if there are shard request timeouts or shard failures.<br>If false, returns an error with no partial results. Defaults to true',
description: '<p>If true, return partial results if there are shard request timeouts or shard failures.</p><p>If false, returns an error with no partial results. Defaults to true.</p>',
type: 'boolean',
default: true,
},
@ -379,7 +379,7 @@ export const documentFields = [
{
displayName: 'Pre-Filter Shard Size',
name: 'pre_filter_shard_size',
description: 'Define a threshold that enforces a pre-filter roundtrip to prefilter search shards based on query rewriting.<br>Only used if the number of shards the search request expands to exceeds the threshold',
description: 'Define a threshold that enforces a pre-filter roundtrip to prefilter search shards based on query rewriting. Only used if the number of shards the search request expands to exceeds the threshold',
type: 'number',
typeOptions: {
minValue: 1,

View file

@ -110,7 +110,7 @@ export const indexFields = [
{
displayName: 'Master Timeout',
name: 'master_timeout',
description: 'Period to wait for a connection to the master node. If no response is received before the timeout expires,<br>the request fails and returns an error. Defaults to <code>1m</code>. See the <a href="https://www.elastic.co/guide/en/elasticsearch/reference/current/common-options.html#time-units">Elasticsearch time units reference</a>',
description: 'Period to wait for a connection to the master node. If no response is received before the timeout expires, the request fails and returns an error. Defaults to <code>1m</code>. See the <a href="https://www.elastic.co/guide/en/elasticsearch/reference/current/common-options.html#time-units">Elasticsearch time units reference</a>',
type: 'string',
default: '1m',
},
@ -128,14 +128,14 @@ export const indexFields = [
{
displayName: 'Timeout',
name: 'timeout',
description: 'Period to wait for a response. If no response is received before the timeout expires, the request<br>fails and returns an error. Defaults to <code>30s</code>. See the <a href="https://www.elastic.co/guide/en/elasticsearch/reference/current/common-options.html#time-units">Elasticsearch time units reference</a>',
description: 'Period to wait for a response. If no response is received before the timeout expires, the request fails and returns an error. Defaults to <code>30s</code>. See the <a href="https://www.elastic.co/guide/en/elasticsearch/reference/current/common-options.html#time-units">Elasticsearch time units reference</a>',
type: 'string',
default: '30s',
},
{
displayName: 'Wait for Active Shards',
name: 'wait_for_active_shards',
description: 'The number of shard copies that must be active before proceeding with the operation. Set to <code>all</code><br>or any positive integer up to the total number of shards in the index. Default: 1, the primary shard',
description: 'The number of shard copies that must be active before proceeding with the operation. Set to <code>all</code> or any positive integer up to the total number of shards in the index. Default: 1, the primary shard',
type: 'string',
default: '1',
},
@ -269,7 +269,7 @@ export const indexFields = [
{
displayName: 'Master Timeout',
name: 'master_timeout',
description: 'Period to wait for a connection to the master node. If no response is received before the timeout expires,<br>the request fails and returns an error. Defaults to <code>1m</code>. See the <a href="https://www.elastic.co/guide/en/elasticsearch/reference/current/common-options.html#time-units">Elasticsearch time units reference</a>',
description: 'Period to wait for a connection to the master node. If no response is received before the timeout expires, the request fails and returns an error. Defaults to <code>1m</code>. See the <a href="https://www.elastic.co/guide/en/elasticsearch/reference/current/common-options.html#time-units">Elasticsearch time units reference</a>',
type: 'string',
default: '1m',
},

View file

@ -36,6 +36,7 @@ export class EmailReadImap implements INodeType {
group: ['trigger'],
version: 1,
description: 'Triggers the workflow when a new email is received',
eventTriggerDescription: 'Waiting for you to receive an email',
defaults: {
name: 'IMAP Email',
color: '#44AA22',
@ -84,7 +85,7 @@ export class EmailReadImap implements INodeType {
],
},
},
description: 'If attachments of emails should be downloaded.<br />Only set if needed as it increases processing.',
description: 'If attachments of emails should be downloaded. Only set if needed as it increases processing.',
},
{
displayName: 'Format',
@ -122,7 +123,7 @@ export class EmailReadImap implements INodeType {
],
},
},
description: 'Prefix for name of the binary property to which to write the attachments. An index starting with 0 will be added.<br />So if name is "attachment_" the first attachment is saved to "attachment_0"',
description: 'Prefix for name of the binary property to which to write the attachments. An index starting with 0 will be added. So if name is "attachment_" the first attachment is saved to "attachment_0"',
},
{
displayName: 'Property Prefix Name',
@ -139,7 +140,7 @@ export class EmailReadImap implements INodeType {
],
},
},
description: 'Prefix for name of the binary property to which to write the attachments. An index starting with 0 will be added.<br />So if name is "attachment_" the first attachment is saved to "attachment_0"',
description: 'Prefix for name of the binary property to which to write the attachments. An index starting with 0 will be added. So if name is "attachment_" the first attachment is saved to "attachment_0"',
},
{
displayName: 'Options',

View file

@ -103,7 +103,7 @@ export class EmailSend implements INodeType {
name: 'attachments',
type: 'string',
default: '',
description: 'Name of the binary properties that contain data to add to email as attachment.<br />Multiple ones can be comma separated.',
description: 'Name of the binary properties that contain data to add to email as attachment. Multiple ones can be comma separated.',
},
{
displayName: 'Options',

View file

@ -288,7 +288,7 @@ export const campaignFields = [
type: 'string',
default: '',
required: true,
description: 'The ID of the campaign to pause.<br>The campaign must be in RUNNING mode.',
description: 'The ID of the campaign to pause. The campaign must be in RUNNING mode.',
displayOptions: {
show: {
resource: [
@ -310,7 +310,7 @@ export const campaignFields = [
type: 'string',
default: '',
required: true,
description: 'The ID of the campaign to start.<br>Email provider and contacts must be set.',
description: 'The ID of the campaign to start. Email provider and contacts must be set.',
displayOptions: {
show: {
resource: [

View file

@ -14,6 +14,7 @@ export class ErrorTrigger implements INodeType {
group: ['trigger'],
version: 1,
description: 'Triggers the workflow when another workflow has an error',
eventTriggerDescription: '',
maxNodes: 1,
defaults: {
name: 'Error Trigger',

View file

@ -204,9 +204,7 @@ export class FacebookGraphApi implements INodeType {
],
},
},
description: `Name of the binary property which contains the data for the file to be uploaded.<br />
For Form-Data Multipart, multiple can be provided in the format:<br />
"sendKey1:binaryProperty1,sendKey2:binaryProperty2`,
description: `Name of the binary property which contains the data for the file to be uploaded. For Form-Data Multipart, they can be provided in the format: <code>"sendKey1:binaryProperty1,sendKey2:binaryProperty2</code>`,
},
{
displayName: 'Options',

View file

@ -86,8 +86,7 @@ export const contactFields = [
],
},
},
description: `Primary email address of the contact. If you want to associate<br>
additional email(s) with this contact, use the other_emails attribute.`,
description: `Primary email address of the contact. If you want to associate additional email(s) with this contact, use the other_emails attribute.`,
},
{
displayName: 'Contact ID',
@ -136,7 +135,7 @@ export const contactFields = [
// name: 'avatar',
// type: '',
// default: '',
// description: `Avatar image of the contact The maximum file size is 5MB<br>
// description: `Avatar image of the contact The maximum file size is 5MB
// and the supported file types are .jpg, .jpeg, .jpe, and .png.`,
// },
{
@ -154,8 +153,7 @@ export const contactFields = [
typeOptions: {
multipleValues: true,
},
description: `Key value pairs containing the name and value of the custom field.<br>
Only dates in the format YYYY-MM-DD are accepted as input for custom date fields.`,
description: `Key value pairs containing the name and value of the custom field. Only dates in the format YYYY-MM-DD are accepted as input for custom date fields.`,
default: [],
options: [
{
@ -199,8 +197,7 @@ export const contactFields = [
],
},
},
description: `Primary email address of the contact. If you want to associate<br>
additional email(s) with this contact, use the other_emails attribute.`,
description: `Primary email address of the contact. If you want to associate additional email(s) with this contact, use the other_emails attribute.`,
},
{
displayName: 'Job Title',
@ -214,9 +211,7 @@ export const contactFields = [
name: 'language',
type: 'string',
default: '',
description: `Language of the contact. Default language is "en".<br>
This attribute can only be set if the Multiple Language feature is<br>
enabled (Garden plan and above).`,
description: `Language of the contact. Default language is "en". This attribute can only be set if the Multiple Language feature is enabled (Garden plan and above).`,
},
{
displayName: 'Mobile',
@ -248,9 +243,7 @@ export const contactFields = [
multipleValues: true,
},
placeholder: 'Add Company',
description: `Additional companies associated with the contact.<br>
This attribute can only be set if the Multiple Companies feature<br>
is enabled (Estate plan and above).`,
description: `Additional companies associated with the contact. This attribute can only be set if the Multiple Companies feature is enabled (Estate plan and above).`,
},
{
displayName: 'Other Emails',
@ -285,8 +278,7 @@ export const contactFields = [
name: 'time_zone',
type: 'string',
default: '',
description: `Time zone of the contact. Default value is the time zone of the domain.<br>
This attribute can only be set if the Multiple Time Zone feature is enabled (Garden plan and above)];`,
description: `Time zone of the contact. Default value is the time zone of the domain. This attribute can only be set if the Multiple Time Zone feature is enabled (Garden plan and above).`,
},
{
displayName: 'Twitter ID',
@ -307,8 +299,7 @@ export const contactFields = [
name: 'view_all_tickets',
type: 'boolean',
default: false,
description: `Set to true if the contact can see all the tickets<br>
that are associated with the company to which he belong.`,
description: `Set to true if the contact can see all the tickets that are associated with the company to which they belong.`,
},
],
},

View file

@ -573,7 +573,6 @@ export class Freshservice implements INodeType {
const assetFields = this.getNodeParameter('assetFieldsUi.assetFieldValue', i, []) as IDataObject[];
Object.assign(body, { type_fields: assetFields.reduce((obj, value) => Object.assign(obj, { [`${value.name}`]: value.value }), {}) });
console.log(body);
responseData = await freshserviceApiRequest.call(this, 'POST', '/assets', body);
} else if (operation === 'delete') {

View file

@ -386,9 +386,7 @@ export const contactFields = [
name: 'exactMatch',
type: 'boolean',
default: false,
description: `When set to true it will search for contacts with the exact value<br>
of the email and name provided in the query string. Without this flag, matching is done via a standard 'like' comparison,<br>
which may sometimes be slow.`,
description: `When set to true it will search for contacts with the exact value of the email and name provided in the query string. Without this flag, matching is done via a standard 'like' comparison, which may sometimes be slow.`,
},
{
displayName: 'Fields',

View file

@ -197,8 +197,7 @@ export const coorganizerFields = [
],
},
},
description: `By default only internal co-organizers (with a GoToWebinar account) can be deleted.</br>
If you want to use this call for external co-organizers you have to set this parameter to 'true'.`,
description: `By default only internal co-organizers (with a GoToWebinar account) can be deleted. If you want to use this call for external co-organizers you have to set this parameter to 'true'.`,
},
// ----------------------------------
@ -276,8 +275,7 @@ export const coorganizerFields = [
type: 'string',
required: true,
default: '',
description: `By default only internal co-organizers (with a GoToWebinar account) can be deleted.</br>
If you want to use this call for external co-organizers you have to set this parameter to 'true'.`,
description: `By default only internal co-organizers (with a GoToWebinar account) can be deleted. If you want to use this call for external co-organizers you have to set this parameter to 'true'.`,
displayOptions: {
show: {
resource: [

View file

@ -310,11 +310,7 @@ export const reportFields = [
name: 'expression',
type: 'string',
default: 'ga:newUsers',
description: `A metric expression in the request. An expression is constructed from one or more metrics and numbers.<br>
Accepted operators include: Plus (+), Minus (-), Negation (Unary -), Divided by (/), Multiplied by (*), Parenthesis,<br>
Positive cardinal numbers (0-9), can include decimals and is limited to 1024 characters. Example ga:totalRefunds/ga:users,<br>
in most cases the metric expression is just a single metric name like ga:users. Adding mixed MetricType (E.g., CURRENCY + PERCENTAGE)<br>
metrics will result in unexpected results.`,
description: `<p>A metric expression in the request. An expression is constructed from one or more metrics and numbers.</p><p>Accepted operators include: Plus (+), Minus (-), Negation (Unary -), Divided by (/), Multiplied by (*), Parenthesis, Positive cardinal numbers (0-9), can include decimals and is limited to 1024 characters.</p><p>Example ga:totalRefunds/ga:users, in most cases the metric expression is just a single metric name like ga:users.</p><p>Adding mixed MetricType (E.g., CURRENCY + PERCENTAGE) metrics will result in unexpected results.</p>`,
},
{
displayName: 'Formatting Type',

View file

@ -258,8 +258,7 @@ export const eventFields = [
name: 'maxAttendees',
type: 'number',
default: 0,
description: `The maximum number of attendees to include in the response.</br>
If there are more than the specified number of attendees, only the participant is returned`,
description: `The maximum number of attendees to include in the response. If there are more than the specified number of attendees, only the participant is returned`,
},
{
displayName: 'Repeat Frecuency',
@ -563,8 +562,7 @@ export const eventFields = [
name: 'maxAttendees',
type: 'number',
default: 0,
description: `The maximum number of attendees to include in the response.</br>
If there are more than the specified number of attendees, only the participant is returned`,
description: `The maximum number of attendees to include in the response. If there are more than the specified number of attendees, only the participant is returned`,
},
{
displayName: 'Timezone',
@ -652,8 +650,7 @@ export const eventFields = [
name: 'maxAttendees',
type: 'number',
default: 0,
description: `The maximum number of attendees to include in the response.</br>
If there are more than the specified number of attendees, only the participant is returned`,
description: `The maximum number of attendees to include in the response. If there are more than the specified number of attendees, only the participant is returned`,
},
{
displayName: 'Order By',
@ -700,8 +697,7 @@ export const eventFields = [
name: 'singleEvents',
type: 'boolean',
default: false,
description: `Whether to expand recurring events into instances and only return single one-off</br>
events and instances of recurring events, but not the underlying recurring events themselves.`,
description: `Whether to expand recurring events into instances and only return single one-off events and instances of recurring events, but not the underlying recurring events themselves.`,
},
{
displayName: 'End Time',
@ -885,8 +881,7 @@ export const eventFields = [
name: 'maxAttendees',
type: 'number',
default: 0,
description: `The maximum number of attendees to include in the response.</br>
If there are more than the specified number of attendees, only the participant is returned`,
description: `The maximum number of attendees to include in the response. If there are more than the specified number of attendees, only the participant is returned`,
},
{
displayName: 'Repeat Frecuency',

View file

@ -125,7 +125,7 @@ export class GoogleCloudNaturalLanguage implements INodeType {
name: 'gcsContentUri',
type: 'string',
default: '',
description: 'The Google Cloud Storage URI where the file content is located. This URI must be of the form: gs://bucket_name/object_name.<br/> For more details, see https://cloud.google.com/storage/docs/reference-uris.',
description: `The Google Cloud Storage URI where the file content is located. This URI must be of the form: <code>gs://bucket_name/object_name</code>. For more details, see <a href="https://cloud.google.com/storage/docs/reference-uris.">reference</a>.`,
required: true,
displayOptions: {
show: {

View file

@ -792,9 +792,7 @@ export class GoogleDrive implements INodeType {
name: 'keepRevisionForever',
type: 'boolean',
default: false,
description: `Whether to set the 'keepForever' field in the new head revision.</br>
his is only applicable to files with binary content in Google Drive.</br>
Only 200 revisions for the file can be kept forever. If the limit is reached, try deleting pinned revisions.`,
description: `Whether to set the 'keepForever' field in the new head revision. This is only applicable to files with binary content in Google Drive. Only 200 revisions for the file can be kept forever. If the limit is reached, try deleting pinned revisions.`,
},
{
displayName: 'OCR Language',
@ -955,7 +953,7 @@ export class GoogleDrive implements INodeType {
],
},
},
description: 'By default the response only contain the ID of the file.<br />If this option gets activated, it will resolve the data automatically.',
description: 'By default the response only contain the ID of the file. If this option gets activated, it will resolve the data automatically.',
},
{
displayName: 'Parents',
@ -1059,8 +1057,7 @@ export class GoogleDrive implements INodeType {
},
},
default: false,
description: `Set to true to opt in to API behavior that aims for all items to have exactly one parent.<br>
This parameter only takes effect if the item is not in a shared drive`,
description: `Set to true to opt in to API behavior that aims for all items to have exactly one parent. This parameter only takes effect if the item is not in a shared drive.`,
},
{
displayName: 'Fields',
@ -1165,8 +1162,7 @@ export class GoogleDrive implements INodeType {
},
},
default: '',
description: `This parameter only takes effect if the item is not in a shared drive and the request is attempting to transfer the ownership of the item.<br>
When set to true, the item is moved to the new owner's My Drive root folder and all prior parents removed`,
description: `<p>This parameter only takes effect if the item is not in a shared drive and the request is attempting to transfer the ownership of the item.</p><p>When set to true, the item is moved to the new owner's My Drive root folder and all prior parents removed.</p>`,
},
{
displayName: 'Send Notification Email',

View file

@ -90,9 +90,7 @@ export const groupFields = [
name: 'description',
type: 'string',
default: '',
description: `An extended description to help users determine the purpose of a group.<br>
For example, you can include information about who should join the group,<br>
the types of messages to send to the group, links to FAQs about the group, or related groups`,
description: `An extended description to help users determine the purpose of a group. For example, you can include information about who should join the group, the types of messages to send to the group, links to FAQs about the group, or related groups`,
},
{
displayName: 'Name',
@ -309,9 +307,7 @@ export const groupFields = [
name: 'description',
type: 'string',
default: '',
description: `An extended description to help users determine the purpose of a group.<br>
For example, you can include information about who should join the group,<br>
the types of messages to send to the group, links to FAQs about the group, or related groups`,
description: `An extended description to help users determine the purpose of a group. For example, you can include information about who should join the group, the types of messages to send to the group, links to FAQs about the group, or related groups`,
},
{
displayName: 'Email',

View file

@ -640,8 +640,7 @@ export const userFields = [
name: 'query',
type: 'string',
default: '',
description: `Free text search terms to find users that match these terms in any field, except for extended properties.</br>
For more information on constructing user queries, see <a href="https://developers.google.com/admin-sdk/directory/v1/guides/search-users">Search for Users</a>`,
description: `Free text search terms to find users that match these terms in any field, except for extended properties. For more information on constructing user queries, see <a href="https://developers.google.com/admin-sdk/directory/v1/guides/search-users">Search for Users</a>`,
},
{
displayName: 'Show Deleted',

View file

@ -209,8 +209,7 @@ export const draftFields = [
name: 'property',
type: 'string',
default: '',
description: `Name of the binary property containing the data to be added to the email as an attachment.</br>
Multiples can be set separated by comma.`,
description: `Name of the binary property containing the data to be added to the email as an attachment. Multiple properties can be set separated by comma.`,
},
],
},
@ -252,7 +251,7 @@ export const draftFields = [
],
},
},
description: 'Prefix for name of the binary property to which to write the attachments. An index starting with 0 will be added.<br />So if name is "attachment_" the first attachment is saved to "attachment_0"',
description: 'Prefix for name of the binary property to which to write the attachments. An index starting with 0 will be added. So if name is "attachment_" the first attachment is saved to "attachment_0"',
},
{
displayName: 'Format',
@ -368,7 +367,7 @@ export const draftFields = [
],
},
},
description: 'Prefix for name of the binary property to which to write the attachments. An index starting with 0 will be added.<br />So if name is "attachment_" the first attachment is saved to "attachment_0"',
description: 'Prefix for name of the binary property to which to write the attachments. An index starting with 0 will be added. So if name is "attachment_" the first attachment is saved to "attachment_0"',
},
{
displayName: 'Format',

View file

@ -244,8 +244,7 @@ export const messageFields = [
name: 'property',
type: 'string',
default: '',
description: `Name of the binary property containing the data to be added to the email as an attachment.</br>
Multiples can be set separated by comma.`,
description: `Name of the binary property containing the data to be added to the email as an attachment. Multiple properties can be set separated by comma.`,
},
],
},
@ -283,9 +282,7 @@ export const messageFields = [
type: 'string',
placeholder: 'Name <test@gmail.com>',
default: '',
description: `The name displayed in your contacts inboxes.</br>
It has to be in the format: "Display-Name &#60;name@gmail.com&#62;".</br>
The email address has to match the email address of the logged in user for the API`,
description: `The name displayed in your contacts inboxes. It has to be in the format: "Display-Name &#60;name@gmail.com&#62;". The email address has to match the email address of the logged in user for the API`,
},
],
},
@ -355,7 +352,7 @@ export const messageFields = [
],
},
},
description: 'Prefix for name of the binary property to which to write the attachments. An index starting with 0 will be added.<br />So if name is "attachment_" the first attachment is saved to "attachment_0"',
description: 'Prefix for name of the binary property to which to write the attachments. An index starting with 0 will be added. So if name is "attachment_" the first attachment is saved to "attachment_0"',
},
],
},
@ -437,7 +434,7 @@ export const messageFields = [
],
},
},
description: 'Prefix for name of the binary property to which to write the attachments. An index starting with 0 will be added.<br />So if name is "attachment_" the first attachment is saved to "attachment_0"',
description: 'Prefix for name of the binary property to which to write the attachments. An index starting with 0 will be added. So if name is "attachment_" the first attachment is saved to "attachment_0"',
},
{
displayName: 'Format',
@ -503,10 +500,7 @@ export const messageFields = [
alwaysOpenEditWindow: true,
},
default: '',
description: `Only return messages matching the specified query.</br>
Supports the same query format as the Gmail search box.</br>
For example, "from:someuser@example.com rfc822msgid:<somemsgid@example.com> is:unread".</br>
Parameter cannot be used when accessing the api using the gmail.metadata scope.`,
description: `Only return messages matching the specified query. Supports the same query format as the Gmail search box. For example, "from:someuser@example.com rfc822msgid:<somemsgid@example.com> is:unread". Parameter cannot be used when accessing the api using the gmail.metadata scope.`,
},
],
},

View file

@ -179,7 +179,7 @@ export class GoogleSheets implements INodeType {
},
default: '',
required: true,
description: 'The ID of the Google Spreadsheet.<br />Found as part of the sheet URL https://docs.google.com/spreadsheets/d/{ID}/',
description: 'The ID of the Google Spreadsheet. Found as part of the sheet URL https://docs.google.com/spreadsheets/d/{ID}/',
},
{
displayName: 'Range',
@ -201,7 +201,7 @@ export class GoogleSheets implements INodeType {
},
default: 'A:F',
required: true,
description: 'The table range to read from or to append data to. See the Google <a href="https://developers.google.com/sheets/api/guides/values#writing">documentation</a> for the details.<br />If it contains multiple sheets it can also be added like this: "MySheet!A:F"',
description: 'The table range to read from or to append data to. See the Google <a href="https://developers.google.com/sheets/api/guides/values#writing">documentation</a> for the details. If it contains multiple sheets it can also be added like this: "MySheet!A:F"',
},
// ----------------------------------
@ -452,7 +452,7 @@ export class GoogleSheets implements INodeType {
},
},
default: 0,
description: 'Index of the row which contains the keys. Starts at 0.<br />The incoming node data is matched to the keys for assignment. The matching is case sensitive.',
description: 'Index of the row which contains the keys. Starts at 0. The incoming node data is matched to the keys for assignment. The matching is case sensitive.',
},
@ -782,7 +782,12 @@ export class GoogleSheets implements INodeType {
type: 'string',
default: '',
placeholder: 'en_US',
description: 'The locale of the spreadsheet in one of the following formats:<br /><ul><li>en (639-1)</li><li>fil (639-2 if no 639-1 format exists)</li><li>en_US (combination of ISO language an country)</li><ul>',
description: `The locale of the spreadsheet in one of the following formats:
<ul>
<li>en (639-1)</li>
<li>fil (639-2 if no 639-1 format exists)</li>
<li>en_US (combination of ISO language an country)</li>
<ul>`,
},
{
displayName: 'Recalculation Interval',

View file

@ -171,7 +171,7 @@ export class GoogleSlides implements INodeType {
{
displayName: 'Presentation ID',
name: 'presentationId',
description: 'ID of the presentation to retrieve. Found in the presentation URL:<br><code>https://docs.google.com/presentation/d/PRESENTATION_ID/edit</code>',
description: 'ID of the presentation to retrieve. Found in the presentation URL: <code>https://docs.google.com/presentation/d/PRESENTATION_ID/edit</code>',
placeholder: '1wZtNFZ8MO-WKrxhYrOLMvyiqSgFwdSz5vn8_l_7eNqw',
type: 'string',
default: '',
@ -335,9 +335,7 @@ export class GoogleSlides implements INodeType {
name: 'revisionId',
type: 'string',
default: '',
description: `The revision ID of the presentation required for the write request.</br>
If specified and the requiredRevisionId doesn't exactly match the presentation's</br>
current revisionId, the request will not be processed and will return a 400 bad request error.`,
description: `The revision ID of the presentation required for the write request. If specified and the requiredRevisionId doesn't exactly match the presentation's current revisionId, the request will not be processed and will return a 400 bad request error.`,
},
],
},

View file

@ -135,16 +135,14 @@ export const playlistFields = [
name: 'onBehalfOfContentOwnerChannel',
type: 'string',
default: '',
description: `The onBehalfOfContentOwnerChannel parameter specifies the YouTube channel ID of the channel to which a video is being added.<br>
This parameter is required when a request specifies a value for the onBehalfOfContentOwner parameter, and it can only be used in conjunction with that parameter.`,
description: `The onBehalfOfContentOwnerChannel parameter specifies the YouTube channel ID of the channel to which a video is being added. This parameter is required when a request specifies a value for the onBehalfOfContentOwner parameter, and it can only be used in conjunction with that parameter.`,
},
{
displayName: 'On Behalf Of Content Owner',
name: 'onBehalfOfContentOwner',
type: 'string',
default: '',
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify<br>
a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
},
],
},
@ -238,8 +236,7 @@ export const playlistFields = [
name: 'onBehalfOfContentOwner',
type: 'string',
default: '',
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify<br>
a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
},
{
displayName: 'On Behalf Of Content Owner Channel',
@ -292,8 +289,7 @@ export const playlistFields = [
name: 'onBehalfOfContentOwner',
type: 'string',
default: '',
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify<br>
a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
},
],
},
@ -444,16 +440,14 @@ export const playlistFields = [
name: 'onBehalfOfContentOwnerChannel',
type: 'string',
default: '',
description: `The onBehalfOfContentOwnerChannel parameter specifies the YouTube channel ID of the channel to which a video is being added.<br>
This parameter is required when a request specifies a value for the onBehalfOfContentOwner parameter, and it can only be used in conjunction with that parameter.`,
description: `The onBehalfOfContentOwnerChannel parameter specifies the YouTube channel ID of the channel to which a video is being added. This parameter is required when a request specifies a value for the onBehalfOfContentOwner parameter, and it can only be used in conjunction with that parameter.`,
},
{
displayName: 'On Behalf Of Content Owner',
name: 'onBehalfOfContentOwner',
type: 'string',
default: '',
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify<br>
a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
},
],
},
@ -535,8 +529,7 @@ export const playlistFields = [
name: 'onBehalfOfContentOwner',
type: 'string',
default: '',
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify<br>
a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
},
{
displayName: 'Privacy Status',

View file

@ -118,8 +118,7 @@ export const playlistItemFields = [
name: 'onBehalfOfContentOwner',
type: 'string',
default: '',
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify<br>
a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
},
{
displayName: 'Position',
@ -222,8 +221,7 @@ export const playlistItemFields = [
name: 'onBehalfOfContentOwner',
type: 'string',
default: '',
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify<br>
a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
},
],
},
@ -269,8 +267,7 @@ export const playlistItemFields = [
name: 'onBehalfOfContentOwner',
type: 'string',
default: '',
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify<br>
a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
},
],
},
@ -400,8 +397,7 @@ export const playlistItemFields = [
name: 'onBehalfOfContentOwner',
type: 'string',
default: '',
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify<br>
a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
},
],
},

View file

@ -296,8 +296,7 @@ export const videoFields = [
name: 'onBehalfOfContentOwner',
type: 'string',
default: '',
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify<br>
a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
},
],
},
@ -407,8 +406,7 @@ export const videoFields = [
name: 'onBehalfOfContentOwner',
type: 'string',
default: '',
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify<br>
a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
description: `The onBehalfOfContentOwner parameter indicates that the request's authorization credentials identify a YouTube CMS user who is acting on behalf of the content owner specified in the parameter value`,
},
],
},

View file

@ -0,0 +1,111 @@
import {
IExecuteFunctions,
} from 'n8n-core';
import {
IDataObject,
ILoadOptionsFunctions,
NodeApiError,
NodeOperationError,
} from 'n8n-workflow';
import {
OptionsWithUri,
} from 'request';
import {
GrafanaCredentials,
} from './types';
export async function grafanaApiRequest(
this: IExecuteFunctions | ILoadOptionsFunctions,
method: string,
endpoint: string,
body: IDataObject = {},
qs: IDataObject = {},
) {
const {
apiKey,
baseUrl: rawBaseUrl,
} = await this.getCredentials('grafanaApi') as GrafanaCredentials;
const baseUrl = tolerateTrailingSlash(rawBaseUrl);
const options: OptionsWithUri = {
headers: {
Authorization: `Bearer ${apiKey}`,
'Content-Type': 'application/json',
},
method,
body,
qs,
uri: `${baseUrl}/api${endpoint}`,
json: true,
};
if (!Object.keys(body).length) {
delete options.body;
}
if (!Object.keys(qs).length) {
delete options.qs;
}
try {
return await this.helpers.request!(options);
} catch (error) {
if (error?.response?.data?.message === 'Team member not found') {
error.response.data.message += '. Are you sure the user is a member of this team?';
}
if (error?.response?.data?.message === 'Team not found') {
error.response.data.message += ' with the provided ID';
}
if (error?.response?.data?.message === 'A dashboard with the same name in the folder already exists') {
error.response.data.message = 'A dashboard with the same name already exists in the selected folder';
}
if (error?.response?.data?.message === 'Team name taken') {
error.response.data.message = 'This team name is already taken. Please choose a new one.';
}
if (error?.code === 'ECONNREFUSED') {
error.message = 'Invalid credentials or error in establishing connection with given credentials';
}
throw new NodeApiError(this.getNode(), error);
}
}
export function throwOnEmptyUpdate(
this: IExecuteFunctions,
resource: string,
updateFields: IDataObject,
) {
if (!Object.keys(updateFields).length) {
throw new NodeOperationError(
this.getNode(),
`Please enter at least one field to update for the ${resource}.`,
);
}
}
export function tolerateTrailingSlash(baseUrl: string) {
return baseUrl.endsWith('/')
? baseUrl.substr(0, baseUrl.length - 1)
: baseUrl;
}
export function deriveUid(this: IExecuteFunctions, uidOrUrl: string) {
if (!uidOrUrl.startsWith('http')) return uidOrUrl;
const urlSegments = uidOrUrl.split('/');
const uid = urlSegments[urlSegments.indexOf('d') + 1];
if (!uid) {
throw new NodeOperationError(this.getNode(), 'Failed to derive UID from URL');
}
return uid;
}

View file

@ -0,0 +1,577 @@
import {
IExecuteFunctions,
} from 'n8n-core';
import {
ICredentialsDecrypted,
ICredentialTestFunctions,
IDataObject,
ILoadOptionsFunctions,
INodeExecutionData,
INodePropertyOptions,
INodeType,
INodeTypeDescription,
NodeApiError,
NodeCredentialTestResult,
} from 'n8n-workflow';
import {
deriveUid,
grafanaApiRequest,
throwOnEmptyUpdate,
tolerateTrailingSlash,
} from './GenericFunctions';
import {
dashboardFields,
dashboardOperations,
teamFields,
teamMemberFields,
teamMemberOperations,
teamOperations,
userFields,
userOperations,
} from './descriptions';
import {
OptionsWithUri,
} from 'request';
import {
DashboardUpdateFields,
DashboardUpdatePayload,
GrafanaCredentials,
LoadedDashboards,
LoadedFolders,
LoadedTeams,
LoadedUsers,
} from './types';
export class Grafana implements INodeType {
description: INodeTypeDescription = {
displayName: 'Grafana',
name: 'grafana',
icon: 'file:grafana.svg',
group: ['transform'],
version: 1,
subtitle: '={{$parameter["operation"] + ": " + $parameter["resource"]}}',
description: 'Consume the Grafana API',
defaults: {
name: 'Grafana',
color: '#fb755a',
},
inputs: ['main'],
outputs: ['main'],
credentials: [
{
name: 'grafanaApi',
required: true,
testedBy: 'grafanaApiTest',
},
],
properties: [
{
displayName: 'Resource',
name: 'resource',
noDataExpression: true,
type: 'options',
options: [
{
name: 'Dashboard',
value: 'dashboard',
},
{
name: 'Team',
value: 'team',
},
{
name: 'Team Member',
value: 'teamMember',
},
{
name: 'User',
value: 'user',
},
],
default: 'dashboard',
},
...dashboardOperations,
...dashboardFields,
...teamOperations,
...teamFields,
...teamMemberOperations,
...teamMemberFields,
...userOperations,
...userFields,
],
};
methods = {
loadOptions: {
async getDashboards(this: ILoadOptionsFunctions): Promise<INodePropertyOptions[]> {
const dashboards = await grafanaApiRequest.call(
this, 'GET', '/search', {}, { qs: 'dash-db' },
) as LoadedDashboards;
return dashboards.map(({ id, title }) => ({ value: id, name: title }));
},
async getFolders(this: ILoadOptionsFunctions): Promise<INodePropertyOptions[]> {
const folders = await grafanaApiRequest.call(this, 'GET', '/folders') as LoadedFolders;
return folders.map(({ id, title }) => ({ value: id, name: title }));
},
async getTeams(this: ILoadOptionsFunctions): Promise<INodePropertyOptions[]> {
const res = await grafanaApiRequest.call(this, 'GET', '/teams/search') as LoadedTeams;
return res.teams.map(({ id, name }) => ({ value: id, name }));
},
async getUsers(this: ILoadOptionsFunctions): Promise<INodePropertyOptions[]> {
const users = await grafanaApiRequest.call(this, 'GET', '/org/users') as LoadedUsers;
return users.map(({ userId, email }) => ({ value: userId, name: email }));
},
},
credentialTest: {
async grafanaApiTest(
this: ICredentialTestFunctions,
credential: ICredentialsDecrypted,
): Promise<NodeCredentialTestResult> {
const { apiKey, baseUrl: rawBaseUrl } = credential.data as GrafanaCredentials;
const baseUrl = tolerateTrailingSlash(rawBaseUrl);
const options: OptionsWithUri = {
headers: {
Authorization: `Bearer ${apiKey}`,
},
method: 'GET',
uri: `${baseUrl}/api/folders`,
json: true,
};
try {
await this.helpers.request(options);
return {
status: 'OK',
message: 'Authentication successful',
};
} catch (error) {
return {
status: 'Error',
message: error.message,
};
}
},
},
};
async execute(this: IExecuteFunctions): Promise<INodeExecutionData[][]> {
const items = this.getInputData();
const returnData: IDataObject[] = [];
const resource = this.getNodeParameter('resource', 0) as string;
const operation = this.getNodeParameter('operation', 0) as string;
let responseData;
for (let i = 0; i < items.length; i++) {
try {
if (resource === 'dashboard') {
// **********************************************************************
// dashboard
// **********************************************************************
if (operation === 'create') {
// ----------------------------------------
// dashboard: create
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/dashboard/#create--update-dashboard
const body = {
dashboard: {
id: null,
title: this.getNodeParameter('title', i),
},
};
const additionalFields = this.getNodeParameter('additionalFields', i) as IDataObject;
if (Object.keys(additionalFields).length) {
if (additionalFields.folderId === '') delete additionalFields.folderId;
Object.assign(body, additionalFields);
}
responseData = await grafanaApiRequest.call(this, 'POST', '/dashboards/db', body);
} else if (operation === 'delete') {
// ----------------------------------------
// dashboard: delete
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/dashboard/#delete-dashboard-by-uid
const uidOrUrl = this.getNodeParameter('dashboardUidOrUrl', i) as string;
const uid = deriveUid.call(this, uidOrUrl);
const endpoint = `/dashboards/uid/${uid}`;
responseData = await grafanaApiRequest.call(this, 'DELETE', endpoint);
} else if (operation === 'get') {
// ----------------------------------------
// dashboard: get
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/dashboard/#get-dashboard-by-uid
const uidOrUrl = this.getNodeParameter('dashboardUidOrUrl', i) as string;
const uid = deriveUid.call(this, uidOrUrl);
const endpoint = `/dashboards/uid/${uid}`;
responseData = await grafanaApiRequest.call(this, 'GET', endpoint);
} else if (operation === 'getAll') {
// ----------------------------------------
// dashboard: getAll
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/folder_dashboard_search/#search-folders-and-dashboards
const qs = {
type: 'dash-db',
};
const filters = this.getNodeParameter('filters', i) as IDataObject;
if (Object.keys(filters).length) {
Object.assign(qs, filters);
}
const returnAll = this.getNodeParameter('returnAll', i) as boolean;
if (!returnAll) {
const limit = this.getNodeParameter('limit', i) as number;
Object.assign(qs, { limit });
}
responseData = await grafanaApiRequest.call(this, 'GET', '/search', {}, qs);
} else if (operation === 'update') {
// ----------------------------------------
// dashboard: update
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/dashboard/#create--update-dashboard
const uidOrUrl = this.getNodeParameter('dashboardUidOrUrl', i) as string;
const uid = deriveUid.call(this, uidOrUrl);
// ensure dashboard to update exists
await grafanaApiRequest.call(this, 'GET', `/dashboards/uid/${uid}`);
const body: DashboardUpdatePayload = {
overwrite: true,
dashboard: { uid },
};
const updateFields = this.getNodeParameter('updateFields', i) as DashboardUpdateFields;
throwOnEmptyUpdate.call(this, resource, updateFields);
const { title, ...rest } = updateFields;
if (!title) {
const { dashboard } = await grafanaApiRequest.call(this, 'GET', `/dashboards/uid/${uid}`);
body.dashboard.title = dashboard.title;
} else {
const dashboards = await grafanaApiRequest.call(this, 'GET', '/search') as Array<{ title: string }>;
const titles = dashboards.map(({ title }) => title);
if (titles.includes(title)) {
throw new NodeApiError(
this.getNode(),
{ message: 'A dashboard with the same name already exists in the selected folder' },
);
}
body.dashboard.title = title;
}
if (title) {
body.dashboard.title = title;
}
if (Object.keys(rest).length) {
if (rest.folderId === '') delete rest.folderId;
Object.assign(body, rest);
}
responseData = await grafanaApiRequest.call(this, 'POST', '/dashboards/db', body);
}
} else if (resource === 'team') {
// **********************************************************************
// team
// **********************************************************************
if (operation === 'create') {
// ----------------------------------------
// team: create
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/team/#add-team
const body = {
name: this.getNodeParameter('name', i) as string,
};
const additionalFields = this.getNodeParameter('additionalFields', i) as IDataObject;
if (Object.keys(additionalFields).length) {
Object.assign(body, additionalFields);
}
responseData = await grafanaApiRequest.call(this, 'POST', '/teams', body);
} else if (operation === 'delete') {
// ----------------------------------------
// team: delete
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/team/#delete-team-by-id
const teamId = this.getNodeParameter('teamId', i);
responseData = await grafanaApiRequest.call(this, 'DELETE', `/teams/${teamId}`);
} else if (operation === 'get') {
// ----------------------------------------
// team: get
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/team/#get-team-by-id
const teamId = this.getNodeParameter('teamId', i);
responseData = await grafanaApiRequest.call(this, 'GET', `/teams/${teamId}`);
} else if (operation === 'getAll') {
// ----------------------------------------
// team: getAll
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/team/#team-search-with-paging
const qs = {} as IDataObject;
const filters = this.getNodeParameter('filters', i) as IDataObject;
if (Object.keys(filters).length) {
Object.assign(qs, filters);
}
responseData = await grafanaApiRequest.call(this, 'GET', '/teams/search', {}, qs);
responseData = responseData.teams;
const returnAll = this.getNodeParameter('returnAll', i) as boolean;
if (!returnAll) {
const limit = this.getNodeParameter('limit', i) as number;
responseData = responseData.slice(0, limit);
}
} else if (operation === 'update') {
// ----------------------------------------
// team: update
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/team/#update-team
const updateFields = this.getNodeParameter('updateFields', i) as IDataObject;
throwOnEmptyUpdate.call(this, resource, updateFields);
const body: IDataObject = {};
const teamId = this.getNodeParameter('teamId', i);
// check if team exists, since API does not specify update failure reason
await grafanaApiRequest.call(this, 'GET', `/teams/${teamId}`);
// prevent email from being overridden to empty
if (!updateFields.email) {
const { email } = await grafanaApiRequest.call(this, 'GET', `/teams/${teamId}`);
body.email = email;
}
if (Object.keys(updateFields).length) {
Object.assign(body, updateFields);
}
responseData = await grafanaApiRequest.call(this, 'PUT', `/teams/${teamId}`, body);
}
} else if (resource === 'teamMember') {
// **********************************************************************
// teamMember
// **********************************************************************
if (operation === 'add') {
// ----------------------------------------
// teamMember: add
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/team/#add-team-member
const userId = this.getNodeParameter('userId', i) as string;
const body = {
userId: parseInt(userId, 10),
};
const teamId = this.getNodeParameter('teamId', i);
const endpoint = `/teams/${teamId}/members`;
responseData = await grafanaApiRequest.call(this, 'POST', endpoint, body);
} else if (operation === 'remove') {
// ----------------------------------------
// teamMember: remove
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/team/#remove-member-from-team
const teamId = this.getNodeParameter('teamId', i);
const memberId = this.getNodeParameter('memberId', i);
const endpoint = `/teams/${teamId}/members/${memberId}`;
responseData = await grafanaApiRequest.call(this, 'DELETE', endpoint);
} else if (operation === 'getAll') {
// ----------------------------------------
// teamMember: getAll
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/team/#get-team-members
const teamId = this.getNodeParameter('teamId', i);
// check if team exists, since API returns all members if team does not exist
await grafanaApiRequest.call(this, 'GET', `/teams/${teamId}`);
const endpoint = `/teams/${teamId}/members`;
responseData = await grafanaApiRequest.call(this, 'GET', endpoint);
const returnAll = this.getNodeParameter('returnAll', i) as boolean;
if (!returnAll) {
const limit = this.getNodeParameter('limit', i) as number;
responseData = responseData.slice(0, limit);
}
}
} else if (resource === 'user') {
// **********************************************************************
// user
// **********************************************************************
if (operation === 'create') {
// ----------------------------------------
// user: create
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/org/#add-a-new-user-to-the-current-organization
const body = {
role: this.getNodeParameter('role', i),
loginOrEmail: this.getNodeParameter('loginOrEmail', i),
};
responseData = await grafanaApiRequest.call(this, 'POST', '/org/users', body);
} else if (operation === 'delete') {
// ----------------------------------------
// user: delete
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/org/#delete-user-in-current-organization
const userId = this.getNodeParameter('userId', i);
responseData = await grafanaApiRequest.call(this, 'DELETE', `/org/users/${userId}`);
} else if (operation === 'getAll') {
// ----------------------------------------
// user: getAll
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/org/#get-all-users-within-the-current-organization
responseData = await grafanaApiRequest.call(this, 'GET', '/org/users');
const returnAll = this.getNodeParameter('returnAll', i) as boolean;
if (!returnAll) {
const limit = this.getNodeParameter('limit', i) as number;
responseData = responseData.slice(0, limit);
}
} else if (operation === 'update') {
// ----------------------------------------
// user: update
// ----------------------------------------
// https://grafana.com/docs/grafana/latest/http_api/org/#updates-the-given-user
const body: IDataObject = {};
const updateFields = this.getNodeParameter('updateFields', i) as IDataObject;
throwOnEmptyUpdate.call(this, resource, updateFields);
if (Object.keys(updateFields).length) {
Object.assign(body, updateFields);
}
const userId = this.getNodeParameter('userId', i) as string;
responseData = await grafanaApiRequest.call(this, 'PATCH', `/org/users/${userId}`, body);
}
}
Array.isArray(responseData)
? returnData.push(...responseData)
: returnData.push(responseData);
} catch (error) {
if (this.continueOnFail()) {
returnData.push({ error: error.message });
continue;
}
throw error;
}
}
return [this.helpers.returnJsonArray(returnData)];
}
}

View file

@ -0,0 +1,271 @@
import {
INodeProperties,
} from 'n8n-workflow';
export const dashboardOperations: INodeProperties[] = [
{
displayName: 'Operation',
name: 'operation',
type: 'options',
noDataExpression: true,
displayOptions: {
show: {
resource: [
'dashboard',
],
},
},
options: [
{
name: 'Create',
value: 'create',
description: 'Create a dashboard',
},
{
name: 'Delete',
value: 'delete',
description: 'Delete a dashboard',
},
{
name: 'Get',
value: 'get',
description: 'Get a dashboard',
},
{
name: 'Get All',
value: 'getAll',
description: 'Get all dashboards',
},
{
name: 'Update',
value: 'update',
description: 'Update a dashboard',
},
],
default: 'create',
},
];
export const dashboardFields: INodeProperties[] = [
{
displayName: 'Title',
name: 'title',
description: 'Title of the dashboard to create',
type: 'string',
required: true,
default: '',
displayOptions: {
show: {
resource: [
'dashboard',
],
operation: [
'create',
],
},
},
},
{
displayName: 'Additional Fields',
name: 'additionalFields',
type: 'collection',
placeholder: 'Add Field',
default: {},
displayOptions: {
show: {
resource: [
'dashboard',
],
operation: [
'create',
],
},
},
options: [
{
displayName: 'Folder Name or ID',
name: 'folderId',
type: 'options',
default: '',
description: 'Folder to create the dashboard in - if the folder is unspecified, the dashboard will be saved to the General folder. Choose from the list or specify an ID. You can also specify the ID using an <a href="https://docs.n8n.io/nodes/expressions.html#expressions">expression</a>.',
typeOptions: {
loadOptionsMethod: 'getFolders',
},
},
],
},
// ----------------------------------------
// dashboard: delete
// ----------------------------------------
{
displayName: 'Dashboard UID or URL',
name: 'dashboardUidOrUrl',
description: 'Unique alphabetic identifier or URL of the dashboard to delete',
placeholder: 'cIBgcSjkk',
type: 'string',
required: true,
default: '',
displayOptions: {
show: {
resource: [
'dashboard',
],
operation: [
'delete',
],
},
},
},
// ----------------------------------------
// dashboard: get
// ----------------------------------------
{
displayName: 'Dashboard UID or URL',
name: 'dashboardUidOrUrl',
description: 'Unique alphabetic identifier or URL of the dashboard to retrieve',
placeholder: 'cIBgcSjkk',
type: 'string',
required: true,
default: '',
displayOptions: {
show: {
resource: [
'dashboard',
],
operation: [
'get',
],
},
},
},
// ----------------------------------
// dashboard: getAll
// ----------------------------------
{
displayName: 'Return All',
name: 'returnAll',
type: 'boolean',
default: false,
description: 'Whether to return all results or only up to a given limit',
displayOptions: {
show: {
resource: [
'dashboard',
],
operation: [
'getAll',
],
},
},
},
{
displayName: 'Limit',
name: 'limit',
type: 'number',
default: 50,
description: 'Max number of results to return',
typeOptions: {
minValue: 1,
maxValue: 100,
},
displayOptions: {
show: {
resource: [
'dashboard',
],
operation: [
'getAll',
],
returnAll: [
false,
],
},
},
},
{
displayName: 'Filters',
name: 'filters',
type: 'collection',
placeholder: 'Add Filter',
default: {},
displayOptions: {
show: {
resource: [
'dashboard',
],
operation: [
'getAll',
],
},
},
options: [
{
displayName: 'Search Query',
name: 'query',
type: 'string',
default: '',
},
],
},
// ----------------------------------------
// dashboard: update
// ----------------------------------------
{
displayName: 'Dashboard UID or URL',
name: 'dashboardUidOrUrl',
description: 'Unique alphabetic identifier or URL of the dashboard to update',
placeholder: 'cIBgcSjkk',
type: 'string',
required: true,
default: '',
displayOptions: {
show: {
resource: [
'dashboard',
],
operation: [
'update',
],
},
},
},
{
displayName: 'Update Fields',
name: 'updateFields',
type: 'collection',
placeholder: 'Add Field',
default: {},
displayOptions: {
show: {
resource: [
'dashboard',
],
operation: [
'update',
],
},
},
options: [
{
displayName: 'Folder Name or ID',
name: 'folderId',
type: 'options',
default: '',
description: 'Folder to move the dashboard into - if the folder is unspecified, the dashboard will be saved to the General folder. Choose from the list or specify an ID using an <a href="https://docs.n8n.io/nodes/expressions.html#expressions">expression</a>.',
typeOptions: {
loadOptionsMethod: 'getFolders',
},
},
{
displayName: 'Title',
name: 'title',
type: 'string',
default: '',
description: 'New title of the dashboard',
},
],
},
];

View file

@ -0,0 +1,270 @@
import {
INodeProperties,
} from 'n8n-workflow';
export const teamOperations: INodeProperties[] = [
{
displayName: 'Operation',
name: 'operation',
type: 'options',
noDataExpression: true,
displayOptions: {
show: {
resource: [
'team',
],
},
},
options: [
{
name: 'Create',
value: 'create',
description: 'Create a team',
},
{
name: 'Delete',
value: 'delete',
description: 'Delete a team',
},
{
name: 'Get',
value: 'get',
description: 'Get a team',
},
{
name: 'Get All',
value: 'getAll',
description: 'Retrieve all teams',
},
{
name: 'Update',
value: 'update',
description: 'Update a team',
},
],
default: 'create',
},
];
export const teamFields: INodeProperties[] = [
// ----------------------------------------
// team: create
// ----------------------------------------
{
displayName: 'Name',
name: 'name',
description: 'Name of the team to create',
placeholder: 'Engineering',
type: 'string',
required: true,
default: '',
displayOptions: {
show: {
resource: [
'team',
],
operation: [
'create',
],
},
},
},
{
displayName: 'Additional Fields',
name: 'additionalFields',
type: 'collection',
placeholder: 'Add Field',
default: {},
displayOptions: {
show: {
resource: [
'team',
],
operation: [
'create',
],
},
},
options: [
{
displayName: 'Email',
name: 'email',
type: 'string',
placeholder: 'engineering@n8n.io',
default: '',
description: 'Email of the team to create',
},
],
},
// ----------------------------------------
// team: delete
// ----------------------------------------
{
displayName: 'Team ID',
name: 'teamId',
description: 'ID of the team to delete',
type: 'string',
required: true,
default: '',
displayOptions: {
show: {
resource: [
'team',
],
operation: [
'delete',
],
},
},
},
// ----------------------------------------
// team: get
// ----------------------------------------
{
displayName: 'Team ID',
name: 'teamId',
description: 'ID of the team to retrieve',
type: 'string',
required: true,
default: '',
displayOptions: {
show: {
resource: [
'team',
],
operation: [
'get',
],
},
},
},
// ----------------------------------------
// team: getAll
// ----------------------------------------
{
displayName: 'Return All',
name: 'returnAll',
type: 'boolean',
default: false,
description: 'Whether to return all results or only up to a given limit',
displayOptions: {
show: {
resource: [
'team',
],
operation: [
'getAll',
],
},
},
},
{
displayName: 'Limit',
name: 'limit',
type: 'number',
default: 50,
description: 'Max number of results to return',
typeOptions: {
minValue: 1,
},
displayOptions: {
show: {
resource: [
'team',
],
operation: [
'getAll',
],
returnAll: [
false,
],
},
},
},
{
displayName: 'Filters',
name: 'filters',
type: 'collection',
placeholder: 'Add Filter',
default: {},
displayOptions: {
show: {
resource: [
'team',
],
operation: [
'getAll',
],
},
},
options: [
{
displayName: 'Name',
name: 'name',
type: 'string',
default: '',
description: 'Name of the team to filter by',
},
],
},
// ----------------------------------------
// team: update
// ----------------------------------------
{
displayName: 'Team ID',
name: 'teamId',
description: 'ID of the team to update',
type: 'string',
required: true,
default: '',
displayOptions: {
show: {
resource: [
'team',
],
operation: [
'update',
],
},
},
},
{
displayName: 'Update Fields',
name: 'updateFields',
type: 'collection',
placeholder: 'Add Field',
default: {},
displayOptions: {
show: {
resource: [
'team',
],
operation: [
'update',
],
},
},
options: [
{
displayName: 'Email',
name: 'email',
type: 'string',
placeholder: 'engineering@n8n.io',
default: '',
description: 'Email of the team to update',
},
{
displayName: 'Name',
name: 'name',
type: 'string',
placeholder: 'Engineering Team',
default: '',
description: 'Name of the team to update',
},
],
},
];

View file

@ -0,0 +1,196 @@
import {
INodeProperties,
} from 'n8n-workflow';
export const teamMemberOperations: INodeProperties[] = [
{
displayName: 'Operation',
name: 'operation',
type: 'options',
noDataExpression: true,
displayOptions: {
show: {
resource: [
'teamMember',
],
},
},
options: [
{
name: 'Add',
value: 'add',
description: 'Add a member to a team',
},
{
name: 'Get All',
value: 'getAll',
description: 'Retrieve all team members',
},
{
name: 'Remove',
value: 'remove',
description: 'Remove a member from a team',
},
],
default: 'add',
},
];
export const teamMemberFields: INodeProperties[] = [
// ----------------------------------------
// teamMember: add
// ----------------------------------------
{
displayName: 'User Name or ID',
name: 'userId',
description: 'User to add to a team. Choose a name from the list, or specify an ID using an <a href="https://docs.n8n.io/nodes/expressions.html#expressions">expression</a>.',
type: 'options',
required: true,
default: '',
typeOptions: {
loadOptionsMethod: 'getUsers',
},
displayOptions: {
show: {
resource: [
'teamMember',
],
operation: [
'add',
],
},
},
},
{
displayName: 'Team Name or ID',
name: 'teamId',
description: 'Team to add the user to. Choose a name from the list, or specify an ID using an <a href="https://docs.n8n.io/nodes/expressions.html#expressions">expression</a>.',
type: 'options',
required: true,
default: '',
typeOptions: {
loadOptionsMethod: 'getTeams',
},
displayOptions: {
show: {
resource: [
'teamMember',
],
operation: [
'add',
],
},
},
},
// ----------------------------------------
// teamMember: remove
// ----------------------------------------
{
displayName: 'User Name or ID',
name: 'memberId',
description: 'User to remove from the team. Choose a name from the list, or specify an ID using an <a href="https://docs.n8n.io/nodes/expressions.html#expressions">expression</a>.',
type: 'options',
required: true,
default: '',
typeOptions: {
loadOptionsMethod: 'getUsers',
},
displayOptions: {
show: {
resource: [
'teamMember',
],
operation: [
'remove',
],
},
},
},
{
displayName: 'Team Name or ID',
name: 'teamId',
description: 'Team to remove the user from. Choose a name from the list, or specify an ID using an <a href="https://docs.n8n.io/nodes/expressions.html#expressions">expression</a>.',
type: 'options',
required: true,
default: '',
typeOptions: {
loadOptionsMethod: 'getTeams',
},
displayOptions: {
show: {
resource: [
'teamMember',
],
operation: [
'remove',
],
},
},
},
// ----------------------------------------
// teamMember: getAll
// ----------------------------------------
{
displayName: 'Team Name or ID',
name: 'teamId',
description: 'Team to retrieve all members from. Choose a name from the list, or specify an ID using an <a href="https://docs.n8n.io/nodes/expressions.html#expressions">expression</a>.',
typeOptions: {
loadOptionsMethod: 'getTeams',
},
type: 'options',
required: true,
default: '',
displayOptions: {
show: {
resource: [
'teamMember',
],
operation: [
'getAll',
],
},
},
},
{
displayName: 'Return All',
name: 'returnAll',
type: 'boolean',
default: false,
description: 'Whether to return all results or only up to a given limit',
displayOptions: {
show: {
resource: [
'teamMember',
],
operation: [
'getAll',
],
},
},
},
{
displayName: 'Limit',
name: 'limit',
type: 'number',
default: 50,
description: 'Max number of results to return',
typeOptions: {
minValue: 1,
},
displayOptions: {
show: {
resource: [
'teamMember',
],
operation: [
'getAll',
],
returnAll: [
false,
],
},
},
},
];

View file

@ -0,0 +1,167 @@
import {
INodeProperties,
} from 'n8n-workflow';
export const userOperations: INodeProperties[] = [
{
displayName: 'Operation',
name: 'operation',
type: 'options',
noDataExpression: true,
displayOptions: {
show: {
resource: [
'user',
],
},
},
options: [
{
name: 'Delete',
value: 'delete',
description: 'Delete a user from the current organization',
},
{
name: 'Get All',
value: 'getAll',
description: 'Retrieve all users in the current organization',
},
{
name: 'Update',
value: 'update',
description: 'Update a user in the current organization',
},
],
default: 'getAll',
},
];
export const userFields: INodeProperties[] = [
// ----------------------------------------
// user: update
// ----------------------------------------
{
displayName: 'User ID',
name: 'userId',
description: 'ID of the user to update',
type: 'string',
required: true,
default: '',
displayOptions: {
show: {
resource: [
'user',
],
operation: [
'update',
],
},
},
},
{
displayName: 'Update Fields',
name: 'updateFields',
type: 'collection',
placeholder: 'Add Field',
default: {},
displayOptions: {
show: {
resource: [
'user',
],
operation: [
'update',
],
},
},
options: [
{
displayName: 'Role',
name: 'role',
type: 'options',
default: 'Admin',
description: 'New role for the user',
options: [
{
name: 'Admin',
value: 'Admin',
},
{
name: 'Editor',
value: 'Editor',
},
{
name: 'Viewer',
value: 'Viewer',
},
],
},
],
},
// ----------------------------------------
// user: delete
// ----------------------------------------
{
displayName: 'User ID',
name: 'userId',
description: 'ID of the user to delete',
type: 'string',
required: true,
default: '',
displayOptions: {
show: {
resource: [
'user',
],
operation: [
'delete',
],
},
},
},
// ----------------------------------------
// user: getAll
// ----------------------------------------
{
displayName: 'Return All',
name: 'returnAll',
type: 'boolean',
default: false,
description: 'Whether to return all results or only up to a given limit',
displayOptions: {
show: {
resource: [
'user',
],
operation: [
'getAll',
],
},
},
},
{
displayName: 'Limit',
name: 'limit',
type: 'number',
default: 50,
description: 'Max number of results to return',
typeOptions: {
minValue: 1,
},
displayOptions: {
show: {
resource: [
'user',
],
operation: [
'getAll',
],
returnAll: [
false,
],
},
},
},
];

View file

@ -0,0 +1,4 @@
export * from './DashboardDescription';
export * from './TeamDescription';
export * from './TeamMemberDescription';
export * from './UserDescription';

File diff suppressed because one or more lines are too long

After

Width:  |  Height:  |  Size: 10 KiB

View file

@ -0,0 +1,36 @@
export type GrafanaCredentials = {
apiKey: string;
baseUrl: string;
};
export type DashboardUpdatePayload = {
overwrite: true,
dashboard: {
uid: string,
title?: string
}
};
export type DashboardUpdateFields = {
title?: string;
folderId?: string;
};
export type LoadedDashboards = Array<{
id: number;
title: string;
}>;
export type LoadedFolders = LoadedDashboards;
export type LoadedTeams = {
teams: Array<{
id: number;
name: string;
}>
};
export type LoadedUsers = Array<{
userId: number;
email: string;
}>;

View file

@ -104,7 +104,7 @@ export class HtmlExtract implements INodeType {
},
default: 'data',
required: true,
description: 'Name of the json property in which the HTML to extract the data from can be found.<br />The property can either contain a string or an array of strings.',
description: 'Name of the json property in which the HTML to extract the data from can be found. The property can either contain a string or an array of strings.',
},
{
displayName: 'Extraction Values',

View file

@ -436,9 +436,7 @@ export class HttpRequest implements INodeType {
],
},
},
description: `Name of the binary property which contains the data for the file to be uploaded.<br />
For Form-Data Multipart, multiple can be provided in the format:<br />
"sendKey1:binaryProperty1,sendKey2:binaryProperty2`,
description: `Name of the binary property which contains the data for the file to be uploaded. For Form-Data Multipart, they can be provided in the format: <code>"sendKey1:binaryProperty1,sendKey2:binaryProperty2</code>`,
},
{
displayName: 'Body Parameters',
@ -772,7 +770,7 @@ export class HttpRequest implements INodeType {
propertyName = propertyDataParts[0];
binaryPropertyName = propertyDataParts[1];
} else if (binaryPropertyNames.length > 1) {
throw new NodeOperationError(this.getNode(), 'If more than one property should be send it is needed to define the in the format: "sendKey1:binaryProperty1,sendKey2:binaryProperty2"');
throw new NodeOperationError(this.getNode(), 'If more than one property should be send it is needed to define the in the format:<code>"sendKey1:binaryProperty1,sendKey2:binaryProperty2"</code>');
}
if (item.binary[binaryPropertyName] === undefined) {

View file

@ -896,18 +896,14 @@ export const companyFields = [
loadOptionsMethod: 'getCompanyProperties',
},
default: '',
description: `Used to include specific company properties in the results.<br/>
By default, the results will only include company ID and will not include the values for any properties for your companys.<br/>
Including this parameter will include the data for the specified property in the results.<br/>
You can include this parameter multiple times to request multiple properties separed by ,.`,
description: `<p>Used to include specific company properties in the results. By default, the results will only include company ID and will not include the values for any properties for your companies.</p><p>Including this parameter will include the data for the specified property in the results. You can include this parameter multiple times to request multiple properties separated by a comma: <code>,</code>.</p>`,
},
{
displayName: 'Properties With History',
name: 'propertiesWithHistory',
type: 'string',
default: '',
description: `Works similarly to properties=, but this parameter will include the history for the specified property,
instead of just including the current value. Use this parameter when you need the full history of changes to a property's value.`,
description: `Works similarly to properties=, but this parameter will include the history for the specified property, instead of just including the current value. Use this parameter when you need the full history of changes to a property's value.`,
},
],
},
@ -1009,8 +1005,7 @@ export const companyFields = [
name: 'includePropertyVersions',
type: 'boolean',
default: false,
description: `By default, you will only get data for the most recent version of a property in the "versions" data.<br/>
If you include this parameter, you will get data for all previous versions.`,
description: `By default, you will only get data for the most recent version of a property in the "versions" data. If you include this parameter, you will get data for all previous versions.`,
},
],
},
@ -1101,10 +1096,7 @@ export const companyFields = [
loadOptionsMethod: 'getCompanyProperties',
},
default: '',
description: `Used to include specific company properties in the results.<br/>
By default, the results will only include company ID and will not include the values for any properties for your companys.<br/>
Including this parameter will include the data for the specified property in the results.<br/>
You can include this parameter multiple times to request multiple properties separed by ,.`,
description: `<p>Used to include specific company properties in the results. By default, the results will only include company ID and will not include the values for any properties for your company.</p><p>Including this parameter will include the data for the specified property in the results. You can include this parameter multiple times to request multiple properties separated by a comma: <code>,</code>.</p>`,
},
],
},

View file

@ -397,10 +397,7 @@ export const contactFields = [
},
},
default: '',
description: `Used to include specific company properties in the results.<br/>
By default, the results will only include company ID and will not include the values for any properties for your companys.<br/>
Including this parameter will include the data for the specified property in the results.<br/>
You can include this parameter multiple times to request multiple properties separed by ,.`,
description: `<p>Used to include specific company properties in the results. By default, the results will only include company ID and will not include the values for any properties for your company.</p><p>Including this parameter will include the data for the specified property in the results. You can include this parameter multiple times to request multiple properties separated by a comma: <code>,</code>.</p>`,
},
{
displayName: 'Postal Code',
@ -580,10 +577,7 @@ export const contactFields = [
loadOptionsMethod: 'getContactProperties',
},
default: '',
description: `Used to include specific company properties in the results.<br/>
By default, the results will only include company ID and will not include the values for any properties for your companys.<br/>
Including this parameter will include the data for the specified property in the results.<br/>
You can include this parameter multiple times to request multiple properties separed by ,.`,
description: `<p>Used to include specific company properties in the results. By default, the results will only include company ID and will not include the values for any properties for your company.</p><p>Including this parameter will include the data for the specified property in the results. You can include this parameter multiple times to request multiple properties separated by a comma: <code>,</code>.</p>`,
},
{
displayName: 'Property Mode',
@ -706,10 +700,7 @@ export const contactFields = [
loadOptionsMethod: 'getContactProperties',
},
default: '',
description: `Used to include specific company properties in the results.<br/>
By default, the results will only include company ID and will not include the values for any properties for your companys.<br/>
Including this parameter will include the data for the specified property in the results.<br/>
You can include this parameter multiple times to request multiple properties separed by ,.`,
description: `<p>Used to include specific company properties in the results. By default, the results will only include company ID and will not include the values for any properties for your company.</p><p>Including this parameter will include the data for the specified property in the results. You can include this parameter multiple times to request multiple properties separated by a comma: <code>,</code>.</p>`,
},
{
displayName: 'Property Mode',
@ -854,10 +845,7 @@ export const contactFields = [
loadOptionsMethod: 'getContactProperties',
},
default: '',
description: `Used to include specific company properties in the results.<br/>
By default, the results will only include company ID and will not include the values for any properties for your companys.<br/>
Including this parameter will include the data for the specified property in the results.<br/>
You can include this parameter multiple times to request multiple properties separed by ,.`,
description: `<p>Used to include specific company properties in the results. By default, the results will only include company ID and will not include the values for any properties for your company.</p><p>Including this parameter will include the data for the specified property in the results. You can include this parameter multiple times to request multiple properties separated by a comma: <code>,</code>.</p>`,
},
{
displayName: 'Property Mode',
@ -1042,10 +1030,7 @@ export const contactFields = [
],
},
],
description: `When multiple filters are provided within a filterGroup, they will be combined using a logical AND operator.<br>
When multiple filterGroups are provided, they will be combined using a logical OR operator.<br>
The system supports a maximum of three filterGroups with up to three filters each.<br>
More info <a href="https://developers.hubspot.com/docs/api/crm/search">here</a>`,
description: `When multiple filters are provided within a filterGroup, they will be combined using a logical AND operator. When multiple filterGroups are provided, they will be combined using a logical OR operator. The system supports a maximum of three filterGroups with up to three filters each. More info <a href="https://developers.hubspot.com/docs/api/crm/search">here</a>`,
},
{
displayName: 'Additional Fields',
@ -1093,10 +1078,7 @@ export const contactFields = [
'lastname',
'email',
],
description: `Used to include specific company properties in the results.<br/>
By default, the results will only include company ID and will not include the values for any properties for your companys.<br/>
Including this parameter will include the data for the specified property in the results.<br/>
You can include this parameter multiple times to request multiple properties separed by ,.`,
description: `<p>Used to include specific company properties in the results. By default, the results will only include company ID and will not include the values for any properties for your company.</p><p>Including this parameter will include the data for the specified property in the results. You can include this parameter multiple times to request multiple properties separated by a comma: <code>,</code>.</p>`,
},
{
displayName: 'Query',

View file

@ -369,8 +369,7 @@ export const dealFields = [
name: 'includePropertyVersions',
type: 'boolean',
default: false,
description: `By default, you will only get data for the most recent version of a property in the "versions" data.<br/>
If you include this parameter, you will get data for all previous versions.`,
description: `By default, you will only get data for the most recent version of a property in the "versions" data. If you include this parameter, you will get data for all previous versions.`,
},
],
},
@ -452,10 +451,7 @@ export const dealFields = [
loadOptionsMethod: 'getDealProperties',
},
default: [],
description: `Used to include specific deal properties in the results.<br/>
By default, the results will only include Deal ID and will not include the values for any properties for your Deals.<br/>
Including this parameter will include the data for the specified property in the results.<br/>
You can include this parameter multiple times to request multiple properties separed by ,.`,
description: `<p>Used to include specific deal properties in the results. By default, the results will only include Deal ID and will not include the values for any properties for your Deals.</p><p>Including this parameter will include the data for the specified property in the results. You can include this parameter multiple times to request multiple properties separated by a comma: <code>,</code>.</p>`,
},
{
displayName: 'Properties With History',
@ -465,8 +461,7 @@ export const dealFields = [
loadOptionsMethod: 'getDealProperties',
},
default: [],
description: `Works similarly to properties=, but this parameter will include the history for the specified property,
instead of just including the current value. Use this parameter when you need the full history of changes to a property's value.`,
description: `Works similarly to properties=, but this parameter will include the history for the specified property, instead of just including the current value. Use this parameter when you need the full history of changes to a property's value.`,
},
],
@ -570,8 +565,7 @@ export const dealFields = [
name: 'includePropertyVersions',
type: 'boolean',
default: false,
description: `By default, you will only get data for the most recent version of a property in the "versions" data.<br/>
If you include this parameter, you will get data for all previous versions.`,
description: `By default, you will only get data for the most recent version of a property in the "versions" data. If you include this parameter, you will get data for all previous versions.`,
},
],
},
@ -739,10 +733,7 @@ export const dealFields = [
],
},
],
description: `When multiple filters are provided within a filterGroup, they will be combined using a logical AND operator.<br>
When multiple filterGroups are provided, they will be combined using a logical OR operator.<br>
The system supports a maximum of three filterGroups with up to three filters each.<br>
More info <a href="https://developers.hubspot.com/docs/api/crm/search">here</a>`,
description: `When multiple filters are provided within a filterGroup, they will be combined using a logical AND operator. When multiple filterGroups are provided, they will be combined using a logical OR operator. The system supports a maximum of three filterGroups with up to three filters each. More info <a href="https://developers.hubspot.com/docs/api/crm/search">here</a>`,
},
{
displayName: 'Additional Fields',
@ -786,10 +777,7 @@ export const dealFields = [
loadOptionsMethod: 'getDealProperties',
},
default: [],
description: `Used to include specific deal properties in the results.<br/>
By default, the results will only include Deal ID and will not include the values for any properties for your companys.<br/>
Including this parameter will include the data for the specified property in the results.<br/>
You can include this parameter multiple times to request multiple properties separed by ,.`,
description: `<p>Used to include specific deal properties in the results. By default, the results will only include Deal ID and will not include the values for any properties for your company.</p><p>Including this parameter will include the data for the specified property in the results. You can include this parameter multiple times to request multiple properties separated by a comma: <code>,</code>.</p>`,
},
{
displayName: 'Query',

View file

@ -154,16 +154,14 @@ export const formFields = [
name: 'sfdcCampaignId',
type: 'string',
default: '',
description: `If the form is for an account using the HubSpot Salesforce Integration,</br>
you can include the ID of a Salesforce campaign to add the contact to the specified campaign.`,
description: `If the form is for an account using the HubSpot Salesforce Integration, you can include the ID of a Salesforce campaign to add the contact to the specified campaign.`,
},
{
displayName: 'Go to Webinar Webinar ID',
name: 'goToWebinarWebinarKey',
type: 'string',
default: '',
description: `If the form is for an account using the HubSpot GoToWebinar Integration,</br>
you can include the ID of a webinar to enroll the contact in that webinar when they submit the form.`,
description: `If the form is for an account using the HubSpot GoToWebinar Integration, you can include the ID of a webinar to enroll the contact in that webinar when they submit the form.`,
},
],
},
@ -270,8 +268,7 @@ export const formFields = [
name: 'value',
type: 'boolean',
default: false,
description: `This must be true when using the 'legitimateInterest' option, as it reflects</br>
the consent indicated by the visitor when submitting the form`,
description: `This must be true when using the 'legitimateInterest' option, as it reflects the consent indicated by the visitor when submitting the form`,
},
{
displayName: 'Legal Basis',

View file

@ -223,8 +223,7 @@ export const ticketFields = [
loadOptionsMethod: 'getOwners',
},
default: '',
description: `The user from your team that the ticket is assigned to.</br>
You can assign additional users to a ticket record by creating a custom HubSpot user property`,
description: `The user from your team that the ticket is assigned to. You can assign additional users to a ticket record by creating a custom HubSpot user property`,
},
],
},
@ -375,8 +374,7 @@ export const ticketFields = [
loadOptionsMethod: 'getOwners',
},
default: '',
description: `The user from your team that the ticket is assigned to.</br>
You can assign additional users to a ticket record by creating a custom HubSpot user property`,
description: `The user from your team that the ticket is assigned to. You can assign additional users to a ticket record by creating a custom HubSpot user property`,
},
],
},
@ -433,18 +431,14 @@ export const ticketFields = [
loadOptionsMethod: 'getTicketProperties',
},
default: [],
description: `Used to include specific ticket properties in the results.<br/>
By default, the results will only include ticket ID and will not include the values for any properties for your tickets.<br/>
Including this parameter will include the data for the specified property in the results.<br/>
You can include this parameter multiple times to request multiple properties separed by ,.`,
description: `<p>Used to include specific ticket properties in the results. By default, the results will only include ticket ID and will not include the values for any properties for your tickets.</p><p>Including this parameter will include the data for the specified property in the results. You can include this parameter multiple times to request multiple properties separated by a comma: <code>,</code>.</p>`,
},
{
displayName: 'Properties With History',
name: 'propertiesWithHistory',
type: 'string',
default: '',
description: `Works similarly to properties=, but this parameter will include the history for the specified property,
instead of just including the current value. Use this parameter when you need the full history of changes to a property's value.`,
description: `Works similarly to properties=, but this parameter will include the history for the specified property, instead of just including the current value. Use this parameter when you need the full history of changes to a property's value.`,
},
],
},
@ -518,18 +512,14 @@ export const ticketFields = [
loadOptionsMethod: 'getTicketProperties',
},
default: [],
description: `Used to include specific ticket properties in the results.<br/>
By default, the results will only include ticket ID and will not include the values for any properties for your tickets.<br/>
Including this parameter will include the data for the specified property in the results.<br/>
You can include this parameter multiple times to request multiple properties separed by ,.`,
description: `<p>Used to include specific ticket properties in the results. By default, the results will only include ticket ID and will not include the values for any properties for your company.</p><p>Including this parameter will include the data for the specified property in the results. You can include this parameter multiple times to request multiple properties separated by a comma: <code>,</code>.</p>`,
},
{
displayName: 'Properties With History',
name: 'propertiesWithHistory',
type: 'string',
default: '',
description: `Works similarly to properties=, but this parameter will include the history for the specified property,
instead of just including the current value. Use this parameter when you need the full history of changes to a property's value.`,
description: `Works similarly to properties=, but this parameter will include the history for the specified property, instead of just including the current value. Use this parameter when you need the full history of changes to a property's value.`,
},
],
},

View file

@ -149,8 +149,7 @@ export const profileFields = [
},
],
default: [],
description: `Fetch the Humantic profile of the user for a particular persona type.<br>
Multiple persona values can be supported using comma as a delimiter.`,
description: `Fetch the Humantic profile of the user for a particular persona type. Multiple persona values can be supported using comma as a delimiter.`,
},
],
},

View file

@ -15,6 +15,7 @@ export class Interval implements INodeType {
group: ['trigger'],
version: 1,
description: 'Triggers the workflow in a given interval',
eventTriggerDescription: '',
defaults: {
name: 'Interval',
color: '#00FF00',

View file

@ -161,9 +161,7 @@ export const userFields = [
name: 'mergeNestedObjects',
type: 'boolean',
default: false,
description: `Merge top level objects instead of overwriting (default: false).<br>
e.g. if user profile has data: {mySettings:{mobile:true}} and change contact field has data: {mySettings:{email:true}},<br>
the resulting profile: {mySettings:{mobile:true,email:true}}`,
description: `Merge top level objects instead of overwriting (default: false), e.g. if user profile has data: {mySettings:{mobile:true}} and change contact field has data: {mySettings:{email:true}}, the resulting profile: {mySettings:{mobile:true,email:true}}`,
},
],
},

View file

@ -550,52 +550,37 @@ export const issueFields = [
name: 'expand',
type: 'string',
default: '',
description: `Use expand to include additional information about the issues in the response.<br/>
This parameter accepts a comma-separated list. Expand options include:<br/>
renderedFields Returns field values rendered in HTML format.<br/>
names Returns the display name of each field.<br/>
schema Returns the schema describing a field type.<br/>
transitions Returns all possible transitions for the issue.<br/>
editmeta Returns information about how each field can be edited.<br/>
changelog Returns a list of recent updates to an issue, sorted by date, starting from the most recent.<br/>
versionedRepresentations Returns a JSON array for each version of a field's value, with the highest number
representing the most recent version. Note: When included in the request, the fields parameter is ignored.`,
description: `<p>Use expand to include additional information about the issues in the response. This parameter accepts a comma-separated list. Expand options include:
<ul>
<li><code>renderedFields</code> Returns field values rendered in HTML format.</li>
<li><code>names</code> Returns the display name of each field.</li>
<li><code>schema</code> Returns the schema describing a field type.</li>
<li><code>transitions</code> Returns all possible transitions for the issue.</li>
<li><code>editmeta</code> Returns information about how each field can be edited.</li>
<li><code>changelog</code> Returns a list of recent updates to an issue, sorted by date, starting from the most recent.</li>
<li><code>versionedRepresentations</code> Returns a JSON array for each version of a field's value, with the highest number representing the most recent version. Note: When included in the request, the fields parameter is ignored.</li>
</ul>`,
},
{
displayName: 'Fields',
name: 'fields',
type: 'string',
default: '',
description: `A list of fields to return for the issue.<br/>
This parameter accepts a comma-separated list.<br/>
Use it to retrieve a subset of fields. Allowed values:<br/>
*all Returns all fields.<br/>
*navigable Returns navigable fields.<br/>
Any issue field, prefixed with a minus to exclude.<br/>`,
description: `A list of fields to return for the issue. This parameter accepts a comma-separated list. Use it to retrieve a subset of fields. Allowed values: <code>*all</code> Returns all fields. <code>*navigable</code> Returns navigable fields. Any issue field, prefixed with a minus to exclude.`,
},
{
displayName: 'Fields By Key',
name: 'fieldsByKey',
type: 'boolean',
default: false,
description: `Indicates whether fields in fields are referenced by keys rather than IDs.<br/>
This parameter is useful where fields have been added by a connect app and a field's key
may differ from its ID.`,
description: `Indicates whether fields in fields are referenced by keys rather than IDs. This parameter is useful where fields have been added by a connect app and a field's key may differ from its ID.`,
},
{
displayName: 'Properties',
name: 'properties',
type: 'string',
default: '',
description: `A list of issue properties to return for the issue.<br/>
This parameter accepts a comma-separated list. Allowed values:<br/>
*all Returns all issue properties.<br/>
Any issue property key, prefixed with a minus to exclude.<br/>
Examples:<br/>
*all Returns all properties.<br/>
*all,-prop1 Returns all properties except prop1.<br/>
prop1,prop2 Returns prop1 and prop2 properties.<br/>
This parameter may be specified multiple times. For example, properties=prop1,prop2& properties=prop3.`,
description: `A list of issue properties to return for the issue. This parameter accepts a comma-separated list. Allowed values: <code>*all</code> Returns all issue properties. Any issue property key, prefixed with a minus to exclude. Examples: <code>*all</code> Returns all properties. <code>*all</code>,-prop1 Returns all properties except prop1. <code>prop1,prop2</code> Returns prop1 and prop2 properties. This parameter may be specified multiple times. For example, properties=prop1,prop2& properties=prop3.`,
},
{
displayName: 'Update History',
@ -724,19 +709,14 @@ export const issueFields = [
name: 'fields',
type: 'string',
default: '*navigable',
description: `A list of fields to return for each issue, use it to retrieve a subset of fields. This parameter accepts a comma-separated list. Expand options include:<br/>
*all Returns all fields.<br/>
*navigable Returns navigable fields.<br/>
Any issue field, prefixed with a minus to exclude.<br/>`,
description: `A list of fields to return for each issue, use it to retrieve a subset of fields. This parameter accepts a comma-separated list. Expand options include: <code>*all</code> Returns all fields. <code>*navigable</code> Returns navigable fields. Any issue field, prefixed with a minus to exclude.`,
},
{
displayName: 'Fields By Key',
name: 'fieldsByKey',
type: 'boolean',
default: false,
description: `Indicates whether fields in fields are referenced by keys rather than IDs.<br/>
This parameter is useful where fields have been added by a connect app and a field's key
may differ from its ID.`,
description: `Indicates whether fields in fields are referenced by keys rather than IDs. This parameter is useful where fields have been added by a connect app and a field's key may differ from its ID.`,
},
{
displayName: ' JQL',
@ -1122,10 +1102,7 @@ export const issueFields = [
name: 'expand',
type: 'string',
default: '',
description: `Use expand to include additional information about transitions in the response.<br/>
This parameter accepts transitions.fields, which returns information about the fields in the
transition screen for each transition. Fields hidden from the screen are not returned. Use this
information to populate the fields and update fields in Transition issue.`,
description: `Use expand to include additional information about transitions in the response. This parameter accepts transitions.fields, which returns information about the fields in the transition screen for each transition. Fields hidden from the screen are not returned. Use this information to populate the fields and update fields in Transition issue.`,
},
{
displayName: 'Transition ID',

View file

@ -69,7 +69,7 @@ export class JotFormTrigger implements INodeType {
name: 'resolveData',
type: 'boolean',
default: true,
description: 'By default does the webhook-data use internal keys instead of the names.<br />If this option gets activated, it will resolve the keys automatically to the actual names.',
description: 'By default does the webhook-data use internal keys instead of the names. If this option gets activated, it will resolve the keys automatically to the actual names.',
},
{
displayName: 'Only Answers',

View file

@ -366,8 +366,7 @@ export const companyFields = [
name: 'fields',
type: 'string',
default: '',
description: `Comma-delimited list of Company properties to include in the response.</br>
(Fields such as notes, fax_number and custom_fields aren't included, by default.)`,
description: `Comma-delimited list of Company properties to include in the response. (Fields such as notes, fax_number and custom_fields aren't included, by default.)`,
},
],
},

View file

@ -72,8 +72,7 @@ export const contactFields = [
},
},
default: 'email',
description: `Performs duplicate checking by one of the following options: Email, EmailAndName,</br>
if a match is found using the option provided, the existing contact will be updated`,
description: `Performs duplicate checking by one of the following options: Email, EmailAndName. If a match is found using the option provided, the existing contact will be updated`,
},
{
displayName: 'Additional Fields',
@ -616,8 +615,7 @@ export const contactFields = [
name: 'fields',
type: 'string',
default: '',
description: `Comma-delimited list of Contact properties to include in the response.</br>
(Some fields such as lead_source_id, custom_fields, and job_title aren't included, by default.)`,
description: `Comma-delimited list of Contact properties to include in the response. (Some fields such as lead_source_id, custom_fields, and job_title aren't included, by default.)`,
},
],
},

View file

@ -155,8 +155,7 @@ export const ecommerceOrderFields = [
name: 'promoCodes',
type: 'string',
default: '',
description: `Uses multiple strings separated by comma as promo codes.</br>
The corresponding discount will be applied to the order.`,
description: `Uses multiple strings separated by comma as promo codes. The corresponding discount will be applied to the order.`,
},
{
displayName: 'Sales Affiliate ID',
@ -310,8 +309,7 @@ export const ecommerceOrderFields = [
minValue: 0,
},
default: 0,
description: `Overridable price of the product, if not specified,</br>
the default will be used.`,
description: `Overridable price of the product, if not specified, the default will be used.`,
},
{
displayName: 'Product ID',

View file

@ -156,8 +156,7 @@ export const emailFields = [
name: 'originalProviderId',
type: 'string',
default: '',
description: `Provider id that sent the email, must be unique when combined with provider.</br>
If omitted a UUID without dashes is autogenerated for the record.`,
description: `Provider id that sent the email, must be unique when combined with provider. If omitted a UUID without dashes is autogenerated for the record.`,
},
{
displayName: 'Plain Content',
@ -383,8 +382,7 @@ export const emailFields = [
name: 'addressField',
type: 'string',
default: '',
description: `Email field of each Contact record to address the email to, such as </br>
'EmailAddress1', 'EmailAddress2', 'EmailAddress3', defaulting to the contact's primary email`,
description: `Email field of each Contact record to address the email to, such as 'EmailAddress1', 'EmailAddress2', 'EmailAddress3', defaulting to the contact's primary email`,
},
{
displayName: 'HTML Content',

View file

@ -13,7 +13,7 @@ export const spaceOperations = [
{
name: 'Get All',
value: 'getAll',
description: 'Retrieve data on all the spaces in the<br>logged-in user\'s organization.',
description: `Retrieve data on all the spaces in the logged-in user's organization.`,
},
],
displayOptions: {

View file

@ -13,7 +13,7 @@ export const userOperations = [
{
name: 'Get All',
value: 'getAll',
description: 'Retrieve data on all the users in the<br>logged-in user\'s organization.',
description: `Retrieve data on all the users in the logged-in user's organization.`,
},
],
displayOptions: {

View file

@ -125,7 +125,7 @@ export const notificationFields = [
},
},
default: 'data',
description: `Name of the property that holds the binary data.<br>`,
description: `Name of the property that holds the binary data.`,
},
],
},
@ -136,8 +136,7 @@ export const notificationFields = [
name: 'notificationDisabled',
type: 'boolean',
default: false,
description: `true: The user doesn't receive a push notification when the message is sent.<br>
false: The user receives a push notification when the message is sent`,
description: `<p>true: The user doesn't receive a push notification when the message is sent.</p><p>false: The user receives a push notification when the message is sent</p>`,
},
{
displayName: 'Sticker',

Some files were not shown because too many files have changed in this diff Show more