A week ago, we introduced the "clone as multiple" feature, which allows you to store cloneable values in multiple rows in the database. To make it works with your existing data, we make it optional and is turned off by default. However, some of you might want to convert the existing data to the new format, which allows you to perform a query based on custom field's value. In this tutorial, I'll show you a quick way to convert the existing custom field values to the new format and make "clone as multiple" feature works for you.

Assuming you have a cloneable custom field start_date, which is created for a custom post type event. Using 'clone' => true, its value is a serialized string of an array like this: a:2:{i:0;s:10:"2019-05-01";i:1;s:10:"2019-04-30";} (['2019-05-01', '2019-04-30']). We need to convert that string back to an array of 2 elements and store them in 2 rows in the database.

And we need to loop through all events and process all of them. Here is the code:



This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters


<?php
function prefix_convert( $field_id ) {
$query = new WP_Query( [
'post_type' => 'event',
'posts_per_page' => -1,
] );
if ( ! $query->have_posts() ) {
return;
}
while ( $query->have_posts() ) {
$query->the_post();
$values = rwmb_meta( $field_id );
if ( ! is_array( $values ) || empty( $values ) ) {
continue;
}
delete_post_meta( get_the_ID(), $field_id );
foreach ( $values as $value ) {
add_post_meta( get_the_ID(), $field_id, $value );
}
}
wp_reset_postdata();
}
add_action( 'init', function() {
if ( ! isset( $_GET['unique_key'] ) ) {
return;
}
$field_id = 'start_date';
prefix_convert( $field_id );
} );
view raw

convert.php

hosted with ❤ by GitHub

The main code is in the prefix_convert function. It does the following tasks:

  1. Query all events (a custom post type event).
  2. For each event, get the value of the cloneable field, which should be an array.
  3. Remove the custom field from the database.
  4. Loop through the value array of the field and insert a new row into the meta table.

To run this function, I created a simple trigger (the code below the prefix_convert function). That code runs in the init hook, it checks for a secret key in the URL (you should change it so you're the only person who knows it) and performs the convert task.

Copy this file into your theme / plugin and just include it in your theme's functions.php file:

include 'convert.php';

To convert the old values, access your site via URL: domain.com/?unique_key.

Important notes:

  • Backup your database before running the code.
  • If you have a staging website (or a copy of your website on your localhost), test the code on that first.
  • After running the code, remove the include statement in you functions.php file. This code should be run only once.

That's it! Hope that helps you easier to use the new feature. If you have any questions, please let me know in the comment.

Read more: How to optimized database for custom fields.

Leave a Reply

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