For storing data in a custom API endpoint, I needed to run code whenever the block editor gets saved. That was easier said than done. The solution you’ll find first is to use subscribe to subscribe to any change and filter it for the one you need.

This however comes with some tradeoffs, since you would need to filter it and since a subscribe runs very often, it’s quite heavy in terms of performance. Additionally, I couldn’t find a possibility to filter the subscription to only run once without using flags and debounces.

Fortunately, I found a widely unseen answer at WordPress Development Stack Exchange, which uses the savePost action of the Post Editor’s Data.

To use it, we need to attach our custom action to this action and execute it whenever it runs successfully. We dispatch our custom action and wrap it to the then action of savePost so that it doesn’t do anything unless the post really has been saved (similar to meta boxes). Then we can run our custom code, in my case I get certain data and use apiFetch to push them to a custom API endpoint.

const [ isDispatched, setIsDispatched ] = useState( false );
const { savePost } = dispatch( 'core/editor' );

if ( ! isDispatched ) {
	dispatch( 'core/editor' ).savePost = () => {
		setIsDispatched( true );
		
		return savePost().then( () => {
			let data = { values: [] };
			const postId = select( 'core/editor' ).getCurrentPostId();
			
			// get data
			
			if ( ! data.values.length ) {
				return;
			}
			
			apiFetch( {
				data,
				method: 'PUT',
				path: '/custom/v1/api/endpoint/' + postId,
			} ).then( () => {
				// TODO: show success message
			} ).catch( ( error ) => {
				// TODO: show error message
			} );
		} );
	}
}
Code language: JavaScript (javascript)

To ensure that the dispatch is only performed once, we also use a local variable isDispatched, which is assigned to the state and is therefore persistent. This is set to true during the first dispatch, so that no further dispatch takes place afterwards. Otherwise, when saving a post for the second time without reloading it first, the action would be performed twice, the next time three times, and so on.

Leave a Reply

Your email address will not be published. Required fields are marked *