mirror of
https://github.com/n8n-io/n8n.git
synced 2026-06-01 17:27:14 +02:00
169 lines
6.0 KiB
TypeScript
169 lines
6.0 KiB
TypeScript
import { confirm, intro, log, outro } from '@clack/prompts';
|
|
import { Args, Command } from '@oclif/core';
|
|
import fs from 'node:fs/promises';
|
|
import path from 'node:path';
|
|
import picocolors from 'picocolors';
|
|
|
|
import { suggestCloudSupportCommand, suggestLintCommand } from '../utils/command-suggestions';
|
|
import { getPackageJson, updatePackageJson } from '../utils/package';
|
|
import { ensureN8nPackage, getCommandHeader, onCancel, withCancelHandler } from '../utils/prompts';
|
|
|
|
export default class CloudSupport extends Command {
|
|
static override description = 'Enable or disable cloud support for this node';
|
|
static override examples = [
|
|
'<%= config.bin %> <%= command.id %>',
|
|
'<%= config.bin %> <%= command.id %> enable',
|
|
'<%= config.bin %> <%= command.id %> disable',
|
|
];
|
|
|
|
static override args = {
|
|
action: Args.string({
|
|
description: 'Action to perform (defaults to showing current status)',
|
|
required: false,
|
|
options: ['enable', 'disable'],
|
|
}),
|
|
};
|
|
|
|
async run(): Promise<void> {
|
|
const { args } = await this.parse(CloudSupport);
|
|
|
|
await ensureN8nPackage('cloud-support');
|
|
|
|
const workingDir = process.cwd();
|
|
|
|
if (args.action === 'enable') {
|
|
await this.enableCloudSupport(workingDir);
|
|
} else if (args.action === 'disable') {
|
|
await this.disableCloudSupport(workingDir);
|
|
} else {
|
|
await this.showCloudSupportStatus(workingDir);
|
|
}
|
|
}
|
|
|
|
private async enableCloudSupport(workingDir: string): Promise<void> {
|
|
intro(await getCommandHeader('n8n-node cloud-support enable'));
|
|
|
|
await this.updateEslintConfig(workingDir, true);
|
|
log.success(`Updated ${picocolors.cyan('eslint.config.mjs')} to use default config`);
|
|
|
|
await this.updateStrictMode(workingDir, true);
|
|
log.success(`Enabled strict mode in ${picocolors.cyan('package.json')}`);
|
|
|
|
const lintCommand = await suggestLintCommand();
|
|
outro(
|
|
`Cloud support enabled. Run "${lintCommand}" to check compliance - your node must pass linting to be eligible for n8n Cloud publishing.`,
|
|
);
|
|
}
|
|
|
|
private async disableCloudSupport(workingDir: string): Promise<void> {
|
|
intro(await getCommandHeader('n8n-node cloud-support disable'));
|
|
|
|
log.warning(`This will make your node ineligible for n8n Cloud verification!
|
|
|
|
The following changes will be made:
|
|
• Switch to ${picocolors.magenta('configWithoutCloudSupport')} in ${picocolors.cyan('eslint.config.mjs')}
|
|
• Disable strict mode in ${picocolors.cyan('package.json')}`);
|
|
|
|
const confirmed = await withCancelHandler(
|
|
confirm({
|
|
message: 'Are you sure you want to disable cloud support?',
|
|
initialValue: false,
|
|
}),
|
|
);
|
|
|
|
if (!confirmed) {
|
|
onCancel('Cloud support unchanged');
|
|
return;
|
|
}
|
|
|
|
// 1. Update eslint.config.mjs
|
|
await this.updateEslintConfig(workingDir, false);
|
|
log.success(
|
|
`Updated ${picocolors.cyan('eslint.config.mjs')} to use ${picocolors.magenta('configWithoutCloudSupport')}`,
|
|
);
|
|
|
|
// 2. Disable strict mode in package.json
|
|
await this.updateStrictMode(workingDir, false);
|
|
log.success(`Disabled strict mode in ${picocolors.cyan('package.json')}`);
|
|
|
|
outro(
|
|
"Cloud support disabled. Your node may pass linting but it won't pass verification for n8n Cloud.",
|
|
);
|
|
}
|
|
|
|
private async updateEslintConfig(workingDir: string, enableCloud: boolean): Promise<void> {
|
|
const eslintConfigPath = path.resolve(workingDir, 'eslint.config.mjs');
|
|
const newConfig = enableCloud
|
|
? `import { config } from '@n8n/node-cli/eslint';
|
|
|
|
export default config;
|
|
`
|
|
: `import { configWithoutCloudSupport } from '@n8n/node-cli/eslint';
|
|
|
|
export default configWithoutCloudSupport;
|
|
`;
|
|
|
|
await fs.writeFile(eslintConfigPath, newConfig, 'utf-8');
|
|
}
|
|
|
|
private async updateStrictMode(workingDir: string, enableStrict: boolean): Promise<void> {
|
|
await updatePackageJson(workingDir, (packageJson) => {
|
|
packageJson.n8n = packageJson.n8n ?? {};
|
|
packageJson.n8n.strict = enableStrict;
|
|
return packageJson;
|
|
});
|
|
}
|
|
|
|
private async showCloudSupportStatus(workingDir: string): Promise<void> {
|
|
intro(await getCommandHeader('n8n-node cloud-support'));
|
|
|
|
try {
|
|
const packageJson = await getPackageJson(workingDir);
|
|
const eslintConfigPath = path.resolve(workingDir, 'eslint.config.mjs');
|
|
|
|
// Check strict mode
|
|
const isStrictMode = packageJson?.n8n?.strict === true;
|
|
|
|
// Check eslint config
|
|
let isUsingDefaultConfig = false;
|
|
try {
|
|
const eslintConfig = await fs.readFile(eslintConfigPath, 'utf-8');
|
|
const normalizedConfig = eslintConfig.replace(/\s+/g, ' ').trim();
|
|
const expectedDefault =
|
|
"import { config } from '@n8n/node-cli/eslint'; export default config;";
|
|
isUsingDefaultConfig = normalizedConfig === expectedDefault;
|
|
} catch {
|
|
// eslint config doesn't exist or can't be read
|
|
}
|
|
|
|
const isCloudSupported = isStrictMode && isUsingDefaultConfig;
|
|
|
|
if (isCloudSupported) {
|
|
log.success(`✅ Cloud support is ${picocolors.green('ENABLED')}
|
|
• Strict mode: ${picocolors.green('enabled')}
|
|
• ESLint config: ${picocolors.green('using default config')}
|
|
• Status: ${picocolors.green('eligible')} for n8n Cloud verification ${picocolors.dim('(if lint passes)')}`);
|
|
} else {
|
|
log.warning(`⚠️ Cloud support is ${picocolors.yellow('DISABLED')}
|
|
• Strict mode: ${isStrictMode ? picocolors.green('enabled') : picocolors.red('disabled')}
|
|
• ESLint config: ${isUsingDefaultConfig ? picocolors.green('using default config') : picocolors.red('using custom config')}
|
|
• Status: ${picocolors.red('NOT eligible')} for n8n Cloud verification`);
|
|
}
|
|
|
|
const enableCommand = await suggestCloudSupportCommand('enable');
|
|
const disableCommand = await suggestCloudSupportCommand('disable');
|
|
const lintCommand = await suggestLintCommand();
|
|
|
|
log.info(`Available commands:
|
|
• ${enableCommand} - Enable cloud support
|
|
• ${disableCommand} - Disable cloud support
|
|
• ${lintCommand} - Check compliance for cloud publishing`);
|
|
|
|
outro('Use the commands above to change cloud support settings or check compliance');
|
|
} catch (error) {
|
|
log.error('Failed to read package.json or determine cloud support status');
|
|
outro('Make sure you are in the root directory of your node package');
|
|
}
|
|
}
|
|
}
|