diff --git a/.changeset/tall-parents-deny.md b/.changeset/tall-parents-deny.md new file mode 100644 index 0000000000..c757b37b79 --- /dev/null +++ b/.changeset/tall-parents-deny.md @@ -0,0 +1,20 @@ +--- +'@backstage/plugin-search-react': minor +--- + +**BREAKING**: `SearchContextProviderForStorybook` and `SearchApiProviderForStorybook` has been deleted. New mock implementation of the `SearchApi` introduced. If you need to mock the api we recommend you to do the following: + +```tsx +import { + searchApiRef, + MockSearchApi, + SearchContextProvider, +} from '@backstage/plugin-search-react'; +import { TestApiProvider } from '@backstage/test-utils'; + + + + + +; +``` diff --git a/plugins/search-react/api-report.md b/plugins/search-react/api-report.md index 969e4d8563..e8d3afff82 100644 --- a/plugins/search-react/api-report.md +++ b/plugins/search-react/api-report.md @@ -5,31 +5,27 @@ ```ts import { ApiRef } from '@backstage/core-plugin-api'; import { AsyncState } from 'react-use/lib/useAsync'; -import { ComponentProps } from 'react'; import { JsonObject } from '@backstage/types'; import { PropsWithChildren } from 'react'; import { default as React_2 } from 'react'; import { SearchQuery } from '@backstage/plugin-search-common'; import { SearchResultSet } from '@backstage/plugin-search-common'; +// @public +export class MockSearchApi implements SearchApi { + constructor(mockedResults?: SearchResultSet | undefined); + // (undocumented) + mockedResults?: SearchResultSet | undefined; + // (undocumented) + query(): Promise; +} + // @public (undocumented) export interface SearchApi { // (undocumented) query(query: SearchQuery): Promise; } -// @public -export function SearchApiProviderForStorybook( - props: SearchApiProviderForStorybookProps, -): JSX.Element; - -// @public -export type SearchApiProviderForStorybookProps = ComponentProps< - typeof SearchContextProvider -> & { - mockedResults?: SearchResultSet; -}; - // @public (undocumented) export const searchApiRef: ApiRef; @@ -38,16 +34,6 @@ export const SearchContextProvider: ( props: SearchContextProviderProps, ) => JSX.Element; -// @public -export const SearchContextProviderForStorybook: ( - props: SearchContextProviderForStorybookProps, -) => JSX.Element; - -// @public -export type SearchContextProviderForStorybookProps = PropsWithChildren<{ - mockedResults?: SearchResultSet; -}>; - // @public export type SearchContextProviderProps = PropsWithChildren<{ initialState?: SearchContextState; diff --git a/plugins/search-react/src/api.ts b/plugins/search-react/src/api.ts index eb8c9c23db..24a247a641 100644 --- a/plugins/search-react/src/api.ts +++ b/plugins/search-react/src/api.ts @@ -30,3 +30,16 @@ export const searchApiRef = createApiRef({ export interface SearchApi { query(query: SearchQuery): Promise; } + +/** + * @public + * + * Search Api Mock that can be used in tests and storybooks + */ +export class MockSearchApi implements SearchApi { + constructor(public mockedResults?: SearchResultSet) {} + + query(): Promise { + return Promise.resolve(this.mockedResults || { results: [] }); + } +} diff --git a/plugins/search-react/src/context/SearchContextForStorybook.stories.tsx b/plugins/search-react/src/context/SearchContextForStorybook.stories.tsx deleted file mode 100644 index 603a89035f..0000000000 --- a/plugins/search-react/src/context/SearchContextForStorybook.stories.tsx +++ /dev/null @@ -1,71 +0,0 @@ -/* - * 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 { ApiProvider } from '@backstage/core-app-api'; -import { SearchResultSet } from '@backstage/plugin-search-common'; -import { TestApiRegistry } from '@backstage/test-utils'; -import React, { ComponentProps, PropsWithChildren } from 'react'; -import { searchApiRef } from '../api'; -import { SearchContextProvider } from './SearchContext'; - -/** - * Props for {@link SearchApiProviderForStorybook} - * @public - */ -export type SearchApiProviderForStorybookProps = ComponentProps< - typeof SearchContextProvider -> & { - mockedResults?: SearchResultSet; -}; - -/** - * Props for {@link SearchContextProviderForStorybook} - * @public - */ -export type SearchContextProviderForStorybookProps = PropsWithChildren<{ - mockedResults?: SearchResultSet; -}>; - -/** - * Utility api provider only for use in Storybook stories. - * - * @public - */ -export function SearchApiProviderForStorybook( - props: SearchApiProviderForStorybookProps, -) { - const { mockedResults, children } = props; - const query: any = () => Promise.resolve(mockedResults || {}); - const apiRegistry = TestApiRegistry.from([searchApiRef, { query }]); - return ; -} - -/** - * Utility context provider only for use in Storybook stories. You should use - * the real `` exported by `@backstage/plugin-search-react` in - * your app instead of this! In some cases (like the search page) it may - * already be provided on your behalf. - * - * @public - */ -export const SearchContextProviderForStorybook = ( - props: SearchContextProviderForStorybookProps, -) => { - return ( - - - - ); -}; diff --git a/plugins/search-react/src/context/index.tsx b/plugins/search-react/src/context/index.tsx index 76e1142bea..304f762943 100644 --- a/plugins/search-react/src/context/index.tsx +++ b/plugins/search-react/src/context/index.tsx @@ -24,11 +24,3 @@ export type { SearchContextState, SearchContextValue, } from './SearchContext'; -export { - SearchContextProviderForStorybook, - SearchApiProviderForStorybook, -} from './SearchContextForStorybook.stories'; -export type { - SearchContextProviderForStorybookProps, - SearchApiProviderForStorybookProps, -} from './SearchContextForStorybook.stories'; diff --git a/plugins/search-react/src/index.ts b/plugins/search-react/src/index.ts index 424c804472..d24bd097de 100644 --- a/plugins/search-react/src/index.ts +++ b/plugins/search-react/src/index.ts @@ -20,19 +20,15 @@ * @packageDocumentation */ -export { searchApiRef } from './api'; +export { searchApiRef, MockSearchApi } from './api'; export type { SearchApi } from './api'; export { SearchContextProvider, useSearch, useSearchContextCheck, - SearchContextProviderForStorybook, - SearchApiProviderForStorybook, } from './context'; export type { SearchContextProviderProps, SearchContextState, SearchContextValue, - SearchContextProviderForStorybookProps, - SearchApiProviderForStorybookProps, } from './context'; diff --git a/plugins/search/src/components/SearchBar/SearchBar.stories.tsx b/plugins/search/src/components/SearchBar/SearchBar.stories.tsx index 72c7deb06b..9728101e97 100644 --- a/plugins/search/src/components/SearchBar/SearchBar.stories.tsx +++ b/plugins/search/src/components/SearchBar/SearchBar.stories.tsx @@ -16,7 +16,12 @@ import { Grid, makeStyles, Paper } from '@material-ui/core'; import React, { ComponentType } from 'react'; -import { SearchContextProviderForStorybook } from '@backstage/plugin-search-react'; +import { + searchApiRef, + MockSearchApi, + SearchContextProvider, +} from '@backstage/plugin-search-react'; +import { TestApiProvider } from '@backstage/test-utils'; import { SearchBar } from './SearchBar'; export default { @@ -24,13 +29,15 @@ export default { component: SearchBar, decorators: [ (Story: ComponentType<{}>) => ( - - - - + + + + + + - - + + ), ], }; diff --git a/plugins/search/src/components/SearchFilter/SearchFilter.stories.tsx b/plugins/search/src/components/SearchFilter/SearchFilter.stories.tsx index 3c49b76699..7e8a7d585a 100644 --- a/plugins/search/src/components/SearchFilter/SearchFilter.stories.tsx +++ b/plugins/search/src/components/SearchFilter/SearchFilter.stories.tsx @@ -16,7 +16,12 @@ import { Grid, Paper } from '@material-ui/core'; import React, { ComponentType } from 'react'; -import { SearchContextProviderForStorybook } from '@backstage/plugin-search-react'; +import { + searchApiRef, + MockSearchApi, + SearchContextProvider, +} from '@backstage/plugin-search-react'; +import { TestApiProvider } from '@backstage/test-utils'; import { SearchFilter } from './SearchFilter'; export default { @@ -24,13 +29,15 @@ export default { component: SearchFilter, decorators: [ (Story: ComponentType<{}>) => ( - - - - + + + + + + - - + + ), ], }; diff --git a/plugins/search/src/components/SearchModal/SearchModal.stories.tsx b/plugins/search/src/components/SearchModal/SearchModal.stories.tsx index e2e3db694b..a4e92f53ec 100644 --- a/plugins/search/src/components/SearchModal/SearchModal.stories.tsx +++ b/plugins/search/src/components/SearchModal/SearchModal.stories.tsx @@ -29,7 +29,12 @@ import React, { ComponentType } from 'react'; import { rootRouteRef } from '../../plugin'; import { DefaultResultListItem } from '../DefaultResultListItem'; import { SearchBar } from '../SearchBar'; -import { SearchApiProviderForStorybook } from '@backstage/plugin-search-react'; +import { + searchApiRef, + MockSearchApi, + SearchContextProvider, +} from '@backstage/plugin-search-react'; +import { TestApiProvider } from '@backstage/test-utils'; import { SearchModal } from './SearchModal'; import { SearchResult } from '../SearchResult'; import { SearchResultPager } from '../SearchResultPager'; @@ -71,9 +76,14 @@ export default { decorators: [ (Story: ComponentType<{}>) => wrapInTestApp( - - - , + + + + + , + { mountedRoutes: { '/search': rootRouteRef } }, ), ], diff --git a/plugins/search/src/components/SearchResult/SearchResult.stories.tsx b/plugins/search/src/components/SearchResult/SearchResult.stories.tsx index 4a3d950164..207f1ae1d7 100644 --- a/plugins/search/src/components/SearchResult/SearchResult.stories.tsx +++ b/plugins/search/src/components/SearchResult/SearchResult.stories.tsx @@ -20,8 +20,13 @@ import React, { ComponentType } from 'react'; import { MemoryRouter } from 'react-router'; import { DefaultResultListItem } from '../DefaultResultListItem'; -import { SearchContextProviderForStorybook } from '@backstage/plugin-search-react'; +import { + searchApiRef, + MockSearchApi, + SearchContextProvider, +} from '@backstage/plugin-search-react'; import { SearchResult } from './SearchResult'; +import { TestApiProvider } from '@backstage/test-utils'; const mockResults = { results: [ @@ -58,9 +63,13 @@ export default { decorators: [ (Story: ComponentType<{}>) => ( - - - + + + + + ), ], diff --git a/plugins/search/src/components/SearchType/SearchType.stories.tsx b/plugins/search/src/components/SearchType/SearchType.stories.tsx index b56f4c089c..415eee19a6 100644 --- a/plugins/search/src/components/SearchType/SearchType.stories.tsx +++ b/plugins/search/src/components/SearchType/SearchType.stories.tsx @@ -19,21 +19,28 @@ import CatalogIcon from '@material-ui/icons/MenuBook'; import DocsIcon from '@material-ui/icons/Description'; import UsersGroupsIcon from '@material-ui/icons/Person'; import React, { ComponentType } from 'react'; -import { SearchContextProviderForStorybook } from '@backstage/plugin-search-react'; import { SearchType } from './SearchType'; +import { TestApiProvider } from '@backstage/test-utils'; +import { + searchApiRef, + MockSearchApi, + SearchContextProvider, +} from '@backstage/plugin-search-react'; export default { title: 'Plugins/Search/SearchType', component: SearchType, decorators: [ (Story: ComponentType<{}>) => ( - - - - + + + + + + - - + + ), ], };