@feature-hub/core
Version:
Create scalable web applications using micro frontends.
201 lines • 10.4 kB
JavaScript
// tslint:disable:no-implicit-dependencies
Object.defineProperty(exports, "__esModule", { value: true });
const create_feature_hub_1 = require("../create-feature-hub");
const feature_app_manager_1 = require("../feature-app-manager");
const feature_service_registry_1 = require("../feature-service-registry");
const logger_1 = require("./logger");
describe('createFeatureHub()', () => {
let featureHubOptions;
beforeEach(() => {
featureHubOptions = { logger: logger_1.logger };
});
describe('without any options', () => {
it('creates a Feature Hub that contains a Feature App manager', () => {
const { featureAppManager } = (0, create_feature_hub_1.createFeatureHub)('test:integrator');
expect(featureAppManager).toBeInstanceOf(feature_app_manager_1.FeatureAppManager);
});
it('creates a Feature Hub that contains a Feature Service registry', () => {
const { featureServiceRegistry } = (0, create_feature_hub_1.createFeatureHub)('test:integrator');
expect(featureServiceRegistry).toBeInstanceOf(feature_service_registry_1.FeatureServiceRegistry);
});
it('creates a Feature Hub that contains an empty set of Feature Services', () => {
const { featureServices } = (0, create_feature_hub_1.createFeatureHub)('test:integrator');
expect(featureServices).toEqual({});
});
});
describe('featureAppManager#getAsyncFeatureAppDefinition', () => {
describe('without a module loader', () => {
it('throws an error', () => {
const { featureAppManager } = (0, create_feature_hub_1.createFeatureHub)('test:integrator');
expect(() => featureAppManager.getAsyncFeatureAppDefinition('http://example.com/test.js')).toThrow(new Error('No module loader provided.'));
});
});
describe('with a module loader', () => {
let mockModuleLoader;
beforeEach(() => {
mockModuleLoader = jest.fn(async () => Promise.resolve());
featureHubOptions = Object.assign(Object.assign({}, featureHubOptions), { moduleLoader: mockModuleLoader });
});
it('uses the module loader to load the Feature App definition', () => {
const { featureAppManager } = (0, create_feature_hub_1.createFeatureHub)('test:integrator', featureHubOptions);
const url = 'http://example.com/test.js';
featureAppManager.getAsyncFeatureAppDefinition(url, 'a');
expect(mockModuleLoader).toHaveBeenCalledWith(url, 'a');
});
});
});
describe('featureAppManager#createFeatureAppScope', () => {
let mockFeatureApp;
let mockFeatureAppCreate;
let mockFeatureAppDefinition;
beforeEach(() => {
mockFeatureApp = {};
mockFeatureAppCreate = jest.fn(() => mockFeatureApp);
mockFeatureAppDefinition = {
dependencies: { externals: { foo: '^1.0.0' } },
create: mockFeatureAppCreate,
};
});
it('creates a Feature App', () => {
const { featureAppManager } = (0, create_feature_hub_1.createFeatureHub)('test:integrator', featureHubOptions);
const { featureApp } = featureAppManager.createFeatureAppScope('test:feature-app', mockFeatureAppDefinition);
expect(mockFeatureAppCreate).toHaveBeenCalledWith({
featureAppId: 'test:feature-app',
featureServices: {},
});
expect(featureApp).toBe(mockFeatureApp);
});
describe('with provided externals', () => {
beforeEach(() => {
featureHubOptions = Object.assign(Object.assign({}, featureHubOptions), { providedExternals: {} });
});
it('throws for a Feature App with mismatching externals', () => {
const { featureAppManager } = (0, create_feature_hub_1.createFeatureHub)('test:integrator', featureHubOptions);
expect(() => featureAppManager.createFeatureAppScope('test:feature-app', mockFeatureAppDefinition)).toThrow(new Error('The external dependency "foo" as required by "test:feature-app" is not provided.'));
});
});
describe('with an onBind callback', () => {
it('calls the onBind callback successfully', () => {
const mockOnBind = jest.fn();
const featureAppId = 'testId';
const featureAppName = 'testName';
const { featureAppManager } = (0, create_feature_hub_1.createFeatureHub)('test:integrator', Object.assign(Object.assign({}, featureHubOptions), { onBind: mockOnBind }));
const parentFeatureApp = {
featureAppId: 'parentTestId',
featureAppName: 'parentTestName',
};
featureAppManager.createFeatureAppScope(featureAppId, mockFeatureAppDefinition, { featureAppName, parentFeatureApp });
expect(mockOnBind.mock.calls).toEqual([
[
{
featureAppDefinition: mockFeatureAppDefinition,
featureAppId,
featureAppName,
parentFeatureApp,
},
],
]);
});
});
});
describe('with Feature Service definitions', () => {
let mockFeatureServiceCreate;
let mockFeatureServiceV1Binder;
let mockFeatureServiceV1;
beforeEach(() => {
mockFeatureServiceV1 = {};
mockFeatureServiceV1Binder = jest.fn(() => ({
featureService: mockFeatureServiceV1,
}));
mockFeatureServiceCreate = jest.fn(() => ({
'1.0.0': mockFeatureServiceV1Binder,
}));
featureHubOptions = Object.assign(Object.assign({}, featureHubOptions), { featureServiceDefinitions: [
{
id: 'test:feature-service',
dependencies: { externals: { foo: '^1.0.0' } },
create: mockFeatureServiceCreate,
},
] });
});
it('registers and creates the Feature Services', () => {
(0, create_feature_hub_1.createFeatureHub)('test:integrator', featureHubOptions);
expect(mockFeatureServiceCreate).toHaveBeenCalledWith({
featureServices: {},
});
});
describe('and with provided externals', () => {
beforeEach(() => {
featureHubOptions = Object.assign(Object.assign({}, featureHubOptions), { providedExternals: {} });
});
it('throws for a Feature Service with mismatching externals', () => {
expect(() => (0, create_feature_hub_1.createFeatureHub)('test:integrator', featureHubOptions)).toThrow(new Error('The external dependency "foo" as required by "test:feature-service" is not provided.'));
});
});
describe('and without Feature Service dependencies', () => {
it('creates a Feature Hub that contains an empty set of Feature Services', () => {
const { featureServices } = (0, create_feature_hub_1.createFeatureHub)('test:integrator', featureHubOptions);
expect(featureServices).toEqual({});
});
});
describe('and with Feature Service dependencies', () => {
beforeEach(() => {
featureHubOptions = Object.assign(Object.assign({}, featureHubOptions), { featureServiceDependencies: { 'test:feature-service': '^1.0.0' } });
});
it('creates a Feature Hub that contains Feature Services that are bound to the integrator', () => {
const { featureServices } = (0, create_feature_hub_1.createFeatureHub)('test:integrator', featureHubOptions);
expect(mockFeatureServiceV1Binder.mock.calls).toEqual([
['test:integrator', undefined],
]);
expect(featureServices['test:feature-service']).toBe(mockFeatureServiceV1);
});
});
});
describe('logging', () => {
let featureAppDefinition;
let featureServiceDefinitions;
let expectedLogCalls;
beforeEach(() => {
featureAppDefinition = { create: jest.fn(() => ({})) };
featureServiceDefinitions = [
{ id: 'test:feature-service', create: () => ({ '1.0.0': jest.fn() }) },
];
expectedLogCalls = [
[
'The Feature Service "test:feature-service" has been successfully registered by registrant "test:integrator".',
],
[
'The Feature App with the ID "test:feature-app" has been successfully created.',
],
];
});
describe('with a custom logger', () => {
it('logs messages using the custom logger', () => {
const { featureAppManager } = (0, create_feature_hub_1.createFeatureHub)('test:integrator', {
featureServiceDefinitions,
logger: logger_1.logger,
});
featureAppManager.createFeatureAppScope('test:feature-app', featureAppDefinition);
expect(logger_1.logger.info.mock.calls).toEqual(expectedLogCalls);
});
});
describe('without a custom logger', () => {
let consoleInfoSpy;
beforeEach(() => {
consoleInfoSpy = jest.spyOn(console, 'info');
});
afterEach(() => {
consoleInfoSpy.mockRestore();
});
it('logs messages using the console', () => {
const { featureAppManager } = (0, create_feature_hub_1.createFeatureHub)('test:integrator', {
featureServiceDefinitions,
});
featureAppManager.createFeatureAppScope('test:feature-app', featureAppDefinition);
expect(consoleInfoSpy.mock.calls).toEqual(expectedLogCalls);
});
});
});
});
//# sourceMappingURL=create-feature-hub.test.js.map
;