Merge pull request #16710 from backstage/search/backend-system-migration
[Search] Migrate search to new backend system
This commit is contained in:
@@ -11,6 +11,7 @@ import { AnalyzeLocationGenerateEntity as AnalyzeLocationGenerateEntity_2 } from
|
||||
import { AnalyzeLocationRequest as AnalyzeLocationRequest_2 } from '@backstage/plugin-catalog-common';
|
||||
import { AnalyzeLocationResponse as AnalyzeLocationResponse_2 } from '@backstage/plugin-catalog-common';
|
||||
import { CatalogApi } from '@backstage/catalog-client';
|
||||
import type { CatalogCollatorEntityTransformer as CatalogCollatorEntityTransformer_2 } from '@backstage/plugin-search-backend-module-catalog';
|
||||
import { CatalogEntityDocument } from '@backstage/plugin-catalog-common';
|
||||
import { CatalogProcessor as CatalogProcessor_2 } from '@backstage/plugin-catalog-node';
|
||||
import { CatalogProcessorCache as CatalogProcessorCache_2 } from '@backstage/plugin-catalog-node';
|
||||
@@ -23,8 +24,9 @@ import { CatalogProcessorRefreshKeysResult as CatalogProcessorRefreshKeysResult_
|
||||
import { CatalogProcessorRelationResult as CatalogProcessorRelationResult_2 } from '@backstage/plugin-catalog-node';
|
||||
import { CatalogProcessorResult as CatalogProcessorResult_2 } from '@backstage/plugin-catalog-node';
|
||||
import { Config } from '@backstage/config';
|
||||
import { DefaultCatalogCollatorFactory as DefaultCatalogCollatorFactory_2 } from '@backstage/plugin-search-backend-module-catalog';
|
||||
import type { DefaultCatalogCollatorFactoryOptions as DefaultCatalogCollatorFactoryOptions_2 } from '@backstage/plugin-search-backend-module-catalog';
|
||||
import { DeferredEntity as DeferredEntity_2 } from '@backstage/plugin-catalog-node';
|
||||
import { DocumentCollatorFactory } from '@backstage/plugin-search-common';
|
||||
import { Entity } from '@backstage/catalog-model';
|
||||
import { EntityPolicy } from '@backstage/catalog-model';
|
||||
import { EntityProvider as EntityProvider_2 } from '@backstage/plugin-catalog-node';
|
||||
@@ -44,7 +46,6 @@ import { PermissionRule } from '@backstage/plugin-permission-node';
|
||||
import { PermissionRuleParams } from '@backstage/plugin-permission-common';
|
||||
import { PluginDatabaseManager } from '@backstage/backend-common';
|
||||
import { PluginEndpointDiscovery } from '@backstage/backend-common';
|
||||
import { Readable } from 'stream';
|
||||
import { Router } from 'express';
|
||||
import { ScmIntegrationRegistry } from '@backstage/integration';
|
||||
import { TokenManager } from '@backstage/backend-common';
|
||||
@@ -160,10 +161,9 @@ export class CatalogBuilder {
|
||||
useLegacySingleProcessorValidation(): this;
|
||||
}
|
||||
|
||||
// @public (undocumented)
|
||||
export type CatalogCollatorEntityTransformer = (
|
||||
entity: Entity,
|
||||
) => Omit<CatalogEntityDocument, 'location' | 'authorization'>;
|
||||
// @public @deprecated (undocumented)
|
||||
export type CatalogCollatorEntityTransformer =
|
||||
CatalogCollatorEntityTransformer_2;
|
||||
|
||||
// @public (undocumented)
|
||||
export type CatalogEnvironment = {
|
||||
@@ -286,34 +286,15 @@ export class DefaultCatalogCollator {
|
||||
readonly visibilityPermission: Permission;
|
||||
}
|
||||
|
||||
// @public (undocumented)
|
||||
export const defaultCatalogCollatorEntityTransformer: CatalogCollatorEntityTransformer;
|
||||
// @public @deprecated (undocumented)
|
||||
export const defaultCatalogCollatorEntityTransformer: CatalogCollatorEntityTransformer_2;
|
||||
|
||||
// @public (undocumented)
|
||||
export class DefaultCatalogCollatorFactory implements DocumentCollatorFactory {
|
||||
// (undocumented)
|
||||
static fromConfig(
|
||||
_config: Config,
|
||||
options: DefaultCatalogCollatorFactoryOptions,
|
||||
): DefaultCatalogCollatorFactory;
|
||||
// (undocumented)
|
||||
getCollator(): Promise<Readable>;
|
||||
// (undocumented)
|
||||
readonly type = 'software-catalog';
|
||||
// (undocumented)
|
||||
readonly visibilityPermission: Permission;
|
||||
}
|
||||
// @public @deprecated (undocumented)
|
||||
export const DefaultCatalogCollatorFactory: typeof DefaultCatalogCollatorFactory_2;
|
||||
|
||||
// @public (undocumented)
|
||||
export type DefaultCatalogCollatorFactoryOptions = {
|
||||
discovery: PluginEndpointDiscovery;
|
||||
tokenManager: TokenManager;
|
||||
locationTemplate?: string;
|
||||
filter?: GetEntitiesRequest['filter'];
|
||||
batchSize?: number;
|
||||
catalogClient?: CatalogApi;
|
||||
entityTransformer?: CatalogCollatorEntityTransformer;
|
||||
};
|
||||
// @public @deprecated (undocumented)
|
||||
export type DefaultCatalogCollatorFactoryOptions =
|
||||
DefaultCatalogCollatorFactoryOptions_2;
|
||||
|
||||
// @public @deprecated (undocumented)
|
||||
export type DeferredEntity = DeferredEntity_2;
|
||||
|
||||
@@ -57,6 +57,7 @@
|
||||
"@backstage/plugin-permission-common": "workspace:^",
|
||||
"@backstage/plugin-permission-node": "workspace:^",
|
||||
"@backstage/plugin-scaffolder-common": "workspace:^",
|
||||
"@backstage/plugin-search-backend-module-catalog": "workspace:^",
|
||||
"@backstage/plugin-search-common": "workspace:^",
|
||||
"@backstage/types": "workspace:^",
|
||||
"@opentelemetry/api": "^1.3.0",
|
||||
|
||||
@@ -27,3 +27,40 @@ export * from './processing';
|
||||
export * from './search';
|
||||
export * from './service';
|
||||
export * from './deprecated';
|
||||
|
||||
import {
|
||||
DefaultCatalogCollatorFactory as _DefaultCatalogCollatorFactory,
|
||||
defaultCatalogCollatorEntityTransformer as _defaultCatalogCollatorEntityTransformer,
|
||||
} from '@backstage/plugin-search-backend-module-catalog';
|
||||
|
||||
/**
|
||||
* @public
|
||||
* @deprecated import from `@backstage/search-backend-module-catalog` instead
|
||||
*/
|
||||
export const DefaultCatalogCollatorFactory = _DefaultCatalogCollatorFactory;
|
||||
|
||||
/**
|
||||
* @public
|
||||
* @deprecated import from `@backstage/search-backend-module-catalog` instead
|
||||
*/
|
||||
export const defaultCatalogCollatorEntityTransformer =
|
||||
_defaultCatalogCollatorEntityTransformer;
|
||||
|
||||
import type {
|
||||
DefaultCatalogCollatorFactoryOptions as _DefaultCatalogCollatorFactoryOptions,
|
||||
CatalogCollatorEntityTransformer as _CatalogCollatorEntityTransformer,
|
||||
} from '@backstage/plugin-search-backend-module-catalog';
|
||||
|
||||
/**
|
||||
* @public
|
||||
* @deprecated import from `@backstage/search-backend-module-catalog` instead
|
||||
*/
|
||||
export type DefaultCatalogCollatorFactoryOptions =
|
||||
_DefaultCatalogCollatorFactoryOptions;
|
||||
|
||||
/**
|
||||
* @public
|
||||
* @deprecated import from `@backstage/search-backend-module-catalog` instead
|
||||
*/
|
||||
export type CatalogCollatorEntityTransformer =
|
||||
_CatalogCollatorEntityTransformer;
|
||||
|
||||
@@ -14,11 +14,6 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
export { DefaultCatalogCollatorFactory } from './DefaultCatalogCollatorFactory';
|
||||
export type { DefaultCatalogCollatorFactoryOptions } from './DefaultCatalogCollatorFactory';
|
||||
export type { CatalogCollatorEntityTransformer } from './CatalogCollatorEntityTransformer';
|
||||
export { defaultCatalogCollatorEntityTransformer } from './defaultCatalogCollatorEntityTransformer';
|
||||
|
||||
/**
|
||||
* todo(backstage/techdocs-core): stop exporting this in a future release.
|
||||
*/
|
||||
|
||||
@@ -3,18 +3,14 @@
|
||||
> Do not edit this file. It is a report generated by [API Extractor](https://api-extractor.com/).
|
||||
|
||||
```ts
|
||||
/// <reference types="node" />
|
||||
|
||||
import { Config } from '@backstage/config';
|
||||
import { DocumentCollatorFactory } from '@backstage/plugin-search-common';
|
||||
import { ExploreTool } from '@backstage/plugin-explore-common';
|
||||
import express from 'express';
|
||||
import { GetExploreToolsRequest } from '@backstage/plugin-explore-common';
|
||||
import { GetExploreToolsResponse } from '@backstage/plugin-explore-common';
|
||||
import { IndexableDocument } from '@backstage/plugin-search-common';
|
||||
import { Logger } from 'winston';
|
||||
import { PluginEndpointDiscovery } from '@backstage/backend-common';
|
||||
import { Readable } from 'stream';
|
||||
import type { ToolDocument as ToolDocument_2 } from '@backstage/plugin-search-backend-module-explore';
|
||||
import { ToolDocumentCollatorFactory as ToolDocumentCollatorFactory_2 } from '@backstage/plugin-search-backend-module-explore';
|
||||
import type { ToolDocumentCollatorFactoryOptions as ToolDocumentCollatorFactoryOptions_2 } from '@backstage/plugin-search-backend-module-explore';
|
||||
|
||||
// @public (undocumented)
|
||||
export function createRouter(options: RouterOptions): Promise<express.Router>;
|
||||
@@ -40,27 +36,13 @@ export class StaticExploreToolProvider implements ExploreToolProvider {
|
||||
getTools(request: GetExploreToolsRequest): Promise<GetExploreToolsResponse>;
|
||||
}
|
||||
|
||||
// @public
|
||||
export interface ToolDocument extends IndexableDocument, ExploreTool {}
|
||||
// @public @deprecated (undocumented)
|
||||
export type ToolDocument = ToolDocument_2;
|
||||
|
||||
// @public
|
||||
export class ToolDocumentCollatorFactory implements DocumentCollatorFactory {
|
||||
// (undocumented)
|
||||
execute(): AsyncGenerator<ToolDocument>;
|
||||
// (undocumented)
|
||||
static fromConfig(
|
||||
_config: Config,
|
||||
options: ToolDocumentCollatorFactoryOptions,
|
||||
): ToolDocumentCollatorFactory;
|
||||
// (undocumented)
|
||||
getCollator(): Promise<Readable>;
|
||||
// (undocumented)
|
||||
readonly type: string;
|
||||
}
|
||||
// @public @deprecated (undocumented)
|
||||
export const ToolDocumentCollatorFactory: typeof ToolDocumentCollatorFactory_2;
|
||||
|
||||
// @public
|
||||
export type ToolDocumentCollatorFactoryOptions = {
|
||||
discovery: PluginEndpointDiscovery;
|
||||
logger: Logger;
|
||||
};
|
||||
// @public @deprecated (undocumented)
|
||||
export type ToolDocumentCollatorFactoryOptions =
|
||||
ToolDocumentCollatorFactoryOptions_2;
|
||||
```
|
||||
|
||||
@@ -25,6 +25,7 @@
|
||||
"@backstage/backend-common": "workspace:^",
|
||||
"@backstage/config": "workspace:^",
|
||||
"@backstage/plugin-explore-common": "workspace:^",
|
||||
"@backstage/plugin-search-backend-module-explore": "workspace:^",
|
||||
"@backstage/plugin-search-common": "workspace:^",
|
||||
"@types/express": "*",
|
||||
"express": "^4.18.1",
|
||||
|
||||
@@ -20,7 +20,6 @@
|
||||
* @packageDocumentation
|
||||
*/
|
||||
|
||||
export * from './search';
|
||||
export * from './service';
|
||||
export * from './tools';
|
||||
|
||||
@@ -28,3 +27,28 @@ export * from './tools';
|
||||
* @internal Example only - do not use in production
|
||||
*/
|
||||
export { exampleTools } from './example/exampleTools';
|
||||
|
||||
import { ToolDocumentCollatorFactory as _ToolDocumentCollatorFactory } from '@backstage/plugin-search-backend-module-explore';
|
||||
import type {
|
||||
ToolDocument as _ToolDocument,
|
||||
ToolDocumentCollatorFactoryOptions as _ToolDocumentCollatorFactoryOptions,
|
||||
} from '@backstage/plugin-search-backend-module-explore';
|
||||
|
||||
/**
|
||||
* @public
|
||||
* @deprecated import from `@backstage/search-backend-module-explore` instead
|
||||
*/
|
||||
export const ToolDocumentCollatorFactory = _ToolDocumentCollatorFactory;
|
||||
|
||||
/**
|
||||
* @public
|
||||
* @deprecated import from `@backstage/search-backend-module-explore` instead
|
||||
*/
|
||||
export type ToolDocument = _ToolDocument;
|
||||
|
||||
/**
|
||||
* @public
|
||||
* @deprecated import from `@backstage/search-backend-module-explore` instead
|
||||
*/
|
||||
export type ToolDocumentCollatorFactoryOptions =
|
||||
_ToolDocumentCollatorFactoryOptions;
|
||||
|
||||
@@ -0,0 +1 @@
|
||||
module.exports = require('@backstage/cli/config/eslint-factory')(__dirname);
|
||||
@@ -0,0 +1,41 @@
|
||||
# search-backend-module-catalog
|
||||
|
||||
> DISCLAIMER: The new backend system is in alpha, and so are the search backend module support for the new backend system. We don't recommend you to migrate your backend installations to the new system yet. But if you want to experiment, you can find getting started guides below.
|
||||
|
||||
This package exports catalog backend modules responsible for extending search.
|
||||
|
||||
## Example
|
||||
|
||||
### Use default schedule
|
||||
|
||||
```tsx
|
||||
// packages/backend-next/src/index.ts
|
||||
import { createBackend } from '@backstage/backend-defaults';
|
||||
import { searchPlugin } from '@backstage/plugin-search-backend/alpha';
|
||||
import { searchModuleCatalogCollator } from '@backstage/plugin-search-backend-module-catalog/alpha';
|
||||
|
||||
const backend = createBackend();
|
||||
backend.add(searchPlugin());
|
||||
backend.add(searchModuleCatalogCollator());
|
||||
backend.start();
|
||||
```
|
||||
|
||||
### Use custom schedule
|
||||
|
||||
```tsx
|
||||
// packages/backend-next/src/index.ts
|
||||
import { createBackend } from '@backstage/backend-defaults';
|
||||
import { searchPlugin } from '@backstage/plugin-search-backend/alpha';
|
||||
import { searchModuleCatalogCollator } from '@backstage/plugin-search-backend-module-catalog/alpha';
|
||||
|
||||
const schedule = {
|
||||
frequency: { minutes: 10 },
|
||||
timeout: { minutes: 15 },
|
||||
initialDelay: { seconds: 3 },
|
||||
};
|
||||
|
||||
const backend = createBackend();
|
||||
backend.add(searchPlugin());
|
||||
backend.add(searchModuleCatalogCollator({ schedule }));
|
||||
backend.start();
|
||||
```
|
||||
@@ -0,0 +1,24 @@
|
||||
## API Report File for "@backstage/plugin-search-backend-module-catalog"
|
||||
|
||||
> Do not edit this file. It is a report generated by [API Extractor](https://api-extractor.com/).
|
||||
|
||||
```ts
|
||||
import { BackendFeature } from '@backstage/backend-plugin-api';
|
||||
import { DefaultCatalogCollatorFactoryOptions } from '@backstage/plugin-search-backend-module-catalog';
|
||||
import { TaskScheduleDefinition } from '@backstage/backend-tasks';
|
||||
|
||||
// @alpha
|
||||
export const searchModuleCatalogCollator: (
|
||||
options?: SearchModuleCatalogCollatorOptions | undefined,
|
||||
) => BackendFeature;
|
||||
|
||||
// @alpha
|
||||
export type SearchModuleCatalogCollatorOptions = Omit<
|
||||
DefaultCatalogCollatorFactoryOptions,
|
||||
'discovery' | 'tokenManager'
|
||||
> & {
|
||||
schedule?: TaskScheduleDefinition;
|
||||
};
|
||||
|
||||
// (No @packageDocumentation comment for this package)
|
||||
```
|
||||
@@ -0,0 +1,52 @@
|
||||
## API Report File for "@backstage/plugin-search-backend-module-catalog"
|
||||
|
||||
> Do not edit this file. It is a report generated by [API Extractor](https://api-extractor.com/).
|
||||
|
||||
```ts
|
||||
/// <reference types="node" />
|
||||
|
||||
import { CatalogApi } from '@backstage/catalog-client';
|
||||
import { CatalogEntityDocument } from '@backstage/plugin-catalog-common';
|
||||
import { Config } from '@backstage/config';
|
||||
import { DocumentCollatorFactory } from '@backstage/plugin-search-common';
|
||||
import { Entity } from '@backstage/catalog-model';
|
||||
import { GetEntitiesRequest } from '@backstage/catalog-client';
|
||||
import { Permission } from '@backstage/plugin-permission-common';
|
||||
import { PluginEndpointDiscovery } from '@backstage/backend-common';
|
||||
import { Readable } from 'stream';
|
||||
import { TokenManager } from '@backstage/backend-common';
|
||||
|
||||
// @public (undocumented)
|
||||
export type CatalogCollatorEntityTransformer = (
|
||||
entity: Entity,
|
||||
) => Omit<CatalogEntityDocument, 'location' | 'authorization'>;
|
||||
|
||||
// @public (undocumented)
|
||||
export const defaultCatalogCollatorEntityTransformer: CatalogCollatorEntityTransformer;
|
||||
|
||||
// @public (undocumented)
|
||||
export class DefaultCatalogCollatorFactory implements DocumentCollatorFactory {
|
||||
// (undocumented)
|
||||
static fromConfig(
|
||||
_config: Config,
|
||||
options: DefaultCatalogCollatorFactoryOptions,
|
||||
): DefaultCatalogCollatorFactory;
|
||||
// (undocumented)
|
||||
getCollator(): Promise<Readable>;
|
||||
// (undocumented)
|
||||
readonly type = 'software-catalog';
|
||||
// (undocumented)
|
||||
readonly visibilityPermission: Permission;
|
||||
}
|
||||
|
||||
// @public (undocumented)
|
||||
export type DefaultCatalogCollatorFactoryOptions = {
|
||||
discovery: PluginEndpointDiscovery;
|
||||
tokenManager: TokenManager;
|
||||
locationTemplate?: string;
|
||||
filter?: GetEntitiesRequest['filter'];
|
||||
batchSize?: number;
|
||||
catalogClient?: CatalogApi;
|
||||
entityTransformer?: CatalogCollatorEntityTransformer;
|
||||
};
|
||||
```
|
||||
@@ -0,0 +1,59 @@
|
||||
{
|
||||
"name": "@backstage/plugin-search-backend-module-catalog",
|
||||
"description": "A module for the search backend that exports catalog modules",
|
||||
"version": "0.0.0",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
"publishConfig": {
|
||||
"access": "public"
|
||||
},
|
||||
"exports": {
|
||||
".": "./src/index.ts",
|
||||
"./alpha": "./src/alpha.ts",
|
||||
"./package.json": "./package.json"
|
||||
},
|
||||
"typesVersions": {
|
||||
"*": {
|
||||
"alpha": [
|
||||
"src/alpha.ts"
|
||||
],
|
||||
"package.json": [
|
||||
"package.json"
|
||||
]
|
||||
}
|
||||
},
|
||||
"backstage": {
|
||||
"role": "backend-plugin-module"
|
||||
},
|
||||
"scripts": {
|
||||
"start": "backstage-cli package start",
|
||||
"build": "backstage-cli package build",
|
||||
"lint": "backstage-cli package lint",
|
||||
"test": "backstage-cli package test",
|
||||
"prepack": "backstage-cli package prepack",
|
||||
"postpack": "backstage-cli package postpack",
|
||||
"clean": "backstage-cli package clean"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "workspace:^",
|
||||
"@backstage/backend-plugin-api": "workspace:^",
|
||||
"@backstage/backend-tasks": "workspace:^",
|
||||
"@backstage/catalog-client": "workspace:^",
|
||||
"@backstage/catalog-model": "workspace:^",
|
||||
"@backstage/config": "workspace:^",
|
||||
"@backstage/plugin-catalog-common": "workspace:^",
|
||||
"@backstage/plugin-permission-common": "workspace:^",
|
||||
"@backstage/plugin-search-backend-node": "workspace:^",
|
||||
"@backstage/plugin-search-common": "workspace:^"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/backend-common": "workspace:^",
|
||||
"@backstage/backend-test-utils": "workspace:^",
|
||||
"@backstage/cli": "workspace:^",
|
||||
"msw": "^1.0.0"
|
||||
},
|
||||
"files": [
|
||||
"dist"
|
||||
]
|
||||
}
|
||||
@@ -0,0 +1,46 @@
|
||||
/*
|
||||
* 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 { startTestBackend } from '@backstage/backend-test-utils';
|
||||
import { searchIndexRegistryExtensionPoint } from '@backstage/plugin-search-backend-node/alpha';
|
||||
import { searchModuleCatalogCollator } from './alpha';
|
||||
|
||||
describe('searchModuleCatalogCollator', () => {
|
||||
const schedule = {
|
||||
frequency: { minutes: 10 },
|
||||
timeout: { minutes: 15 },
|
||||
initialDelay: { seconds: 3 },
|
||||
};
|
||||
|
||||
it('should register the catalog collator to the search index registry extension point with factory and schedule', async () => {
|
||||
const extensionPointMock = {
|
||||
addCollator: jest.fn(),
|
||||
};
|
||||
|
||||
await startTestBackend({
|
||||
extensionPoints: [
|
||||
[searchIndexRegistryExtensionPoint, extensionPointMock],
|
||||
],
|
||||
features: [searchModuleCatalogCollator({ schedule })],
|
||||
});
|
||||
|
||||
expect(extensionPointMock.addCollator).toHaveBeenCalledTimes(1);
|
||||
expect(extensionPointMock.addCollator).toHaveBeenCalledWith({
|
||||
factory: expect.objectContaining({ type: 'software-catalog' }),
|
||||
schedule: expect.objectContaining({ run: expect.any(Function) }),
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -0,0 +1,89 @@
|
||||
/*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @packageDocumentation
|
||||
* A module for the search backend that exports Catalog modules.
|
||||
*/
|
||||
|
||||
import {
|
||||
coreServices,
|
||||
createBackendModule,
|
||||
} from '@backstage/backend-plugin-api';
|
||||
import { TaskScheduleDefinition } from '@backstage/backend-tasks';
|
||||
import { searchIndexRegistryExtensionPoint } from '@backstage/plugin-search-backend-node/alpha';
|
||||
|
||||
import {
|
||||
DefaultCatalogCollatorFactory,
|
||||
DefaultCatalogCollatorFactoryOptions,
|
||||
} from '@backstage/plugin-search-backend-module-catalog';
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Options for {@link searchModuleCatalogCollator}.
|
||||
*/
|
||||
export type SearchModuleCatalogCollatorOptions = Omit<
|
||||
DefaultCatalogCollatorFactoryOptions,
|
||||
'discovery' | 'tokenManager'
|
||||
> & {
|
||||
schedule?: TaskScheduleDefinition;
|
||||
};
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Search backend module for the Catalog index.
|
||||
*/
|
||||
export const searchModuleCatalogCollator = createBackendModule(
|
||||
(options?: SearchModuleCatalogCollatorOptions) => ({
|
||||
moduleId: 'catalogCollator',
|
||||
pluginId: 'search',
|
||||
register(env) {
|
||||
env.registerInit({
|
||||
deps: {
|
||||
config: coreServices.config,
|
||||
discovery: coreServices.discovery,
|
||||
tokenManager: coreServices.tokenManager,
|
||||
scheduler: coreServices.scheduler,
|
||||
indexRegistry: searchIndexRegistryExtensionPoint,
|
||||
},
|
||||
async init({
|
||||
config,
|
||||
discovery,
|
||||
tokenManager,
|
||||
scheduler,
|
||||
indexRegistry,
|
||||
}) {
|
||||
const defaultSchedule = {
|
||||
frequency: { minutes: 10 },
|
||||
timeout: { minutes: 15 },
|
||||
initialDelay: { seconds: 3 },
|
||||
};
|
||||
|
||||
indexRegistry.addCollator({
|
||||
schedule: scheduler.createScheduledTaskRunner(
|
||||
options?.schedule ?? defaultSchedule,
|
||||
),
|
||||
factory: DefaultCatalogCollatorFactory.fromConfig(config, {
|
||||
...options,
|
||||
discovery,
|
||||
tokenManager,
|
||||
}),
|
||||
});
|
||||
},
|
||||
});
|
||||
},
|
||||
}),
|
||||
);
|
||||
@@ -0,0 +1,21 @@
|
||||
/*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
export { DefaultCatalogCollatorFactory } from './DefaultCatalogCollatorFactory';
|
||||
export type { DefaultCatalogCollatorFactoryOptions } from './DefaultCatalogCollatorFactory';
|
||||
|
||||
export { defaultCatalogCollatorEntityTransformer } from './defaultCatalogCollatorEntityTransformer';
|
||||
export type { CatalogCollatorEntityTransformer } from './CatalogCollatorEntityTransformer';
|
||||
@@ -0,0 +1,22 @@
|
||||
/*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @packageDocumentation
|
||||
* A module for the search backend that exports Catalog modules.
|
||||
*/
|
||||
|
||||
export * from './collators';
|
||||
@@ -0,0 +1,22 @@
|
||||
## API Report File for "@backstage/plugin-search-backend-module-elasticsearch"
|
||||
|
||||
> Do not edit this file. It is a report generated by [API Extractor](https://api-extractor.com/).
|
||||
|
||||
```ts
|
||||
import { BackendFeature } from '@backstage/backend-plugin-api';
|
||||
import { ElasticSearchCustomIndexTemplate } from '@backstage/plugin-search-backend-module-elasticsearch';
|
||||
import { ElasticSearchQueryTranslator } from '@backstage/plugin-search-backend-module-elasticsearch';
|
||||
|
||||
// @alpha
|
||||
export const searchModuleElasticsearchEngine: (
|
||||
options?: SearchModuleElasticsearchEngineOptions | undefined,
|
||||
) => BackendFeature;
|
||||
|
||||
// @alpha
|
||||
export type SearchModuleElasticsearchEngineOptions = {
|
||||
translator?: ElasticSearchQueryTranslator;
|
||||
indexTemplate?: ElasticSearchCustomIndexTemplate;
|
||||
};
|
||||
|
||||
// (No @packageDocumentation comment for this package)
|
||||
```
|
||||
@@ -6,9 +6,22 @@
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
"publishConfig": {
|
||||
"access": "public",
|
||||
"main": "dist/index.cjs.js",
|
||||
"types": "dist/index.d.ts"
|
||||
"access": "public"
|
||||
},
|
||||
"exports": {
|
||||
".": "./src/index.ts",
|
||||
"./alpha": "./src/alpha.ts",
|
||||
"./package.json": "./package.json"
|
||||
},
|
||||
"typesVersions": {
|
||||
"*": {
|
||||
"alpha": [
|
||||
"src/alpha.ts"
|
||||
],
|
||||
"package.json": [
|
||||
"package.json"
|
||||
]
|
||||
}
|
||||
},
|
||||
"backstage": {
|
||||
"role": "backend-plugin-module"
|
||||
@@ -23,6 +36,8 @@
|
||||
"clean": "backstage-cli package clean"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "workspace:^",
|
||||
"@backstage/backend-plugin-api": "workspace:^",
|
||||
"@backstage/config": "workspace:^",
|
||||
"@backstage/plugin-search-backend-node": "workspace:^",
|
||||
"@backstage/plugin-search-common": "workspace:^",
|
||||
|
||||
@@ -0,0 +1,74 @@
|
||||
/*
|
||||
* 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 {
|
||||
coreServices,
|
||||
createBackendModule,
|
||||
} from '@backstage/backend-plugin-api';
|
||||
import { loggerToWinstonLogger } from '@backstage/backend-common';
|
||||
import { searchEngineRegistryExtensionPoint } from '@backstage/plugin-search-backend-node/alpha';
|
||||
|
||||
import {
|
||||
ElasticSearchCustomIndexTemplate,
|
||||
ElasticSearchQueryTranslator,
|
||||
ElasticSearchSearchEngine,
|
||||
} from '@backstage/plugin-search-backend-module-elasticsearch';
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Options for {@link searchModuleElasticsearchEngine}.
|
||||
*/
|
||||
export type SearchModuleElasticsearchEngineOptions = {
|
||||
translator?: ElasticSearchQueryTranslator;
|
||||
indexTemplate?: ElasticSearchCustomIndexTemplate;
|
||||
};
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Search backend module for the Elasticsearch engine.
|
||||
*/
|
||||
export const searchModuleElasticsearchEngine = createBackendModule(
|
||||
(options?: SearchModuleElasticsearchEngineOptions) => ({
|
||||
moduleId: 'elasticsearchEngine',
|
||||
pluginId: 'search',
|
||||
register(env) {
|
||||
env.registerInit({
|
||||
deps: {
|
||||
searchEngineRegistry: searchEngineRegistryExtensionPoint,
|
||||
logger: coreServices.logger,
|
||||
config: coreServices.config,
|
||||
},
|
||||
async init({ searchEngineRegistry, logger, config }) {
|
||||
const searchEngine = await ElasticSearchSearchEngine.fromConfig({
|
||||
logger: loggerToWinstonLogger(logger),
|
||||
config: config,
|
||||
});
|
||||
|
||||
// set custom translator if available
|
||||
if (options?.translator) {
|
||||
searchEngine.setTranslator(options.translator);
|
||||
}
|
||||
|
||||
// set custom index template if available
|
||||
if (options?.indexTemplate) {
|
||||
searchEngine.setIndexTemplate(options.indexTemplate);
|
||||
}
|
||||
|
||||
searchEngineRegistry.setSearchEngine(searchEngine);
|
||||
},
|
||||
});
|
||||
},
|
||||
}),
|
||||
);
|
||||
@@ -0,0 +1 @@
|
||||
module.exports = require('@backstage/cli/config/eslint-factory')(__dirname);
|
||||
@@ -0,0 +1,41 @@
|
||||
# search-backend-module-explore
|
||||
|
||||
> DISCLAIMER: The new backend system is in alpha, and so are the search backend module support for the new backend system. We don't recommend you to migrate your backend installations to the new system yet. But if you want to experiment, you can find getting started guides below.
|
||||
|
||||
This package exports explore backend modules responsible for extending search.
|
||||
|
||||
## Example
|
||||
|
||||
### Use default schedule
|
||||
|
||||
```tsx
|
||||
// packages/backend-next/src/index.ts
|
||||
import { createBackend } from '@backstage/backend-defaults';
|
||||
import { searchPlugin } from '@backstage/plugin-search-backend/alpha';
|
||||
import { searchModuleExploreCollator } from '@backstage/plugin-search-backend-module-explore/alpha';
|
||||
|
||||
const backend = createBackend();
|
||||
backend.add(searchPlugin());
|
||||
backend.add(searchModuleExploreCollator());
|
||||
backend.start();
|
||||
```
|
||||
|
||||
### Use custom schedule
|
||||
|
||||
```tsx
|
||||
// packages/backend-next/src/index.ts
|
||||
import { createBackend } from '@backstage/backend-defaults';
|
||||
import { searchPlugin } from '@backstage/plugin-search-backend/alpha';
|
||||
import { searchModuleExploreCollator } from '@backstage/plugin-search-backend-module-explore/alpha';
|
||||
|
||||
const schedule = {
|
||||
frequency: { minutes: 10 },
|
||||
timeout: { minutes: 15 },
|
||||
initialDelay: { seconds: 3 },
|
||||
};
|
||||
|
||||
const backend = createBackend();
|
||||
backend.add(searchPlugin());
|
||||
backend.add(searchModuleExploreCollator({ schedule }));
|
||||
backend.start();
|
||||
```
|
||||
@@ -0,0 +1,24 @@
|
||||
## API Report File for "@backstage/plugin-search-backend-module-explore"
|
||||
|
||||
> Do not edit this file. It is a report generated by [API Extractor](https://api-extractor.com/).
|
||||
|
||||
```ts
|
||||
import { BackendFeature } from '@backstage/backend-plugin-api';
|
||||
import { TaskScheduleDefinition } from '@backstage/backend-tasks';
|
||||
import { ToolDocumentCollatorFactoryOptions } from '@backstage/plugin-search-backend-module-explore';
|
||||
|
||||
// @alpha
|
||||
export const searchModuleExploreCollator: (
|
||||
options?: SearchModuleExploreCollatorOptions | undefined,
|
||||
) => BackendFeature;
|
||||
|
||||
// @alpha
|
||||
export type SearchModuleExploreCollatorOptions = Omit<
|
||||
ToolDocumentCollatorFactoryOptions,
|
||||
'logger' | 'discovery'
|
||||
> & {
|
||||
schedule?: TaskScheduleDefinition;
|
||||
};
|
||||
|
||||
// (No @packageDocumentation comment for this package)
|
||||
```
|
||||
@@ -0,0 +1,39 @@
|
||||
## API Report File for "@backstage/plugin-search-backend-module-explore"
|
||||
|
||||
> Do not edit this file. It is a report generated by [API Extractor](https://api-extractor.com/).
|
||||
|
||||
```ts
|
||||
/// <reference types="node" />
|
||||
|
||||
import { Config } from '@backstage/config';
|
||||
import { DocumentCollatorFactory } from '@backstage/plugin-search-common';
|
||||
import { ExploreTool } from '@backstage/plugin-explore-common';
|
||||
import { IndexableDocument } from '@backstage/plugin-search-common';
|
||||
import { Logger } from 'winston';
|
||||
import { PluginEndpointDiscovery } from '@backstage/backend-common';
|
||||
import { Readable } from 'stream';
|
||||
|
||||
// @public
|
||||
export interface ToolDocument extends IndexableDocument, ExploreTool {}
|
||||
|
||||
// @public
|
||||
export class ToolDocumentCollatorFactory implements DocumentCollatorFactory {
|
||||
// (undocumented)
|
||||
execute(): AsyncGenerator<ToolDocument>;
|
||||
// (undocumented)
|
||||
static fromConfig(
|
||||
_config: Config,
|
||||
options: ToolDocumentCollatorFactoryOptions,
|
||||
): ToolDocumentCollatorFactory;
|
||||
// (undocumented)
|
||||
getCollator(): Promise<Readable>;
|
||||
// (undocumented)
|
||||
readonly type: string;
|
||||
}
|
||||
|
||||
// @public
|
||||
export type ToolDocumentCollatorFactoryOptions = {
|
||||
discovery: PluginEndpointDiscovery;
|
||||
logger: Logger;
|
||||
};
|
||||
```
|
||||
@@ -0,0 +1,56 @@
|
||||
{
|
||||
"name": "@backstage/plugin-search-backend-module-explore",
|
||||
"description": "A module for the search backend that exports explore modules",
|
||||
"version": "0.0.0",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
"publishConfig": {
|
||||
"access": "public"
|
||||
},
|
||||
"exports": {
|
||||
".": "./src/index.ts",
|
||||
"./alpha": "./src/alpha.ts",
|
||||
"./package.json": "./package.json"
|
||||
},
|
||||
"typesVersions": {
|
||||
"*": {
|
||||
"alpha": [
|
||||
"src/alpha.ts"
|
||||
],
|
||||
"package.json": [
|
||||
"package.json"
|
||||
]
|
||||
}
|
||||
},
|
||||
"backstage": {
|
||||
"role": "backend-plugin-module"
|
||||
},
|
||||
"scripts": {
|
||||
"start": "backstage-cli package start",
|
||||
"build": "backstage-cli package build",
|
||||
"lint": "backstage-cli package lint",
|
||||
"test": "backstage-cli package test",
|
||||
"prepack": "backstage-cli package prepack",
|
||||
"postpack": "backstage-cli package postpack",
|
||||
"clean": "backstage-cli package clean"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "workspace:^",
|
||||
"@backstage/backend-plugin-api": "workspace:^",
|
||||
"@backstage/backend-tasks": "workspace:^",
|
||||
"@backstage/config": "workspace:^",
|
||||
"@backstage/plugin-explore-common": "workspace:^",
|
||||
"@backstage/plugin-search-backend-node": "workspace:^",
|
||||
"@backstage/plugin-search-common": "workspace:^",
|
||||
"node-fetch": "^2.6.7",
|
||||
"winston": "^3.2.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/backend-test-utils": "workspace:^",
|
||||
"@backstage/cli": "workspace:^"
|
||||
},
|
||||
"files": [
|
||||
"dist"
|
||||
]
|
||||
}
|
||||
@@ -0,0 +1,46 @@
|
||||
/*
|
||||
* 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 { startTestBackend } from '@backstage/backend-test-utils';
|
||||
import { searchIndexRegistryExtensionPoint } from '@backstage/plugin-search-backend-node/alpha';
|
||||
import { searchModuleExploreCollator } from './alpha';
|
||||
|
||||
describe('searchModuleExploreCollator', () => {
|
||||
const schedule = {
|
||||
frequency: { minutes: 10 },
|
||||
timeout: { minutes: 15 },
|
||||
initialDelay: { seconds: 3 },
|
||||
};
|
||||
|
||||
it('should register the explore collator to the search index registry extension point with factory and schedule', async () => {
|
||||
const extensionPointMock = {
|
||||
addCollator: jest.fn(),
|
||||
};
|
||||
|
||||
await startTestBackend({
|
||||
extensionPoints: [
|
||||
[searchIndexRegistryExtensionPoint, extensionPointMock],
|
||||
],
|
||||
features: [searchModuleExploreCollator({ schedule })],
|
||||
});
|
||||
|
||||
expect(extensionPointMock.addCollator).toHaveBeenCalledTimes(1);
|
||||
expect(extensionPointMock.addCollator).toHaveBeenCalledWith({
|
||||
factory: expect.objectContaining({ type: 'tools' }),
|
||||
schedule: expect.objectContaining({ run: expect.any(Function) }),
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -0,0 +1,84 @@
|
||||
/*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @packageDocumentation
|
||||
* A module for the search backend that exports Explore modules.
|
||||
*/
|
||||
|
||||
import {
|
||||
coreServices,
|
||||
createBackendModule,
|
||||
} from '@backstage/backend-plugin-api';
|
||||
import { TaskScheduleDefinition } from '@backstage/backend-tasks';
|
||||
import { loggerToWinstonLogger } from '@backstage/backend-common';
|
||||
import { searchIndexRegistryExtensionPoint } from '@backstage/plugin-search-backend-node/alpha';
|
||||
|
||||
import {
|
||||
ToolDocumentCollatorFactory,
|
||||
ToolDocumentCollatorFactoryOptions,
|
||||
} from '@backstage/plugin-search-backend-module-explore';
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Options for {@link searchModuleExploreCollator}.
|
||||
*/
|
||||
export type SearchModuleExploreCollatorOptions = Omit<
|
||||
ToolDocumentCollatorFactoryOptions,
|
||||
'logger' | 'discovery'
|
||||
> & {
|
||||
schedule?: TaskScheduleDefinition;
|
||||
};
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Search backend module for the Explore index.
|
||||
*/
|
||||
export const searchModuleExploreCollator = createBackendModule(
|
||||
(options?: SearchModuleExploreCollatorOptions) => ({
|
||||
moduleId: 'exploreCollator',
|
||||
pluginId: 'search',
|
||||
register(env) {
|
||||
env.registerInit({
|
||||
deps: {
|
||||
config: coreServices.config,
|
||||
logger: coreServices.logger,
|
||||
discovery: coreServices.discovery,
|
||||
scheduler: coreServices.scheduler,
|
||||
indexRegistry: searchIndexRegistryExtensionPoint,
|
||||
},
|
||||
async init({ config, logger, discovery, scheduler, indexRegistry }) {
|
||||
const defaultSchedule = {
|
||||
frequency: { minutes: 10 },
|
||||
timeout: { minutes: 15 },
|
||||
initialDelay: { seconds: 3 },
|
||||
};
|
||||
|
||||
indexRegistry.addCollator({
|
||||
schedule: scheduler.createScheduledTaskRunner(
|
||||
options?.schedule ?? defaultSchedule,
|
||||
),
|
||||
factory: ToolDocumentCollatorFactory.fromConfig(config, {
|
||||
...options,
|
||||
discovery,
|
||||
logger: loggerToWinstonLogger(logger),
|
||||
}),
|
||||
});
|
||||
},
|
||||
});
|
||||
},
|
||||
}),
|
||||
);
|
||||
+1
@@ -15,6 +15,7 @@
|
||||
*/
|
||||
|
||||
export { ToolDocumentCollatorFactory } from './ToolDocumentCollatorFactory';
|
||||
|
||||
export type {
|
||||
ToolDocument,
|
||||
ToolDocumentCollatorFactoryOptions,
|
||||
@@ -0,0 +1,22 @@
|
||||
/*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @packageDocumentation
|
||||
* A module for the search backend that exports Explore modules.
|
||||
*/
|
||||
|
||||
export * from './collators';
|
||||
@@ -0,0 +1,12 @@
|
||||
## API Report File for "@backstage/plugin-search-backend-module-pg"
|
||||
|
||||
> Do not edit this file. It is a report generated by [API Extractor](https://api-extractor.com/).
|
||||
|
||||
```ts
|
||||
import { BackendFeature } from '@backstage/backend-plugin-api';
|
||||
|
||||
// @alpha
|
||||
export const searchModulePostgresEngine: () => BackendFeature;
|
||||
|
||||
// (No @packageDocumentation comment for this package)
|
||||
```
|
||||
@@ -6,9 +6,22 @@
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
"publishConfig": {
|
||||
"access": "public",
|
||||
"main": "dist/index.cjs.js",
|
||||
"types": "dist/index.d.ts"
|
||||
"access": "public"
|
||||
},
|
||||
"exports": {
|
||||
".": "./src/index.ts",
|
||||
"./alpha": "./src/alpha.ts",
|
||||
"./package.json": "./package.json"
|
||||
},
|
||||
"typesVersions": {
|
||||
"*": {
|
||||
"alpha": [
|
||||
"src/alpha.ts"
|
||||
],
|
||||
"package.json": [
|
||||
"package.json"
|
||||
]
|
||||
}
|
||||
},
|
||||
"backstage": {
|
||||
"role": "backend-plugin-module"
|
||||
@@ -24,6 +37,7 @@
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "workspace:^",
|
||||
"@backstage/backend-plugin-api": "workspace:^",
|
||||
"@backstage/config": "workspace:^",
|
||||
"@backstage/plugin-search-backend-node": "workspace:^",
|
||||
"@backstage/plugin-search-common": "workspace:^",
|
||||
|
||||
@@ -0,0 +1,46 @@
|
||||
/*
|
||||
* 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 {
|
||||
coreServices,
|
||||
createBackendModule,
|
||||
} from '@backstage/backend-plugin-api';
|
||||
import { searchEngineRegistryExtensionPoint } from '@backstage/plugin-search-backend-node/alpha';
|
||||
import { PgSearchEngine } from './PgSearchEngine';
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Search backend module for the Postgres engine.
|
||||
*/
|
||||
export const searchModulePostgresEngine = createBackendModule({
|
||||
moduleId: 'postgresEngine',
|
||||
pluginId: 'search',
|
||||
register(env) {
|
||||
env.registerInit({
|
||||
deps: {
|
||||
searchEngineRegistry: searchEngineRegistryExtensionPoint,
|
||||
database: coreServices.database,
|
||||
config: coreServices.config,
|
||||
},
|
||||
async init({ searchEngineRegistry, database, config }) {
|
||||
searchEngineRegistry.setSearchEngine(
|
||||
await PgSearchEngine.fromConfig(config, {
|
||||
database: database,
|
||||
}),
|
||||
);
|
||||
},
|
||||
});
|
||||
},
|
||||
});
|
||||
@@ -0,0 +1 @@
|
||||
module.exports = require('@backstage/cli/config/eslint-factory')(__dirname);
|
||||
@@ -0,0 +1,41 @@
|
||||
# search-backend-module-techdocs
|
||||
|
||||
> DISCLAIMER: The new backend system is in alpha, and so are the search backend module support for the new backend system. We don't recommend you to migrate your backend installations to the new system yet. But if you want to experiment, you can find getting started guides below.
|
||||
|
||||
This package exports techdocs backend modules responsible for extending search.
|
||||
|
||||
## Example
|
||||
|
||||
### Use default schedule
|
||||
|
||||
```tsx
|
||||
// packages/backend-next/src/index.ts
|
||||
import { createBackend } from '@backstage/backend-defaults';
|
||||
import { searchPlugin } from '@backstage/plugin-search-backend/alpha';
|
||||
import { searchModuleTechDocsCollator } from '@backstage/plugin-search-backend-module-techdocs/alpha';
|
||||
|
||||
const backend = createBackend();
|
||||
backend.add(searchPlugin());
|
||||
backend.add(searchModuleTechDocsCollator());
|
||||
backend.start();
|
||||
```
|
||||
|
||||
### Use custom schedule
|
||||
|
||||
```tsx
|
||||
// packages/backend-next/src/index.ts
|
||||
import { createBackend } from '@backstage/backend-defaults';
|
||||
import { searchPlugin } from '@backstage/plugin-search-backend/alpha';
|
||||
import { searchModuleTechDocsCollator } from '@backstage/plugin-search-backend-module-techdocs/alpha';
|
||||
|
||||
const schedule = {
|
||||
frequency: { minutes: 10 },
|
||||
timeout: { minutes: 15 },
|
||||
initialDelay: { seconds: 3 },
|
||||
};
|
||||
|
||||
const backend = createBackend();
|
||||
backend.add(searchPlugin());
|
||||
backend.add(searchModuleTechDocsCollator({ schedule }));
|
||||
backend.start();
|
||||
```
|
||||
@@ -0,0 +1,24 @@
|
||||
## API Report File for "@backstage/plugin-search-backend-module-techdocs"
|
||||
|
||||
> Do not edit this file. It is a report generated by [API Extractor](https://api-extractor.com/).
|
||||
|
||||
```ts
|
||||
import { BackendFeature } from '@backstage/backend-plugin-api';
|
||||
import { TaskScheduleDefinition } from '@backstage/backend-tasks';
|
||||
import { TechDocsCollatorFactoryOptions } from '@backstage/plugin-search-backend-module-techdocs';
|
||||
|
||||
// @alpha
|
||||
export const searchModuleTechDocsCollator: (
|
||||
options?: SearchModuleTechDocsCollatorOptions | undefined,
|
||||
) => BackendFeature;
|
||||
|
||||
// @alpha
|
||||
export type SearchModuleTechDocsCollatorOptions = Omit<
|
||||
TechDocsCollatorFactoryOptions,
|
||||
'logger' | 'discovery' | 'tokenManager'
|
||||
> & {
|
||||
schedule?: TaskScheduleDefinition;
|
||||
};
|
||||
|
||||
// (No @packageDocumentation comment for this package)
|
||||
```
|
||||
@@ -0,0 +1,42 @@
|
||||
## API Report File for "@backstage/plugin-search-backend-module-techdocs"
|
||||
|
||||
> Do not edit this file. It is a report generated by [API Extractor](https://api-extractor.com/).
|
||||
|
||||
```ts
|
||||
/// <reference types="node" />
|
||||
|
||||
import { CatalogApi } from '@backstage/catalog-client';
|
||||
import { Config } from '@backstage/config';
|
||||
import { DocumentCollatorFactory } from '@backstage/plugin-search-common';
|
||||
import { Logger } from 'winston';
|
||||
import { Permission } from '@backstage/plugin-permission-common';
|
||||
import { PluginEndpointDiscovery } from '@backstage/backend-common';
|
||||
import { Readable } from 'stream';
|
||||
import { TokenManager } from '@backstage/backend-common';
|
||||
|
||||
// @public
|
||||
export class DefaultTechDocsCollatorFactory implements DocumentCollatorFactory {
|
||||
// (undocumented)
|
||||
static fromConfig(
|
||||
config: Config,
|
||||
options: TechDocsCollatorFactoryOptions,
|
||||
): DefaultTechDocsCollatorFactory;
|
||||
// (undocumented)
|
||||
getCollator(): Promise<Readable>;
|
||||
// (undocumented)
|
||||
readonly type: string;
|
||||
// (undocumented)
|
||||
readonly visibilityPermission: Permission;
|
||||
}
|
||||
|
||||
// @public
|
||||
export type TechDocsCollatorFactoryOptions = {
|
||||
discovery: PluginEndpointDiscovery;
|
||||
logger: Logger;
|
||||
tokenManager: TokenManager;
|
||||
locationTemplate?: string;
|
||||
catalogClient?: CatalogApi;
|
||||
parallelismLimit?: number;
|
||||
legacyPathCasing?: boolean;
|
||||
};
|
||||
```
|
||||
@@ -0,0 +1,63 @@
|
||||
{
|
||||
"name": "@backstage/plugin-search-backend-module-techdocs",
|
||||
"description": "A module for the search backend that exports techdocs modules",
|
||||
"version": "0.0.0",
|
||||
"main": "src/index.ts",
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
"publishConfig": {
|
||||
"access": "public"
|
||||
},
|
||||
"exports": {
|
||||
".": "./src/index.ts",
|
||||
"./alpha": "./src/alpha.ts",
|
||||
"./package.json": "./package.json"
|
||||
},
|
||||
"typesVersions": {
|
||||
"*": {
|
||||
"alpha": [
|
||||
"src/alpha.ts"
|
||||
],
|
||||
"package.json": [
|
||||
"package.json"
|
||||
]
|
||||
}
|
||||
},
|
||||
"backstage": {
|
||||
"role": "backend-plugin-module"
|
||||
},
|
||||
"scripts": {
|
||||
"start": "backstage-cli package start",
|
||||
"build": "backstage-cli package build",
|
||||
"lint": "backstage-cli package lint",
|
||||
"test": "backstage-cli package test",
|
||||
"prepack": "backstage-cli package prepack",
|
||||
"postpack": "backstage-cli package postpack",
|
||||
"clean": "backstage-cli package clean"
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "workspace:^",
|
||||
"@backstage/backend-plugin-api": "workspace:^",
|
||||
"@backstage/backend-tasks": "workspace:^",
|
||||
"@backstage/catalog-client": "workspace:^",
|
||||
"@backstage/catalog-model": "workspace:^",
|
||||
"@backstage/config": "workspace:^",
|
||||
"@backstage/plugin-catalog-common": "workspace:^",
|
||||
"@backstage/plugin-permission-common": "workspace:^",
|
||||
"@backstage/plugin-search-backend-node": "workspace:^",
|
||||
"@backstage/plugin-search-common": "workspace:^",
|
||||
"@backstage/plugin-techdocs-node": "workspace:^",
|
||||
"lodash": "^4.17.21",
|
||||
"node-fetch": "^2.6.7",
|
||||
"p-limit": "^3.1.0",
|
||||
"winston": "^3.2.1"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/backend-test-utils": "workspace:^",
|
||||
"@backstage/cli": "workspace:^",
|
||||
"msw": "^1.0.0"
|
||||
},
|
||||
"files": [
|
||||
"dist"
|
||||
]
|
||||
}
|
||||
@@ -0,0 +1,46 @@
|
||||
/*
|
||||
* 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 { startTestBackend } from '@backstage/backend-test-utils';
|
||||
import { searchIndexRegistryExtensionPoint } from '@backstage/plugin-search-backend-node/alpha';
|
||||
import { searchModuleTechDocsCollator } from './alpha';
|
||||
|
||||
describe('searchModuleTechDocsCollator', () => {
|
||||
const schedule = {
|
||||
frequency: { minutes: 10 },
|
||||
timeout: { minutes: 15 },
|
||||
initialDelay: { seconds: 3 },
|
||||
};
|
||||
|
||||
it('should register the techdocs collator to the search index registry extension point with factory and schedule', async () => {
|
||||
const extensionPointMock = {
|
||||
addCollator: jest.fn(),
|
||||
};
|
||||
|
||||
await startTestBackend({
|
||||
extensionPoints: [
|
||||
[searchIndexRegistryExtensionPoint, extensionPointMock],
|
||||
],
|
||||
features: [searchModuleTechDocsCollator({ schedule })],
|
||||
});
|
||||
|
||||
expect(extensionPointMock.addCollator).toHaveBeenCalledTimes(1);
|
||||
expect(extensionPointMock.addCollator).toHaveBeenCalledWith({
|
||||
factory: expect.objectContaining({ type: 'techdocs' }),
|
||||
schedule: expect.objectContaining({ run: expect.any(Function) }),
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -0,0 +1,93 @@
|
||||
/*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @packageDocumentation
|
||||
* A module for the search backend that exports TechDocs modules.
|
||||
*/
|
||||
|
||||
import {
|
||||
coreServices,
|
||||
createBackendModule,
|
||||
} from '@backstage/backend-plugin-api';
|
||||
import { TaskScheduleDefinition } from '@backstage/backend-tasks';
|
||||
import { loggerToWinstonLogger } from '@backstage/backend-common';
|
||||
import { searchIndexRegistryExtensionPoint } from '@backstage/plugin-search-backend-node/alpha';
|
||||
|
||||
import {
|
||||
DefaultTechDocsCollatorFactory,
|
||||
TechDocsCollatorFactoryOptions,
|
||||
} from '@backstage/plugin-search-backend-module-techdocs';
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Options for {@link searchModuleTechDocsCollator}.
|
||||
*/
|
||||
export type SearchModuleTechDocsCollatorOptions = Omit<
|
||||
TechDocsCollatorFactoryOptions,
|
||||
'logger' | 'discovery' | 'tokenManager'
|
||||
> & {
|
||||
schedule?: TaskScheduleDefinition;
|
||||
};
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Search backend module for the TechDocs index.
|
||||
*/
|
||||
export const searchModuleTechDocsCollator = createBackendModule(
|
||||
(options?: SearchModuleTechDocsCollatorOptions) => ({
|
||||
moduleId: 'techDocsCollator',
|
||||
pluginId: 'search',
|
||||
register(env) {
|
||||
env.registerInit({
|
||||
deps: {
|
||||
config: coreServices.config,
|
||||
logger: coreServices.logger,
|
||||
discovery: coreServices.discovery,
|
||||
tokenManager: coreServices.tokenManager,
|
||||
scheduler: coreServices.scheduler,
|
||||
indexRegistry: searchIndexRegistryExtensionPoint,
|
||||
},
|
||||
async init({
|
||||
config,
|
||||
logger,
|
||||
discovery,
|
||||
tokenManager,
|
||||
scheduler,
|
||||
indexRegistry,
|
||||
}) {
|
||||
const defaultSchedule = {
|
||||
frequency: { minutes: 10 },
|
||||
timeout: { minutes: 15 },
|
||||
initialDelay: { seconds: 3 },
|
||||
};
|
||||
|
||||
indexRegistry.addCollator({
|
||||
schedule: scheduler.createScheduledTaskRunner(
|
||||
options?.schedule ?? defaultSchedule,
|
||||
),
|
||||
factory: DefaultTechDocsCollatorFactory.fromConfig(config, {
|
||||
...options,
|
||||
discovery,
|
||||
tokenManager,
|
||||
logger: loggerToWinstonLogger(logger),
|
||||
}),
|
||||
});
|
||||
},
|
||||
});
|
||||
},
|
||||
}),
|
||||
);
|
||||
@@ -0,0 +1,19 @@
|
||||
/*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
export { DefaultTechDocsCollatorFactory } from './DefaultTechDocsCollatorFactory';
|
||||
|
||||
export type { TechDocsCollatorFactoryOptions } from './DefaultTechDocsCollatorFactory';
|
||||
@@ -0,0 +1,22 @@
|
||||
/*
|
||||
* 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.
|
||||
*/
|
||||
|
||||
/**
|
||||
* @packageDocumentation
|
||||
* A module for the search backend that exports TechDocs modules.
|
||||
*/
|
||||
|
||||
export * from './collators';
|
||||
@@ -0,0 +1,50 @@
|
||||
## API Report File for "@backstage/plugin-search-backend-node"
|
||||
|
||||
> Do not edit this file. It is a report generated by [API Extractor](https://api-extractor.com/).
|
||||
|
||||
```ts
|
||||
import { DocumentTypeInfo } from '@backstage/plugin-search-common';
|
||||
import { ExtensionPoint } from '@backstage/backend-plugin-api';
|
||||
import { RegisterCollatorParameters } from '@backstage/plugin-search-backend-node';
|
||||
import { RegisterDecoratorParameters } from '@backstage/plugin-search-backend-node';
|
||||
import { SearchEngine } from '@backstage/plugin-search-common';
|
||||
import { ServiceRef } from '@backstage/backend-plugin-api';
|
||||
|
||||
// @alpha
|
||||
export interface SearchEngineRegistryExtensionPoint {
|
||||
// (undocumented)
|
||||
setSearchEngine(searchEngine: SearchEngine): void;
|
||||
}
|
||||
|
||||
// @alpha
|
||||
export const searchEngineRegistryExtensionPoint: ExtensionPoint<SearchEngineRegistryExtensionPoint>;
|
||||
|
||||
// @alpha
|
||||
export interface SearchIndexRegistryExtensionPoint {
|
||||
// (undocumented)
|
||||
addCollator(options: RegisterCollatorParameters): void;
|
||||
// (undocumented)
|
||||
addDecorator(options: RegisterDecoratorParameters): void;
|
||||
}
|
||||
|
||||
// @alpha
|
||||
export const searchIndexRegistryExtensionPoint: ExtensionPoint<SearchIndexRegistryExtensionPoint>;
|
||||
|
||||
// @alpha
|
||||
export interface SearchIndexService {
|
||||
getDocumentTypes(): Record<string, DocumentTypeInfo>;
|
||||
start(options: SearchIndexServiceStartOptions): Promise<void>;
|
||||
}
|
||||
|
||||
// @alpha
|
||||
export const searchIndexServiceRef: ServiceRef<SearchIndexService, 'plugin'>;
|
||||
|
||||
// @alpha
|
||||
export type SearchIndexServiceStartOptions = {
|
||||
searchEngine: SearchEngine;
|
||||
collators: RegisterCollatorParameters[];
|
||||
decorators: RegisterDecoratorParameters[];
|
||||
};
|
||||
|
||||
// (No @packageDocumentation comment for this package)
|
||||
```
|
||||
@@ -6,9 +6,22 @@
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
"publishConfig": {
|
||||
"access": "public",
|
||||
"main": "dist/index.cjs.js",
|
||||
"types": "dist/index.d.ts"
|
||||
"access": "public"
|
||||
},
|
||||
"exports": {
|
||||
".": "./src/index.ts",
|
||||
"./alpha": "./src/alpha.ts",
|
||||
"./package.json": "./package.json"
|
||||
},
|
||||
"typesVersions": {
|
||||
"*": {
|
||||
"alpha": [
|
||||
"src/alpha.ts"
|
||||
],
|
||||
"package.json": [
|
||||
"package.json"
|
||||
]
|
||||
}
|
||||
},
|
||||
"backstage": {
|
||||
"role": "node-library"
|
||||
@@ -24,6 +37,7 @@
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "workspace:^",
|
||||
"@backstage/backend-plugin-api": "workspace:^",
|
||||
"@backstage/backend-tasks": "workspace:^",
|
||||
"@backstage/config": "workspace:^",
|
||||
"@backstage/errors": "workspace:^",
|
||||
|
||||
@@ -0,0 +1,159 @@
|
||||
/*
|
||||
* 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 { Logger } from 'winston';
|
||||
|
||||
import {
|
||||
createServiceRef,
|
||||
createServiceFactory,
|
||||
coreServices,
|
||||
} from '@backstage/backend-plugin-api';
|
||||
import { loggerToWinstonLogger } from '@backstage/backend-common';
|
||||
import {
|
||||
DocumentTypeInfo,
|
||||
SearchEngine,
|
||||
} from '@backstage/plugin-search-common';
|
||||
import { createExtensionPoint } from '@backstage/backend-plugin-api';
|
||||
|
||||
import {
|
||||
RegisterCollatorParameters,
|
||||
RegisterDecoratorParameters,
|
||||
} from '@backstage/plugin-search-backend-node';
|
||||
|
||||
import { IndexBuilder } from './IndexBuilder';
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Options for build method on {@link SearchIndexService}.
|
||||
*/
|
||||
export type SearchIndexServiceStartOptions = {
|
||||
searchEngine: SearchEngine;
|
||||
collators: RegisterCollatorParameters[];
|
||||
decorators: RegisterDecoratorParameters[];
|
||||
};
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Interface for implementation of index service.
|
||||
*/
|
||||
export interface SearchIndexService {
|
||||
/**
|
||||
* Starts indexing process
|
||||
*/
|
||||
start(options: SearchIndexServiceStartOptions): Promise<void>;
|
||||
/**
|
||||
* Returns an index types list.
|
||||
*/
|
||||
getDocumentTypes(): Record<string, DocumentTypeInfo>;
|
||||
}
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Interface for search index registry extension point.
|
||||
*/
|
||||
export interface SearchIndexRegistryExtensionPoint {
|
||||
addCollator(options: RegisterCollatorParameters): void;
|
||||
addDecorator(options: RegisterDecoratorParameters): void;
|
||||
}
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Interface for search engine registry extension point.
|
||||
*/
|
||||
export interface SearchEngineRegistryExtensionPoint {
|
||||
setSearchEngine(searchEngine: SearchEngine): void;
|
||||
}
|
||||
|
||||
type DefaultSearchIndexServiceOptions = {
|
||||
logger: Logger;
|
||||
};
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Reponsible for register the indexing task and start the schedule.
|
||||
*/
|
||||
class DefaultSearchIndexService implements SearchIndexService {
|
||||
private logger: Logger;
|
||||
private indexBuilder: IndexBuilder | null = null;
|
||||
|
||||
private constructor(options: DefaultSearchIndexServiceOptions) {
|
||||
this.logger = options.logger;
|
||||
}
|
||||
|
||||
static fromConfig(options: DefaultSearchIndexServiceOptions) {
|
||||
return new DefaultSearchIndexService(options);
|
||||
}
|
||||
|
||||
async start(options: SearchIndexServiceStartOptions): Promise<void> {
|
||||
this.indexBuilder = new IndexBuilder({
|
||||
logger: this.logger,
|
||||
searchEngine: options.searchEngine,
|
||||
});
|
||||
|
||||
options.collators.forEach(collator =>
|
||||
this.indexBuilder?.addCollator(collator),
|
||||
);
|
||||
|
||||
options.decorators.forEach(decorator =>
|
||||
this.indexBuilder?.addDecorator(decorator),
|
||||
);
|
||||
|
||||
const { scheduler } = await this.indexBuilder?.build();
|
||||
scheduler.start();
|
||||
}
|
||||
|
||||
getDocumentTypes(): Record<string, DocumentTypeInfo> {
|
||||
return this.indexBuilder?.getDocumentTypes() ?? {};
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Service that builds a search index.
|
||||
*/
|
||||
export const searchIndexServiceRef = createServiceRef<SearchIndexService>({
|
||||
id: 'search.index.service',
|
||||
defaultFactory: async service =>
|
||||
createServiceFactory({
|
||||
service,
|
||||
deps: {
|
||||
logger: coreServices.logger,
|
||||
},
|
||||
factory({ logger }) {
|
||||
return DefaultSearchIndexService.fromConfig({
|
||||
logger: loggerToWinstonLogger(logger),
|
||||
});
|
||||
},
|
||||
}),
|
||||
});
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Extension point for register a search engine.
|
||||
*/
|
||||
export const searchEngineRegistryExtensionPoint =
|
||||
createExtensionPoint<SearchEngineRegistryExtensionPoint>({
|
||||
id: 'search.engine.registry',
|
||||
});
|
||||
|
||||
/**
|
||||
* @alpha
|
||||
* Extension point for registering collators and decorators
|
||||
*/
|
||||
export const searchIndexRegistryExtensionPoint =
|
||||
createExtensionPoint<SearchIndexRegistryExtensionPoint>({
|
||||
id: 'search.index.registry',
|
||||
});
|
||||
@@ -0,0 +1,12 @@
|
||||
## API Report File for "@backstage/plugin-search-backend"
|
||||
|
||||
> Do not edit this file. It is a report generated by [API Extractor](https://api-extractor.com/).
|
||||
|
||||
```ts
|
||||
import { BackendFeature } from '@backstage/backend-plugin-api';
|
||||
|
||||
// @alpha
|
||||
export const searchPlugin: () => BackendFeature;
|
||||
|
||||
// (No @packageDocumentation comment for this package)
|
||||
```
|
||||
@@ -6,9 +6,22 @@
|
||||
"types": "src/index.ts",
|
||||
"license": "Apache-2.0",
|
||||
"publishConfig": {
|
||||
"access": "public",
|
||||
"main": "dist/index.cjs.js",
|
||||
"types": "dist/index.d.ts"
|
||||
"access": "public"
|
||||
},
|
||||
"exports": {
|
||||
".": "./src/index.ts",
|
||||
"./alpha": "./src/alpha.ts",
|
||||
"./package.json": "./package.json"
|
||||
},
|
||||
"typesVersions": {
|
||||
"*": {
|
||||
"alpha": [
|
||||
"src/alpha.ts"
|
||||
],
|
||||
"package.json": [
|
||||
"package.json"
|
||||
]
|
||||
}
|
||||
},
|
||||
"backstage": {
|
||||
"role": "backend-plugin"
|
||||
@@ -24,6 +37,7 @@
|
||||
},
|
||||
"dependencies": {
|
||||
"@backstage/backend-common": "workspace:^",
|
||||
"@backstage/backend-plugin-api": "workspace:^",
|
||||
"@backstage/config": "workspace:^",
|
||||
"@backstage/errors": "workspace:^",
|
||||
"@backstage/plugin-auth-node": "workspace:^",
|
||||
@@ -43,6 +57,7 @@
|
||||
"zod": "~3.18.0"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@backstage/backend-test-utils": "workspace:^",
|
||||
"@backstage/cli": "workspace:^",
|
||||
"@types/supertest": "^2.0.8",
|
||||
"supertest": "^6.1.3"
|
||||
|
||||
@@ -0,0 +1,31 @@
|
||||
/*
|
||||
* 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 { startTestBackend } from '@backstage/backend-test-utils';
|
||||
import request from 'supertest';
|
||||
import { searchPlugin } from './alpha';
|
||||
|
||||
describe('searchPlugin', () => {
|
||||
it('should serve search results on query endpoint', async () => {
|
||||
const { server } = await startTestBackend({
|
||||
features: [searchPlugin()],
|
||||
});
|
||||
|
||||
const response = await request(server).get('/api/search/query');
|
||||
expect(response.status).toBe(200);
|
||||
expect(response.body).toEqual({ numberOfResults: 0, results: [] });
|
||||
});
|
||||
});
|
||||
@@ -0,0 +1,130 @@
|
||||
/*
|
||||
* 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 {
|
||||
coreServices,
|
||||
createBackendPlugin,
|
||||
} from '@backstage/backend-plugin-api';
|
||||
import { loggerToWinstonLogger } from '@backstage/backend-common';
|
||||
import {
|
||||
RegisterCollatorParameters,
|
||||
RegisterDecoratorParameters,
|
||||
LunrSearchEngine,
|
||||
} from '@backstage/plugin-search-backend-node';
|
||||
import {
|
||||
searchIndexServiceRef,
|
||||
searchIndexRegistryExtensionPoint,
|
||||
SearchIndexRegistryExtensionPoint,
|
||||
SearchEngineRegistryExtensionPoint,
|
||||
searchEngineRegistryExtensionPoint,
|
||||
} from '@backstage/plugin-search-backend-node/alpha';
|
||||
|
||||
import { createRouter } from './service/router';
|
||||
import { SearchEngine } from '@backstage/plugin-search-common';
|
||||
|
||||
class SearchIndexRegistry implements SearchIndexRegistryExtensionPoint {
|
||||
private collators: RegisterCollatorParameters[] = [];
|
||||
private decorators: RegisterDecoratorParameters[] = [];
|
||||
|
||||
public addCollator(options: RegisterCollatorParameters): void {
|
||||
this.collators.push(options);
|
||||
}
|
||||
|
||||
public addDecorator(options: RegisterDecoratorParameters): void {
|
||||
this.decorators.push(options);
|
||||
}
|
||||
|
||||
public getCollators(): RegisterCollatorParameters[] {
|
||||
return this.collators;
|
||||
}
|
||||
|
||||
public getDecorators(): RegisterDecoratorParameters[] {
|
||||
return this.decorators;
|
||||
}
|
||||
}
|
||||
|
||||
class SearchEngineRegistry implements SearchEngineRegistryExtensionPoint {
|
||||
private searchEngine: SearchEngine | null = null;
|
||||
|
||||
public setSearchEngine(searchEngine: SearchEngine): void {
|
||||
if (this.searchEngine) {
|
||||
throw new Error('Multiple Search engines is not supported at this time');
|
||||
}
|
||||
this.searchEngine = searchEngine;
|
||||
}
|
||||
|
||||
public getSearchEngine(): SearchEngine | null {
|
||||
return this.searchEngine;
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* The Search plugin is responsible for starting search indexing processes and return search results.
|
||||
* @alpha
|
||||
*/
|
||||
export const searchPlugin = createBackendPlugin({
|
||||
pluginId: 'search',
|
||||
register(env) {
|
||||
const searchIndexRegistry = new SearchIndexRegistry();
|
||||
env.registerExtensionPoint(
|
||||
searchIndexRegistryExtensionPoint,
|
||||
searchIndexRegistry,
|
||||
);
|
||||
|
||||
const searchEngineRegistry = new SearchEngineRegistry();
|
||||
env.registerExtensionPoint(
|
||||
searchEngineRegistryExtensionPoint,
|
||||
searchEngineRegistry,
|
||||
);
|
||||
|
||||
env.registerInit({
|
||||
deps: {
|
||||
logger: coreServices.logger,
|
||||
config: coreServices.config,
|
||||
permissions: coreServices.permissions,
|
||||
http: coreServices.httpRouter,
|
||||
searchIndexService: searchIndexServiceRef,
|
||||
},
|
||||
async init({ config, logger, permissions, http, searchIndexService }) {
|
||||
let searchEngine = searchEngineRegistry.getSearchEngine();
|
||||
if (!searchEngine) {
|
||||
searchEngine = new LunrSearchEngine({
|
||||
logger: loggerToWinstonLogger(logger),
|
||||
});
|
||||
}
|
||||
|
||||
const collators = searchIndexRegistry.getCollators();
|
||||
const decorators = searchIndexRegistry.getDecorators();
|
||||
|
||||
await searchIndexService.start({
|
||||
searchEngine,
|
||||
collators,
|
||||
decorators,
|
||||
});
|
||||
|
||||
const router = await createRouter({
|
||||
config,
|
||||
permissions,
|
||||
logger: loggerToWinstonLogger(logger),
|
||||
engine: searchEngine,
|
||||
types: searchIndexService.getDocumentTypes(),
|
||||
});
|
||||
|
||||
http.use(router);
|
||||
},
|
||||
});
|
||||
},
|
||||
});
|
||||
@@ -3,12 +3,10 @@
|
||||
> Do not edit this file. It is a report generated by [API Extractor](https://api-extractor.com/).
|
||||
|
||||
```ts
|
||||
/// <reference types="node" />
|
||||
|
||||
import { CatalogApi } from '@backstage/catalog-client';
|
||||
import { CatalogClient } from '@backstage/catalog-client';
|
||||
import { Config } from '@backstage/config';
|
||||
import { DocumentCollatorFactory } from '@backstage/plugin-search-common';
|
||||
import { DefaultTechDocsCollatorFactory as DefaultTechDocsCollatorFactory_2 } from '@backstage/plugin-search-backend-module-techdocs';
|
||||
import { Entity } from '@backstage/catalog-model';
|
||||
import express from 'express';
|
||||
import { GeneratorBuilder } from '@backstage/plugin-techdocs-node';
|
||||
@@ -19,7 +17,7 @@ import { PluginCacheManager } from '@backstage/backend-common';
|
||||
import { PluginEndpointDiscovery } from '@backstage/backend-common';
|
||||
import { PreparerBuilder } from '@backstage/plugin-techdocs-node';
|
||||
import { PublisherBase } from '@backstage/plugin-techdocs-node';
|
||||
import { Readable } from 'stream';
|
||||
import type { TechDocsCollatorFactoryOptions as TechDocsCollatorFactoryOptions_2 } from '@backstage/plugin-search-backend-module-techdocs';
|
||||
import { TechDocsDocument } from '@backstage/plugin-techdocs-node';
|
||||
import { TokenManager } from '@backstage/backend-common';
|
||||
import * as winston from 'winston';
|
||||
@@ -47,20 +45,8 @@ export class DefaultTechDocsCollator {
|
||||
readonly visibilityPermission: Permission;
|
||||
}
|
||||
|
||||
// @public
|
||||
export class DefaultTechDocsCollatorFactory implements DocumentCollatorFactory {
|
||||
// (undocumented)
|
||||
static fromConfig(
|
||||
config: Config,
|
||||
options: TechDocsCollatorFactoryOptions,
|
||||
): DefaultTechDocsCollatorFactory;
|
||||
// (undocumented)
|
||||
getCollator(): Promise<Readable>;
|
||||
// (undocumented)
|
||||
readonly type: string;
|
||||
// (undocumented)
|
||||
readonly visibilityPermission: Permission;
|
||||
}
|
||||
// @public @deprecated (undocumented)
|
||||
export const DefaultTechDocsCollatorFactory: typeof DefaultTechDocsCollatorFactory_2;
|
||||
|
||||
// @public
|
||||
export interface DocsBuildStrategy {
|
||||
@@ -105,16 +91,8 @@ export type ShouldBuildParameters = {
|
||||
entity: Entity;
|
||||
};
|
||||
|
||||
// @public
|
||||
export type TechDocsCollatorFactoryOptions = {
|
||||
discovery: PluginEndpointDiscovery;
|
||||
logger: Logger;
|
||||
tokenManager: TokenManager;
|
||||
locationTemplate?: string;
|
||||
catalogClient?: CatalogApi;
|
||||
parallelismLimit?: number;
|
||||
legacyPathCasing?: boolean;
|
||||
};
|
||||
// @public @deprecated (undocumented)
|
||||
export type TechDocsCollatorFactoryOptions = TechDocsCollatorFactoryOptions_2;
|
||||
|
||||
// @public
|
||||
export type TechDocsCollatorOptions = {
|
||||
|
||||
@@ -57,6 +57,7 @@
|
||||
"@backstage/integration": "workspace:^",
|
||||
"@backstage/plugin-catalog-common": "workspace:^",
|
||||
"@backstage/plugin-permission-common": "workspace:^",
|
||||
"@backstage/plugin-search-backend-module-techdocs": "workspace:^",
|
||||
"@backstage/plugin-search-common": "workspace:^",
|
||||
"@backstage/plugin-techdocs-node": "workspace:^",
|
||||
"@types/express": "^4.17.6",
|
||||
|
||||
@@ -14,11 +14,23 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
export { DefaultTechDocsCollatorFactory } from './DefaultTechDocsCollatorFactory';
|
||||
export type { TechDocsCollatorFactoryOptions } from './DefaultTechDocsCollatorFactory';
|
||||
|
||||
/**
|
||||
* todo(backstage/techdocs-core): stop exporting these in a future release.
|
||||
*/
|
||||
export { DefaultTechDocsCollator } from './DefaultTechDocsCollator';
|
||||
export type { TechDocsCollatorOptions } from './DefaultTechDocsCollator';
|
||||
|
||||
import { DefaultTechDocsCollatorFactory as _DefaultTechDocsCollatorFactory } from '@backstage/plugin-search-backend-module-techdocs';
|
||||
import type { TechDocsCollatorFactoryOptions as _TechDocsCollatorFactoryOptions } from '@backstage/plugin-search-backend-module-techdocs';
|
||||
|
||||
/**
|
||||
* @public
|
||||
* @deprecated import from `@backstage/search-backend-module-techdocs` instead
|
||||
*/
|
||||
export type TechDocsCollatorFactoryOptions = _TechDocsCollatorFactoryOptions;
|
||||
|
||||
/**
|
||||
* @public
|
||||
* @deprecated import from `@backstage/search-backend-module-techdocs` instead
|
||||
*/
|
||||
export const DefaultTechDocsCollatorFactory = _DefaultTechDocsCollatorFactory;
|
||||
|
||||
Reference in New Issue
Block a user