WordPress как на ладони
Готовые темы (шаблоны) для WordPress wordpress jino

register_setting() WP 2.7

Регистрирует новую опцию и callback функцию (функцию обратного вызова) для обработки значения опции при её сохранении в БД.

Используется в связке с другими функциями API настроек:

Они упрощают создание страницы настроек.

Функция также может использоваться для регистрации новой опции, которая будет добавлена на базовую страницу настроек WordPress (Общие, Медиафайлы, Чтение...). Опция добавляется в существующую секцию при помощи функции add_settings_field() или можно создать новую секцию функцией add_settings_section() и добавить опцию туда.

Хуки из функции:
Возвращает

null. Ничего не возвращает.

Использование

register_setting( $option_group, $option_name, $args );
$option_group(строка) (обязательный)
Название группы, к которой будет принадлежать опция. Это название должно совпадать с названием группы в функции settings_fields().
По умолчанию: нет
$option_name(строка) (обязательный)
Название опции, которая будет сохраняться в БД.
По умолчанию: нет
$args(массив)

Данные регистрируемой опции.

$defaults = array(
	'type'              => 'string',
	'group'             => $option_group,
	'description'       => '',
	'sanitize_callback' => null,
	'show_in_rest'      => false,
);

sanitize_callback (строка/массив)
Название функции обратного вызова, которая будет обрабатывать значение опции перед сохранением.
Важно! Функция получит один параметр - значение опции. Значение которое указанная функция вернет, будет записано в опцию.

type (строка)
Тип данных с которыми опция ассоциирована.

description (строка)
Описание данных, которые будут храниться в этой опции.

show_in_rest (логический)
Нужно ли добавлять данные этой опции в REST API.

default (разное)
Значение по умолчанию при вызове get_option().

По умолчанию: array()

Примеры

#1. Пример показывающий как нужно подключать функцию через хук admin_init:

add_action( 'admin_init', 'register_my_setting' );
function register_my_setting() {
	register_setting( 'my_options_group', 'my_option_name', 'intval' ); 
} 

#2. Другие примеры

Еще примеры смотрите в описании API опций.

Заметки

#1. Если данные проходят через функцию обработки 2 раза

Например, эта функция вернет строку с двумя восклицательными знаками:

function append_exclamation ($input) { return $input.'!'; }

В этом случае, скорее всего, опции еще не существует в таблице wp_options, поэтому функция update_option() "увидев", что такой опции нет, вызывает add_option(), чтобы добавить новую опцию. Проблема в том, что хук sanitize_option вызывается до вызова функции add_option() и срабатывает второй раз, уже внутри add_option().

#2. Ошибка: ERROR: options page not found - объяснение и решение проблемы:

Такая ошибка возникает, когда фильтр whitelist_options ничего не знает о вашей новой опции.

register_settings() добавляет данные в глобальную переменную $new_whitelist_options. Затем эта переменная объединяется с переменной $whitelist_options в option_update_filter(), которая в свою очередь добавляет новые данные в $new_whitelist_options, где $option_group - используется как индекс новых данных. Когда вы получаете ошибку "ERROR: options page not found" - это означает, что не удалось найти опции по ключу.

Путаница получается, потому что первый аргумент $options_group используется как ключ, а реальное сравнение в файле options.php происходит с параметром $options_page, который равен $hook_suffix, получаемый из результата работы функции add_submenu_page().

Простое решение этой проблемы, указывать одинаковые названия для параметров $option_group и $option_name.

Другая причина этой ошибки - когда неправильно указан параметр $page при вызове функции:

add_settings_section( $id, $title, $callback, $page )

или

add_settings_field( $id, $title, $callback, $page, $section, $args ) 

Заметка: $page должен быть равен $menu_slug из функции:

add_theme_page( $page_title, $menu_title, $capability, $menu_slug, $function );

Код register setting: wp-includes/option.php WP 4.7.5

<?php
function register_setting( $option_group, $option_name, $args = array() ) {
	global $new_whitelist_options, $wp_registered_settings;

	$defaults = array(
		'type'              => 'string',
		'group'             => $option_group,
		'description'       => '',
		'sanitize_callback' => null,
		'show_in_rest'      => false,
	);

	// Back-compat: old sanitize callback is added.
	if ( is_callable( $args ) ) {
		$args = array(
			'sanitize_callback' => $args,
		);
	}

	/**
	 * Filters the registration arguments when registering a setting.
	 *
	 * @since 4.7.0
	 *
	 * @param array  $args         Array of setting registration arguments.
	 * @param array  $defaults     Array of default arguments.
	 * @param string $option_group Setting group.
	 * @param string $option_name  Setting name.
	 */
	$args = apply_filters( 'register_setting_args', $args, $defaults, $option_group, $option_name );
	$args = wp_parse_args( $args, $defaults );

	if ( ! is_array( $wp_registered_settings ) ) {
		$wp_registered_settings = array();
	}

	if ( 'misc' == $option_group ) {
		_deprecated_argument( __FUNCTION__, '3.0.0', sprintf( __( 'The "%s" options group has been removed. Use another settings group.' ), 'misc' ) );
		$option_group = 'general';
	}

	if ( 'privacy' == $option_group ) {
		_deprecated_argument( __FUNCTION__, '3.5.0', sprintf( __( 'The "%s" options group has been removed. Use another settings group.' ), 'privacy' ) );
		$option_group = 'reading';
	}

	$new_whitelist_options[ $option_group ][] = $option_name;
	if ( ! empty( $args['sanitize_callback'] ) ) {
		add_filter( "sanitize_option_{$option_name}", $args['sanitize_callback'] );
	}
	if ( array_key_exists( 'default', $args ) ) {
		add_filter( "default_option_{$option_name}", 'filter_default_option', 10, 3 );
	}

	$wp_registered_settings[ $option_name ] = $args;
}

Cвязанные функции

Из раздела: API Настроек

register_setting 5 комментариев
  • campusboy1455 cайт: wp-plus.ru
    @

    А вот к примеру, мне нужно сохранить JS скрипт (рекламный блок), как правильно сделать очистку, чтобы XSS-атаку не словить или ещё чего? Или тут палка о 2 концах?

    • Kama4349

      На выводе использовать функции esc_*... В твоем случае очевидно esc_textarea()

      • campusboy1455 cайт: wp-plus.ru
        @

        Эта функция заменит сущности и если человек изменит немного код и снова сохранит, то это всё сохранится не как js-код, а как просто набор символов и на фронте не заработает уже. Верно?

        • Kama4349

          Не понял, ты что делаешь? Если ты даешь возможность пользователю добавлять JS код, который потом будет работать на твоем сайте - то все - это дыра. Тут либо нужно доверять юзеру, либо закрыть возможность добавить свой JS код на твой сайт...

  • Дима

    А как избежать того, что функция обработчик вызывается 2 раза в случае сохранения настройки которой еще нет в базе данных?

    Ответить5 дней назад #

Здравствуйте, !

Ваш комментарий