How To: List Filters That You Are About to Apply

I was working on a project where I had to find out all the registered filters that I was about to apply, so here’s a WordPress quickie for you! I found this out by inspecting the apply_filters function inside the plugin.php core file, and apparently there’s a $wp_filter global that contains them all in an associative array where keys are tags.

So by doing a print_r at a certain time in your theme or function, you’re able to find out the whole list, but you might as well filter to the hook that you’re looking for. As an example let’s take “comment_text” as the filter tag and list all it’s callbacks — i.e. let’s find out what filters are applied to the comment text before we print it out. Note that this has to run at a point where the filters have already been added, probably before a call to the comment_text() function.

 global $wp_filter;
 print_r( $wp_filter['comment_text'] );

This may seem pretty useless at first sight, but did you know that the comment_text is passed through wptexturize, convert_chars, make_clickable, convert_smilies and several other filters? I didn’t, and I used this trick to find out, which lead me to the make_clickable function which I was looking for in the first place ;)

If you’re wondering what the array keys are in the array that you’ve printed, those are the priorities which were passed (or defaulted) when calling add_filter.

I hope this turns out to be useful to somebody, so thanks for retweeting!

A Thought on WordPress Page Templates

WordPress Page TemplatesI was looking into more premium themes for WordPress the other day, and I see that most of them simply love to give users different page templates. Not all of them are doing it the correct way, but it still is a value add to a WordPress theme.

If you recall from the Codex pages, Page Templates in WordPress are defined with a special comment header in the template files. They can then be chosen at the Edit Page screen from within the WordPress admin area and the chosen template will be used instead of the standard page.php (or other fallback). So today I was playing around with that, and thought that it’d be nice if page templates actually showed the way they look before I’m applying them, at least schematically.

So I fired up my image editor and came up with this screenshot (on the right). Of course you can simply select a page template and then hit the preview button before publishing, and that works most of the times, but what if there are ten or twenty page templates defined by the theme? The template names I’ve seen aren’t too descriptive, then again, there isn’t much space there for that, so an extra description field would definitely be cool. A schematic representation would clearly show what the template looks like, if it has got any sidebars on the right, top, bottom? Or maybe an icon representing a specific logic behind the template. A grid of blocks for “Portfolio Page” for example.

That now makes me thing that post formats can have icon representations too, look at Tumblr! And the WordPress design team has a great taste, according to the icon set in the admin area ;)

I actually ran a short experiment and found a great function called get_page_templates (thank you @nacin!) which returns an array of the available page templates associated with the currently running theme. Below is the draft code that I came up with, it basically lists all the page templates available together with the URLs to their images. Description can be added same way.

$templates = get_page_templates();
$base = trailingslashit( get_stylesheet_directory() );

foreach ( $templates as $template_name => $template_file ) {
    $template_data = implode( '', file( $base . $template_file ) );
    $template_image = '';

    if ( preg_match( '|Template Image:(.*)$|mi', $template_data, $template_image ) );
         $template_image = trim( $template_image[1] );

    if ( $template_image )
        $template_image = trailingslashit( get_stylesheet_directory_uri() ) . $template_image;

    echo "Template Name: {$template_name}<br />Template Image: {$template_image}";
}

This could be used inside a new (or the existing) meta box on the Edit Page screen, and with a few more lines of code and some javascript magic, we can override the default functionality. But do we need to?

Right, do we need to? I know that you, my friends, are more techy than just WordPress users, but think about the normal people for a second. Would this be an easier way to access and work with Page Templates in WordPress? Or does this just make it even more complicated than it already is? Thank you for your input and retweets!

Snippet: Using jQuery 1.5 in WordPress

Yes! jQuery 1.5 was released and I’m sure some of you can’t wait to start using it in their WordPress themes and plugins. So, with a few filters magic, we can get jQuery 1.5 up and running. Add the following code to your theme’s function.php file:

add_filter( 'script_loader_src', 'my_script_loader_src', 10, 2 );
function my_script_loader_src( $src, $handle ) {
    if ( $handle == "jquery" )
        return "http://code.jquery.com/jquery-1.5.min.js";
    return $src;
}

And that’s it! Now every call to wp_enqueue_script jquery will pass through this filter and load up 1.5 instead of the one shipped with your WordPress bundle. Feel free to change the URL of the jQuery script to different CDNs including Microsoft’s and Google’s.

