diff --git a/plugins/techdocs-addons/src/context.test.tsx b/plugins/techdocs-addons/src/context.test.tsx new file mode 100644 index 0000000000..5455264f04 --- /dev/null +++ b/plugins/techdocs-addons/src/context.test.tsx @@ -0,0 +1,157 @@ +/* + * 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 React from 'react'; +import { + techdocsApiRef, + TechDocsApi, + TechDocsMetadata, +} from '@backstage/plugin-techdocs'; +import { + useEntityMetadata, + useTechDocsMetadata, + useTechDocsReaderPage, + useShadowRoot, + useShadowRootElements, + TechDocsEntityProvider, + TechDocsMetadataProvider, + TechDocsReaderPageProvider, +} from './context'; +import { renderHook, act } from '@testing-library/react-hooks'; + +import { Entity, CompoundEntityRef } from '@backstage/catalog-model'; +import { TestApiProvider } from '@backstage/test-utils'; + +const mockEntity: Entity = { + apiVersion: 'v1', + kind: 'Component', + metadata: { name: 'test-component', namespace: 'default' }, +}; + +const mockTechDocsMetadata: TechDocsMetadata = { + site_name: 'test-componnet', + site_description: 'this is a test component', +}; + +const mockShadowRoot = () => { + const div = document.createElement('div'); + const shadowRoot = div.attachShadow({ mode: 'open' }); + shadowRoot.innerHTML = '

Shadow DOM Mock

'; + return shadowRoot; +}; + +const techdocsApi: Partial = { + getEntityMetadata: () => Promise.resolve(mockEntity), + getTechDocsMetadata: () => Promise.resolve(mockTechDocsMetadata), +}; + +const wrapper = ({ + entityName = { + namespace: mockEntity.metadata.namespace!!, + kind: mockEntity.kind, + name: mockEntity.metadata.name, + }, + children, +}: { + entityName: CompoundEntityRef; + children: React.ReactNode; +}) => ( + + + + + {children} + + + + +); + +describe('context', () => { + describe('useEntityMetadata', () => { + it('should return loading state', async () => { + const { result } = renderHook(() => useEntityMetadata()); + + await expect(result.current.loading).toEqual(true); + }); + + it('should return expected entity values', async () => { + const { result, waitForNextUpdate } = renderHook( + () => useEntityMetadata(), + { wrapper }, + ); + + await waitForNextUpdate(); + + expect(result.current.value).toBeDefined(); + expect(result.current.error).toBeUndefined(); + expect(result.current.value).toMatchObject(mockEntity); + }); + }); + + describe('useTechDocsMetadata', () => { + it('should return loading state', async () => { + const { result } = renderHook(() => useTechDocsMetadata()); + + await expect(result.current.loading).toEqual(true); + }); + + it('should return expected techdocs metadata values', async () => { + const { result, waitForNextUpdate } = renderHook( + () => useTechDocsMetadata(), + { wrapper }, + ); + + await waitForNextUpdate(); + expect(result.current.value).toBeDefined(); + expect(result.current.error).toBeUndefined(); + expect(result.current.value).toMatchObject(mockTechDocsMetadata); + }); + }); + + describe('useTechDocsReaderPage', () => { + it('should set title', () => { + const { result } = renderHook(() => useTechDocsReaderPage(), { wrapper }); + + expect(result.current.title).toBe(''); + + act(() => result.current.setTitle('test site title')); + expect(result.current.title).toBe('test site title'); + }); + + it('should set subtitle', () => { + const { result } = renderHook(() => useTechDocsReaderPage(), { wrapper }); + + expect(result.current.subtitle).toBe(''); + + act(() => result.current.setSubtitle('test site subtitle')); + expect(result.current.subtitle).toBe('test site subtitle'); + }); + + it('should set shadow root', async () => { + const { result } = renderHook(() => useTechDocsReaderPage(), { wrapper }); + + // mock shadowroot + const shadowRoot = mockShadowRoot(); + + act(() => result.current.setShadowRoot(shadowRoot)); + + expect(result.current.shadowRoot?.innerHTML).toBe( + '

Shadow DOM Mock

', + ); + }); + }); +});