core-*: migrate to using TestApiProvider

Signed-off-by: Patrik Oldsberg <poldsberg@gmail.com>
This commit is contained in:
Patrik Oldsberg
2021-11-17 10:45:39 +01:00
parent 417f80c0c8
commit b811fadaec
11 changed files with 108 additions and 128 deletions
@@ -16,14 +16,15 @@
import React from 'react';
import { FeatureFlagged } from './FeatureFlagged';
import { render } from '@testing-library/react';
import { ApiProvider, ApiRegistry, LocalStorageFeatureFlags } from '../apis';
import { LocalStorageFeatureFlags } from '../apis';
import { TestApiProvider } from '@backstage/test-utils';
import { featureFlagsApiRef } from '@backstage/core-plugin-api';
const mockFeatureFlagsApi = new LocalStorageFeatureFlags();
const Wrapper = ({ children }: { children?: React.ReactNode }) => (
<ApiProvider apis={ApiRegistry.with(featureFlagsApiRef, mockFeatureFlagsApi)}>
<TestApiProvider apis={[[featureFlagsApiRef, mockFeatureFlagsApi]]}>
{children}
</ApiProvider>
</TestApiProvider>
);
describe('FeatureFlagged', () => {
@@ -17,17 +17,18 @@
import { render, RenderResult } from '@testing-library/react';
import React, { ReactNode } from 'react';
import { MemoryRouter, Route, Routes, useOutlet } from 'react-router-dom';
import { ApiProvider, ApiRegistry, LocalStorageFeatureFlags } from '../apis';
import { LocalStorageFeatureFlags } from '../apis';
import { featureFlagsApiRef } from '@backstage/core-plugin-api';
import { AppContext } from '../app';
import { AppContextProvider } from '../app/AppContext';
import { FlatRoutes } from './FlatRoutes';
import { TestApiProvider } from '@backstage/test-utils';
const mockFeatureFlagsApi = new LocalStorageFeatureFlags();
const Wrapper = ({ children }: { children?: React.ReactNode }) => (
<ApiProvider apis={ApiRegistry.with(featureFlagsApiRef, mockFeatureFlagsApi)}>
<TestApiProvider apis={[[featureFlagsApiRef, mockFeatureFlagsApi]]}>
{children}
</ApiProvider>
</TestApiProvider>
);
function makeRouteRenderer(node: ReactNode) {
@@ -17,78 +17,66 @@
import React from 'react';
import { AlertDisplay } from './AlertDisplay';
import { alertApiRef } from '@backstage/core-plugin-api';
import {
ApiProvider,
ApiRegistry,
AlertApiForwarder,
} from '@backstage/core-app-api';
import { AlertApiForwarder } from '@backstage/core-app-api';
import Observable from 'zen-observable';
import { renderInTestApp } from '@backstage/test-utils';
import { renderInTestApp, TestApiProvider } from '@backstage/test-utils';
const TEST_MESSAGE = 'TEST_MESSAGE';
describe('<AlertDisplay />', () => {
it('renders without exploding', async () => {
const apiRegistry = ApiRegistry.from([
[alertApiRef, new AlertApiForwarder()],
]);
const { queryByText } = await renderInTestApp(
<ApiProvider apis={apiRegistry}>
<TestApiProvider apis={[[alertApiRef, new AlertApiForwarder()]]}>
<AlertDisplay />
</ApiProvider>,
</TestApiProvider>,
);
expect(queryByText(TEST_MESSAGE)).not.toBeInTheDocument();
});
it('renders with message', async () => {
const apiRegistry = ApiRegistry.from([
[
alertApiRef,
{
post() {},
alert$() {
return Observable.of({ message: TEST_MESSAGE });
},
},
],
]);
const { queryByText } = await renderInTestApp(
<ApiProvider apis={apiRegistry}>
<TestApiProvider
apis={[
[
alertApiRef,
{
post() {},
alert$() {
return Observable.of({ message: TEST_MESSAGE });
},
},
],
]}
>
<AlertDisplay />
</ApiProvider>,
</TestApiProvider>,
);
expect(queryByText(TEST_MESSAGE)).toBeInTheDocument();
});
describe('with multiple messages', () => {
let apiRegistry: ApiRegistry;
beforeEach(() => {
apiRegistry = ApiRegistry.from([
[
alertApiRef,
{
post() {},
alert$() {
return Observable.of(
{ message: 'message one' },
{ message: 'message two' },
{ message: 'message three' },
);
},
const apis = [
[
alertApiRef,
{
post() {},
alert$() {
return Observable.of(
{ message: 'message one' },
{ message: 'message two' },
{ message: 'message three' },
);
},
],
]);
});
},
] as const,
] as const;
it('renders first message', async () => {
const { queryByText } = await renderInTestApp(
<ApiProvider apis={apiRegistry}>
<TestApiProvider apis={apis}>
<AlertDisplay />
</ApiProvider>,
</TestApiProvider>,
);
expect(queryByText('message one')).toBeInTheDocument();
@@ -96,9 +84,9 @@ describe('<AlertDisplay />', () => {
it('renders a count of remaining messages', async () => {
const { queryByText } = await renderInTestApp(
<ApiProvider apis={apiRegistry}>
<TestApiProvider apis={apis}>
<AlertDisplay />
</ApiProvider>,
</TestApiProvider>,
);
expect(queryByText('(2 older messages)')).toBeInTheDocument();
@@ -17,10 +17,9 @@
import React from 'react';
import { fireEvent } from '@testing-library/react';
import { act } from 'react-dom/test-utils';
import { renderInTestApp } from '@backstage/test-utils';
import { renderInTestApp, TestApiProvider } from '@backstage/test-utils';
import { CopyTextButton } from './CopyTextButton';
import { ApiProvider, ApiRegistry } from '@backstage/core-app-api';
import { errorApiRef, ErrorApi } from '@backstage/core-plugin-api';
import { errorApiRef } from '@backstage/core-plugin-api';
import { useCopyToClipboard } from 'react-use';
jest.mock('popper.js', () => {
@@ -51,22 +50,18 @@ const props = {
tooltipText: 'mockTooltip',
};
const apiRegistry = ApiRegistry.from([
[
errorApiRef,
{
post: jest.fn(),
error$: jest.fn(),
} as ErrorApi,
],
]);
const mockErrorApi = {
post: jest.fn(),
error$: jest.fn(),
};
const apis = [[errorApiRef, mockErrorApi] as const] as const;
describe('<CopyTextButton />', () => {
it('renders without exploding', async () => {
const { getByTitle, queryByText } = await renderInTestApp(
<ApiProvider apis={apiRegistry}>
<TestApiProvider apis={apis}>
<CopyTextButton {...props} />
</ApiProvider>,
</TestApiProvider>,
);
expect(getByTitle('mockTooltip')).toBeInTheDocument();
expect(queryByText('mockTooltip')).not.toBeInTheDocument();
@@ -80,9 +75,9 @@ describe('<CopyTextButton />', () => {
spy.mockReturnValue([{}, copy]);
const rendered = await renderInTestApp(
<ApiProvider apis={apiRegistry}>
<TestApiProvider apis={apis}>
<CopyTextButton {...props} />
</ApiProvider>,
</TestApiProvider>,
);
const button = rendered.getByTitle('mockTooltip');
fireEvent.click(button);
@@ -101,10 +96,10 @@ describe('<CopyTextButton />', () => {
spy.mockReturnValue([{ error }, jest.fn()]);
await renderInTestApp(
<ApiProvider apis={apiRegistry}>
<TestApiProvider apis={apis}>
<CopyTextButton {...props} />
</ApiProvider>,
</TestApiProvider>,
);
expect(apiRegistry.get(errorApiRef)?.post).toHaveBeenCalledWith(error);
expect(mockErrorApi.post).toHaveBeenCalledWith(error);
});
});
@@ -18,12 +18,13 @@ import React from 'react';
import { DismissableBanner } from './DismissableBanner';
import Link from '@material-ui/core/Link';
import Typography from '@material-ui/core/Typography';
import { ApiProvider, ApiRegistry, WebStorage } from '@backstage/core-app-api';
import { WebStorage } from '@backstage/core-app-api';
import {
ErrorApi,
storageApiRef,
StorageApi,
} from '@backstage/core-plugin-api';
import { TestApiProvider } from '@backstage/test-utils';
export default {
title: 'Feedback/DismissableBanner',
@@ -37,47 +38,47 @@ const createWebStorage = (): StorageApi => {
return WebStorage.create({ errorApi });
};
const apis = ApiRegistry.from([[storageApiRef, createWebStorage()]]);
const apis = [[storageApiRef, createWebStorage()] as const];
export const Default = () => (
<div style={containerStyle}>
<ApiProvider apis={apis}>
<TestApiProvider apis={apis}>
<DismissableBanner
message="This is a dismissable banner"
variant="info"
id="default_dismissable"
/>
</ApiProvider>
</TestApiProvider>
</div>
);
export const Error = () => (
<div style={containerStyle}>
<ApiProvider apis={apis}>
<TestApiProvider apis={apis}>
<DismissableBanner
message="This is a dismissable banner with an error message"
variant="error"
id="error_dismissable"
/>
</ApiProvider>
</TestApiProvider>
</div>
);
export const EmojisIncluded = () => (
<div style={containerStyle}>
<ApiProvider apis={apis}>
<TestApiProvider apis={apis}>
<DismissableBanner
message="This is a dismissable banner with emojis: 🚀 💚 😆 "
variant="info"
id="emojis_dismissable"
/>
</ApiProvider>
</TestApiProvider>
</div>
);
export const WithLink = () => (
<div style={containerStyle}>
<ApiProvider apis={apis}>
<TestApiProvider apis={apis}>
<DismissableBanner
message={
<Typography>
@@ -90,29 +91,29 @@ export const WithLink = () => (
variant="info"
id="linked_dismissable"
/>
</ApiProvider>
</TestApiProvider>
</div>
);
export const Fixed = () => (
<div style={containerStyle}>
<ApiProvider apis={apis}>
<TestApiProvider apis={apis}>
<DismissableBanner
message="This is a dismissable banner with a fixed position fixed at the bottom of the page"
variant="info"
id="fixed_dismissable"
fixed
/>
</ApiProvider>
</TestApiProvider>
</div>
);
export const Warning = () => (
<div style={containerStyle}>
<ApiProvider apis={apis}>
<TestApiProvider apis={apis}>
<DismissableBanner
message="This is a dismissable banner with a warning message"
variant="warning"
id="warning_dismissable"
/>
</ApiProvider>
</TestApiProvider>
</div>
);
@@ -16,13 +16,17 @@
import React from 'react';
import { fireEvent } from '@testing-library/react';
import { renderWithEffects, wrapInTestApp } from '@backstage/test-utils';
import {
renderWithEffects,
TestApiRegistry,
wrapInTestApp,
} from '@backstage/test-utils';
import { DismissableBanner } from './DismissableBanner';
import { ApiRegistry, ApiProvider, WebStorage } from '@backstage/core-app-api';
import { ApiProvider, WebStorage } from '@backstage/core-app-api';
import { storageApiRef, StorageApi } from '@backstage/core-plugin-api';
describe('<DismissableBanner />', () => {
let apis: ApiRegistry;
let apis: TestApiRegistry;
const mockErrorApi = { post: jest.fn(), error$: jest.fn() };
const createWebStorage = (): StorageApi => {
return WebStorage.create({
@@ -31,7 +35,7 @@ describe('<DismissableBanner />', () => {
};
beforeEach(() => {
apis = ApiRegistry.from([[storageApiRef, createWebStorage()]]);
apis = TestApiRegistry.with([storageApiRef, createWebStorage()]);
});
it('renders the message and the popover', async () => {
@@ -16,8 +16,11 @@
import React from 'react';
import { render, fireEvent, waitFor } from '@testing-library/react';
import { MockAnalyticsApi, wrapInTestApp } from '@backstage/test-utils';
import { ApiProvider, ApiRegistry } from '@backstage/core-app-api';
import {
MockAnalyticsApi,
TestApiProvider,
wrapInTestApp,
} from '@backstage/test-utils';
import { analyticsApiRef } from '@backstage/core-plugin-api';
import { isExternalUri, Link } from './Link';
import { Route, Routes } from 'react-router';
@@ -48,11 +51,11 @@ describe('<Link />', () => {
const { getByText } = render(
wrapInTestApp(
<ApiProvider apis={ApiRegistry.from([[analyticsApiRef, analyticsApi]])}>
<TestApiProvider apis={[[analyticsApiRef, analyticsApi]]}>
<Link to="/test" onClick={customOnClick}>
{linkText}
</Link>
</ApiProvider>,
</TestApiProvider>,
),
);
@@ -20,9 +20,9 @@ import { ErrorBoundary } from './ErrorBoundary';
import {
MockErrorApi,
renderInTestApp,
TestApiProvider,
withLogCollector,
} from '@backstage/test-utils';
import { ApiProvider, ApiRegistry } from '@backstage/core-app-api';
import { errorApiRef } from '@backstage/core-plugin-api';
type BombProps = {
@@ -41,25 +41,25 @@ const Bomb = ({ shouldThrow }: BombProps) => {
describe('<ErrorBoundary/>', () => {
it('should render error boundary with and without error', async () => {
const { error } = await withLogCollector(['error'], async () => {
const apis = ApiRegistry.with(errorApiRef, new MockErrorApi());
const errorApi = new MockErrorApi();
const { rerender, queryByRole, getByRole, getByText } =
await renderInTestApp(
<ApiProvider apis={apis}>
<TestApiProvider apis={[[errorApiRef, errorApi]]}>
<ErrorBoundary>
<Bomb />
</ErrorBoundary>
</ApiProvider>,
</TestApiProvider>,
);
expect(queryByRole('alert')).not.toBeInTheDocument();
expect(getByText(/working component/i)).toBeInTheDocument();
rerender(
<ApiProvider apis={apis}>
<TestApiProvider apis={[[errorApiRef, errorApi]]}>
<ErrorBoundary>
<Bomb shouldThrow />
</ErrorBoundary>
</ApiProvider>,
</TestApiProvider>,
);
expect(getByRole('alert')).toBeInTheDocument();
@@ -15,13 +15,9 @@
*/
import React from 'react';
import { renderInTestApp } from '@backstage/test-utils';
import { renderInTestApp, TestApiProvider } from '@backstage/test-utils';
import { Header } from './Header';
import {
ApiRegistry,
ConfigReader,
ApiProvider,
} from '@backstage/core-app-api';
import { ConfigReader } from '@backstage/core-app-api';
import { configApiRef } from '@backstage/core-plugin-api';
jest.mock('react-helmet', () => {
@@ -72,14 +68,12 @@ describe('<Header/>', () => {
});
it('should use app.title', async () => {
const apiRegistry = ApiRegistry.with(
configApiRef,
new ConfigReader({ app: { title: 'Blah' } }),
);
const rendered = await renderInTestApp(
<ApiProvider apis={apiRegistry}>
<TestApiProvider
apis={[[configApiRef, new ConfigReader({ app: { title: 'Blah' } })]]}
>
<Header title="Title" type="tool" typeLink="/tool" />,
</ApiProvider>,
</TestApiProvider>,
);
rendered.getAllByText(/Title | Blah/);
});
@@ -14,16 +14,12 @@
* limitations under the License.
*/
import { renderWithEffects } from '@backstage/test-utils';
import { renderWithEffects, TestApiProvider } from '@backstage/test-utils';
import { HomepageTimer } from './HomepageTimer';
import React from 'react';
import { lightTheme } from '@backstage/theme';
import { ThemeProvider } from '@material-ui/core/styles';
import {
ApiProvider,
ApiRegistry,
ConfigReader,
} from '@backstage/core-app-api';
import { ConfigReader } from '@backstage/core-app-api';
import { ConfigApi, configApiRef } from '@backstage/core-plugin-api';
it('changes default timezone to GMT', async () => {
@@ -41,9 +37,9 @@ it('changes default timezone to GMT', async () => {
const rendered = await renderWithEffects(
<ThemeProvider theme={lightTheme}>
<ApiProvider apis={ApiRegistry.from([[configApiRef, configApi]])}>
<TestApiProvider apis={[[configApiRef, configApi]]}>
<HomepageTimer />
</ApiProvider>
</TestApiProvider>
</ThemeProvider>,
);
@@ -18,11 +18,8 @@ import { useElementFilter } from './useElementFilter';
import { renderHook } from '@testing-library/react-hooks';
import { attachComponentData } from './componentData';
import { featureFlagsApiRef } from '../apis';
import {
ApiProvider,
ApiRegistry,
LocalStorageFeatureFlags,
} from '@backstage/core-app-api';
import { LocalStorageFeatureFlags } from '@backstage/core-app-api';
import { TestApiProvider } from '@backstage/test-utils';
const WRAPPING_COMPONENT_KEY = 'core.blob.testing';
const INNER_COMPONENT_KEY = 'core.blob2.testing';
@@ -45,9 +42,9 @@ const FeatureFlagComponent = (_props: {
attachComponentData(FeatureFlagComponent, 'core.featureFlagged', true);
const mockFeatureFlagsApi = new LocalStorageFeatureFlags();
const Wrapper = ({ children }: { children?: React.ReactNode }) => (
<ApiProvider apis={ApiRegistry.with(featureFlagsApiRef, mockFeatureFlagsApi)}>
<TestApiProvider apis={[[featureFlagsApiRef, mockFeatureFlagsApi]]}>
{children}
</ApiProvider>
</TestApiProvider>
);
describe('useElementFilter', () => {