Video icon 64
Learning to code? Skill up faster with our practical video courses. Start your free trial today.
Advertisement

Adding Posts to a Site's Front-End Using AJAX

by

WordPress basically divides itself into two portions, the front end section where people can come and read posts or articles on the site. The other is the WordPress admin section from which one can create posts and pages. This works very well if WordPress is used as a general blogging site. But as WordPress is used for different kinds of sites it sometimes becomes necessary to give the user a way to create posts from the front end of the site without forcing him to go in the WordPress admin section.

In this tutorial we are going to see how to create a widget to let users create posts from the front end. This will help the users of the site to create content.


Step 1 Creating the Plugin

To create a plugin, create a file ajaxpostfromfront.php in your wp-content/plugins/ajaxpostfromfront folder. To create a plugin in WordPress we have to add the plugin header as follows:

/*
Plugin Name: Ajax post from front
Plugin URI: 
Description:Allows to post from front end
Author: Abbas Suterwala
Version: 
Author URI: 
*/

We will also define some named constants for our plugin base URL and the plugin path as follows:

define('APFSURL', WP_PLUGIN_URL."/".dirname( plugin_basename( __FILE__ ) ) );
define('APFPATH', WP_PLUGIN_DIR."/".dirname( plugin_basename( __FILE__ ) ) );

This will help us to use them easily where needed in the plugin. Also create a js folder in your ajaxpostfromfront folder and add a file apf.js in it. So the folder structure of the plugin would be as follows:

We will now enqueue the scripts by hooking on to the action hook 'wp_enqueue_scripts' and enqueue our javascript file and localize it to store the WordPress ajax URL which we will use for our ajax calls.

function apf_enqueuescripts()
{
	wp_enqueue_script('apf', APFSURL.'/js/apf.js', array('jquery'));
	wp_localize_script( 'apf', 'apfajax', array( 'ajaxurl' => admin_url( 'admin-ajax.php' ) ) );
}
add_action('wp_enqueue_scripts', apf_enqueuescripts);

If everything has gone right until now we will be able to see our plugin in the plugin list and we should activate it.


Step 2 Understanding the WordPress Functions to Create a New Post

WordPress has a rich set of APIs or functions which are exposed to perform tasks for plugins. It has functions for all types of tasks like creating a post, creating a page, comments etc. In this plugin we are going to use the WordPress function wp_insert_post.

wp_insert_post takes in an array of the different information required to create a post in WordPress. It takes in different parameters like the post title, post content, post status, etc. It also takes in the array of categories which are to be associated with the post. It also contains some other parameters like post password and post excerpt etc.

For a complete list of parameters you can visit the wp_insert_post page in the WordPress Codex.


Step 3 Creating the UI to Create Post From Front End

Next we are going to create the UI for our post from front end plugin. For this we are going to write the following function:

function apf_post_form()
{
	?>

	<form id="apfform" action="" method="post"enctype="multipart/form-data">

		<div id="apf-text">

			<div id="apf-response" style="background-color:#E6E6FA"></div>

			<strong>Title </strong> <br/>
			<input type="text" id="apftitle" name="apftitle"/><br />
			<br/>

			<strong>Contents </strong> <br/>
			<textarea id="apfcontents" name="apfcontents"  rows="10" cols="20"></textarea><br />
			<br/>

			<a onclick="apfaddpost(apftitle.value,apfcontents.value);" style="cursor: pointer"><b>Create Post</b></a>

		</div>
	</form>

	<?php
}

In the function we will first create a form using the <form> tag. In this we will create a div with the ID apf-response which will update with the message that comes from the AJAX response we will get. Then we have created a text box for the title and a text area for the content of the post.

Next let us create a link called 'create post' which calls a javascript function apfaddpost which will make an AJAX call to create the post. We will see the implementation of the AJAX call in the below steps.

In case we call the function apf_post_form in the theme files you will see it as follows. In my theme I have just called it before the main loop.


Step 4 Creating a Widget to Display the UI on Front End

Now we are going to create a widget for our post from front plugin. This widget will display the UI for posting from the front which we created. Following is the code for the widget.

class AjaxPostFromFrontWidget extends WP_Widget {
	function AjaxPostFromFrontWidget() {
		// widget actual processes
		$widget_ops = array('classname' => 'AjaxPostFromFrontWidget', 'description' => 'Lets you create post from front end' );
		$this->WP_Widget('AjaxPostFromFrontWidget','AjaxPostFromFrontWidget', $widget_ops);
	}

	function form($instance) {
		// outputs the options form on admin
		$defaults = array( 'title' => 'Ajax Post From Front' );
		$instance = wp_parse_args( (array) $instance, $defaults );

		?>
		<p>
			<label for="<?php echo $this->get_field_id( 'title' ); ?>"><?php echo 'Title:'; ?></label>
			<input id="<?php echo $this->get_field_id( 'title' ); ?>" name="<?php echo $this->get_field_name( 'title' ); ?>" value="<?php echo $instance['title']; ?>" class="widefat" />
		</p>
		<?php
	}

