WordPressのSettings APIはregister_setting()とsettings_fields()のgroup名をそろえる
公開日: 執筆:佐藤
WordPressの設定画面からoptionを保存するなら、register_setting()で保存対象のoption名とsanitize callbackを登録し、form内のsettings_fields()へ同じgroup名を渡します。group名が違うと、formが示す設定groupと、保存を許可したoptionが対応しません。
register_setting()は入力欄を作る関数ではなく、settings_fields()も値を保存する関数ではありません。設定の登録、hidden fieldの出力、入力欄の表示、値のsanitize、保存後の確認を分けます。
register_setting()はgroup、option、sanitize callbackを登録する
WordPress 3.9.1のregister_setting()は、次の三つを受け取ります。
register_setting( $option_group, $option_name, $sanitize_callback );
第一引数は設定group、第二引数は保存するoption名、第三引数は保存前のsanitize callbackです。関数はoption名をgroupの保存対象へ加え、callbackがあれば、そのoption用のsanitize filterへ登録します。
次は、一行の連絡先を保存対象として登録する説明用の例です。satolab_contactとsatolab_contact_phoneは実在するpluginの値ではありません。
function satolab_register_contact_setting() {
register_setting(
'satolab_contact',
'satolab_contact_phone',
'sanitize_text_field'
);
}
add_action( 'admin_init', 'satolab_register_contact_setting' );
2014年2月8日保存のWordPress Codexは、register_setting()をadmin_initのcallbackから呼ぶよう説明しています。設定画面を表示したときだけでなく、formの送信先であるoptions.phpが処理するときにも登録が必要だからです。
settings_fields()には同じgroup名を渡す
独自の設定formは、POSTでoptions.phpへ送ります。そのform内へsettings_fields()を置き、register_setting()と同じgroup名を渡します。
<form method="post" action="options.php">
<?php settings_fields( 'satolab_contact' ); ?>
<label for="satolab-contact-phone">連絡先</label>
<input
id="satolab-contact-phone"
name="satolab_contact_phone"
type="text"
value="<?php echo esc_attr( get_option( 'satolab_contact_phone', '' ) ); ?>"
/>
<?php submit_button(); ?>
</form>
このformは設定画面の出力部分だけを示す仮例です。管理画面のmenuやpageを登録する処理は含みません。
WordPress 3.9.1のsettings_fields()は、group名を持つoption_page、値がupdateのaction、nonceをhidden fieldとして出力します。入力欄のnameは、register_setting()の第二引数で登録したoption名と一致させます。
options.phpは権限、nonce、保存対象を別々に確認する
WordPress 3.9.1のoptions.phpは、設定保存について次を分けて処理します。
- 利用者が必要なcapabilityを持つか確認する。
- group名に対応するnonceを確認する。
- groupへ登録されたoption名だけを保存対象にする。
- 送られた値を
update_option()へ渡す。
Settings APIを使うoption pageでは、既定のcapabilityはmanage_optionsです。設定画面のmenuを別のcapabilityで表示しても、保存側のcapabilityと一致していなければ保存できません。画面を見られることと、設定を変更できることを分けて確認します。
nonceは、その要求が意図したformから送られたかを確認する材料です。入力値の内容が業務上正しいことや、表示してよい利用者であることまで一つで保証しません。capabilityとsanitizeを別に残します。
sanitize callbackは入力の用途に合わせる
例で使ったsanitize_text_field()は、一行の文字列について、不正なUTF-8、tag、改行、tab、余分な空白などを処理します。WordPress 3.9.1の実装で、その処理を確認できます。
ただし、一般的な一行文字列へ整えることと、電話番号、メールアドレス、URL、数値などの形式を確定することは別です。許可する形式と範囲が決まっている値には、その条件を確認する専用callbackを用意します。
保存時のsanitizeと、HTMLへ出力するときのescapeも役割が違います。formへ値を戻す例では、attribute値なのでesc_attr()を使います。保存時にsanitizeしたことを理由に、出力場所ごとのescapeを省きません。
group名とoption名は定数のように一か所で管理する
group名やoption名を複数箇所へ手入力すると、変更時に片方だけが古い名前になる可能性があります。小さなpluginでも、登録、form、取得、削除で使う名前を一覧にします。
| 名前 | 使う場所 | 役割 |
|---|---|---|
satolab_contact |
register_setting()、settings_fields() |
保存対象をまとめるgroup |
satolab_contact_phone |
register_setting()、inputのname、get_option() |
保存するoption |
sanitize_text_field |
register_setting()の第三引数 |
保存前のsanitize callback |
pluginを停止しても、保存したoptionが自動的に消えるとは限りません。停止、削除、設定値の削除を別の処理として設計し、どの値を残すかを事業者が確認できるようにします。
設定画面の制作を外部へ任せる場合も、group名、option名、初期値、許容形式、保存権限、削除条件を引き継ぎます。画面の見た目だけを受け取っても、保存データの意味と責任は分かりません。
最初の一手は、既存の設定formを一つ選び、register_setting()とsettings_fields()のgroup名、inputのnameとoption名、sanitize callbackの三組を突き合わせることです。
関連記事

