diff --git a/packages/editor/src/components/post-revisions-preview/revisions-slider.js b/packages/editor/src/components/post-revisions-preview/revisions-slider.js index c902523875f6a8..55083a8244984d 100644 --- a/packages/editor/src/components/post-revisions-preview/revisions-slider.js +++ b/packages/editor/src/components/post-revisions-preview/revisions-slider.js @@ -35,11 +35,23 @@ function RevisionsSlider() { } const entityConfig = getEntityConfig( 'postType', postType ); + const _revisionKey = entityConfig?.revisionKey || 'id'; const query = { per_page: -1, context: 'edit', - _fields: - 'id,date,author,meta,title.raw,excerpt.raw,content.raw', + _fields: [ + ...new Set( [ + 'id', + 'date', + 'modified', + 'author', + 'meta', + 'title.raw', + 'excerpt.raw', + 'content.raw', + _revisionKey, + ] ), + ].join(), }; return { revisions: getRevisions( 'postType', postType, postId, query ), @@ -52,7 +64,7 @@ function RevisionsSlider() { currentRevisionId: unlock( select( editorStore ) ).getCurrentRevisionId(), - revisionKey: entityConfig?.revisionKey || 'id', + revisionKey: _revisionKey, }; }, [] @@ -60,14 +72,21 @@ function RevisionsSlider() { const { setCurrentRevisionId } = unlock( useDispatch( editorStore ) ); + // Template revisions use the template REST API format, which exposes + // 'modified' instead of 'date'. + const revisionDateField = revisionKey === 'wp_id' ? 'modified' : 'date'; + const sortedRevisions = useMemo( () => { return ( revisions ?.slice() - .sort( ( a, b ) => new Date( a.date ) - new Date( b.date ) ) ?? - [] + .sort( + ( a, b ) => + new Date( a[ revisionDateField ] ) - + new Date( b[ revisionDateField ] ) + ) ?? [] ); - }, [ revisions ] ); + }, [ revisions, revisionDateField ] ); const selectedIndex = sortedRevisions.findIndex( ( r ) => r[ revisionKey ] === currentRevisionId @@ -87,7 +106,10 @@ function RevisionsSlider() { if ( ! revision ) { return index; } - return dateI18n( dateSettings.formats.datetime, revision.date ); + return dateI18n( + dateSettings.formats.datetime, + revision[ revisionDateField ] + ); }; if ( isLoading ) { diff --git a/packages/editor/src/store/private-actions.js b/packages/editor/src/store/private-actions.js index 133f346dd85d41..f8781626c51ccd 100644 --- a/packages/editor/src/store/private-actions.js +++ b/packages/editor/src/store/private-actions.js @@ -627,6 +627,11 @@ export const restoreRevision = const postType = select.getCurrentPostType(); const postId = select.getCurrentPostId(); + const entityConfig = registry + .select( coreStore ) + .getEntityConfig( 'postType', postType ); + const revisionKey = entityConfig?.revisionKey || 'id'; + // Use resolveSelect to ensure the revision is fetched if not yet // in the store. The _fields parameter matches the query used by // getRevisions so the result is served from cache without an @@ -635,8 +640,19 @@ export const restoreRevision = .resolveSelect( coreStore ) .getRevision( 'postType', postType, postId, revisionId, { context: 'edit', - _fields: - 'id,date,author,meta,title.raw,excerpt.raw,content.raw', + _fields: [ + ...new Set( [ + 'id', + 'date', + 'modified', + 'author', + 'meta', + 'title.raw', + 'excerpt.raw', + 'content.raw', + revisionKey, + ] ), + ].join(), } ); if ( ! revision ) { @@ -672,7 +688,12 @@ export const restoreRevision = sprintf( /* translators: %s: Date and time of the revision. */ __( 'Restored to revision from %s.' ), - dateI18n( getDateSettings().formats.datetime, revision.date ) + dateI18n( + getDateSettings().formats.datetime, + // Template revisions use the template REST API format, which + // exposes 'modified' instead of 'date'. + revisionKey === 'wp_id' ? revision.modified : revision.date + ) ), { type: 'snackbar', diff --git a/packages/editor/src/store/private-selectors.js b/packages/editor/src/store/private-selectors.js index 39bc47379924e9..05f85cec182881 100644 --- a/packages/editor/src/store/private-selectors.js +++ b/packages/editor/src/store/private-selectors.js @@ -390,6 +390,11 @@ export const getCurrentRevision = createRegistrySelector( } const { type: postType, id: postId } = getCurrentPost( state ); + const entityConfig = select( coreStore ).getEntityConfig( + 'postType', + postType + ); + const revisionKey = entityConfig?.revisionKey || 'id'; // - Use getRevisions (plural) instead of getRevision (singular) to // avoid a race condition where both API calls complete around the // same time and the single revision fetch overwrites the list in the @@ -404,19 +409,27 @@ export const getCurrentRevision = createRegistrySelector( { per_page: -1, context: 'edit', - _fields: - 'id,date,author,meta,title.raw,excerpt.raw,content.raw', + _fields: [ + ...new Set( [ + 'id', + 'date', + 'modified', + 'author', + 'meta', + 'title.raw', + 'excerpt.raw', + 'content.raw', + revisionKey, + ] ), + ].join(), } ); if ( ! revisions ) { return null; } - const entityConfig = select( coreStore ).getEntityConfig( - 'postType', - postType + return ( + revisions.find( ( r ) => r[ revisionKey ] === revisionId ) ?? null ); - const revKey = entityConfig?.revisionKey || 'id'; - return revisions.find( ( r ) => r[ revKey ] === revisionId ) ?? null; } ); @@ -457,6 +470,11 @@ export const getPreviousRevision = createRegistrySelector( } const { type: postType, id: postId } = getCurrentPost( state ); + const entityConfig = select( coreStore ).getEntityConfig( + 'postType', + postType + ); + const revisionKey = entityConfig?.revisionKey || 'id'; const revisions = select( coreStore ).getRevisions( 'postType', postType, @@ -464,27 +482,39 @@ export const getPreviousRevision = createRegistrySelector( { per_page: -1, context: 'edit', - _fields: - 'id,date,author,meta,title.raw,excerpt.raw,content.raw', + _fields: [ + ...new Set( [ + 'id', + 'date', + 'modified', + 'author', + 'meta', + 'title.raw', + 'excerpt.raw', + 'content.raw', + revisionKey, + ] ), + ].join(), } ); if ( ! revisions ) { return null; } + // Template revisions use the template REST API format, which exposes + // 'modified' instead of 'date'. Regular post revisions use 'date'. + const revisionDateField = revisionKey === 'wp_id' ? 'modified' : 'date'; + // Sort by date ascending (oldest first). const sortedRevisions = [ ...revisions ].sort( - ( a, b ) => new Date( a.date ) - new Date( b.date ) + ( a, b ) => + new Date( a[ revisionDateField ] ) - + new Date( b[ revisionDateField ] ) ); // Find current revision index. - const entityConfig = select( coreStore ).getEntityConfig( - 'postType', - postType - ); - const revKey = entityConfig?.revisionKey || 'id'; const currentIndex = sortedRevisions.findIndex( - ( r ) => r[ revKey ] === currentRevisionId + ( r ) => r[ revisionKey ] === currentRevisionId ); // Return the previous revision (older one) if it exists.