	function update($new_instance, $old_instance) {
		// processes widget options to be saved
		$instance = $old_instance;
		$instance['title'] = strip_tags( $new_instance['title'] );

		return $instance;
	}
	
	function widget($args, $instance) {
		// outputs the content of the widget
		extract( $args );

		$title = apply_filters('widget_title', $instance['title'] );
		echo $before_widget;
		if ( $title )
			echo $before_title . $title . $after_title;
		echo '<ul>';
		echo apf_post_form();
		echo '</ul>';
		echo $after_widget;
	}
}

In the constructor we give the class name and the description of the widget. In the form function currently we display only one field that is the title to be displayed for the widget. We update the title field in the update function.

In the widget function we get the title saved in the widget instance and display that. Then we call the function apf_post_form which will display the form that we created in the previous step.

We will register the widget as follows:

function apf_widget_init() {
	// Check for the required API functions
	if ( !function_exists('register_widget') )
		return;

	register_widget('AjaxPostFromFrontWidget');
}
add_action('widgets_init', 'apf_widget_init');

Now we can drag and drop our new widget on the sidebar.

Once the widget is dropped on the side bar you should be able to see the form on the home page in the sidebar as follows:


Step 5 Creating a Post via AJAX From the Front End

Now let's create a function to handle the AJAX request of creating the post. The function to handle the AJAX request is as follows:

function apf_addpost() {
	$results = '';

	$title = $_POST['apftitle'];
	$content =	$_POST['apfcontents'];

	$post_id = wp_insert_post( array(
		'post_title'		=> $title,
		'post_content'		=> $content,
		'post_status'		=> 'publish',
		'post_author'       => '1'
	) );

	if ( $post_id != 0 )
	{
		$results = '*Post Added';
	}
	else {
		$results = '*Error occurred while adding the post';
	}
	// Return the String
	die($results);
}

In this function we get the values of the title and the content from the $_POST variable. With those values using the wp_insert_post function of WordPress to create the post. The function wp_insert_post returns the newly created post id if succeeded and zero if failed. So using that value we either sent a success or a failure message back from the AJAX.

To register this function with the WordPress AJAX system we will call the following:

// creating Ajax call for WordPress
add_action( 'wp_ajax_nopriv_apf_addpost', 'apf_addpost' );
add_action( 'wp_ajax_apf_addpost', 'apf_addpost' );

Once our AJAX handler is done we just need to make the AJAX request from our javascript code as follows:

function apfaddpost(posttitle,postcontent) {

	jQuery.ajax({

		type: 'POST',

		url: apfajax.ajaxurl,

		data: {
			action: 'apf_addpost',
			apftitle: posttitle,
			apfcontents: postcontent
		},

		success: function(data, textStatus, XMLHttpRequest) {
			var id = '#apf-response';
			jQuery(id).html('');
			jQuery(id).append(data);

			resetvalues();
		},

		error: function(MLHttpRequest, textStatus, errorThrown) {
			alert(errorThrown);
		}

	});
}

function resetvalues() {

	var title = document.getElementById("apftitle");
	title.value = '';

	var content = document.getElementById("apfcontents");
	content.value = '';

}

In the function apfaddpost we just make an AJAX request passing the post title and the post content. Once the response is received we just display the message returned by the AJAX handler in the div apf-response. After that we reset the values in the form.

After clicking on create post the post will be created and the message will be seen as follows:


Step 6 Adding the Option of Letting Only Logged in Users Post

Now we will add the functionality to let the admin choose if they do not want users who are not logged in to create posts.

For this we update the apf_post_form as follows to take an argument $allowNotLoggedInuser. In that case when the user is not logged in, it will not display the form but will display a message to login.

function apf_post_form($allowNotLoggedInuser='yes') {
	if ( $allowNotLoggedInuser == 'no' &&  !is_user_logged_in() ) {
		echo "Please Login to create new post";
		return;
	}
	?>

	<form id="apfform" action="" method="post"enctype="multipart/form-data">

		<div id="apf-text">

			<div id="apf-response" style="background-color:#E6E6FA ;color:blue;"></div>

			<strong>Title </strong> <br/>
			<input type="text" id="apftitle" name="apftitle"/><br />
			<br/>

			<strong>Contents </strong> <br/>
			<textarea id="apfcontents" name="apfcontents"  rows="10" cols="20"></textarea><br />

			<br/>

			<a onclick="apfaddpost(apftitle.value,apfcontents.value);" style="cursor: pointer"><b>Create Post</b></a>

		</div>
	</form>

	<?php
}

We will also update the widget to display one more option in the form function to display a select field asking whether it is allowed for non logged in users to post. We will also update the values in the update function. In the widget function now we read the value which was set in the widget and then pass it to the apf_post_form function.

The updated widget code should look like this:

class AjaxPostFromFrontWidget extends WP_Widget {
	function AjaxPostFromFrontWidget() {
		// widget actual processes
		$widget_ops = array('classname' => 'AjaxPostFromFrontWidget', 'description' => 'Lets you create post from front end' );
		$this->WP_Widget('AjaxPostFromFrontWidget','AjaxPostFromFrontWidget', $widget_ops);
	}

