Page MenuHomeSealhub

No OneTemporary

diff --git a/nodes/Phabricator/Phabricator.node.ts b/nodes/Phabricator/Phabricator.node.ts
index 5962602..736a983 100644
--- a/nodes/Phabricator/Phabricator.node.ts
+++ b/nodes/Phabricator/Phabricator.node.ts
@@ -1,138 +1,146 @@
import {
IExecuteFunctions,
INodeExecutionData,
INodeType,
INodeTypeDescription,
NodeExecutionWithMetadata,
} from 'n8n-workflow';
import qs from 'qs';
import { constraints } from './constraints';
import { methods, apps, fields } from './methods';
import { short_descriptions } from './short-descriptions';
+async function runForItem(this: IExecuteFunctions, index: number): Promise<any> {
+ const { token, domain } = (await this.getCredentials('phabricatorApi')) as {
+ token: string;
+ domain: string;
+ };
+ const parameters = { ...this.getNode().parameters };
+ const { operation } = parameters;
+ for (const key in parameters) {
+ let value = parameters[key];
+ if (typeof value == 'string' && value.startsWith('=')) {
+ value = this.evaluateExpression(value, index);
+ if (typeof value == 'string' && value.startsWith('=')) {
+ value = value.slice(1);
+ }
+ }
+ if (parameters[key] == '') {
+ delete parameters[key];
+ } else if (key.startsWith('constraint_')) {
+ const actual_key = key.replace('constraint_', '');
+ if (!parameters.constraints) {
+ parameters.constraints = {};
+ }
+ (parameters.constraints as any)[actual_key] = value;
+ this.sendMessageToUI(actual_key);
+ this.sendMessageToUI(constraints[operation as string][actual_key]?.type.startsWith('list<'));
+ this.sendMessageToUI(!Array.isArray(value));
+ if (/^(Optional )?list</.test(constraints[operation as string][actual_key]?.type)) {
+ if (!Array.isArray(value)) {
+ this.sendMessageToUI('Changing to array!');
+ (parameters.constraints as any)[actual_key] = [value];
+ }
+ }
+ delete parameters[key];
+ } else {
+ parameters[key] = value;
+ }
+ }
+
+ for (const key of ['token', 'resource', 'operation']) {
+ delete parameters[key];
+ }
+ const request = {
+ url: domain + '/api/' + this.getNodeParameter('operation', index),
+ headers: {
+ 'Content-Type': 'application/x-www-form-urlencoded',
+ },
+ body: qs.stringify({ 'api.token': token, ...parameters }),
+ method: <const>'POST',
+ };
+ this.sendMessageToUI(request);
+ return this.helpers.httpRequest(request);
+}
+
export class Phabricator implements INodeType {
description: INodeTypeDescription = {
displayName: 'Phabricator',
name: 'phabricator',
icon: 'file:phabricator.svg',
group: ['transform'],
version: 1,
subtitle: '={{$parameter["operation"]}}',
description: 'Interact with Phabricator',
defaults: {
name: 'Phabricator',
},
inputs: ['main'],
outputs: ['main'],
credentials: [
{
name: 'phabricatorApi',
required: true,
},
],
properties: [
{
displayName: 'Resource',
name: 'resource',
type: 'options',
noDataExpression: true,
options: apps.map((method) => ({
name: method,
value: method,
action: method,
description: `Call ${method} Conduit method`,
})),
default: 'user.whoami',
},
...apps
.filter((app) => ['maniphest', 'transaction'].includes(app))
.map((app) => ({
displayName: 'Operation',
name: 'operation',
type: <const>'options',
noDataExpression: true,
description: 'Choose an operation',
required: true,
displayOptions: {
show: {
resource: [app],
},
},
options: Object.entries(methods)
.filter(([method_name]) => {
return method_name.startsWith(app + '.');
})
.map(([method_name, method]) => ({
name: method_name,
value: method_name,
description: method.description,
action:
method_name.split('.').slice(1).join('.') + ': ' + short_descriptions[method_name],
})),
default: Object.keys(methods).filter((method_name) =>
method_name.startsWith(app + '.'),
)[0],
})),
...fields,
],
};
- async execute(
+ async exec(
this: IExecuteFunctions,
+ index: number,
): Promise<INodeExecutionData[][] | NodeExecutionWithMetadata[][] | null> {
- const { token, domain } = (await this.getCredentials('phabricatorApi')) as {
- token: string;
- domain: string;
- };
- const parameters = { ...this.getNode().parameters };
- const { operation } = parameters;
- for (const key in parameters) {
- let value = parameters[key];
- if (typeof value == 'string' && value.startsWith('=')) {
- value = this.evaluateExpression(value, 0);
- if (typeof value == 'string' && value.startsWith('=')) {
- value = value.slice(1);
- }
- }
- if (parameters[key] == '') {
- delete parameters[key];
- } else if (key.startsWith('constraint_')) {
- const actual_key = key.replace('constraint_', '');
- if (!parameters.constraints) {
- parameters.constraints = {};
- }
- (parameters.constraints as any)[actual_key] = value;
- this.sendMessageToUI(actual_key);
- this.sendMessageToUI(
- constraints[operation as string][actual_key]?.type.startsWith('list<'),
- );
- this.sendMessageToUI(!Array.isArray(value));
- if (/^(Optional )?list</.test(constraints[operation as string][actual_key]?.type)) {
- if (!Array.isArray(value)) {
- this.sendMessageToUI('Changing to array!');
- (parameters.constraints as any)[actual_key] = [value];
- }
- }
- delete parameters[key];
- } else {
- parameters[key] = value;
- }
- }
-
- for (const key of ['token', 'resource', 'operation']) {
- delete parameters[key];
+ const items = this.getInputData();
+ const promises = [];
+ for (let i = 0; i < items.length; i++) {
+ promises.push(runForItem.bind(this)(i));
}
- const request = {
- url: domain + '/api/' + this.getNodeParameter('operation', 0),
- headers: {
- 'Content-Type': 'application/x-www-form-urlencoded',
- },
- body: qs.stringify({ 'api.token': token, ...parameters }),
- method: <const>'POST',
- };
- this.sendMessageToUI(request);
- const response = await this.helpers.httpRequest(request);
- return [this.helpers.returnJsonArray([response])];
+ const responses = await Promise.all(promises);
+ return [this.helpers.returnJsonArray(responses)];
}
}

File Metadata

Mime Type
text/x-diff
Expires
Sat, Nov 8, 12:37 (11 h, 57 m)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
1034590
Default Alt Text
(6 KB)

Event Timeline