GRAPHNOTES

【WP】acf_form()でフロント(固定ページ)での記事投稿を行うメモ

日付:
2017年09月28日
カテゴリー:
Wordpress

Advanced Custom FieldsはWordpressの定番プラグインですが、acf_form()関数によって手軽にフロントページでの投稿/編集を行うことが出来ます。

ユーザー参加型のサイトで、wp-adminダッシュボードを使用させたくない場合などにナイスですね。

Customise WordPress with powerful, professional and intuitive fields

目次

基本

基本形の例

<?php acf_form_head(); ?>
<?php get_header(); ?>

	<main>

			<?php while ( have_posts() ) : the_post(); ?>

				<?php acf_form(); ?>

			<?php endwhile; ?>

	</main>

<?php get_sidebar(); ?>
<?php get_footer(); ?>

acf_form_head() を最初に読み込みます。
acf_form()でフォームを表示します。

記事の更新

<?php acf_form_head(); ?>
<?php get_header(); ?>

	<main>

			<?php while ( have_posts() ) : the_post(); ?>

				<?php acf_form(array(
					'post_id'	=> 123,
					'post_title'	=> false,
					'submit_value'	=> 'Update the post!'
				)); ?>

			<?php endwhile; ?>

	</main>

<?php get_sidebar(); ?>
<?php get_footer(); ?>

新規投稿

<?php acf_form_head(); ?>
<?php get_header(); ?>

	<main>

			<?php while ( have_posts() ) : the_post(); ?>

				<?php acf_form(array(
					'post_id'		=> 'new_post',
					'new_post'		=> array(
						'post_type'		=> 'event',
						'post_status'		=> 'publish'
					),
					'submit_value'		=> 'Create a new event'
				)); ?>

			<?php endwhile; ?>

	</main>

<?php get_sidebar(); ?>
<?php get_footer(); ?>

固定ページから制御してみる

post上での更新ではなく、いわゆるマイページとなる固定ページから記事の投稿・更新を管理してみます。
下記のページテンプレートを作成します。

  • 自分の記事一覧(page-my_posts.php)
  • 記事投稿編集(page-edit_my_post.php)

自分の記事一覧(page-my_posts.php)

ログインユーザーの記事一覧を取得し、参照します。
記事編集のページへGETなどでページIDを渡せるようにします。

<?php
/*
Template Name: マイページ/記事一覧ページ
*/
?>
<?php
	get_header();

	//ログインしていないか、投稿者でなければTOPへリダイレクト
	if (! is_user_logged_in() || ! in_array('author', $this_user->roles)) {
	 wp_redirect( home_url().'/' );
	}
	$current_user = wp_get_current_user();//ログインユーザー情報を取得
	$user_id = $current_user->ID;//ユーザーIDを取得
	$query = new WP_Query(
		array(
		'author' => $user_id,
		'posts_per_page' =>10,
		)
	);
	if ( $query->have_posts() ):
		while ( $query->have_posts() ):
		$query->the_post();
?>
<main>
	<h2><?php the_title();?></h2>
	<form action="<?php echo home_url(); ?>/edit_my_post/" method="get"><!--記事投稿編集URLを指定-->
		<input type="hidden" value="<?php echo $id;//ページIDを渡す ?>" name="editpostID" class="editpost">	
		<button type="submit">編集する</button>
	</form>
</main>

<? endwhile; endif;?>
<?php get_footer();?>

記事投稿編集(page-edit_my_post.php)

<?php
/*
Template Name: マイページ/記事投稿編集ページ
*/
?>
<?php acf_form_head(); ?>
<?php
	
	//対象になるpost_idを取得  (新規の場合は0で)
	$editpostID = $_GET['editpostID'];
	if($editpostID==''){
		$post_id = 0;
	}else {
		$post_id = $editpostID;
	}

	$this_user = wp_get_current_user();
	if (! empty($_REQUEST['pid'])) {
	  $post_id = intval($_REQUEST['pid']);
	}
	//ログインしていないか、投稿者でなければTOPへリダイレクト
	if (! is_user_logged_in() || ! in_array('author', $this_user->roles)) {
	  wp_redirect( home_url().'/' );
	}
	//本人の投稿ではない場合はマイページへリダイレクト
	if (! check_post_id_by_user($post_id)) {
	  wp_redirect( home_url().'/my_posts/' );
	}

	acf_form_head();
	get_header();
?>
<main>
	<?php
	if (have_posts()) : while (have_posts()) : the_post();
	  $opt = array(
		'return' => home_url()..'/my_posts/',
	  );
	  if (intval($post_id) > 0) {
		$opt['post_id'] = intval($post_id);
		$opt['post_title'] = true;
		$opt['post_content'] = true;
		$opt['submit_value'] = '更新';
	  } else {
		$opt['post_id'] = 'new_post';
		$opt['post_title'] = true;
		$opt['post_content'] = true;
		$opt['submit_value'] = '新規登録';
	  }
	  acf_form($opt);

	  the_content();
	endwhile; endif;

	?>
</main>
<?php get_footer();?>


フロントでの投稿画面

 

記事の削除/非公開で登録

acf/save_postフックを使用する

・wp_delete_post()で当該の記事を削除
・wp_update_post()で当該の記事ステータスを更新

【functions.php】
// acfで投稿を削除または非公開にする
add_filter('acf/save_post', 'delete_private_post');
function delete_private_post($post_id) {
	if (is_admin() || get_post_type($post_id) == '適用しないカスタム投稿タイプ名') {
		return $post_id;
	}
	//削除
	if (get_field('delete_this_post', $post_id)) {//「delete_this_post」フィールド(真/偽)で判定
		$force_delete = false;// 完全に削除する場合はtrueに設定
		wp_delete_post($post_id, $force_delete);
		wp_redirect(home_url().'/my_posts/');// 記事が無くなるのでリダイレクトさせる
		exit;
	}
	//非公開
	elseif (get_field('private_this_post', $post_id)) {//「private_this_post」フィールド(真/偽)で判定
		$args = array(
			'ID' => $post_id,
			'post_status' => 'private'
		  );

		wp_update_post($args);
		return $post_id;
	}else {
		$args = array(
			'ID' => $post_id,
			'post_status' => 'publish'
		  );

		wp_update_post($args);
		return $post_id;
	}	
}

上記の場合、カスタムフィールドフィールドタイプ「真/偽」で作成しておき、チェックを入れて更新した場合は記事を削除・更新するようにします。

実際の運用では条件判定を使用して他のフィールドと二段階認証にするなどの対応が望ましいでしょう。


カスタムフィールドで記事のステータスを制御&削除

入力と出力の制限

セキュリティ担保のために入出力の制限を行います。

入力

文字数制限やアップロードファイルの容量制限を行います。
Advanced Custom Fieldsでは管理画面より手軽に設定が行なえます。

出力

XSSなどの対策のためエスケープ処理を行います。

<?php
	$str = get_field('フィールド名');
	echo esc_html( $str );
?>

 

引用元/参照

acf_form() – advancedcustomfields.com

【WordPress】カスタムフィールドも含めたフロントエンドでの投稿 その1 – hanano-ya.jp

ACF Form Delete Post – www.advancedcustomfields.com

広告枠