WordPress データ登録機構を知ってもっと自由で効率的なフローを

アプリケーション開発者であればデータ登録機構を把握しておくこと重要であり、APIを叩かずに直にSQLに接続した方が問題解決が容易になることは多い。

ということで、WordPressのデータ登録機構について。

WrodPressのデータベース構造についておおよそのイメージができていることが必須。
記事や固定ページのデータは wp_posts テーブル、カスタムタクソノミーは wp_terms テーブルとかに登録されてる、くらいは知っておくこと。

WordPress Codex/データベース構造

投稿記事

投稿記事のメインデータは wp_posts テーブルに登録される。
( *以後、必要なカラムのみ抜粋)

> wp_posts テーブル

ID post_content post_title post_name post_parent guid post_type
{$post_id} {$post_content} {$post_title} {$post_slug} {$parent_post_id} {$guid} {$post_type}
parent_post_id: 固定ページおよび階層型カスタム投稿の場合にのみ有効
post_type: 投稿はpost, 固定ページはpage, カスタム投稿は$post_type
guid: GUIDは get_the_guid で取得可能

カスタムフィールドがある場合

> wp_postmeta テーブル

post_id meta_key meta_value
{$post_id} {$field_key} {$field_value}
post_id: メインデータのID( wp_posts テーブルの ID )

アップロードファイル

アップロードファイルを入稿した場合、wp_posts テーブルに1レコード、wp_postmeta テーブルに2レコードの、合計3レコードがセットで登録される。

> wp_posts テーブル

post_title post_status post_name guid post_type post_mine_type
{$file_name} inherit {$file_name} {$guid} attachment {$mine_type}
post_status: inherit 固定
post_type: attachment 固定
post_mime_type: MIMEタイプは get_post_mime_type で取得可能

> wp_postmeta テーブル

post_id meta_key meta_value
{$attachment_id} _wp_attached_file {$file_name}
{$attachment_id} _wp_attachment_metadata シリアライズされたメタデータ
_wp_attached_file: wp_content/uploads/ディレクトリ以下の相対パス
_wp_attachment_metadata: シリアライズされたメタデータ
いずれも wp_get_attachment_metadata で取得可能。

メディアからファイルを単体でアップロードしても、記事編集時にアップロードして同様。
また、記事内にアップロードファイルが添付されていたとしても、記事とアップロードファイルにデータ上の関連性はない。
記事のデータにアップロードファイルのパスが挿入されるだけ。

eq.) sample.png をアップロードした場合

> wp_posts テーブル

ID post_title post_status post_name guid post_type post_mine_type
1 sample inherit sample http://root/uploads/2014/11/sample.png attachment image/png

> wp_postmeta テーブル

meta_id post_id meta_key meta_value
1 1 _wp_attached_file 2014/11/sample.png
2 1 _wp_attachment_metadata a:5:{s:5:”width”;i:538;s:6:”height”;i:190;s:4:…(省略)

タクソノミー

タクソノミー関連のテーブルは3つある。

> wp_terms テーブル

term_id name slug term_group
{$term_name} {$term_slug}

> wp_term_taxonomy テーブル

term_taxonomy_id term_id taxonomy description parent count
{$taxonomy_name} {$term_description} {$parent_term_id} 関連記事数

> wp_term_relationships テーブル

object_id term_taxonomy_id term_order
{$post_id} {$term_id}
parent_term_id: 階層型タクソノミーの場合のみ有効

タクソノミー( taxonomy )を定義しただけではなにもデータは登録されない。
タームを定義した時にはじめてデータが登録される。
タームを定義した時のデータ( name, slug, description, parent_term_id )は、wp_terms テーブルと wp_term_taxonomy テーブルに分散して登録される。

ユーザ

> wp_users テーブル

user_login user_pass user_nicename user_email
{$username} 暗号化パスワード {$nicename} {$email}

WordPress では phpass というライブラリを使ってパスワードを暗号化している。
ユーザデータをインポートする場合は、同じ方式で暗号化してから登録する必要がある。

require '/wp-includes/class-phpass.php';
$x = new PasswordHash( 8, true );
$hash = $x->HashPassword( 'password' );

> wp_usermeta テーブル

user_id meta_key meta_value
{$user_id} {$meta_key} {$meta_value}

最低限必要なデータの項目は、wp_capabilities と wp_user_level くらいだろうか。
wp_capabilities には以下にような権限名の配列をシリアライズ化したもの、wp_user_level には 1〜10 の権限レベルが登録される。

array(
 [administrator] => 1
)

おまけ – ACF( Advanced Custom Fields plugins)のカスタムフィールド

カスタムフィールドの拡張として ACF プラグインが有名なので、そのデータ登録機構についても。

基本

> wp_postmeta テーブル

post_id meta_key meta_value
{$post_id} {$field_name} {$field_value}
{$post_id} _{$field_name} {$field_key}

ACF のカスタムフィールドでは、{$field_name} に対する {$field_value} とは別に、アンダースコアがプレフィックスされた _{$field_name} に対する {$field_key} という2つのレコードが登録される。
field_name と field_key に整合性がないと正しく機能しない。

この field_key については、管理UI上では隠されていて自由に設定することはできず、自動的に乱数が設定される。
あとでデータをインポートすることを考えているなら、フィールドグループをPHPエクスポートして、field_key を再定義しておくことが必須となる。

* 以下の部分を書き換える。

...
register_field_group(array (
	'id' => 'acf_field-group1',
	'title' => 'field group1',
	'fields' => array (
		array (
			'key' => 'field_5463050afa9c1',
			'label' => 'text',
			'name' => 'text',
			'type' => 'text',
			'default_value' => '',
			'placeholder' => '',
			'prepend' => '',
			'append' => '',
			'formatting' => 'html',
			'maxlength' => '',
		),
		array (
			'key' => 'field_5463050ffa9c2',
			'label' => 'img',
			'name' => 'img',
			'type' => 'image',
			'save_format' => 'object',
			'preview_size' => 'thumbnail',
			'library' => 'all',
		),
	),
	...
));

繰り返しフィールド

> wp_postmeta テーブル

post_id meta_key meta_value
{$post_id} {$field_name} サブフィールド数
{$post_id} _{$field_name} {$field_key}
{$post_id} {$field_name}_%_{$sub_field_name} {$sub_field_value}
{$post_id} _{$field_name}_%_{$sub_field_name} {$sub_field_key}

親の field_name には値はないので、サブフィールド数が登録される。
以下、サブフィールドの数だけ、{$field_name}_0_{$sub_field_name}, {$field_name}_1_{$sub_field_name} とナンバリングされて登録されていく。

オプションフィールド

> wp_options テーブル

option_name option_value autoload
options_{$field_name} {$field_value} no
_options_{$field_name} {$field_key} no

オプションフィールドの場合、関連する記事が存在しないため、wp_postmeta ではなく wp_options テーブルが使用される。
field_name には、options のプレフィックスが付加される。
autoload の初期値は yes であることにも注意。

まとめ

データ登録機構を把握しておくと、データのインポートやエクスポートを行うツール開発などに役立つ。
イニシャルリリース時に大量のデータ入稿が必要だったり、エクセルベースでデータ入稿を行う運用を前提としている場合などね。

制作開発フェーズだけ考えているとさほど気にならないが、プロジェクトフロー全体を考慮すると、データ入稿や運用をどう行うかを検討することはかなり重要になってくるポイント。

Comments

【覚書】Wordpressのメディアにあるタイトル・キャプション・代替テキスト・説明は どうちがうのか? | shortycolossus へ返信する コメントをキャンセル