wordpress (3)

Settings in WordPress plugins

I’ve rewritten my facebook helper for wordpress to make it a bit cleaner and as an example use case for the jQuery facebook helper I wrote last week.  I’ve also delved into the wordpress code a little more and added an option to set the facebook app_id from the wordpress admin page rather than having to set it directly in the code.  So lets take a look at that:

First we need to tell wordpress where our setting is going to be displayed in the admin interface:

            'Post to Facebook',

function tpfb_setting_section_callback_function() {
        echo "'Tall' Paul's Facebook plugin.  Publishing a post will also post it on your facebook wall. <br/> To use the plugin, you need to createa  facebook app<br/>See <a href='http://www.tall-paul.co.uk/2012/03/06/facebook-plugin-for-wordpress/'>this post</a> for details";

In this example we’re adding a new section to the already existing ‘writing’ settings page.  Since I only have one setting (the app_id) it would be overkill to create a whole new page in the setting sinterface for it.  There’s four parameters for the ‘add_settings_section’ function, but they’re fairly straightforward.  The first is an identifier for your section, which can be anything but you’ll use it later so make it sensible.  The second is the title that will appear for this settings section (we’ll see what this looks like later).  Third is a callback function which will be called when this section is ‘placed’ on the page.  This is generally used to add some introducrtory or descriptive text at the top of your section, so people know what it’s for as you can see from my example.  Finally we have the identifier for the ‘page’ that we want the section to appear in.  Here we’re using the pre-existing ‘writing’ page, rather than creating our own.

With our section setup, we now need to add a setting to it.   For my plugin, I only need one setting (the facebook ‘app_id’) so here we go:

add_settings_field('tpfp_appid','Facebook App ID','tpfb_app_id_display','writing','tpfb_setting_section');

The ‘add_settings_field’ function actually places our setting on the admin page (although we control how the field appears using a callback function as we’ll see shortly),  it has 5 parameters, but the first 4 are logically similar to those we’ve seen for ‘add_settings_section’: an identifier for this field, a title to display next to the field, a callback function (which we’ll look at in a minute, because here the callback is used to display the field itself) and then the page for the field to appear on.  Finally, we also have a 5th parameter which refers back to our section identifier so the setting appears in our created section.

If you run the code as it is at this point, you’ll see a new section in the ‘writing’ page, but no setting will appear in it…because we haven’t told wordpress how to display this field.  To do that, we make use of the callback function we declared in ‘add_settings_field’:

function tpfb_app_id_display(){
        $option = get_option('tpfb_appid');
        echo "<input id='tfpb_appid' name='tpfb_appid' size='40' type='text' value='$option' />";    

There’s only really 2 things to note here.  The first is how we get the current saved state of our setting back from wordpress usingthe ‘get_option’ function, with the identifier of the setting (as used in ‘add_settings_field’) as a parameter. Secondly we can see how we actually get an input for this setting placed on the admin page… we simply echo it directly to the page from this callback function.  There’s a lot of flexibility over how you want your settings to appear inherent in this method, since you have total control over this stage of the page construction.

And that’s almost everything.  There’s a couple of final steps required.  First, for each setting we’ve added we need to ‘register’ it with wordpress.  This instructs wordpress to save these settings along with everything else when the page is submitted.  This is incredibly straightforward:


You should be able to tell what those parameters refer to now…the first is your page identifier, and second is the identifier of the new setting.

Finally, how do we get wordpress to include all this code when building its admin pages?  Simple, we use the ‘hook’ system to plug our code into the correct place in wordpress.  First we wrap all our code so far in one function:

function tpfb_settings_api_init() {
  //all your code here
  function tpfb_setting_section_callback_function(){}

//don't forget to close the wrapping function!

and then we add an ‘action’ to hook into WordPress’ admin page initialisation:

add_action('admin_init', 'tpfb_settings_api_init');

And that’s it!  here’s how it looks in the admin interface:

You can find the code for this article as part of my facebook plugin for wordpress which you can download here:


Job Hunting!

Thought I might as well post something here, you never know who reads these things…

I am currently on the hunt for a job.  Ideally something in PHP / Web development that pays around £30k (or slightly less for the right role) and is based somewhere near Manchester (UK).  Working from home would be nice though if you’re based on the other side of the world.

email me for a CV if you have any opportunities that might fit the bill.

WP Akismet plugin behind proxy

The new HTTP Api in wordpress 2.9 is fantastic, it standardises http requests and allows you to define a proxy through which all http requests are routed.  Useful if, like me, you run a wordpress server on a corporate network.

You can configure your proxy server by adding the following lines to your ‘wp-config.php’

define('WP_PROXY_HOST', '');
define('WP_PROXY_PORT', '800');

However there’s currently one problem with the default installation of wordpress when it comes to proxy support. Akismet (the spam filtering plugin) Doesn’t work behind the proxy. No matter what you put in for your proxy settings you’ll be told ‘unable to connect’.

The reason is that Akismet uses a ‘raw’ socket connection to do its http requests, rather than the spiffy new API. So, here’s how to fix it:

you need to edit the file ‘/wp-content/plugins/akismet/akismet.php’.

search for the function ‘akismet_http_post’ and replace the entire function (you can just rename the old function) with my newly crafted one:

function akismet_http_post($request, $host, $path, $port = 80, $ip=null){
        global $wp_version;
	$akismet_version = constant('AKISMET_VERSION');
        $args = array(
             'user-agent'=>"User-Agent: WordPress/$wp_version | Akismet/$akismet_version",
         $url = "http://".$host.$path;

         if( !class_exists( 'WP_Http' ) )
         include_once( ABSPATH . WPINC. '/class-http.php' );
	 $http_request = new WP_Http;
         $http_response = $http_request->request($url,$args);
         if( is_wp_error( $http_response ) )
         $response[0] = $http_response['headers'];
         $response[1] = $http_response['body'];
	return $response;

And voila, working spam detection behind a proxy.