From beed5864d0d94fb7660459ec3b6d70d9e5fee692 Mon Sep 17 00:00:00 2001 From: blam Date: Tue, 3 Jan 2023 17:02:35 +0100 Subject: [PATCH] chore: added some more mock defintions and refactoring the `TaskManager.forPlugin` Signed-off-by: blam --- .../scheduler/schedulerFactory.ts | 10 +++- .../backend-tasks/src/tasks/TaskScheduler.ts | 23 ++++++---- .../src/next/implementations/index.ts | 3 ++ .../next/implementations/mockConfigService.ts | 30 ++++++++++++ .../implementations/mockDatabaseService.ts | 46 +++++++++++++++++++ .../implementations/mockDiscoveryService.ts | 40 ++++++++++++++++ .../src/next/wiring/TestBackend.ts | 16 ++++--- 7 files changed, 151 insertions(+), 17 deletions(-) create mode 100644 packages/backend-test-utils/src/next/implementations/mockConfigService.ts create mode 100644 packages/backend-test-utils/src/next/implementations/mockDatabaseService.ts create mode 100644 packages/backend-test-utils/src/next/implementations/mockDiscoveryService.ts diff --git a/packages/backend-app-api/src/services/implementations/scheduler/schedulerFactory.ts b/packages/backend-app-api/src/services/implementations/scheduler/schedulerFactory.ts index a6edec868a..692f05f6d7 100644 --- a/packages/backend-app-api/src/services/implementations/scheduler/schedulerFactory.ts +++ b/packages/backend-app-api/src/services/implementations/scheduler/schedulerFactory.ts @@ -17,6 +17,7 @@ import { coreServices, createServiceFactory, + loggerToWinstonLogger, } from '@backstage/backend-plugin-api'; import { TaskScheduler } from '@backstage/backend-tasks'; @@ -26,11 +27,16 @@ export const schedulerFactory = createServiceFactory({ deps: { config: coreServices.config, plugin: coreServices.pluginMetadata, + databaseManager: coreServices.database, + logger: coreServices.logger, }, async factory({ config }) { const taskScheduler = TaskScheduler.fromConfig(config); - return async ({ plugin }) => { - return taskScheduler.forPlugin(plugin.getId()); + return async ({ plugin, databaseManager, logger }) => { + return taskScheduler.forPlugin(plugin.getId(), { + databaseManager, + logger: loggerToWinstonLogger(logger), + }); }; }, }); diff --git a/packages/backend-tasks/src/tasks/TaskScheduler.ts b/packages/backend-tasks/src/tasks/TaskScheduler.ts index f14fb9fc2b..f35669d76e 100644 --- a/packages/backend-tasks/src/tasks/TaskScheduler.ts +++ b/packages/backend-tasks/src/tasks/TaskScheduler.ts @@ -14,7 +14,11 @@ * limitations under the License. */ -import { DatabaseManager, getRootLogger } from '@backstage/backend-common'; +import { + DatabaseManager, + getRootLogger, + PluginDatabaseManager, +} from '@backstage/backend-common'; import { Config } from '@backstage/config'; import { once } from 'lodash'; import { Duration } from 'luxon'; @@ -56,9 +60,15 @@ export class TaskScheduler { * @param pluginId - The unique ID of the plugin, for example "catalog" * @returns A {@link PluginTaskScheduler} instance */ - forPlugin(pluginId: string): PluginTaskScheduler { + forPlugin( + pluginId: string, + options?: { databaseManager?: PluginDatabaseManager; logger?: Logger }, + ): PluginTaskScheduler { + const databaseManager = + options?.databaseManager ?? this.databaseManager.forPlugin(pluginId); + const logger = options?.logger ?? this.logger.child({ plugin: pluginId }); + const databaseFactory = once(async () => { - const databaseManager = this.databaseManager.forPlugin(pluginId); const knex = await databaseManager.getClient(); if (!databaseManager.migrations?.skip) { @@ -68,16 +78,13 @@ export class TaskScheduler { const janitor = new PluginTaskSchedulerJanitor({ knex, waitBetweenRuns: Duration.fromObject({ minutes: 1 }), - logger: this.logger, + logger, }); janitor.start(); return knex; }); - return new PluginTaskSchedulerImpl( - databaseFactory, - this.logger.child({ plugin: pluginId }), - ); + return new PluginTaskSchedulerImpl(databaseFactory, logger); } } diff --git a/packages/backend-test-utils/src/next/implementations/index.ts b/packages/backend-test-utils/src/next/implementations/index.ts index 073e47f5e4..ba8bb5fb5e 100644 --- a/packages/backend-test-utils/src/next/implementations/index.ts +++ b/packages/backend-test-utils/src/next/implementations/index.ts @@ -14,3 +14,6 @@ * limitations under the License. */ export { mockTokenManagerFactory } from './mockTokenManagerService'; +export { mockConfigFactory } from './mockConfigService'; +export { mockDatabaseFactory } from './mockDatabaseService'; +export { mockDiscoveryFactory } from './mockDiscoveryService'; diff --git a/packages/backend-test-utils/src/next/implementations/mockConfigService.ts b/packages/backend-test-utils/src/next/implementations/mockConfigService.ts new file mode 100644 index 0000000000..976167b473 --- /dev/null +++ b/packages/backend-test-utils/src/next/implementations/mockConfigService.ts @@ -0,0 +1,30 @@ +/* + * Copyright 2022 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +import { + coreServices, + createServiceFactory, +} from '@backstage/backend-plugin-api'; +import { AppConfig, ConfigReader } from '@backstage/config'; + +/** @public */ +export const mockConfigFactory = createServiceFactory({ + service: coreServices.config, + deps: {}, + async factory(_, options?: { config?: AppConfig }) { + return new ConfigReader(options?.config); + }, +}); diff --git a/packages/backend-test-utils/src/next/implementations/mockDatabaseService.ts b/packages/backend-test-utils/src/next/implementations/mockDatabaseService.ts new file mode 100644 index 0000000000..b0d67c1f1e --- /dev/null +++ b/packages/backend-test-utils/src/next/implementations/mockDatabaseService.ts @@ -0,0 +1,46 @@ +/* + * Copyright 2022 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ + +import { DatabaseManager } from '@backstage/backend-common'; +import { + coreServices, + createServiceFactory, +} from '@backstage/backend-plugin-api'; +import { ConfigReader } from '@backstage/config'; + +/** @public */ +export const mockDatabaseFactory = createServiceFactory({ + service: coreServices.database, + deps: { + config: coreServices.config, + plugin: coreServices.pluginMetadata, + }, + async factory({ config }) { + const databaseManager = config.getOptional('backend.database') + ? DatabaseManager.fromConfig(config) + : DatabaseManager.fromConfig( + new ConfigReader({ + backend: { + database: { client: 'better-sqlite', connection: ':memory:' }, + }, + }), + ); + + return async ({ plugin }) => { + return databaseManager.forPlugin(plugin.getId()); + }; + }, +}); diff --git a/packages/backend-test-utils/src/next/implementations/mockDiscoveryService.ts b/packages/backend-test-utils/src/next/implementations/mockDiscoveryService.ts new file mode 100644 index 0000000000..3af69187e8 --- /dev/null +++ b/packages/backend-test-utils/src/next/implementations/mockDiscoveryService.ts @@ -0,0 +1,40 @@ +/* + * Copyright 2023 The Backstage Authors + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License. + */ +import { SingleHostDiscovery } from '@backstage/backend-common'; +import { + coreServices, + createServiceFactory, +} from '@backstage/backend-plugin-api'; +import { ConfigReader } from '@backstage/config'; + +/** @public */ +export const mockDiscoveryFactory = createServiceFactory({ + service: coreServices.discovery, + deps: {}, + async factory() { + // todo(blam): we want to grab the port from the httpRouter when that's available here + // to provide a better way to create our mockDiscoveryService. + const discovery = SingleHostDiscovery.fromConfig( + new ConfigReader({ + backend: { baseUrl: 'http://localhost:7000', listen: '0.0.0.0:7000' }, + }), + ); + + return async () => { + return discovery; + }; + }, +}); diff --git a/packages/backend-test-utils/src/next/wiring/TestBackend.ts b/packages/backend-test-utils/src/next/wiring/TestBackend.ts index 7b78ad3d95..a4ac8be7a2 100644 --- a/packages/backend-test-utils/src/next/wiring/TestBackend.ts +++ b/packages/backend-test-utils/src/next/wiring/TestBackend.ts @@ -21,10 +21,7 @@ import { rootLifecycleFactory, loggerFactory, rootLoggerFactory, - configFactory, - discoveryFactory, cacheFactory, - databaseFactory, permissionsFactory, schedulerFactory, urlReaderFactory, @@ -38,7 +35,12 @@ import { ExtensionPoint, } from '@backstage/backend-plugin-api'; -import { mockTokenManagerFactory } from '../implementations'; +import { + mockConfigFactory, + mockDatabaseFactory, + mockTokenManagerFactory, + mockDiscoveryFactory, +} from '../implementations'; /** @alpha */ export interface TestBackendOptions< @@ -66,9 +68,9 @@ export interface TestBackendOptions< const defaultServiceFactories = [ cacheFactory(), - configFactory(), - databaseFactory(), - discoveryFactory(), + mockConfigFactory(), + mockDatabaseFactory(), + mockDiscoveryFactory(), lifecycleFactory(), loggerFactory(), permissionsFactory(),