mirror of
https://github.com/n8n-io/n8n.git
synced 2026-10-12 02:19:43 +00:00
chore: Resolve master-to-3.x sync conflicts
This commit is contained in:
@@ -4,8 +4,4 @@ export const NPM_COMMUNITY_NODE_SEARCH_API_URL = 'https://api.npms.io/v2/';
|
||||
* Node-authoring API level this runtime supports, and so the highest
|
||||
* `n8nNodesApiVersion` a node may declare to be installed.
|
||||
*/
|
||||
<<<<<<< HEAD
|
||||
export const N8N_NODES_API_VERSION = 3;
|
||||
=======
|
||||
export const N8N_NODES_API_VERSION = '1.0';
|
||||
>>>>>>> 7424f0ca0452f9dc9fe4cf6627ecbf0b315ed1e3
|
||||
export const N8N_NODES_API_VERSION = '3.0';
|
||||
|
||||
@@ -2,7 +2,17 @@
|
||||
|
||||
This list shows all the versions which include breaking changes and how to upgrade.
|
||||
|
||||
<<<<<<< HEAD
|
||||
# Unreleased
|
||||
|
||||
## n8n Packages (preview)
|
||||
|
||||
Package manifest requirements now use `usedBy: [{ "kind": "workflow", "id": "workflow-id" }]`.
|
||||
The `usedByWorkflows` field is no longer supported.
|
||||
Re-export packages after upgrading.
|
||||
Regenerate existing Promotions snapshots.
|
||||
Package import errors also use `usedBy` for resource consumers.
|
||||
Update API clients to read each consumer's `kind` and `id`.
|
||||
|
||||
# 3.0.0
|
||||
|
||||
### What changed?
|
||||
@@ -68,19 +78,7 @@ The `$evaluateExpression()` helper was removed from the Code node. A Code node t
|
||||
### When is action necessary?
|
||||
|
||||
If your Code nodes call `$evaluateExpression()`. Evaluate the expression in a node field instead, for example in an Edit Fields (Set) node before the Code node, and read the result from the input item. Code nodes on a secure-mode task runner, the default since 2.0, already failed on this call.
|
||||
=======
|
||||
# Unreleased
|
||||
|
||||
## n8n Packages (preview)
|
||||
|
||||
Package manifest requirements now use `usedBy: [{ "kind": "workflow", "id": "workflow-id" }]`.
|
||||
The `usedByWorkflows` field is no longer supported.
|
||||
Re-export packages after upgrading.
|
||||
Regenerate existing Promotions snapshots.
|
||||
Package import errors also use `usedBy` for resource consumers.
|
||||
Update API clients to read each consumer's `kind` and `id`.
|
||||
|
||||
>>>>>>> 7424f0ca0452f9dc9fe4cf6627ecbf0b315ed1e3
|
||||
# 2.0.0
|
||||
|
||||
### What changed?
|
||||
|
||||
@@ -196,16 +196,8 @@ export class N8nPackagesService {
|
||||
const dependencyPolicy = request.dependencyPolicy ?? ExportDependencyPolicy.Fail;
|
||||
const isReferenceOnly = dependencyPolicy === ExportDependencyPolicy.ReferenceOnly;
|
||||
|
||||
<<<<<<< HEAD
|
||||
const workflowIds = request.workflowIds ?? [];
|
||||
const folderIds = request.folderIds ?? [];
|
||||
const projectIds = request.projectIds ?? [];
|
||||
const includeTags = request.includeTags ?? true;
|
||||
const workflowVersionPolicy = request.workflowVersionPolicy ?? WorkflowVersionPolicy.Latest;
|
||||
=======
|
||||
const includeTags = (request.includeTags ?? true) && !this.globalConfig.tags.disabled;
|
||||
const versionPolicy = request.versionPolicy ?? ExportVersionPolicy.Latest;
|
||||
>>>>>>> 7424f0ca0452f9dc9fe4cf6627ecbf0b315ed1e3
|
||||
const credentialExportPolicy =
|
||||
request.credentialExportPolicy ?? CredentialExportPolicy.ExpressionValuesOnly;
|
||||
const includeArchivedWorkflows = request.includeArchivedWorkflows ?? false;
|
||||
|
||||
@@ -27,8 +27,12 @@ describe('inline sub-workflow with a deprecated node', () => {
|
||||
'n8n-nodes-base.manualTrigger',
|
||||
'n8n-nodes-base.executeWorkflow',
|
||||
'n8n-nodes-base.executeWorkflowTrigger',
|
||||
'n8n-nodes-base.function',
|
||||
]);
|
||||
const deprecatedNode = utils.createDeprecatedNodeType('n8n-nodes-base.function');
|
||||
deprecatedNode.description.inputs = [NodeConnectionTypes.Main];
|
||||
deprecatedNode.description.outputs = [NodeConnectionTypes.Main];
|
||||
deprecatedNode.execute = async () => [[{ json: { ran: 'function' } }]];
|
||||
nodeTypes['n8n-nodes-base.function'] = { type: deprecatedNode, sourcePath: '' };
|
||||
|
||||
await utils.initNodeTypes(nodeTypes);
|
||||
await utils.initBinaryDataService();
|
||||
|
||||
@@ -16,8 +16,6 @@ import { HttpBasicAuth } from 'n8n-nodes-base/credentials/HttpBasicAuth.credenti
|
||||
import { HttpHeaderAuth } from 'n8n-nodes-base/credentials/HttpHeaderAuth.credentials';
|
||||
import { OpenAiApi } from 'n8n-nodes-base/credentials/OpenAiApi.credentials';
|
||||
import { FormTrigger } from 'n8n-nodes-base/nodes/Form/FormTrigger.node';
|
||||
import { Function as FunctionNode } from 'n8n-nodes-base/nodes/Function/Function.node';
|
||||
import { FunctionItem } from 'n8n-nodes-base/nodes/FunctionItem/FunctionItem.node';
|
||||
import { ManualTrigger } from 'n8n-nodes-base/nodes/ManualTrigger/ManualTrigger.node';
|
||||
import { ScheduleTrigger } from 'n8n-nodes-base/nodes/Schedule/ScheduleTrigger.node';
|
||||
import { Set } from 'n8n-nodes-base/nodes/Set/Set.node';
|
||||
@@ -114,6 +112,15 @@ function minimalNodeType(name: string, properties: INodeProperties[] = []): INod
|
||||
};
|
||||
}
|
||||
|
||||
// Test-only definitions keep deprecation coverage after 3.x removes the legacy nodes.
|
||||
export function createDeprecatedNodeType(name: string): INodeType {
|
||||
const { type } = minimalNodeType(name, [
|
||||
{ displayName: 'Code', name: 'functionCode', type: 'string', default: '' },
|
||||
]);
|
||||
type.description.deprecated = true;
|
||||
return type as INodeType;
|
||||
}
|
||||
|
||||
function buildDefaultNodes(): INodeTypeData {
|
||||
ScheduleTrigger.prototype.trigger = async () => ({});
|
||||
return {
|
||||
@@ -140,11 +147,11 @@ function buildDefaultNodes(): INodeTypeData {
|
||||
sourcePath: '',
|
||||
},
|
||||
'n8n-nodes-base.function': {
|
||||
type: new FunctionNode(),
|
||||
type: createDeprecatedNodeType('n8n-nodes-base.function'),
|
||||
sourcePath: '',
|
||||
},
|
||||
'n8n-nodes-base.functionItem': {
|
||||
type: new FunctionItem(),
|
||||
type: createDeprecatedNodeType('n8n-nodes-base.functionItem'),
|
||||
sourcePath: '',
|
||||
},
|
||||
// Minimal mocks for node types the package-import fixtures reference at typeVersion 1.
|
||||
|
||||
@@ -33,11 +33,6 @@ const ALLOWED_KEY_EXPORTS = [
|
||||
'EXTERNAL_SECRETS_PROVIDER_MODAL_KEY',
|
||||
'FROM_AI_PARAMETERS_MODAL_KEY',
|
||||
'IMPORT_CURL_MODAL_KEY',
|
||||
<<<<<<< HEAD
|
||||
'LOG_STREAM_MODAL_KEY',
|
||||
=======
|
||||
'IMPORT_WORKFLOW_URL_MODAL_KEY',
|
||||
>>>>>>> 7424f0ca0452f9dc9fe4cf6627ecbf0b315ed1e3
|
||||
'MIGRATE_WORKFLOW_MODAL_KEY',
|
||||
'NEW_ASSISTANT_SESSION_MODAL',
|
||||
'NPS_SURVEY_MODAL_KEY',
|
||||
|
||||
@@ -9,11 +9,6 @@ import {
|
||||
DELETE_SECRETS_PROVIDER_MODAL_KEY,
|
||||
FROM_AI_PARAMETERS_MODAL_KEY,
|
||||
IMPORT_CURL_MODAL_KEY,
|
||||
<<<<<<< HEAD
|
||||
LOG_STREAM_MODAL_KEY,
|
||||
=======
|
||||
IMPORT_WORKFLOW_URL_MODAL_KEY,
|
||||
>>>>>>> 7424f0ca0452f9dc9fe4cf6627ecbf0b315ed1e3
|
||||
VERSIONS_MODAL_KEY,
|
||||
NEW_ASSISTANT_SESSION_MODAL,
|
||||
NPS_SURVEY_MODAL_KEY,
|
||||
|
||||
@@ -12,11 +12,6 @@ import {
|
||||
EXTERNAL_SECRETS_PROVIDER_MODAL_KEY,
|
||||
FROM_AI_PARAMETERS_MODAL_KEY,
|
||||
IMPORT_CURL_MODAL_KEY,
|
||||
<<<<<<< HEAD
|
||||
LOG_STREAM_MODAL_KEY,
|
||||
=======
|
||||
IMPORT_WORKFLOW_URL_MODAL_KEY,
|
||||
>>>>>>> 7424f0ca0452f9dc9fe4cf6627ecbf0b315ed1e3
|
||||
MIGRATE_WORKFLOW_MODAL_KEY,
|
||||
NEW_ASSISTANT_SESSION_MODAL,
|
||||
NPS_SURVEY_MODAL_KEY,
|
||||
|
||||
@@ -1,8 +0,0 @@
|
||||
import { Function } from './Function.node';
|
||||
|
||||
describe('Function Node', () => {
|
||||
it('is marked deprecated so the backend refuses new instances', () => {
|
||||
const node = new Function();
|
||||
expect(node.description.deprecated).toBe(true);
|
||||
});
|
||||
});
|
||||
@@ -1,8 +0,0 @@
|
||||
import { FunctionItem } from './FunctionItem.node';
|
||||
|
||||
describe('FunctionItem Node', () => {
|
||||
it('is marked deprecated so the backend refuses new instances', () => {
|
||||
const node = new FunctionItem();
|
||||
expect(node.description.deprecated).toBe(true);
|
||||
});
|
||||
});
|
||||
@@ -1,4 +1,5 @@
|
||||
import { N8N_NODES_API_VERSION } from '@n8n/constants';
|
||||
import { parseNodesApiLevel } from 'n8n-workflow';
|
||||
|
||||
import { test as base } from '../base';
|
||||
import { IMPORT_MARKER_DIR, PUBLISHED_PACKAGES, type FixturePackage } from './fixture-packages';
|
||||
@@ -20,7 +21,7 @@ export interface PackageDisk {
|
||||
type Fixtures = {
|
||||
/** Publishes every fixture package into the stack's registry, once per worker, before any test runs. */
|
||||
publishedPackages: readonly FixturePackage[];
|
||||
/** Node API level the instance supports: 2.x runs level 1, 3.x runs level 3. */
|
||||
/** Major node API level for fixtures that require integer levels. */
|
||||
supportedNodesApiVersion: number;
|
||||
/** What the package left on the instance's disk; follows the main container across a restart. */
|
||||
packageDisk: PackageDisk;
|
||||
@@ -44,7 +45,7 @@ export const test = base.extend<
|
||||
],
|
||||
|
||||
supportedNodesApiVersion: async ({ api: _api }, use) => {
|
||||
await use(N8N_NODES_API_VERSION);
|
||||
await use(parseNodesApiLevel(N8N_NODES_API_VERSION)!.major);
|
||||
},
|
||||
|
||||
packageDisk: async ({ n8nContainer }, use) => {
|
||||
|
||||
@@ -164,15 +164,9 @@ test.describe(
|
||||
await expect(n8n.ndv.getNodeVersion()).toContainText('Latest');
|
||||
await n8n.ndv.close();
|
||||
|
||||
<<<<<<< HEAD
|
||||
await n8n.canvas.openNode('Read Spreadsheet File');
|
||||
await n8n.ndv.openSettings();
|
||||
await expect(n8n.ndv.getNodeVersion()).toContainText('Spreadsheet File node version 1');
|
||||
=======
|
||||
await n8n.canvas.openNode('Cron');
|
||||
await n8n.ndv.openSettings();
|
||||
await expect(n8n.ndv.getNodeVersion()).toContainText('Cron node version 1');
|
||||
>>>>>>> 7424f0ca0452f9dc9fe4cf6627ecbf0b315ed1e3
|
||||
await expect(n8n.ndv.getNodeVersion()).toContainText('Deprecated');
|
||||
await n8n.ndv.close();
|
||||
});
|
||||
|
||||
@@ -38,12 +38,8 @@
|
||||
"type": "n8n-nodes-base.code",
|
||||
"position": [620, 420],
|
||||
"parameters": {
|
||||
<<<<<<< HEAD
|
||||
"mode": "runOnceForAllItems",
|
||||
"jsCode": "const _ = require('lodash')\n\nconst sanitize = str => _.chain(str)\n .replace(/[^A-Za-z0-9&.-]/g, '-') // sanitise via whitelist of characters\n .replace(/-(?=-)/g, '') // remove repeated dashes - https://regexr.com/6ag8h\n .trim('-') // trim any leading/trailing dashes\n .truncate({\n length: 60,\n omission: '-' // when the string ends with '-', you'll know it was truncated\n })\n .value()\n\nconst result = _.flatMap($input.all().map(item => {\n //console.log({item})\n\n // Maps each attachment to a separate item\n return _.values(item.binary).map(file => {\n console.log(\"Saving attachement:\", file.fileName, 'from:', ...item.json.from.value)\n \n // sanitize filename but exclude extension\n const filename_parts = file.fileName.split('.')\n const ext = _.slice(filename_parts, filename_parts.length-1)\n const filename_main = _.join(_.dropRight(filename_parts), '.')\n file.fileName = sanitize(filename_main) + '.' + ext\n \n return {\n json: {\n from: sanitize(item.json.from.value[0].name),\n date: sanitize(new Date(item.json.date).toISOString().split(\"T\")[0]) // get date part \"2020-01-01\"\n }, \n binary: { file }\n }\n })\n}))\n\n//console.log(result)\nreturn result"
|
||||
=======
|
||||
"jsCode": "const _ = require('lodash')\n\nconst sanitize = str => _.chain(str)\n .replace(/[^A-Za-z0-9&.-]/g, '-') // sanitise via whitelist of characters\n .replace(/-(?=-)/g, '') // remove repeated dashes - https://regexr.com/6ag8h\n .trim('-') // trim any leading/trailing dashes\n .truncate({\n length: 60,\n omission: '-' // when the string ends with '-', you'll know it was truncated\n })\n .value()\n\nconst result = _.flatMap(items.map(item => {\n //console.log({item})\n\n // Maps each attachment to a separate item\n return _.values(item.binary).map(file => {\n console.log(\"Saving attachement:\", file.fileName, 'from:', ...item.json.from.value)\n \n // sanitize filename but exclude extension\n const filename_parts = file.fileName.split('.')\n const ext = _.slice(filename_parts, filename_parts.length-1)\n const filename_main = _.join(_.dropRight(filename_parts), '.')\n file.fileName = sanitize(filename_main) + '.' + ext\n \n return {\n json: {\n from: sanitize(item.json.from.value[0].name),\n date: sanitize(new Date(item.json.date).toISOString().split(\"T\")[0]) // get date part \"2020-01-01\"\n }, \n binary: { file }\n }\n })\n}))\n\n//console.log(result)\nreturn result"
|
||||
>>>>>>> 7424f0ca0452f9dc9fe4cf6627ecbf0b315ed1e3
|
||||
},
|
||||
"typeVersion": 2
|
||||
}
|
||||
@@ -77,12 +73,6 @@
|
||||
"workflowInfo": {
|
||||
"nodeCount": 3,
|
||||
"nodeTypes": {
|
||||
<<<<<<< HEAD
|
||||
=======
|
||||
"n8n-nodes-base.code": {
|
||||
"count": 1
|
||||
},
|
||||
>>>>>>> 7424f0ca0452f9dc9fe4cf6627ecbf0b315ed1e3
|
||||
"n8n-nodes-base.nextCloud": {
|
||||
"count": 1
|
||||
},
|
||||
@@ -125,11 +115,7 @@
|
||||
},
|
||||
{
|
||||
"id": 14,
|
||||
<<<<<<< HEAD
|
||||
"icon": "node:code",
|
||||
=======
|
||||
"icon": "fa:code",
|
||||
>>>>>>> 7424f0ca0452f9dc9fe4cf6627ecbf0b315ed1e3
|
||||
"name": "n8n-nodes-base.code",
|
||||
"defaults": {
|
||||
"name": "Code"
|
||||
|
||||
@@ -10,13 +10,8 @@
|
||||
},
|
||||
{
|
||||
"id": "1ea0a87c-3395-4bd9-84fb-cf8b0f769cc4",
|
||||
<<<<<<< HEAD
|
||||
"name": "Read Spreadsheet File",
|
||||
"type": "n8n-nodes-base.spreadsheetFile",
|
||||
=======
|
||||
"name": "Cron",
|
||||
"type": "n8n-nodes-base.cron",
|
||||
>>>>>>> 7424f0ca0452f9dc9fe4cf6627ecbf0b315ed1e3
|
||||
"typeVersion": 1,
|
||||
"position": [960, 460],
|
||||
"parameters": {}
|
||||
|
||||
Reference in New Issue
Block a user