[Self-hosted] New custom node environment variable and custom attribute

Hello everyone! I recently decided to create a custom node which is using the webhooksMethods create and delete.

My goal, at the moment of the creation, is to register the node in a third-party app and get a unique ID, so what I need to do is to get access to environments variables to understand what is the environment I am trying to connect with, and once I get the response from the client, I would like to store the value to be used in the delete method.

Here is my code:

export class CustomTrigger implements INodeType {
	description: INodeTypeDescription = {
		displayName: 'Custom Trigger',
		name: 'customTrigger',
		description: '...',
		icon: '...',
		group: ['trigger'],
		version: 1,
		defaults: {
			name: 'Custom Trigger',
			color: '...',
		},
		inputs: [],
		outputs: ['main'],
		credentials: [
			{
				name: 'myCustomCredentials',
				required: true,
			}
		],
		webhooks: [
			{
				name: 'default',
				httpMethod: 'POST',
				path: 'customTrigger',
				responseMode: 'onReceived',
			},
		],
		properties: [
			{
				displayName: 'Event Type',
				name: 'eventType',
				type: 'options',
				required: true,
				default: '',
				options: [
					{
						name: 'Option 1',
						value: 'option1',
					},
					{
						name: 'Option 2',
						value: 'option2',
					}
				],
			},
		],
	};

	webhookMethods = {
		default: {
			async checkExists(this: IHookFunctions): Promise<boolean> {
				// TODO: Check if this workflow is subscribed already to the external service
				return false;
			},
			async create(this: IHookFunctions): Promise<boolean> {
				const credentials = this.getCredentials('customCredentials');
				const webhookUrl = this.getNodeWebhookUrl('default');
				const event = this.getNodeParameter('eventType') as string;
				
                                // TODO: Subscribe to the external service and get the ID
				// TODO: Store the webhook ID so we can delete it later
				const client = platformClient({ 
					**endpoint: "https://url-of-external-service.io", // This should be read from an environment variable defined in cli/config/index**
					authorizationToken: credentials.apiKey
				})

				const newSubscription = await client.subscribeToWebhook({
					url: webhookUrl,
					eventTypes: event
				})
				
				// TODO: We need to persist the **newSubscription.id**
				return true;
			},
			async delete(this: IHookFunctions): Promise<boolean> {
                                // TODO: Similar to create but here we will remove the subscription
				return true;
			},
		},
	};

	async webhook(this: IWebhookFunctions): Promise<IWebhookResponseData> {
		const req = this.getRequestObject();
		const { body } = req as { body: IDataObject };
		return {
			workflowData: [[{ json: body }]],
		};
	}
}

So what I need to do is 1st, read an environment variable I have defined as part of cli/config/index.ts, and then I need to persist the value either, as part of the Node information or the Workflow.

How can I do this?

Hi @b3nshi! First of all, welcome to the community!

I think @RicardoE105 would be best placed to answer this question, so I have flagged this to him :slight_smile:

1 Like

First, you should not make changes to cli/config/index.ts and that is also not necessary. You can read an environment variable the same way inside of n8n than in any other Node.js application, with process.env.VARIABLE_NAME.

You can save data in the static data of a node like most Trigger-Nodes do:

const webhookData = this.getWorkflowStaticData('node');
webhookData.yourVariable = 1;

One example would be the GitHub-Trigger Node:

1 Like

Thank you so much for your answers, now the node is working as expected!

The example you shared was really helpful! I thought the way to add new env variables was via the config/index.ts just to validate before using them, but it makes sense what you said since the node is not part of the base functionality.

Glad to hear that it was helpful.

Yes, we discourage generally adding anything to the n8n-core code. That can cause potential issues and makes updating n8n more complicated.

Have fun!

1 Like