передать объект/JSON в сценарий локализации wp
У меня есть рабочий фрагмент javascript, который содержит объектный литерал. Но мне нужно его локализовать, и я пытаюсь понять, как его переписать, чтобы я мог получить wp_localize_script(), чтобы получить его и вывести правильный формат.
Нелокализованная (нединамическая) версия выглядит следующим образом:
var layoyt_config = {
'header' : 1
, 'footer' : 1
, 'ls' : {'sb1':1}
, 'rs' : {'sb1':1,'sb2':1}
, 'align' : 'center'
};
Теперь, чтобы эти значения были сгенерированы php (на основе некоторых wp_settings) Я хочу использовать wp_localize_script, чтобы я мог взять его из там:
var layoyt_config = my_localized_data.layoyt_config;
И чтобы получить эти данные в это свойство объекта, я "думал", что смогу это сделать, но, очевидно, нет:
$data = array(
'layout_config' => {
'header' : 1
, 'footer' : 1
, 'ls' : {'sb1': 1}
, 'rs' : {'sb1': 1,'sb2': 1}
, 'align' : 'center'
}
);
wp_localize_script('my-script-handle', 'my_localized_data', $data);
Поскольку это приведет к ошибке синтаксического анализа PHP, я попытался переписать синтаксис json в массив, так как wp_localize_script преобразует его обратно в нотацию объектов, но это также не работает для меня:
$data = array(
'layout_config' => array(
'header' => 1
, 'footer' => 1
, 'ls' => array('sb1'=>1)
, 'rs' => array('sb1'=>1,'sb2'=>1)
, 'align' => 'center'
)
);
wp_localize_script('my-script-handle', 'my_localized_data', $data);
И хотя это проходит гладко через синтаксический анализатор php, я не получаю ожидаемый результат в источнике моей страницы, как my_localized_data.layout_config становится строкой "Массив", вот вывод:
<script type='text/javascript'>
/* <![CDATA[ */
var wpkit_localized_data = {
layout_config: "Array"
};
/* ]]> */
</script>
Итак.. Как я могу это сделать (или мне просто нужно смириться с тем, что я должен "сгладить" свой объект в дискретные переменные, такие как:
lc_header = '1';
ls_ls_sb1 = '1';
etc...
2 answers
Действительно, wp_localize_script()
это просто, он просто добавляет кавычки вокруг значений и экранирует содержимое, ожидая, что все они будут строками.
Однако существует ключ l10n_print_after
массива, который будет напечатан без каких-либо помех вообще. Его можно использовать для выполнения произвольного кода после передачи строк. Вы можете использовать его для передачи ваших дополнительных данных.
$data = array(
'layout_config' => {
'ls' : {'sb1': 1}
}
);
$reshuffled_data = array(
'l10n_print_after' => 'my_localized_data = ' . json_encode( $data ) . ';'
);
wp_localize_script('my-script-handle', 'my_localized_data', $reshuffled_data);
В итоге вы получите такой код:
var my_localized_data = {}; // What is left of your array
my_localized_data = {'layout_config': {'ls': {'sb1': 1}}}; // From l10n_print_after
Отказ от ответственности - Здесь я не разбираюсь в вопросах безопасности JS.
Во-первых, чтобы соответствовать желаемому результату, вы отключены по уровню вложенности. Имя объекта используется в качестве параметра в вызове локализации (вместо ключа массива):
$data = array(
'header' => 1
, 'footer' => 1
, 'ls' => array('sb1'=>1)
, 'rs' => array('sb1'=>1,'sb2'=>1)
, 'align' => 'center'
);
wp_localize_script('my-script-handle', 'layout_config', $data);
Но ls
и rs
все еще нарушены, потому что метод WP_Scripts->print_scripts_l10n()
не обрабатывает случай, когда переменная является массивом.
Лучшее, что я мог придумать, чтобы исправить это, - это следующий фильтр (как указано выше - не уверен, насколько безопасно было бы использовать его в производстве, но дать общее идея):
add_filter('js_escape','js_escape_nested', 10, 2);
function js_escape_nested($safe_text, $text) {
if(is_array($text) )
return str_replace( '"', "'", json_encode ($text) );
return $safe_text;
}