Вопрос или проблема
У меня есть поле ACF с отношениями для пользовательского типа записи, свойства. Более того, содержимое этих свойств может быть на английском или испанском языке. Когда я использую поле ACF с отношениями для ассоциации свойств с пользователем на странице редактирования пользователя — /wp/wp-admin/user-edit.php
— все работает, как ожидается, и я могу выбирать из выпадающего списка те свойства, которые я хочу для этого пользователя.
Мой вопрос таков: как я могу написать запрос внутри этого фильтра, чтобы отображались только английские свойства, независимо от языка страницы (английский или испанский), который установлен с помощью переключателя WPML? Я знаю, как написать такой запрос в SQL:
SELECT *
FROM wp_2_posts
INNER JOIN wp_2_icl_translations
ON wp_2_icl_translations.element_id = wp_2_posts.id
AND wp_2_icl_translations.language_code="en"
WHERE wp_2_posts.post_type="properties";
Но фильтр требует внесения изменений в $args
, которые соответствуют WP_Query. Я не знаю, как написать вышеуказанный INNER JOIN
на wp_2_icl_translations
, чтобы отображать только пользовательские типы записей свойства на английском языке. Может кто-нибудь объяснить мне, как это сделать, чтобы фильтр ACF работал так, как мне нужно?
Итак, способ, которым я смог всего лишь показать английские свойства на странице администратора пользователя, был с помощью этого posts_request
хука:
add_filter('posts_request', function($sql, $query) {
$is_user_edit_page = (
isset($_SERVER['HTTP_REFERER']) &&
strpos($_SERVER['HTTP_REFERER'], 'user-edit') !== false
);
$is_property_sql = (strpos($sql, 'property') !== false);
if ($is_user_edit_page && $is_property_sql) {
$sql = str_replace("'sp'", "'en'", $sql);
}
return $sql;
}, 10, 2);
В этом хуке я уверен, что он выполняется только на странице user-edit
, и что SQL, который он изменяет, относится к свойствам. Если все эти условия истинны, то я просто заменяю код языка испанского на английский. И в результате SQL, используемый для запроса свойств, вынужден запрашивать только английские.
Спасибо @Howdy_McGee за ваши комментарии по моему вопросу.
Ответ или решение
Как написать INNER JOIN с помощью WP_Query: Подробное руководство
При работе с ACF (Advanced Custom Fields) и WPML (WordPress Multilingual Plugin) возникает необходимость извлечения определённых данных в зависимости от языка. В этом руководстве мы рассмотрим, как использовать WP_Query для выбора только англоязычных свойств в отношении, с использованием коктейля из PHP и SQL.
Контекст
У вас есть кастомный пост-тип "properties", связанный с ACF полем типа "relationship". При редактировании пользователей в админке вам требуется отображать только англоязычные свойства, независимо от языка страницы, который установлен с помощью WPML. Вы уже написали SQL-запрос с INNER JOIN, но стиль использования WP_Query требует другого подхода.
Использование WP_Query для INNER JOIN
К сожалению, WP_Query сам по себе не поддерживает выполнение SQL-запросов с JOIN. Однако, вы можете модифицировать SQL-запросы, используя соответствующие хуки. В вашей ситуации вы нашли решение с использованием хука posts_request
, что является отличным подходом. Давайте посмотрим, как это работает подробнее.
Хук posts_request
add_filter('posts_request', function($sql, $query) {
// Проверяем, находимся ли мы на странице редактирования пользователя
$is_user_edit_page = (
isset($_SERVER['HTTP_REFERER']) &&
strpos($_SERVER['HTTP_REFERER'], 'user-edit') !== false
);
// Проверяем, относится ли SQL к постам типа 'properties'
$is_property_sql = (strpos($sql, 'properties') !== false);
// Если оба условия истинны, заменяем язык на английский
if ($is_user_edit_page && $is_property_sql) {
$sql = str_replace("'sp'", "'en'", $sql);
}
return $sql;
}, 10, 2);
Объяснение кода
-
Проверка страницы редактирования пользователя: Мы используем
$_SERVER['HTTP_REFERER']
для определения, находимся ли мы на странице редактирования пользователя. Это помогает избежать нежелательных изменений SQL на других страницах админки. -
Проверка типа поста: Мы выполняем проверку, чтобы убедиться, что в SQL-запросе уже есть упоминание о "properties". Это позволяет нам точно контролировать, когда изменения должны быть применены.
-
Замена кода языка: Если оба условия верны, мы меняем испанский код языка (
'sp'
) на английский ('en'
). Таким образом, на запрос будет влиять только выборка англоязычных свойств.
Результат
После добавления этого фильтра в файл вашей темы (или в плагин), при переходе на страницу редактирования пользователя будут загружаться только англоязычные свойства, даже если страница отображает контент на испанском языке.
Заключение
Использование хуков WordPress позволяет гибко изменять поведение запросов, не прибегая к непосредственному редактированию SQL-запросов. В вашем случае использование хука posts_request
эффективно изолирует изменения, относящиеся только к конкретным страницам и типам данных. Этот подход улучшает производительность и наглядность вашего кода.
Если вам нужны дополнительные возможности обработки данных, рассмотрите возможность использования кастомных мета-запросов в WP_Query, чтобы углубиться в фильтрацию данных.
Надеюсь, это руководство поможет вам успешно реализовать необходимый функционал в вашем проекте!