Browse Source

fix(core): Prevent plugin providers multiple instantiation

Michael Bromley 4 years ago
parent
commit
98e463ea85

+ 3 - 3
packages/core/src/plugin/dynamic-plugin-api.module.ts

@@ -22,11 +22,11 @@ export function createDynamicGraphQlModulesForPlugins(apiType: 'shop' | 'admin')
                 const className = dynamicClassName(pluginModule, apiType);
                 dynamicApiModuleClassMap[className] = class {};
                 Object.defineProperty(dynamicApiModuleClassMap[className], 'name', { value: className });
-                const { imports, providers } = getModuleMetadata(pluginModule);
+                const { imports } = getModuleMetadata(pluginModule);
                 return {
                     module: dynamicApiModuleClassMap[className],
-                    imports,
-                    providers: [...providers, ...resolvers],
+                    imports: [pluginModule, ...imports],
+                    providers: [...resolvers],
                 };
             }
         })

+ 3 - 1
packages/core/src/plugin/plugin.module.ts

@@ -3,9 +3,11 @@ import { DynamicModule, Module } from '@nestjs/common';
 import { getConfig } from '../config/config-helpers';
 import { ConfigModule } from '../config/config.module';
 
+import { getModuleMetadata } from './plugin-metadata';
+
 /**
  * This module collects and re-exports all providers defined in plugins so that they can be used in other
- * modules and in responsible for executing any lifecycle methods defined by the plugins.
+ * modules.
  */
 @Module({
     imports: [ConfigModule],

+ 9 - 0
packages/core/src/plugin/vendure-plugin.ts

@@ -129,6 +129,15 @@ export function VendurePlugin(pluginMetadata: VendurePluginMetadata): ClassDecor
             }
         }
         const nestModuleMetadata = pick(pluginMetadata, Object.values(MODULE_METADATA) as any);
+        // Automatically add any of the Plugin's "providers" to the "exports" array. This is done
+        // because when a plugin defines GraphQL resolvers, these resolvers are used to dynamically
+        // created a new Module in the ApiModule, and if those resolvers depend on any providers,
+        // the must be exported. See the function {@link createDynamicGraphQlModulesForPlugins}
+        // for the implementation.
+        nestModuleMetadata.exports = [
+            ...(nestModuleMetadata.exports || []),
+            ...(nestModuleMetadata.providers || []),
+        ];
         Module(nestModuleMetadata)(target);
     };
 }