I guess this post will be outdated upon the next WordPress release, but it still may be valuable, since the same trick is used to run jQuery and other libraries shipped with WordPress from different sources like Google or Amazon CloudFront.

Snippet: A "Feed Only" Shortcode for WordPress

This might be valuable for banner ads, pitches to get people on to your website rather than simply reading stuff in their RSS feeds. You can address your RSS subscribers differently in each and every post, just by using this WordPress shortcode trick!

I’m not and ad-guy myself and I don’t care much if people read my feed or browse my website, as long as they’re reading my content. But I do know that some of you own websites that are driven by adverts and that’s good. Giving not full content but excerpts in your RSS feeds is one way to solve the problem, but that annoys most people including myself.

With this shortcode trick, you’ll be able to squeeze content into your posts that will be displayed in your feeds only. And by extending this example with a few extra lines, you’ll be able to do the same thing but the other way round — hide certain parts of your content in your RSS feed. Combining the two you might be able to give the full post content, where for instance the download link is visible to people on your website, while people reading your RSS feed get a different message, like “download available from this website”.

On to the code (for functions.php)!

function feedonly_shortcode( $atts, $content = null) {
	if (!is_feed()) return "";
	return $content;
}
add_shortcode('feedonly', 'feedonly_shortcode');

Once that is done, go ahead and create a new post, write some content, and then add:

... some content ...
[feedonly]Dear RSS readers, I'd really appreciate if you you came to <a href="http://yourwebsite.com">my website</a> and clicked a few banner ads ;)[/feedonly]

When you publish that you won’t see the text between the feedonly short codes on your website, but you will if you open up your RSS feed.

I believe this is a more intelligent and interactive way to speak to your RSS subscribers, rather than just sticking banners at the top/bottom of each feed entry, which don’t get clicked anyway ;) Hope this gets you closer to your feed readers, and please don’t annoy them too much ;)

Thank you for reading!

Using Google's URL Shortener (goo.gl) in WordPress

The Google URL Shortener API has been released this week so I came up with a short snippet that generates short goo.gl URLs. The script is quite simple, you can paste it in your theme’s functions.php file or create a plugin out of it, so without further ado:

function googl_shortlink($url, $post_id) {
	global $post;
	if (!$post_id && $post) $post_id = $post->ID;

	if ($post->post_status != 'publish')
		return "";

	$shortlink = get_post_meta($post_id, '_googl_shortlink', true);
	if ($shortlink)
		return $shortlink;

	$permalink = get_permalink($post_id);

	$http = new WP_Http();
	$headers = array('Content-Type' => 'application/json');
	$result = $http->request('https://www.googleapis.com/urlshortener/v1/url', array( 'method' => 'POST', 'body' => '{"longUrl": "' . $permalink . '"}', 'headers' => $headers));
	$result = json_decode($result['body']);
	$shortlink = $result->id;

	if ($shortlink) {
		add_post_meta($post_id, '_googl_shortlink', $shortlink, true);
		return $shortlink;
	}
	else {
		return $url;
	}
}

add_filter('get_shortlink', 'googl_shortlink', 9, 2);

For the tech people I’ll explain what I’m trying to do here. So first of all we don’t want to shorten links on draft posts as that could be a waste of resources, so we return an empty string. The magic with get_post_meta and add_post meta in the middle and at the end of the function are done for caching purposes — we don’t want to send too many requests to the Google API so let’s keep the already shortened links in the post’s custom fields. This may be annoying in the UI so you might want to add an underscore in the meta key (“_googl_shortlink”) which will make it invisible to the UI.

Next up, I retrieve the permalink of the published post, since we don’t want to shorten an already shortened URL which is that ugly one by WordPress. I use that permalink in an HTTP request to Google’s API using WordPress’ WP_Http object. Note that I’ve added the Content-Type header, which is required by Google, otherwise it’ll return an error. I decode the result body using json_decode (you need PHP 5.2 or later to do this) and if there’s a valid id, which is the shortened URL, I save it to the post’s meta and return the shortlink. If something went wrong, I return the original WordPress’ short URL.

So, clicking on the “Get Shortlink” button in your admin UI will now produce a Goo.gl shortened link to your post. Neat eh? You can also use short links in your theme, somewhere in The Loop:

echo "Shortlink: " . wp_get_shortlink();

Goo.gl Analytics

