diff --git a/packages/block-library/src/post-date/edit.js b/packages/block-library/src/post-date/edit.js index 9cc90f3d61dbee..e78de01032cab5 100644 --- a/packages/block-library/src/post-date/edit.js +++ b/packages/block-library/src/post-date/edit.js @@ -210,7 +210,7 @@ export default function PostDateEdit( props ) { isLink !== false } label={ - postType?.labels.singular_name + postType?.labels?.singular_name ? sprintf( // translators: %s: Name of the post type e.g: "post". __( 'Link to %s' ), @@ -223,7 +223,7 @@ export default function PostDateEdit( props ) { > ) } diff --git a/packages/editor/src/components/post-type-support-check/test/index.js b/packages/editor/src/components/post-type-support-check/test/index.js index 848a0227de81a9..cf74d2a680337a 100644 --- a/packages/editor/src/components/post-type-support-check/test/index.js +++ b/packages/editor/src/components/post-type-support-check/test/index.js @@ -54,6 +54,17 @@ describe( 'PostTypeSupportCheck', () => { expect( container ).not.toHaveTextContent( 'Supported' ); } ); + it( 'does not crash when the post type has no `supports` object', () => { + setupUseSelectMock( {} ); + const { container } = render( + + Supported + + ); + + expect( container ).not.toHaveTextContent( 'Supported' ); + } ); + it( 'renders its children when post type is known and supports', () => { setupUseSelectMock( { supports: { diff --git a/packages/editor/src/components/post-url/index.js b/packages/editor/src/components/post-url/index.js index f55ac973be50e6..05855b1ca240ee 100644 --- a/packages/editor/src/components/post-url/index.js +++ b/packages/editor/src/components/post-url/index.js @@ -58,7 +58,7 @@ export default function PostURL( { onClose } ) { postSlug: safeDecodeURIComponent( select( editorStore ).getEditedPostSlug() ), - viewPostLabel: postType?.labels.view_item, + viewPostLabel: postType?.labels?.view_item, postLink: post.link, permalinkPrefix: permalinkParts?.prefix, permalinkSuffix: permalinkParts?.suffix, diff --git a/packages/editor/src/components/post-view-link/index.js b/packages/editor/src/components/post-view-link/index.js index a15b7546fa7c9f..6ad80f97783265 100644 --- a/packages/editor/src/components/post-view-link/index.js +++ b/packages/editor/src/components/post-view-link/index.js @@ -24,7 +24,7 @@ export default function PostViewLink() { return { permalink: select( editorStore ).getPermalink(), isPublished: select( editorStore ).isCurrentPostPublished(), - label: postType?.labels.view_item, + label: postType?.labels?.view_item, hasLoaded: !! postType, showIconLabels: get( 'core', 'showIconLabels' ), }; diff --git a/packages/editor/src/components/post-view-link/test/index.js b/packages/editor/src/components/post-view-link/test/index.js new file mode 100644 index 00000000000000..c627944aedefd7 --- /dev/null +++ b/packages/editor/src/components/post-view-link/test/index.js @@ -0,0 +1,71 @@ +/** + * External dependencies + */ +import { render, screen } from '@testing-library/react'; + +/** + * WordPress dependencies + */ +import { useSelect } from '@wordpress/data'; + +/** + * Internal dependencies + */ +import PostViewLink from '../'; + +jest.mock( '@wordpress/data/src/components/use-select', () => jest.fn() ); + +const DEFAULTS = { + postType: { labels: { view_item: 'View Post' } }, + permalink: 'https://example.com/sample/', + isPublished: true, + showIconLabels: false, +}; + +function setupUseSelectMock( overrides = {} ) { + // Use object spread (not destructure defaults) so an explicit `undefined` + // override actually overrides the default value. + const data = { ...DEFAULTS, ...overrides }; + useSelect.mockImplementation( ( cb ) => + cb( () => ( { + getCurrentPostType: () => 'post', + getPostType: () => data.postType, + getPermalink: () => data.permalink, + isCurrentPostPublished: () => data.isPublished, + get: () => data.showIconLabels, + } ) ) + ); +} + +describe( 'PostViewLink', () => { + it( 'renders the post type-specific view label when available', () => { + setupUseSelectMock(); + render( ); + expect( screen.getByLabelText( 'View Post' ) ).toBeInTheDocument(); + } ); + + it( 'falls back to "View post" without crashing when the post type has no labels', () => { + // See https://github.com/WordPress/gutenberg/issues/62918. + setupUseSelectMock( { postType: {} } ); + render( ); + expect( screen.getByLabelText( 'View post' ) ).toBeInTheDocument(); + } ); + + it( 'renders nothing if the post is not published', () => { + setupUseSelectMock( { isPublished: false } ); + const { container } = render( ); + expect( container ).toBeEmptyDOMElement(); + } ); + + it( 'renders nothing if no permalink is available', () => { + setupUseSelectMock( { permalink: undefined } ); + const { container } = render( ); + expect( container ).toBeEmptyDOMElement(); + } ); + + it( 'renders nothing while the post type has not loaded', () => { + setupUseSelectMock( { postType: undefined } ); + const { container } = render( ); + expect( container ).toBeEmptyDOMElement(); + } ); +} );