В стандартном WordPress есть несколько типов метаданных: метаданные постов, пользователей, комментариев и терминов. Однако иногда возникает необходимость хранить дополнительные данные, не привязанные напрямую к этим сущностям, или же создать собственный объект метаданных для удобного и структурированного хранения информации.
Что такое собственный объект метаданных и зачем он нужен
Собственный объект метаданных — это пользовательская структура данных, которая позволяет хранить произвольные данные, связанные с определённой логической сущностью вашего сайта. Например, если вы разрабатываете плагин для управления мероприятиями, может понадобиться хранить дополнительные параметры, которые не подходят под стандартные типы метаданных WordPress.
Ключевые преимущества создания собственных объектов метаданных:
- Гибкое и расширяемое хранение данных, не зависящее от стандартных таблиц wp_postmeta и других.
- Улучшенная производительность при большом объёме данных, поскольку можно оптимизировать структуру таблиц под свои нужды.
- Лёгкая интеграция с REST API для кастомных решений.
Далее рассмотрим, как создать собственный объект метаданных на примере плагина для WordPress.
Создание таблицы для собственного объекта метаданных
Первым шагом создадим таблицу в базе данных для хранения наших метаданных. Для этого используем функцию активации плагина и класс dbDelta, который умеет создавать и обновлять таблицы.
function wpunit_create_custom_meta_table() {
global $wpdb;
$table_name = $wpdb->prefix . 'wpunit_custom_meta';
$charset_collate = $wpdb->get_charset_collate();
$sql = "CREATE TABLE $table_name (
id bigint(20) unsigned NOT NULL AUTO_INCREMENT,
object_id bigint(20) unsigned NOT NULL,
meta_key varchar(255) NOT NULL,
meta_value longtext NOT NULL,
PRIMARY KEY (id),
KEY object_id (object_id),
KEY meta_key (meta_key)
) $charset_collate;";
require_once( ABSPATH . 'wp-admin/includes/upgrade.php' );
dbDelta( $sql );
}
register_activation_hook( __FILE__, 'wpunit_create_custom_meta_table' );В этой таблице:
object_id— идентификатор объекта, с которым связаны метаданные (например, ID мероприятия).meta_key— ключ метаданных.meta_value— значение метаданных.
Это структура похожа на стандартную таблицу метаданных, но вы можете расширять её, добавляя дополнительные поля, если нужно.
Функции для работы с собственными метаданными
Теперь создадим набор функций для удобной работы с нашими метаданными: добавление, получение, обновление и удаление.
function wpunit_add_custom_meta( $object_id, $meta_key, $meta_value ) {
global $wpdb;
$table_name = $wpdb->prefix . 'wpunit_custom_meta';
return $wpdb->insert( $table_name, [
'object_id' => $object_id,
'meta_key' => $meta_key,
'meta_value' => maybe_serialize( $meta_value )
] );
}
function wpunit_get_custom_meta( $object_id, $meta_key = '', $single = true ) {
global $wpdb;
$table_name = $wpdb->prefix . 'wpunit_custom_meta';
if ( $meta_key ) {
$results = $wpdb->get_col( $wpdb->prepare(
"SELECT meta_value FROM $table_name WHERE object_id = %d AND meta_key = %s",
$object_id, $meta_key
) );
} else {
$results = $wpdb->get_results( $wpdb->prepare(
"SELECT meta_key, meta_value FROM $table_name WHERE object_id = %d",
$object_id
), OBJECT_K );
}
if ( ! $results ) {
return $single ? '' : [];
}
if ( $single ) {
return maybe_unserialize( $results[0] );
} else {
$unserialized = [];
foreach ( $results as $key => $value ) {
$unserialized[ $key ] = maybe_unserialize( $value );
}
return $unserialized;
}
}
function wpunit_update_custom_meta( $object_id, $meta_key, $meta_value ) {
global $wpdb;
$table_name = $wpdb->prefix . 'wpunit_custom_meta';
$updated = $wpdb->update( $table_name, [
'meta_value' => maybe_serialize( $meta_value )
], [
'object_id' => $object_id,
'meta_key' => $meta_key
] );
if ( false === $updated ) {
return false;
}
if ( 0 === $updated ) {
return wpunit_add_custom_meta( $object_id, $meta_key, $meta_value );
}
return true;
}
function wpunit_delete_custom_meta( $object_id, $meta_key = '' ) {
global $wpdb;
$table_name = $wpdb->prefix . 'wpunit_custom_meta';
if ( $meta_key ) {
return $wpdb->delete( $table_name, [ 'object_id' => $object_id, 'meta_key' => $meta_key ] );
} else {
return $wpdb->delete( $table_name, [ 'object_id' => $object_id ] );
}
}Эти функции полностью повторяют логику стандартных функций метаданных WordPress, но работают с нашей собственной таблицей.
Пример использования собственного объекта метаданных
Предположим, вы разработали плагин для управления мероприятиями, и хотите хранить дополнительные параметры для каждого события, например, организатора, контактный телефон, адрес и т. д.
Добавим метаданные к событию с ID 123:
wpunit_add_custom_meta( 123, 'organizer', 'Иван Иванов' );
wpunit_add_custom_meta( 123, 'phone', '+7 999 123-45-67' );
wpunit_add_custom_meta( 123, 'address', 'г. Москва, ул. Пушкина, д. 10' );Получим все метаданные события:
$event_meta = wpunit_get_custom_meta( 123, '', false );
foreach ( $event_meta as $key => $value ) {
echo "<p><strong>" . esc_html( $key ) . ":</strong> " . esc_html( $value ) . "</p>";
}Обновим телефон:
wpunit_update_custom_meta( 123, 'phone', '+7 999 765-43-21' );Удалим адрес:
wpunit_delete_custom_meta( 123, 'address' );Интеграция с REST API WordPress для доступа к кастомным метаданным
Чтобы использовать собственные метаданные в REST API, нужно зарегистрировать новые поля. Это позволит получать и менять данные через стандартные методы API.
add_action( 'rest_api_init', function () {
register_rest_field( 'event', 'custom_meta', [
'get_callback' => function ( $object ) {
return wpunit_get_custom_meta( $object['id'], '', false );
},
'update_callback' => function ( $value, $object ) {
if ( ! is_array( $value ) ) {
return;
}
foreach ( $value as $key => $meta_value ) {
wpunit_update_custom_meta( $object->ID, $key, $meta_value );
}
},
'schema' => null,
] );
} );В этом примере мы добавляем поле custom_meta к сущности «event» в REST API. При получении API вернёт все метаданные, а при обновлении — сохранит переданные данные.
Полезные советы и рекомендации
При использовании собственного объекта метаданных обращайте внимание на следующие моменты:
- Безопасность: обязательно проверяйте и фильтруйте входящие данные перед сохранением.
- Оптимизация запросов: создавайте индексы для ускорения выборок, если ожидается большое количество записей.
- Совместимость: если вы планируете интеграцию с другими плагинами или темами, продумывайте API для доступа к вашим метаданным.
- Используйте сериализацию: функция
maybe_serializeпозволяет хранить сложные данные, включая массивы и объекты.
Пример использования плагина Clearfy Pro для оптимизации кастомных метаданных
Если вы используете плагин Clearfy Pro, его возможности по оптимизации и очистке базы данных помогут поддерживать производительность при работе с кастомными таблицами метаданных. В частности, Clearfy умеет автоматически очищать устаревшие записи и оптимизировать запросы, что полезно при большом количестве пользовательских данных.