Right, you might want to see your short links’ analytics at some point. Well, Goo.gl shortened links are all public and their analytics are public too, so all you have to do is browse to goo.gl/info/code where code is the 5-6 alphanumeric digits attached to your shortened URL at the end.

For convenience I wrote a little snippet that would output the short URL and a link to it’s analytics page in your posts list screen inside the admin panel. Below is the code that should go to your functions.php file or plugin file:

function googl_post_columns($columns) {
	$columns['shortlink'] = 'Shortlink';
	return $columns;
}

function googl_custom_columns($column) {
	global $post;
	if ('shortlink' == $column)
	{
		$shorturl = wp_get_shortlink();
		$shorturl_caption = str_replace('http://', '', $shorturl);
		$shorturl_info = str_replace('goo.gl/', 'goo.gl/info/', $shorturl);
		echo "<a href='{$shorturl}'>{$shorturl_caption}</a> (<a href='{$shorturl_info}'>info</a>)";
	}
}

add_action('manage_posts_custom_column', 'googl_custom_columns');
add_filter('manage_edit-post_columns', 'googl_post_columns');

I wrote about custom columns in a post called Custom Post Types in WordPress 3.0, which should give you a general idea of what’s going on here. For more details visit the WordPress Codex.

That’s about it! Yeah, I know there’s some stuff that can be improved here, like smooth error handling, but it’s up to you to implement it. For more info check out the Google URL Shortener Getting Started page. A good place for experiments with Google’s APIs is Google APIs Console.

The plugin-version of this code is available at the WordPress plugin directory: Goo.gl for WordPress. Thank you for reading and retweeting ;)

Counting Facebook Fans in PHP: The Graph API Way

In a previous blog post called How to Count Facebook Fans in PHP I’ve shown a code snippet of how to count the number of fans on a fan page using PHP. Times have changed, the Graph API has been introduced, and due to some responses I introduce here the new way of retrieving your fans count using the new Graph API and php.

Before you copy and paste, flush my comments with ‘my code is not working’ posts, I’d like to get your attention to versioning of the Facebook PHP SDK which we’ve been using all this time. The SDK has changed and of course the old method doesn’t work with the new SDK which is mostly tuned to Graph API, therefore, my previous code still works on a dozen on websites, because I have the old SDK installed back there. So please, be careful to what you download and use, read release notes and change logs, it will save you hours of googling.

The following snippet is based on the Facebook PHP SDK version 2.1.1 (use the Switch Tags option on github to browse through different tags). So get a fresh copy of facebook.php and have it somewhere nearby.

Unlike the old FBQL way, the new Graph API is much easier to work with, and retrieving the fans count is literally two lines of code (initialization doesn’t count). Here’s the snippet to retrieve the fans count for Mashable (don’t forget to replace your application ID and API secret):

require('facebook.php');

$facebook = new Facebook(array(
	'appId' => 'your-app-id',
	'secret' => 'your-api-secret',
));

$mashable = $facebook->api('/mashable');
echo 'Mashable has ' . $mashable['fan_count'] . ' fans';

Easy as that! I was also surprised to see that the Graph API is doing so well. Yeah, the documentation is not very rich, but whenever you need to retrieve something from Facebook, you can always print_r the results, which gives you the full picture. Sending data into Facebook is a little trickier and I’ll show you how in a later blog post.

Cheers!

WordPress: Oh Those Actions and Filters!

Reading Joost de Valk’s quick post about Simple WordPress Debugging with a query variable made me think for a while. Really, how often do you come accross a white screen with no clue of what’s happening? Very effective indeed, and good note about the security issue, but anyways, what came into my mind is a life-saver for all WordPress themes and plugins developers.

I came accross this following snippet quite some time ago on IRC I believe, but never shared it for no specific reason. Perhaps I thought that everybody is aware of it, but looking at how more and more people struggle with debugging WordPress actions and filters, ugh. Here’s your life-saver:

add_action('all', create_function('', 'var_dump(current_filter());'));

This should be used in functions.php or some plugin, and at first sight you’ll notice a huge bunch of text on the output. Fire up the source view of the page you’re looking at (works for admin panels too) and look through the code. You’ll notice that all actions and filters are printed on screen whenever they’re fired.

How could that be used? It clearly shows the order of each action and filter and it clearly shows the names (which tend to be forgotten sometimes). Maybe there are a few more pros I can’t think of right now. Downsides? It doesn’t actually tell you whether it’s an action or a filter, but anyways – short, useful, could be added up to Joost’s snippet.

