diff --git a/packages/core/server/src/plugin-manager/PluginManager.ts b/packages/core/server/src/plugin-manager/PluginManager.ts index 6e986682a..8e72b7261 100644 --- a/packages/core/server/src/plugin-manager/PluginManager.ts +++ b/packages/core/server/src/plugin-manager/PluginManager.ts @@ -176,6 +176,7 @@ export class PluginManager { if (!options?.async) { this._tmpPluginArgs.push([plugin, options]); } + let name: string; if (typeof plugin === 'string') { name = plugin; @@ -192,7 +193,9 @@ export class PluginManager { enabled: true, ...options, }); + const pluginName = instance.getName(); + if (this.plugins.has(pluginName)) { throw new Error(`plugin name [${pluginName}] already exists`); } @@ -223,7 +226,12 @@ export class PluginManager { if (Array.isArray(plugin)) { const t = transaction || (await this.app.db.sequelize.transaction()); try { - const items = await Promise.all(plugin.map((p) => this.add(p, options, t))); + const items = []; + + for (const p of plugin) { + items.push(await this.add(p, options, t)); + } + await t.commit(); return items; } catch (error) { @@ -231,20 +239,26 @@ export class PluginManager { throw error; } } + const packageName = await PluginManager.findPackage(plugin); - const packageJson = require(`${packageName}/package.json`); + await this.generateClientFile(plugin, packageName); + const instance = this.addStatic(plugin, { ...options, async: true, }); + let model = await this.repository.findOne({ transaction, filter: { name: plugin }, }); + + const packageJson = PluginManager.getPackageJson(packageName); + if (!model) { const { enabled, builtIn, installed, ...others } = options; - model = await this.repository.create({ + await this.repository.create({ transaction, values: { name: plugin, @@ -337,6 +351,10 @@ export class PluginManager { this.app.reload(); } + static getPackageJson(packageName: string) { + return require(`${packageName}/package.json`); + } + static getPackageName(name: string) { const prefixes = this.getPluginPkgPrefix(); for (const prefix of prefixes) { diff --git a/packages/core/test/src/mockServer.ts b/packages/core/test/src/mockServer.ts index 0272a287f..b3b93ec8f 100644 --- a/packages/core/test/src/mockServer.ts +++ b/packages/core/test/src/mockServer.ts @@ -1,5 +1,5 @@ import { Database, mockDatabase } from '@nocobase/database'; -import Application, { ApplicationOptions } from '@nocobase/server'; +import Application, { ApplicationOptions, PluginManager } from '@nocobase/server'; import qs from 'qs'; import supertest, { SuperAgentTest } from 'supertest'; @@ -130,6 +130,26 @@ export class MockServer extends Application { } export function mockServer(options: ApplicationOptions = {}) { + if (typeof TextEncoder === 'undefined') { + global.TextEncoder = require('util').TextEncoder; + } + + if (typeof TextDecoder === 'undefined') { + global.TextDecoder = require('util').TextDecoder; + } + + // @ts-ignore + if (!PluginManager.findPackagePatched) { + PluginManager.getPackageJson = () => { + return { + version: '0.0.0', + }; + }; + + // @ts-ignore + PluginManager.findPackagePatched = true; + } + let database; if (options?.database instanceof Database) { database = options.database; @@ -137,11 +157,15 @@ export function mockServer(options: ApplicationOptions = {}) { database = mockDatabase(options?.database || {}); } - return new MockServer({ + const app = new MockServer({ acl: false, ...options, database, }); + + app.pm.generateClientFile = async () => {}; + + return app; } export function createMockServer() {}