カスタム投稿タイプ instructor の編集画面。register_post_type() で 'show_ui' => true、デフォルトエディタは無効化('supports' => ['title'])し、全フィールドをカスタムメタボックスで構成。メタボックスは add_meta_box() で登録し、基本プロフィール・資格・経歴の3ボックスを 'normal'、担当講義紐付けを 'normal'、公開ボックス・顔写真・統計を 'side' に配置。保存は save_post_instructor フックで一括処理。顔写真はWPメディアライブラリ連携(wp_enqueue_media())。担当講義一覧は WP_Query(post_type: web_lecture / live_seminar、meta_query: _lms_instructor_id 一致)で動的取得。
編集画面アクセス: manage_lms_content 権限を current_user_can() で検証。新規作成・編集・公開状態の変更は同権限で許可。ゴミ箱移動は manage_lms_content 必須、完全削除は管理者(manage_options)のみ。担当講義一覧は参照専用のため書き込み権限は不要。統計メタボックスは全権限者に読み取り専用で表示。顔写真アップロードは upload_files 権限を前提。
投稿テーブル: wp_posts(post_type = 'instructor'、post_title = 氏名)。メタデータ: wp_postmeta に _lms_ プレフィックスで保存。主要キー: _lms_instructor_id(自動採番 INS-xxx)、_lms_instructor_kana(ふりがな)、_lms_instructor_display_name、_lms_position、_lms_email、_lms_qualifications(シリアライズ配列)、_lms_specialty、_lms_category_ids(配列)、_lms_profile、_lms_career、_lms_message、_lms_photo_id(メディアID)、_lms_sort_order。担当講義は逆引き参照(各講義の _lms_instructor_id から検索)。統計はキャッシュテーブル lms_instructor_stats から集計(TTL: 1時間)。
編集画面個別の行アクションは不要(一覧画面 B-CNT-004 一覧で定義)。「← 一覧に戻る」リンクで一覧に戻る。「更新」後のリダイレクト先: admin.php?page=lms-instructors&action=edit&id={id}&message=1。「ゴミ箱へ移動」はJS確認ダイアログ後に実行。担当講義一覧の「編集」リンクは各講義の編集画面(admin.php?page=lms-web-lectures&action=edit 等)へ遷移。資格タグの追加・削除はJSでDOM操作後、hidden inputにシリアライズして送信。
編集画面のメタボックス表示/非表示はWP標準の Screen Options で制御。add_meta_box() で登録した各ボックスが Screen Options パネルに自動反映。折りたたみ状態はユーザーメタ closedpostboxes_instructor に保存。メタボックスの並べ替えはWP標準の postbox.js を利用。担当講義統計メタボックスは折りたたみ可だが Screen Options での非表示は推奨しない(必要情報のため)。表示件数のオプションは不要(担当講義一覧は全件表示)。
全フォーム送信時に wp_nonce_field('lms_save_instructor', 'lms_instructor_nonce') でNonce検証必須。テキスト系フィールドは sanitize_text_field()、プロフィール文・経歴は wp_kses_post()(改行タグのみ許可)でサニタイズ。メールアドレスは sanitize_email()。資格・カテゴリIDはシリアライズ前に各要素を sanitize_text_field() / absint() で検証。顔写真IDは absint() で数値のみ許可し、attachment_url_to_postid() で実在確認。担当講義一覧の取得は WP_Query を使用(直接SQLは不可)。統計はトランジェントAPI(set_transient('lms_instructor_stats_{id}', ..., HOUR_IN_SECONDS))でキャッシュし、更新時に delete_transient() でキャッシュクリア。autoloadは 'no' を指定し、不要なメタデータのメモリ消費を抑制。