How To: Retrieve a User ID via SOAP in SugarCRM

Following the Lead Generation Forms with WordPress and SugarCRM post, I came across the need to assign the generated lead to some person in the CRM. It would be easy if you could do it by simply using usernames in the system, but unfortunately usernames may change, but user IDs do not.

User IDs in SugarCRM are stored in a 36-byte alphanumeric string with symbols, which is easy to capture from the database, but not very usable that way. I worked a little more on the snippet I gave before and came up with a new function called getUserId, where a search is performed based on the username.

I’m not sure if this is very secure, but will surely work if you need to simply capture the ID of a certain user and perhaps hard-code it in your script or settings file. Make sure you read the previous post about SugarCRM to capture the whole Sugar class together with the authentication and lead creation functions. The following function is simply an addition to the class:

function getUserId($username)
{
	$result = $this->soap->call('get_entry_list', array(
		'session' => $this->session,
		'module_name' => 'Users',
		'query' => "user_name = 'pavel'",
		'max_results' => 1
	));

	return $result;
}

Once you’re done with that, use your sugar object to authenticate and request for a user id:

$sugar = new SugarCRM('username', 'password');
$sugar->login();

$result = $sugar->getUserId('john');
print_r($result);

So $result will contain an array where you’ll find the alphanumeric ID of the person with the username “john”.

I believe there was some other method for doing that in SugarCRM version prior to 5.5.2 CE, but the new SOAP Web Services are mostly based on a few general methods – get_entry, get_entry_list, set_entry, etc, which are applicable to basically any module including Users.

Now, in order to assign the new lead to your retrieved user (using the createLead function), just add an extra parameter to the array:

$result = $sugar->createLead(array(
	'lead_source' => 'Web Site',
	'lead_source_description' => 'Contact form on my website',
	'lead_status' => 'New',
	'first_name' => $_POST['firstname'],
	'last_name' => $_POST['lastname'],
	'phone_work' => $_POST['phonenumber'],
	'description' => $_POST['description'],
	'email1' => $_POST['email'],
	'assigned_user_id' => $user_id // Your ID goes here
));

Now your newly created leads will be assigned to your user, which is quite convenient when you have e-mail notifications turned on during assignment. Hope that helped somebody! Cheers, and thanks for sharing!

WordPress Snippet: List Authors/Contributors

We were playing around with Brian (@bkmacdaddy) today on a WordPress blog with a few over 50 authors, then bumped into an issue where we had to output a list of all contributors. It’s quite easy at first sight, and functions such as wp_list_authors are quite good at it, but not good enough.

The main issue was that the authors had to be paged and sorted by their names. Moreover, each entry had to contain the contributor’s avatar, Twitter profile, short biography and the website URL. And the other funny part is that we had to exclude the admin user and all users with no posts, which turned out to have quite a simple solution.

After a few hours struggling, we finally came to a solution that is quite interesting, and most importantly, seems to work. There may be a little drawback when retrieving the whole users list, and a direct query to the SQL database with a few JOINs and a LIMIT could have solved that, but it’s not the case if we have some caching plugin turned on. So, here’s the snippet:

// Use this to sort authors by display name
function sort_authors($a, $b)
{
	return strcmp($a['display_name'], $b['display_name']);
}