	function form($instance) {
		// outputs the options form on admin
		$defaults = array( 'title' => 'Ajax Post From Front','allow_not_logged_users' => 'no' );
		$instance = wp_parse_args( (array) $instance, $defaults );

		?>
		<p>
			<label for="<?php echo $this->get_field_id( 'title' ); ?>"><?php echo 'Title:'; ?></label>
			<input id="<?php echo $this->get_field_id( 'title' ); ?>" name="<?php echo $this->get_field_name( 'title' ); ?>" value="<?php echo $instance['title']; ?>" class="widefat" />
		</p>

		<p>
			<label for="<?php echo $this->get_field_id( 'allow_not_logged_users' ); ?>">allow_not_logged_users:</label>
			<select id="<?php echo $this->get_field_id( 'allow_not_logged_users' ); ?>" name="<?php echo $this->get_field_name( 'allow_not_logged_users' ); ?>" class="widefat" style="width:100%;">
				<option <?php if ( 'no' == $instance['allow_not_logged_users'] ) echo 'selected="selected"'; ?>>no</option>
				<option <?php if ( 'yes' == $instance['allow_not_logged_users'] ) echo 'selected="selected"'; ?>>yes</option>
			</select>
		</p>

		<?php
	}

	function update($new_instance, $old_instance) {
		// processes widget options to be saved
		$instance = $old_instance;

		$instance['title'] = strip_tags( $new_instance['title'] );
		$instance['allow_not_logged_users'] = $new_instance['allow_not_logged_users'];
		return $instance;
	}

	function widget($args, $instance) {
		// outputs the content of the widget
		extract( $args );
		$allow_not_logged_users = isset( $instance['allow_not_logged_users'] ) ? $instance['allow_not_logged_users'] : 'no';

		$title = apply_filters('widget_title', $instance['title'] );
		echo $before_widget;
		if ( $title )
			echo $before_title . $title . $after_title;
		echo '<ul>';
		echo apf_post_form($allow_not_logged_users);
		echo '</ul>';
		echo $after_widget;
	}
}

Now from the widget are we can choose the option to whether allow logged in users or no as seen below.

Now in case the option is set to no and someone visits the home page without logging in they will see the following message to login to post.


Step 7 Adding the Option of Adding Categories to Post via Front End Widget

Now we will add the functionality to add categories to the post which we are creating from the front end. To achieve this first we will get the list of all the categories and display them as check boxes on the UI.

For this we add the following code to the function apf_post_form.

<strong>Contents </strong> <br/>
<textarea id="apfcontents" name="apfcontents"  rows="10" cols="20"></textarea><br />

<?php
	$categories = get_categories(array('hide_empty'=> 0));
	foreach ( $categories as $category ) {
		echo "<input type='checkbox' name='apfcategorycheck' id='apfcategorycheck' value='$category->term_id' />";
		echo $category->cat_name;
		echo '<br>';
	}
?>
<br/>

<a onclick="apfaddpost(apftitle.value,apfcontents.value,apfcategorycheck);" style="cursor: pointer"><b>Create Post</b></a>

The above code just gets the list of all categories and displays them as check boxes. That value is passed to our javascript function apfaddpost as an extra parameter.

In the function apfaddpost we get the values which are checked and pass it in the AJAX call as follows:

function apfaddpost ( posttitle,postcontent,postcategory ) {

	var postCatergoryArray = new Array();

	for ( var i=0; i < postcategory.length; i++ ) {
		if ( postcategory[i].checked ) {
			postCatergoryArray[postCatergoryArray.length] = postcategory[i].value;
		}
	}

	jQuery.ajax({

		type: 'POST',

		url: apfajax.ajaxurl,

		data: {
			action: 'apf_addpost',
			apftitle: posttitle,
			apfcontents: postcontent,
			apfcategory:postCatergoryArray
		}
	});

We will need to update the AJAX handler as follows to take the array of ids of the categories and then pass it to the wp_insert_post function , so that the newly created post have the categories appropriately.

function apf_addpost() {
	$results = '';

	$title = $_POST['apftitle'];
	$content =	$_POST['apfcontents'];
	$category = $_POST['apfcategory'];

	$post_id = wp_insert_post( array(
		'post_title'		=> $title,
		'post_content'		=> $content,
		'post_status'		=> 'publish',
		'post_category'		=> $category,
		'post_author'       => '1'
	) );

	if ( $post_id != 0 ) {
		$results = '*Post Added';
	}
	else {
		$results = '*Error occured while adding the post';
	}
	// Return the String
	die($results);
}

Now if we see the widget it will be seen as follows:

And the post created will have those selected categories associated with it as seen below.


Conclusion

WordPress is an extensible platform. We can extend WordPress to add different functionality to so the WordPress platform can be used for different types of sites rather than just blogs. Like in this plugin we have added the functionality of creating posts from the front end, WordPress can be extended in different ways. So happy WordPress coding!

Advertisement