// Output a list of contributors
function contributors() {
	$authors = array();

	// Get all blog users
	$blogusers = get_users();
	foreach ($blogusers as $bloguser)
	{
		// Fetch
		$user = get_userdata($bloguser->user_id);
		$numposts = get_usernumposts($user->ID);

		// Skip if admin or has no posts
		if ($user->user_login == 'admin' || $numposts < 1) continue;
		$authors[] = (array) $user;
	}

	// Sort the authors by display name
	usort($authors, 'sort_authors');

	// Get the current page
	$paged = get_query_var('paged');
	if (!$paged) $paged = 1;

	// We'll return these at a later stage
	$current_page = $paged;
	$total_pages = ceil(count($authors) / 10);

	// Calculate the starting and ending points
	// Assuming we'll be showing 10 authors per page
	$start = ($paged - 1) * 10;
	$end = $paged * 10;
	if ($end > count($authors)) $end = count($authors);

	// Loop through the authors
	for ($i = $start; $i < $end; $i++)
	{
		$author = $authors[$i];

		// Gather data and meta
		$nicename = $author['user_nicename'];
		$display_name = $author['display_name'];
		$avatar = get_avatar($author['ID']);
		$author_profile_url = get_bloginfo('url') . '/author/' . $nicename . '/';
		$website = get_usermeta($author['ID'], 'user_url');
		$twitter = get_usermeta($author['ID'], 'twitter');
		$bio = $author['description'];

		// Hide if empty
		$twitter = strlen($twitter) > 0 ? 'Twitter: <a href="http://twitter.com/' . $twitter . '" target="_blank">@' . $twitter . '</a><br />' : '';
		$website = strlen($website) > 0 ? 'Website: <a href="' . $website . '" target="_blank">Visit</a><br />' : '';
		$bio = strlen($bio) > 0 ? 'Bio: ' . substr($bio, 0, 50) . '... <a href="' . $author_profile_url . '">Read more</a><br />' : '';

		// Output the list
		print <<<HTML
			<li>
				<a href="{$author_profile_url}">{$avatar}</a>
				<div>
					<a href="{$author_profile_url}">{$display_name}</a><br />
					{$bio}
					{$website}
					{$twitter}
					<a href="{$author_profile_url}">Visit {$display_name}'s Profile Page</a>
				</div>
			</li>
HTML;
	}

	// Return an array containing current and total pages
	// These values could be used to output pagination
	return array(
		'current_page' => $current_page,
		'total_pages' => $total_pages
	);
}

The snippet consists of two functions. The first function is simply a helper function that is passed to the usort function when we need to reorder the contributors in alphabetical order. A simple strcmp is used as the sorting algorithm.

The second function is quite complex. We use the get_users_of_blog function, which unfortunately is not described in the Codex. It returns all the users of the current blog (in our case, there’s only one blog). Looping through all the users, we eliminate the admin, and those who haven’t got any published posts, then form an array of authors. This array is then sorted, and finally, after some pagination tweaks and calculations, we output the list of contributors, depending on the current page (uses get_query_var).

After all that messy stuff, we return our two variables which will help build the pagination UI. And we’re done. Use this in your functions.php and call contributors() in a page template or something ;)

Cheers, and don’t forget to share this post!

Twitter Followers Count Snippet for WordPress

Here’s a short snippet to grab and display your twitter followers count in WordPress. You can use this anywhere, sidebar, posts, header, footer. We’ll be firing an anonymous call to the Twitter API for a user profile. This method does not require authentication, unless you’re trying to view a protected profile. To make this slightly easier I’ve used the JSON functions which are available in PHP 5, but you can easily get them to work in PHP 4 (and as Alex mentioned in the comments below, WordPress comes with it’s own JSON functions for PHP 4 users, which is awesome).

I’ve modified the snippet a little bit due to comments below, and thank you again Alex (@Viper007Bond) for clarifying things with the WordPress HTTP API and those very useful Transients. I actually grabbed some ideas from Alex’s own version of the Twitter Followers Count for WordPress snippet and added a fail-safe route (for times when the Twitter API is down).

Anyways, the snippet now consists of a single function, which checks for a transient (for caching purposes), then fires a query to the Twitter API, and in case of an error return a stored followers count value from the past. In case the Twitter API responded fine, we set a new transient and store the value as the last successful. Here’s the new snippet:

// Use this function to retrieve the followers count
function my_followers_count($screen_name = 'kovshenin')
{
	$key = 'my_followers_count_' . $screen_name;

	// Let's see if we have a cached version
	$followers_count = get_transient($key);
	if ($followers_count !== false)
		return $followers_count;
	else
	{
		// If there's no cached version we ask Twitter
		$response = wp_remote_get("http://api.twitter.com/1/users/show.json?screen_name={$screen_name}");
		if (is_wp_error($response))
		{
			// In case Twitter is down we return the last successful count
			return get_option($key);
		}
		else
		{
			// If everything's okay, parse the body and json_decode it
			$json = json_decode(wp_remote_retrieve_body($response));
			$count = $json->followers_count;

			// Store the result in a transient, expires after 1 day
			// Also store it as the last successful using update_option
			set_transient($key, $count, 60*60*24);
			update_option($key, $count);
			return $count;
		}
	}
}

echo "I have " . my_followers_count('kovshenin') . " followers";

Yup, quite simple isn’t it? Now call my_followers_count whenever you need to retrieve your followers count ;) Hope this will be of use to someone ;) Cheers!