<?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/"
	>

<channel>
	<title>numerodix blog &#187; wordpress</title>
	<atom:link href="http://www.matusiak.eu/numerodix/blog/index.php/category/techno-babble/wordpress/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.matusiak.eu/numerodix/blog</link>
	<description>A blog about nothing</description>
	<lastBuildDate>Sun, 12 Feb 2012 18:25:03 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.8.6</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<item>
		<title>git by example &#8211; upgrade wordpress like a ninja</title>
		<link>http://www.matusiak.eu/numerodix/blog/index.php/2008/09/21/git-by-example-keeping-wordpress-up-to-date/</link>
		<comments>http://www.matusiak.eu/numerodix/blog/index.php/2008/09/21/git-by-example-keeping-wordpress-up-to-date/#comments</comments>
		<pubDate>Sun, 21 Sep 2008 20:19:42 +0000</pubDate>
		<dc:creator>numerodix</dc:creator>
				<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://www.matusiak.eu/numerodix/blog/?p=1352</guid>
		<description><![CDATA[I addressed the issue of wordpress upgrades once before. That was a hacky home grown solution. For a while now I&#8217;ve been using git instead, which is the organized way of doing it. This method is not specific to wordpress, it works with any piece of code where you want to keep current with updates, [...]]]></description>
			<content:encoded><![CDATA[<p><img class="alignright size-full wp-image-1420" title="git_wordpress_ss" src="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/git_wordpress_ss.png" alt="" width="263" height="173" />I addressed the issue of wordpress upgrades <a href="http://www.matusiak.eu/numerodix/blog/index.php/2007/09/22/wordpress-update-script/">once before</a>. That was a hacky home grown solution. For a while now I&#8217;ve been using git instead, which is the organized way of doing it. <strong>This method is not specific to wordpress, it works with <em>any</em> piece of code where you want to keep current with updates, and yet you have some local modifications of your own.</strong></p>
<p>To recap the problem shortly.. you installed wordpress on your server. Then you made some changes to the code, maybe you changed the fonts in the theme, for instance. (In practice, you will have a lot more modifications if you&#8217;ve installed any plugins or uploaded files.) And now the wordpress people are saying there is an upgrade available, so you want to upgrade, but you want to keep your changes.</p>
<p>If you are handling this manually, you now have to track down all the changes you made, do the upgrade, and then go over the list and see if they all still apply, and if so re-apply them. git just says: <em>you&#8217;re using a computer, you git, I&#8217;ll do it for you</em>. In fact, with git you can keep track of what changes you have made and have access to them at any time. And that&#8217;s exactly what you want.</p>
<h3>1. Starting up (the first time)</h3>
<p>The first thing you should find out is which <a href="http://wordpress.org/download/release-archive/">version</a> of wordpress you&#8217;re running. In this demo I&#8217;m running 2.6. So what I&#8217;m going to do is create a git repository and start with the wordpress-2.6 codebase.</p>
<pre class="bash"><span style="color: #808080; font-style: italic;"># download and extract the currently installed version</span>
wget http://wordpress.org/wordpress<span style="color: #cc66cc;">-2</span>.<span style="color: #cc66cc;">6</span>.tar.gz
tar xzvf wordpress<span style="color: #cc66cc;">-2</span>.<span style="color: #cc66cc;">6</span>.tar.gz
<span style="color: #000066;">cd</span> wordpress
&nbsp;
<span style="color: #808080; font-style: italic;"># initiate git repository</span>
git-init
&nbsp;
<span style="color: #808080; font-style: italic;"># add all the wordpress files</span>
git-add .
&nbsp;
<span style="color: #808080; font-style: italic;"># check status of repository</span>
git-status
&nbsp;
<span style="color: #808080; font-style: italic;"># commit these files</span>
git-commit -m<span style="color: #ff0000;">'check in initial 2.6.0 upstream'</span>
&nbsp;
<span style="color: #808080; font-style: italic;"># see a graphical picture of your repository</span>
gitk --all</pre>
<p><i>Download this code: </i><a href="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/git_wordpress_init">git_wordpress_init</a></p>
<p>This is the typical way of initializing a repository, you run an init command to get an empty repo (you&#8217;ll notice a <code>.git/</code> directory was created). Then you add some files and check the status. git will tell you that you&#8217;ve added lots of files, which is correct. So you make a commit. Now you have one commit in the repo. You&#8217;ll want to use the gui program <code>gitk</code> to visualize the repo, I think you&#8217;ll find it&#8217;s extremely useful. This is what your repo looks like now:</p>
<p><img class="alignnone size-full wp-image-1361" title="git_wordpress_init_img" src="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/git_wordpress_init_img.png" alt="" width="441" height="21" /></p>
<p>gitk is saying that you have one commit, it&#8217;s showing the commit message, and it&#8217;s telling you that you&#8217;re on the <code>master</code> branch. This may seem odd seeing as how we didn&#8217;t create any branches, but <code>master</code> is the standard branch that every repository gets on init.</p>
<p>The plan is to keep the upstream wordpress code separate from your local changes, so you&#8217;ll only be using <code>master</code> to add new wordpress releases. For your own stuff, let&#8217;s create a new branch called <code>mine</code> (the names of branches don&#8217;t mean anything to git, you can call them anything you want).</p>
<pre class="bash"><span style="color: #808080; font-style: italic;"># create a branch where I'll keep my own changes</span>
git-branch mine
&nbsp;
<span style="color: #808080; font-style: italic;"># switch to mine branch</span>
git-checkout mine
&nbsp;
<span style="color: #808080; font-style: italic;"># see how the repository has changed</span>
gitk --all</pre>
<p><i>Download this code: </i><a href="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/git_wordpress_branch">git_wordpress_branch</a></p>
<p>When we now look at gitk the repository hasn&#8217;t changed dramatically (after all we haven&#8217;t made any new commits). But we now see that the single commit belongs to both branches <code>master</code> and <code>mine</code>. What&#8217;s more, <code>mine</code> is displayed in boldface, which means this is the branch we are on right now.</p>
<p><img class="alignnone size-full wp-image-1369" title="git_wordpress_branch_img" src="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/git_wordpress_branch_img.png" alt="" width="441" height="21" /></p>
<p>What this means is that we have two brances, but they currently have the exact same history.</p>
<h3>2. Making changes (on every edit)</h3>
<p>So now we have the repository all set up and we&#8217;re ready to make some edits to the code. Make sure you do this on the <code>mine</code> branch.</p>
<p>If you&#8217;re already running wordpress-2.6 with local modifications, now is the time to import your modified codebase. Just copy your <code>wordpress/</code> directory to the same location. This will obviously overwrite all the original files with yours, and it will add all the files that you have added (plugins, uploads etc). Don&#8217;t worry though, this is perfectly safe. git will figure out what&#8217;s what.</p>
<p>Importing your codebase into git only needs to be done the first time, after that you&#8217;ll just be making edits to the code.</p>
<pre class="bash"><span style="color: #808080; font-style: italic;"># switch to mine branch</span>
git-checkout mine
&nbsp;
<span style="color: #808080; font-style: italic;"># copy my own tree into the git repository mine branch</span>
<span style="color: #808080; font-style: italic;">#cp -ar mine/wordpress .. </span>
&nbsp;
<span style="color: #808080; font-style: italic;"># make changes to the code</span>
<span style="color: #808080; font-style: italic;">#vim wp-content/themes/default/style.css</span>
&nbsp;
<span style="color: #808080; font-style: italic;"># check status of repository</span>
git-status</pre>
<p><i>Download this code: </i><a href="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/git_wordpress_edit">git_wordpress_edit</a></p>
<p>When you check the status you&#8217;ll see that git has figured out which files have changed between the original wordpress version and your local one. git also shows the files that are in your version, but not in the original wordpress distribution as &#8220;untracked files&#8221;, ie. files that are lying around that you haven&#8217;t yet asked git to keep track of.</p>
<p>So let&#8217;s add these files and from now on every time something happens to them, git will tell you. And then commit these changes. You actually want to write a commit message that describes exactly the changes you made. That way, later on you can look at the repo history and see these messages and they will tell you something useful.</p>
<pre class="bash"><span style="color: #808080; font-style: italic;"># add all new files and changed files</span>
git-add .
&nbsp;
<span style="color: #808080; font-style: italic;"># check in my changes on mine branch</span>
git-commit -m<span style="color: #ff0000;">'check in my mods'</span>
&nbsp;
<span style="color: #808080; font-style: italic;"># see how the repository has changed</span>
gitk --all</pre>
<p><i>Download this code: </i><a href="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/git_wordpress_commit">git_wordpress_commit</a></p>
<p>When you look at the repo history with gitk, you&#8217;ll see a change. There is a new commit on the <code>mine</code> branch. Furthermore, <code>mine</code> and <code>master</code> no longer coincide. <code>mine</code> originates from (is based on) <code>master</code>, because the two dots are connected with a line.</p>
<p><img class="alignnone size-full wp-image-1381" title="git_wordpress_commit_img" src="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/git_wordpress_commit_img.png" alt="" width="441" height="34" /></p>
<p>What&#8217;s interesting here is that this commit history is exactly what we wanted. If we go back to <code>master</code>, we have the upstream version of wordpress untouched. Then we move to <code>mine</code>, and we get our local changes applied to upstream. Every time we make a change and commit, we&#8217;ll add another commit to <code>mine</code>, stacking all of these changes on top of <code>master</code>.</p>
<p>You can also use <code>git-log master..mine</code> to see the commit history, and <code>git-diff master..mine</code> to see the actual file edits between those two branches.</p>
<h3>3. Upgrading wordpress (on every upgrade)</h3>
<p>Now suppose you want to upgrade to wordpress-2.6.2. You have two branches, <code>mine</code> for local changes, and <code>master</code> for upstream releases. So let&#8217;s change to <code>master</code> and extract the files from upstream. Again you&#8217;re overwriting the tree, but by now you know that git will sort it out. <img src='http://www.matusiak.eu/numerodix/blog/wp-includes/images/smilies/wink.png' alt=';)' class='wp-smiley' /> </p>
<pre class="bash"><span style="color: #808080; font-style: italic;"># switch to the master branch</span>
git-checkout master
&nbsp;
<span style="color: #808080; font-style: italic;"># download and extract new wordpress version</span>
<span style="color: #000066;">cd</span> ..
wget http://wordpress.org/wordpress<span style="color: #cc66cc;">-2</span>.<span style="color: #cc66cc;">6</span>.<span style="color: #cc66cc;">2</span>.tar.gz
tar xzvf wordpress<span style="color: #cc66cc;">-2</span>.<span style="color: #cc66cc;">6</span>.<span style="color: #cc66cc;">2</span>.tar.gz
<span style="color: #000066;">cd</span> wordpress
&nbsp;
<span style="color: #808080; font-style: italic;"># check status</span>
git-status</pre>
<p><i>Download this code: </i><a href="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/git_wordpress_upgrade">git_wordpress_upgrade</a></p>
<p>Checking the status at this point is fairly important, because git has now figured out exactly what has changed in wordpress between 2.6 and 2.6.2, and here you get to see it. You should probably look through this list quite carefully and think about how it affects your local modifications. If a file is marked as changed and you want to see the actual changes you can use <code>git-diff &lt;filename&gt;</code>.</p>
<p>Now you add the changes and make a new commit on the <code>master</code> branch.</p>
<pre class="bash"><span style="color: #808080; font-style: italic;"># add all new files and changed files</span>
git-add .
&nbsp;
<span style="color: #808080; font-style: italic;"># commit new version</span>
git-commit -m<span style="color: #ff0000;">'check in 2.6.2 upstream'</span>
&nbsp;
<span style="color: #808080; font-style: italic;"># see how the repository has changed</span>
gitk --all</pre>
<p><i>Download this code: </i><a href="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/git_wordpress_commitnew">git_wordpress_commitnew</a></p>
<p>When you now look at the repo history there&#8217;s been an interesting development. As expected, the <code>master</code> branch has moved on one commit, but since this is a different commit than the one <code>mine</code> has, the branches have diverged. They have a common history, to be sure, but they are no longer on the same path.</p>
<p><img class="alignnone size-full wp-image-1395" title="git_wordpress_commitnew_img" src="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/git_wordpress_commitnew_img.png" alt="" width="441" height="45" /></p>
<p>Here you&#8217;ve hit the classical problem of a user who wants to modify code for his own needs. The code is moving in two different directions, one is upstream, the other is your own.</p>
<p>Now cheer up, git knows how to deal with this situation. It&#8217;s called &#8220;rebasing&#8221;. First we switch back to the <code>mine</code> branch. And now we use <code>git-rebase</code>, which takes all the commits in <code>mine</code> and stacks them on top of <code>master</code> again (ie. we base our commits on <code>master</code>).</p>
<pre class="bash"><span style="color: #808080; font-style: italic;"># check out mine branch</span>
git-checkout mine
&nbsp;
<span style="color: #808080; font-style: italic;"># stack my changes on top of master branch</span>
git-rebase master
&nbsp;
<span style="color: #808080; font-style: italic;"># see how the repository has changed</span>
gitk --all</pre>
<p><i>Download this code: </i><a href="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/git_wordpress_rebase">git_wordpress_rebase</a></p>
<p>Keep in mind that rebasing can fail. Suppose you made a change on line 4, and the wordpress upgrade also made a change on line 4. How is git supposed to know which of these to use? In such a case you&#8217;ll get a &#8220;conflict&#8221;. This means you have to edit the file yourself (git will show you where in the file the conflict is) and decide which change to apply. Once you&#8217;ve done that, <code>git-add</code> the file and then <code>git-rebase --continue</code> to keep going with the rebase.</p>
<p>Although conflicts happen, they are rare. All of your changes that don&#8217;t affect the changes in the upgrade will be applied automatically to wordpress-2.6.2, as if you were doing it yourself. You&#8217;ll only hit a conflict in a case where if you were doing this manually it would not be obvious how to apply your modification.</p>
<p>Once you&#8217;re done rebasing, your history will look like this. As you can see, all is well again, we&#8217;ve returned to the state that we had at the end of section 2. Once again, your changes are based on upstream. This is what a successful upgrade looks like, and you didn&#8217;t have to do it manually. <img src='http://www.matusiak.eu/numerodix/blog/wp-includes/images/smilies/cap.png' alt=':cap:' class='wp-smiley' /> </p>
<p><img class="alignnone size-full wp-image-1400" title="git_wordpress_rebase_img" src="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/git_wordpress_rebase_img.png" alt="" width="442" height="45" /></p>
<h3>Tips</h3>
<p><strong>Don&#8217;t be afraid to screw up</strong></p>
<p>You will, lots of times. The way that git works, every working directory is a full copy of the repository. So if you&#8217;re worried that you might screw up something, just make a copy of it before you start (you can do this at any stage in the process), and then you can revert to that if something goes wrong. git itself has a lot of ways to undo mistakes, and once you learn more about it you&#8217;ll start using those methods instead.</p>
<p><strong>Upgrade offline</strong></p>
<p>If you are using git to upgrade wordpress on your web server, make a copy of the repo before you start, then do the upgrade on that copy. When you&#8217;re done, replace the live directory with the upgraded one. You don&#8217;t want your users to access the directory while you&#8217;re doing the upgrade, both because it will look broken to them, and because errors can occur if you try to write to the database in this inconsistent state.</p>
<p><strong>Keep your commits small and topical</strong></p>
<p>You will probably be spending most of your time in stage 2 &#8211; making edits. It&#8217;s good practice to make a new commit for every topical change you make. So if your goal is to &#8220;make all links blue&#8221; then you should make all the changes related to that goal, and then commit. By working this way, you can review your repo history and be able to see what you tried to accomplish and what you changed on each little goal.</p>
<p><strong>Revision control is about working habits</strong></p>
<p>You&#8217;ve only seen a small, albeit useful, slice of git in this tutorial. git is a big and complicated program, but as with many other things, it already pays off if you know a little about it, it allows you to be more efficient. So don&#8217;t worry about not knowing the rest, it will come one step at a time. And above all, git is all about the way you work, which means you won&#8217;t completely change your working habits overnight, it will have to be gradual.</p>
<p>This tutorial alone should show you that it&#8217;s entirely possible to keep local changes and still upgrade frequently without a lot of effort or risk. I used to dread upgrades, thinking it would be a lot of work and my code would break. I don&#8217;t anymore.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.matusiak.eu/numerodix/blog/index.php/2008/09/21/git-by-example-keeping-wordpress-up-to-date/feed/</wfw:commentRss>
		<slash:comments>6</slash:comments>
		</item>
		<item>
		<title>the unhappy reality of upgrades</title>
		<link>http://www.matusiak.eu/numerodix/blog/index.php/2007/09/25/the-unhappy-reality-of-upgrades/</link>
		<comments>http://www.matusiak.eu/numerodix/blog/index.php/2007/09/25/the-unhappy-reality-of-upgrades/#comments</comments>
		<pubDate>Tue, 25 Sep 2007 21:22:23 +0000</pubDate>
		<dc:creator>numerodix</dc:creator>
				<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://www.matusiak.eu/numerodix/blog/index.php/2007/09/25/the-unhappy-reality-of-upgrades/</guid>
		<description><![CDATA[It struck me today that as coders we do what we can to wrap our nasty, complicated code in a neat package that the user will love. They don&#8217;t realize, and we don&#8217;t want them to know, just how convoluted and messy the stuff is on the inside. And this holds up for long periods [...]]]></description>
			<content:encoded><![CDATA[<p>It struck me today that as coders we do what we can to wrap our nasty, complicated code in a neat package that the user will love. They don&#8217;t realize, and we don&#8217;t want them to know, just how convoluted and messy the stuff is on the inside. And this holds up for long periods of time. But there comes a time when our neat little illusion cracks up and the ugliness comes into view. Bugs expose it sometimes, but upgrades do this with <a href="http://www.matusiak.eu/numerodix/blog/index.php/2007/02/01/upgrading-ubuntu-the-horror/">immaculate</a> <a href="http://www.matusiak.eu/numerodix/blog/index.php/2007/08/12/bugs-are-better-when-fun/">regularity</a>.</p>
<p>Why today? Because <a href="http://wordpress.org/development/2007/09/wordpress-23/">Wordpress 2.3</a> was dropped today. The Wordpress people decided to toss out categories in favor of a wonderfully engineered (isn&#8217;t that what we always believe?) taxonomy system. With the immediate consequence that any code that has anything to do with categories would break. That&#8217;s two of my plugins. Clearly these guys are not Windows users. Microsoft&#8217;s Patch and Play strategy with Windows has kept *a lot* of companies happy, as they continually strive to emulate their old bugs to accommodate programs that were written to cope with them. This has seriously handicapped Windows from making progress, because they keep pulling that huge sack of legacy code going back to probably Win3.1 (with Workgroups, yay!).</p>
<p>Posts used to be related to Categories with an in-between table, the classic N:M relational idiom. Now there are 4 tables, all related to each other in interesting ways. It took me quite a while to crack this code. This was introduced to add tagging support, which is quite the annoyance, because I have no interest in tagging. I find it a useless errand. And, of course, for those not tagging from the beginning you always come back to having to post-tag 600 old posts. Forget it.</p>
<p><a href="http://www.matusiak.eu/numerodix/blog/index.php/2007/09/22/wordpress-update-script/">Tools</a> always help a lot, but it&#8217;s very difficult to capture all the nuances, and in many cases human review is necessary anyway (particularly when themes change). And this is the sad reality of it. While minor upgrades are now handled routinely, bigger changes will always cause problems.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.matusiak.eu/numerodix/blog/index.php/2007/09/25/the-unhappy-reality-of-upgrades/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>wordpress update script</title>
		<link>http://www.matusiak.eu/numerodix/blog/index.php/2007/09/22/wordpress-update-script/</link>
		<comments>http://www.matusiak.eu/numerodix/blog/index.php/2007/09/22/wordpress-update-script/#comments</comments>
		<pubDate>Sat, 22 Sep 2007 12:39:55 +0000</pubDate>
		<dc:creator>numerodix</dc:creator>
				<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://www.matusiak.eu/numerodix/blog/index.php/2007/09/22/wordpress-update-script/</guid>
		<description><![CDATA[Aah, the free world. It&#8217;s beautiful, you have frequent releases, the code is there for you, everything&#8217;s wondeful. But for web apps like Wordpress the maintenance cycle is less convenient than with desktop applications. There&#8217;s no package manager to handle updates for you. Yes, that&#8217;s the downside.
I&#8217;ve upgraded Wordpress now 3-4 times and I&#8217;m already [...]]]></description>
			<content:encoded><![CDATA[<p>Aah, the free world. It&#8217;s beautiful, you have frequent releases, the code is there for you, everything&#8217;s wondeful. But for web apps like Wordpress the maintenance cycle is less convenient than with desktop applications. There&#8217;s no package manager to handle updates for you. Yes, that&#8217;s the downside.</p>
<p>I&#8217;ve upgraded Wordpress now 3-4 times and I&#8217;m already sick of it. It&#8217;s so mechanical. I&#8217;ve also rehearsed the cycle a bunch of times with vBulletin. Well, compared to the tidy and elegant Wordpress, vBulletin is a monster. But the upgrade issues are the same, albeit less painful now. I should have done this years ago, but now at least I have an organized way of handling these upgrades.</p>
<p>Here&#8217;s the rationale. You download some Wordpress version from <a href="http://wordpress.org/">wordpress.org</a> and install it. This we call the <strong>ref</strong>erence version. Then you hack on it a bit. You install plugins, maybe you hack the source a little. You change the theme a bit. And in the course of using Wordpress you also upload files with posts sometimes, for instance to include pictures with your posts.</p>
<p style="text-align: center"><img src="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/wordpress_upgrade.png" alt="wordpress_upgrade.png" align="right" /></p>
<p>So now the state of your Wordpress tree has changed a bit, you&#8217;ve added some files, maybe you&#8217;ve changed some files. Basically, it&#8217;s different from the vanilla version. This we call <strong>mine</strong>. And now you&#8217;ve decided that the next Wordpress version has some nice features and bug fixes you want. This version we call <strong>latest</strong>.</p>
<p>You want to upgrade, but there is no upgrade path from <strong>mine</strong> to <strong>latest</strong>, because the Wordpress people can&#8217;t know what you did with your local version. Upgrading from <strong>mine</strong> to <strong>latest</strong> may not be safe, it hasn&#8217;t been tried.</p>
<p><img src="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/wordpress_upgrade2.png" alt="wordpress_upgrade2.png" align="right" />Of course, this sort of problem is nothing new. Coders have faced it forever. And that&#8217;s why we have things like <code>diff</code> and <code>patch</code>, standard Unix tools. So here&#8217;s how to upgrade safely.</p>
<ul>
<li>First roll back the local changes so that we return to the <strong>ref</strong>erence version.</li>
<li>Save the local modifications.</li>
<li>Do a standard Wordpress upgrade going from <strong>ref</strong> to <strong>latest</strong>.</li>
<li>Re-apply, if possible, the local modifications.</li>
</ul>
<p>And this replicates exactly what you would do manually if you wanted to be sure that the upgrade doesn&#8217;t break anything. Just that it&#8217;s a lot of hassle to do by hand. The upgrade is done offsite, so your blog continues to run in the meantime. And once you&#8217;ve upgraded, you can just move it into the right location.</p>
<p>In the event that merging <strong>diff</strong> and <strong>latest</strong> does not succeed, you have a list of the patches and files so that you know exactly which ones didn&#8217;t succeed.</p>
<p>So far I&#8217;ve used it to do two updates, 2.2.1-&gt;2.2.2, 2.2.2-&gt;2.2.3, without any hiccups.</p>
<pre class="bash"><span style="color: #808080; font-style: italic;">#!/bin/bash</span>
&nbsp;
<span style="color: #808080; font-style: italic;"># &gt;&gt; 0.3</span>
<span style="color: #808080; font-style: italic;"># added file/dir permission tracking</span>
<span style="color: #808080; font-style: italic;"># added hint for failed file merges</span>
<span style="color: #808080; font-style: italic;"># added hint for failed patches</span>
&nbsp;
echo&lt;&lt;header <span style="color: #ff0000;">"
################################################################################
#                                                                              #
#                      Wordpress Updater / version 0.3                         #
#                   Martin Matusiak ~ numerodix@gmail.com                      #
#                                                                              #
#  Description: A script to automate [part of] the Wordpress update cycle, by  #
#  finding my modifications to the codebase (mine), diffing them against the   #
#  official codebase (ref), and migrating files and patches to the latest      #
#  version (latest).                                                           #
#                                                                              #
#  Warning: Upgrading to a new version will probably not always work           #
#  seamlessly, depending on what changes have occurred. Do not use this as a   #
#  substitute for following the official upgrade instructions. Furthermore, if #
#  you don't understand what this script does, you probably shouldn't use it.  #
#  Also, it's always a good idea to backup your files before you begin.        #
#                                                                              #
#  Licensed under the GNU Public License, version 3.                           #
#                                                                              #
################################################################################
"</span>
header
&nbsp;
<span style="color: #808080; font-style: italic;">### &lt;Configutation&gt;</span>
&nbsp;
<span style="color: #0000ff;">wpmine=</span><span style="color: #ff0000;">"/home/user/www/numerodix/blog"</span>
<span style="color: #0000ff;">version_file=</span><span style="color: #ff0000;">"${wpmine}/wp-includes/version.php"</span>
<span style="color: #0000ff;">wordpress_baseurl=</span><span style="color: #ff0000;">"http://wordpress.org"</span>
<span style="color: #0000ff;">temp_path=</span><span style="color: #ff0000;">"/home/user/t"</span>
&nbsp;
<span style="color: #808080; font-style: italic;">### &lt;/Configuration&gt;</span>
&nbsp;
&nbsp;
<span style="color: #000066;">echo</span> -e <span style="color: #ff0000;">"Pausing 10 seconds... (Ctrl+C to abort)<span style="color: #000099; font-weight: bold;">\\0</span>07"</span>
sleep <span style="color: #cc66cc;">10</span>
&nbsp;
&nbsp;
msg<span style="color: #66cc66;">&#40;</span><span style="color: #66cc66;">&#41;</span> <span style="color: #66cc66;">&#123;</span>
<span style="color: #0000ff;">fill=</span>$<span style="color: #66cc66;">&#40;</span><span style="color: #b1b100;">for</span> i <span style="color: #b1b100;">in</span> $<span style="color: #66cc66;">&#40;</span>seq <span style="color: #cc66cc;">1</span> $<span style="color: #66cc66;">&#40;</span><span style="color: #66cc66;">&#40;</span><span style="color: #cc66cc;">76</span> - $<span style="color: #66cc66;">&#123;</span><span style="color: #808080; font-style: italic;">#1}))); do echo -n &quot; &quot;; done)</span>
echo&lt;&lt;msg <span style="color: #ff0000;">"
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
+  ${1}${fill}+
++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
"</span>
msg
<span style="color: #66cc66;">&#125;</span>
&nbsp;
&nbsp;
<span style="color: #b1b100;">if</span> ! mkdir -p <span style="color: #0000ff;">$temp_path</span>; <span style="color: #b1b100;">then</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"$temp_path not created"</span>; <span style="color: #000066;">exit</span> <span style="color: #cc66cc;">1</span>
<span style="color: #b1b100;">fi</span>
&nbsp;
msg <span style="color: #ff0000;">"Checking installed version... "</span>
<span style="color: #b1b100;">if</span> <span style="color: #66cc66;">&#91;</span> -f <span style="color: #0000ff;">$version_file</span> <span style="color: #66cc66;">&#93;</span>; <span style="color: #b1b100;">then</span>
	<span style="color: #0000ff;">ref=</span>$<span style="color: #66cc66;">&#40;</span>cat <span style="color: #0000ff;">$version_file</span> | grep <span style="color: #ff0000;">"<span style="color: #000099; font-weight: bold;">\\$</span>wp_version"</span> | tr -d <span style="color: #ff0000;">" _$'';=[:alpha:]"</span><span style="color: #66cc66;">&#41;</span>
	<span style="color: #000066;">echo</span> <span style="color: #0000ff;">$ref</span>
<span style="color: #b1b100;">else</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"$version_file not found"</span>; <span style="color: #000066;">exit</span> <span style="color: #cc66cc;">1</span>
<span style="color: #b1b100;">fi</span>
&nbsp;
&nbsp;
msg <span style="color: #ff0000;">"Fetching version $ref... "</span>
<span style="color: #66cc66;">&#91;</span> -f <span style="color: #0000ff;">$temp_path</span>/wordpress-<span style="color: #0000ff;">$ref</span>.tar.gz <span style="color: #66cc66;">&#93;</span> &amp;&amp; rm <span style="color: #0000ff;">$temp_path</span>/wordpress-<span style="color: #0000ff;">$ref</span>.tar.gz
<span style="color: #b1b100;">if</span> wget -q -P <span style="color: #0000ff;">$temp_path</span> <span style="color: #0000ff;">$wordpress_baseurl</span>/wordpress-<span style="color: #0000ff;">$ref</span>.tar.gz; <span style="color: #b1b100;">then</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"downloaded to $temp_path"</span>
<span style="color: #b1b100;">else</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"could not fetch $wordpress_baseurl/wordpress-$ref.tar.gz"</span>; <span style="color: #000066;">exit</span> <span style="color: #cc66cc;">1</span>
<span style="color: #b1b100;">fi</span>
&nbsp;
&nbsp;
msg <span style="color: #ff0000;">"Unpacking reference version $ref... "</span>
<span style="color: #66cc66;">&#91;</span> -d <span style="color: #0000ff;">$temp_path</span>/wordpress-<span style="color: #0000ff;">$ref</span> <span style="color: #66cc66;">&#93;</span> &amp;&amp; rm -rf <span style="color: #0000ff;">$temp_path</span>/wordpress-<span style="color: #0000ff;">$ref</span>
<span style="color: #b1b100;">if</span> <span style="color: #66cc66;">&#40;</span><span style="color: #000066;">cd</span> <span style="color: #0000ff;">$temp_path</span> &amp;&amp; tar zxf wordpress-<span style="color: #0000ff;">$ref</span>.tar.gz &amp;&amp; mv wordpress wordpress-<span style="color: #0000ff;">$ref</span><span style="color: #66cc66;">&#41;</span>; <span style="color: #b1b100;">then</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"unpacked to $temp_path/wordpress-$ref"</span>
<span style="color: #b1b100;">else</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"failed"</span>; <span style="color: #000066;">exit</span> <span style="color: #cc66cc;">1</span>
<span style="color: #b1b100;">fi</span>
&nbsp;
<span style="color: #0000ff;">wpref=</span><span style="color: #ff0000;">"$temp_path/wordpress-$ref"</span>
&nbsp;
&nbsp;
msg <span style="color: #ff0000;">"Diffing codebase... "</span>
<span style="color: #66cc66;">&#40;</span> <span style="color: #000066;">cd</span> <span style="color: #0000ff;">$wpref</span> &amp;&amp; find . -<span style="color: #000066;">type</span> f | sed <span style="color: #ff0000;">"s|<span style="color: #000099; font-weight: bold;">\\.</span>/||g"</span> | sort &gt; <span style="color: #0000ff;">$temp_path</span>/files-<span style="color: #0000ff;">$ref</span>-ref <span style="color: #66cc66;">&#41;</span> &amp;&amp;
<span style="color: #66cc66;">&#40;</span> <span style="color: #000066;">cd</span> <span style="color: #0000ff;">$wpmine</span> &amp;&amp; find . -<span style="color: #000066;">type</span> f | sed <span style="color: #ff0000;">"s|<span style="color: #000099; font-weight: bold;">\\.</span>/||g"</span> | sort &gt; <span style="color: #0000ff;">$temp_path</span>/files-<span style="color: #0000ff;">$ref</span>-mine <span style="color: #66cc66;">&#41;</span> &amp;&amp;
diff <span style="color: #0000ff;">$temp_path</span>/files-<span style="color: #0000ff;">$ref</span>-ref <span style="color: #0000ff;">$temp_path</span>/files-<span style="color: #0000ff;">$ref</span>-mine &gt; <span style="color: #0000ff;">$temp_path</span>/diff
<span style="color: #b1b100;">if</span> <span style="color: #66cc66;">&#91;</span><span style="color: #66cc66;">&#91;</span> $? &lt; <span style="color: #cc66cc;">2</span> <span style="color: #66cc66;">&#93;</span><span style="color: #66cc66;">&#93;</span>; <span style="color: #b1b100;">then</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"diff written to $temp_path/diff"</span>
<span style="color: #b1b100;">else</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"failed"</span>; <span style="color: #000066;">exit</span> <span style="color: #cc66cc;">1</span>
<span style="color: #b1b100;">fi</span>
&nbsp;
&nbsp;
msg <span style="color: #ff0000;">"Recording my file/dir permissions..."</span>
<span style="color: #000066;">cd</span> <span style="color: #0000ff;">$wpmine</span> &amp;&amp; \\
find . -<span style="color: #000066;">exec</span> ls -ld --time-<span style="color: #0000ff;">style=</span>+%s <span style="color: #66cc66;">&#123;</span><span style="color: #66cc66;">&#125;</span> \\; | sed <span style="color: #ff0000;">"s|<span style="color: #000099; font-weight: bold;">\\.</span>/||g"</span> | sort -k <span style="color: #cc66cc;">7</span> \\
&gt; <span style="color: #0000ff;">$temp_path</span>/files-<span style="color: #0000ff;">$ref</span>-mine.perms
<span style="color: #b1b100;">if</span> <span style="color: #66cc66;">&#91;</span><span style="color: #66cc66;">&#91;</span> $? == <span style="color: #cc66cc;">0</span> <span style="color: #66cc66;">&#93;</span><span style="color: #66cc66;">&#93;</span>; <span style="color: #b1b100;">then</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"written to $temp_path/files-$ref-mine.perms"</span>
<span style="color: #b1b100;">else</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"failed"</span>; <span style="color: #000066;">exit</span> <span style="color: #cc66cc;">1</span>
<span style="color: #b1b100;">fi</span>
&nbsp;
&nbsp;
msg <span style="color: #ff0000;">"Listing files added/removed... "</span>
<span style="color: #66cc66;">&#40;</span> cat <span style="color: #0000ff;">$temp_path</span>/diff | grep <span style="color: #ff0000;">"^&gt;"</span> | awk <span style="color: #ff0000;">'{ print $2 }'</span> &gt; <span style="color: #0000ff;">$temp_path</span>/only_mine <span style="color: #66cc66;">&#41;</span> &amp;&amp;
<span style="color: #66cc66;">&#40;</span> cat <span style="color: #0000ff;">$temp_path</span>/diff | grep <span style="color: #ff0000;">"^&lt;"</span> | awk <span style="color: #ff0000;">'{ print $2 }'</span> &gt; <span style="color: #0000ff;">$temp_path</span>/only_ref <span style="color: #66cc66;">&#41;</span> &amp;&amp;
<span style="color: #66cc66;">&#40;</span> cat <span style="color: #0000ff;">$temp_path</span>/only_mine &gt; <span style="color: #0000ff;">$temp_path</span>/not_common <span style="color: #66cc66;">&#41;</span> &amp;&amp;
<span style="color: #66cc66;">&#40;</span> cat <span style="color: #0000ff;">$temp_path</span>/only_ref &gt;&gt; <span style="color: #0000ff;">$temp_path</span>/not_common <span style="color: #66cc66;">&#41;</span>
<span style="color: #b1b100;">if</span> <span style="color: #66cc66;">&#91;</span><span style="color: #66cc66;">&#91;</span> $? == <span style="color: #cc66cc;">0</span> <span style="color: #66cc66;">&#93;</span><span style="color: #66cc66;">&#93;</span>; <span style="color: #b1b100;">then</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"mine only files written to $temp_path/only_mine"</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"ref only files written to $temp_path/only_ref"</span>
<span style="color: #b1b100;">else</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"failed"</span>; <span style="color: #000066;">exit</span> <span style="color: #cc66cc;">1</span>
<span style="color: #b1b100;">fi</span>
&nbsp;
&nbsp;
msg <span style="color: #ff0000;">"Listing files changed... "</span>
<span style="color: #66cc66;">&#91;</span> -f <span style="color: #0000ff;">$temp_path</span>/changed <span style="color: #66cc66;">&#93;</span> &amp;&amp; rm <span style="color: #0000ff;">$temp_path</span>/changed &amp;&amp; touch <span style="color: #0000ff;">$temp_path</span>/changed
<span style="color: #b1b100;">for</span> i <span style="color: #b1b100;">in</span> $<span style="color: #66cc66;">&#40;</span>cat <span style="color: #0000ff;">$temp_path</span>/files-<span style="color: #0000ff;">$ref</span>-ref<span style="color: #66cc66;">&#41;</span>; <span style="color: #b1b100;">do</span>
	<span style="color: #b1b100;">if</span> ! grep -x <span style="color: #0000ff;">$i</span> <span style="color: #0000ff;">$temp_path</span>/not_common &gt;/dev/null; <span style="color: #b1b100;">then</span>
		<span style="color: #b1b100;">if</span> ! diff -q <span style="color: #0000ff;">$temp_path</span>/wordpress-<span style="color: #0000ff;">$ref</span>/<span style="color: #0000ff;">$i</span> <span style="color: #0000ff;">$wpmine</span>/<span style="color: #0000ff;">$i</span> &gt;/dev/null; <span style="color: #b1b100;">then</span>
			<span style="color: #000066;">echo</span> <span style="color: #0000ff;">$i</span> &gt;&gt; <span style="color: #0000ff;">$temp_path</span>/changed
		<span style="color: #b1b100;">fi</span>
	<span style="color: #b1b100;">fi</span>
<span style="color: #b1b100;">done</span>
<span style="color: #b1b100;">if</span> <span style="color: #66cc66;">&#91;</span><span style="color: #66cc66;">&#91;</span> $<span style="color: #66cc66;">&#40;</span>wc -l &lt; <span style="color: #0000ff;">$temp_path</span>/changed<span style="color: #66cc66;">&#41;</span> == <span style="color: #ff0000;">"0"</span> <span style="color: #66cc66;">&#93;</span><span style="color: #66cc66;">&#93;</span>; <span style="color: #b1b100;">then</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"No changes detected"</span>
<span style="color: #b1b100;">else</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"Files changed written to $temp_path/changed"</span>
<span style="color: #b1b100;">fi</span>
&nbsp;
&nbsp;
msg <span style="color: #ff0000;">"Writing individual diffs... "</span>
<span style="color: #66cc66;">&#91;</span> -d <span style="color: #0000ff;">$temp_path</span>/diffs <span style="color: #66cc66;">&#93;</span> &amp;&amp; rm -rf <span style="color: #0000ff;">$temp_path</span>/diffs
mkdir -p <span style="color: #0000ff;">$temp_path</span>/diffs
<span style="color: #b1b100;">for</span> i <span style="color: #b1b100;">in</span> $<span style="color: #66cc66;">&#40;</span>cat <span style="color: #0000ff;">$temp_path</span>/changed<span style="color: #66cc66;">&#41;</span>; <span style="color: #b1b100;">do</span>
	<span style="color: #0000ff;">e=</span>$<span style="color: #66cc66;">&#40;</span> <span style="color: #000066;">echo</span> <span style="color: #0000ff;">$i</span> | sed <span style="color: #ff0000;">"s|<span style="color: #000099; font-weight: bold;">\\.</span>/||g"</span> | tr <span style="color: #ff0000;">"/"</span> <span style="color: #ff0000;">"."</span> <span style="color: #66cc66;">&#41;</span>
	diff -u <span style="color: #0000ff;">$temp_path</span>/wordpress-<span style="color: #0000ff;">$ref</span>/<span style="color: #0000ff;">$i</span> <span style="color: #0000ff;">$wpmine</span>/<span style="color: #0000ff;">$i</span> &gt; <span style="color: #0000ff;">$temp_path</span>/diffs/<span style="color: #0000ff;">$e</span>
<span style="color: #b1b100;">done</span>
<span style="color: #0000ff;">ds=</span>$<span style="color: #66cc66;">&#40;</span>ls <span style="color: #0000ff;">$temp_path</span>/diffs | wc -l<span style="color: #66cc66;">&#41;</span>
<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"$ds diffs in $temp_path/diffs"</span>
&nbsp;
&nbsp;
msg <span style="color: #ff0000;">"Fetching latest version... "</span>
<span style="color: #66cc66;">&#91;</span> -f <span style="color: #0000ff;">$temp_path</span>/latest.tar.gz <span style="color: #66cc66;">&#93;</span> &amp;&amp; rm <span style="color: #0000ff;">$temp_path</span>/latest.tar.gz
<span style="color: #b1b100;">if</span> wget -q -P <span style="color: #0000ff;">$temp_path</span> <span style="color: #0000ff;">$wordpress_baseurl</span>/latest.tar.gz; <span style="color: #b1b100;">then</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"downloaded to $temp_path"</span>
<span style="color: #b1b100;">else</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"could not fetch $wordpress_baseurl/latest.tar.gz"</span>; <span style="color: #000066;">exit</span> <span style="color: #cc66cc;">1</span>
<span style="color: #b1b100;">fi</span>
&nbsp;
&nbsp;
msg <span style="color: #ff0000;">"Unpacking latest version... "</span>
<span style="color: #66cc66;">&#91;</span> -d <span style="color: #0000ff;">$temp_path</span>/wordpress-latest <span style="color: #66cc66;">&#93;</span> &amp;&amp; rm -rf <span style="color: #0000ff;">$temp_path</span>/wordpress-latest
<span style="color: #b1b100;">if</span> <span style="color: #66cc66;">&#40;</span><span style="color: #000066;">cd</span> <span style="color: #0000ff;">$temp_path</span> &amp;&amp; tar zxf latest.tar.gz &amp;&amp; mv wordpress wordpress-latest<span style="color: #66cc66;">&#41;</span>; <span style="color: #b1b100;">then</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"unpacked to $temp_path/wordpress-latest"</span>
<span style="color: #b1b100;">else</span>
	<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"failed"</span>; <span style="color: #000066;">exit</span> <span style="color: #cc66cc;">1</span>
<span style="color: #b1b100;">fi</span>
&nbsp;
<span style="color: #0000ff;">wplatest=</span><span style="color: #ff0000;">"$temp_path/wordpress-latest"</span>
&nbsp;
&nbsp;
msg <span style="color: #ff0000;">"Trying to patch diffs... "</span>
<span style="color: #0000ff;">post=</span>$<span style="color: #66cc66;">&#40;</span><span style="color: #000066;">echo</span> <span style="color: #0000ff;">$wpmine</span> | tr -d <span style="color: #ff0000;">"/"</span><span style="color: #66cc66;">&#41;</span>
<span style="color: #0000ff;">patch_level=</span>$<span style="color: #66cc66;">&#40;</span><span style="color: #66cc66;">&#40;</span> $<span style="color: #66cc66;">&#123;</span><span style="color: #808080; font-style: italic;">#wpmine} - ${#post} ))</span>
<span style="color: #66cc66;">&#91;</span> -f <span style="color: #0000ff;">$temp_path</span>/patches.failed <span style="color: #66cc66;">&#93;</span> &amp;&amp; rm <span style="color: #0000ff;">$temp_path</span>/patches.failed
<span style="color: #b1b100;">for</span> i <span style="color: #b1b100;">in</span> $<span style="color: #66cc66;">&#40;</span>ls <span style="color: #0000ff;">$temp_path</span>/diffs<span style="color: #66cc66;">&#41;</span>; <span style="color: #b1b100;">do</span>
	<span style="color: #000066;">cd</span> <span style="color: #0000ff;">$wplatest</span> &amp;&amp; patch -p<span style="color: #0000ff;">$patch_level</span> &lt; <span style="color: #0000ff;">$temp_path</span>/diffs/<span style="color: #0000ff;">$i</span>
	<span style="color: #b1b100;">if</span> <span style="color: #66cc66;">&#91;</span><span style="color: #66cc66;">&#91;</span> $? != <span style="color: #cc66cc;">0</span> <span style="color: #66cc66;">&#93;</span><span style="color: #66cc66;">&#93;</span>; <span style="color: #b1b100;">then</span>
		<span style="color: #000066;">echo</span> <span style="color: #0000ff;">$temp_path</span>/diffs/<span style="color: #0000ff;">$i</span> &gt;&gt; <span style="color: #0000ff;">$temp_path</span>/patches.failed
	<span style="color: #b1b100;">fi</span>
<span style="color: #b1b100;">done</span>
&nbsp;
&nbsp;
msg <span style="color: #ff0000;">"Merging in my files... "</span>
<span style="color: #66cc66;">&#91;</span> -f <span style="color: #0000ff;">$temp_path</span>/file-merge.failed <span style="color: #66cc66;">&#93;</span> &amp;&amp; rm <span style="color: #0000ff;">$temp_path</span>/file-merge.failed
<span style="color: #b1b100;">for</span> i <span style="color: #b1b100;">in</span> $<span style="color: #66cc66;">&#40;</span>cat <span style="color: #0000ff;">$temp_path</span>/only_mine<span style="color: #66cc66;">&#41;</span>; <span style="color: #b1b100;">do</span>
	<span style="color: #0000ff;">d=</span>$<span style="color: #66cc66;">&#40;</span>dirname	<span style="color: #0000ff;">$wplatest</span>/<span style="color: #0000ff;">$i</span><span style="color: #66cc66;">&#41;</span>
	mkdir -p <span style="color: #0000ff;">$d</span>
	<span style="color: #b1b100;">if</span> <span style="color: #66cc66;">&#91;</span> -e <span style="color: #0000ff;">$wplatest</span>/<span style="color: #0000ff;">$i</span> <span style="color: #66cc66;">&#93;</span>; <span style="color: #b1b100;">then</span>
		<span style="color: #66cc66;">&#40;</span> <span style="color: #000066;">echo</span> <span style="color: #ff0000;">"file already exists: $i"</span>;
		<span style="color: #000066;">echo</span> <span style="color: #0000ff;">$i</span> &gt;&gt; <span style="color: #0000ff;">$temp_path</span>/file-merge.failed <span style="color: #66cc66;">&#41;</span>
	<span style="color: #b1b100;">else</span>
		<span style="color: #66cc66;">&#40;</span> <span style="color: #000066;">echo</span> <span style="color: #ff0000;">"merging: $i"</span> &amp;&amp; cp -a <span style="color: #0000ff;">$wpmine</span>/<span style="color: #0000ff;">$i</span> <span style="color: #0000ff;">$wplatest</span>/<span style="color: #0000ff;">$i</span> <span style="color: #66cc66;">&#41;</span>
	<span style="color: #b1b100;">fi</span>
<span style="color: #b1b100;">done</span>
&nbsp;
&nbsp;
msg <span style="color: #ff0000;">"Merging file/dir permissions..."</span>
<span style="color: #b1b100;">while</span> <span style="color: #000066;">read</span> line; <span style="color: #b1b100;">do</span>
	<span style="color: #0000ff;">f=</span>$<span style="color: #66cc66;">&#40;</span><span style="color: #000066;">echo</span> <span style="color: #0000ff;">$line</span> | awk <span style="color: #ff0000;">'{ print $7 }'</span><span style="color: #66cc66;">&#41;</span>
	<span style="color: #0000ff;">p=</span>$<span style="color: #66cc66;">&#40;</span><span style="color: #000066;">echo</span> <span style="color: #0000ff;">$line</span> | awk <span style="color: #ff0000;">'{ print $1 }'</span><span style="color: #66cc66;">&#41;</span>; <span style="color: #0000ff;">p=</span>$<span style="color: #66cc66;">&#123;</span>p:<span style="color: #cc66cc;">1</span>:<span style="color: #cc66cc;">9</span><span style="color: #66cc66;">&#125;</span>
	<span style="color: #0000ff;">u=</span>$<span style="color: #66cc66;">&#40;</span><span style="color: #000066;">echo</span> $<span style="color: #66cc66;">&#123;</span>p:<span style="color: #cc66cc;">0</span>:<span style="color: #cc66cc;">3</span><span style="color: #66cc66;">&#125;</span> | tr -d <span style="color: #ff0000;">'-'</span><span style="color: #66cc66;">&#41;</span>
	<span style="color: #0000ff;">g=</span>$<span style="color: #66cc66;">&#40;</span><span style="color: #000066;">echo</span> $<span style="color: #66cc66;">&#123;</span>p:<span style="color: #cc66cc;">3</span>:<span style="color: #cc66cc;">3</span><span style="color: #66cc66;">&#125;</span> | tr -d <span style="color: #ff0000;">'-'</span><span style="color: #66cc66;">&#41;</span>
	<span style="color: #0000ff;">o=</span>$<span style="color: #66cc66;">&#40;</span><span style="color: #000066;">echo</span> $<span style="color: #66cc66;">&#123;</span>p:<span style="color: #cc66cc;">6</span>:<span style="color: #cc66cc;">3</span><span style="color: #66cc66;">&#125;</span> | tr -d <span style="color: #ff0000;">'-'</span><span style="color: #66cc66;">&#41;</span>
	<span style="color: #b1b100;">if</span> <span style="color: #66cc66;">&#91;</span> -e <span style="color: #0000ff;">$wplatest</span>/<span style="color: #0000ff;">$f</span> <span style="color: #66cc66;">&#93;</span>; <span style="color: #b1b100;">then</span>
		<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"setting: $p $f"</span>
		chmod <span style="color: #0000ff;">u=</span><span style="color: #0000ff;">$u</span> <span style="color: #0000ff;">$wplatest</span>/<span style="color: #0000ff;">$f</span>
		chmod <span style="color: #0000ff;">g=</span><span style="color: #0000ff;">$g</span> <span style="color: #0000ff;">$wplatest</span>/<span style="color: #0000ff;">$f</span>
		chmod <span style="color: #0000ff;">o=</span><span style="color: #0000ff;">$o</span> <span style="color: #0000ff;">$wplatest</span>/<span style="color: #0000ff;">$f</span>
	<span style="color: #b1b100;">fi</span>
<span style="color: #b1b100;">done</span> &lt; <span style="color: #0000ff;">$temp_path</span>/files-<span style="color: #0000ff;">$ref</span>-mine.perms
&nbsp;
&nbsp;
msg <span style="color: #ff0000;">"Removing files I deleted... "</span>
<span style="color: #b1b100;">for</span> i <span style="color: #b1b100;">in</span> $<span style="color: #66cc66;">&#40;</span>cat <span style="color: #0000ff;">$temp_path</span>/only_ref<span style="color: #66cc66;">&#41;</span>; <span style="color: #b1b100;">do</span>
	<span style="color: #66cc66;">&#91;</span> -f <span style="color: #0000ff;">$wplatest</span>/<span style="color: #0000ff;">$i</span> <span style="color: #66cc66;">&#93;</span> &amp;&amp; <span style="color: #66cc66;">&#40;</span><span style="color: #000066;">echo</span> <span style="color: #ff0000;">"removing: $i"</span> &amp;&amp; rm <span style="color: #0000ff;">$wplatest</span>/<span style="color: #0000ff;">$i</span><span style="color: #66cc66;">&#41;</span>
<span style="color: #b1b100;">done</span>
&nbsp;
&nbsp;
msg <span style="color: #ff0000;">"Complete"</span>
&nbsp;
<span style="color: #66cc66;">&#91;</span> -f <span style="color: #0000ff;">$temp_path</span>/patches.failed <span style="color: #66cc66;">&#93;</span> &amp;&amp;
<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"Some of my patches failed to apply, listed in $temp_path/patches.failed"</span>
&nbsp;
<span style="color: #66cc66;">&#91;</span> -f <span style="color: #0000ff;">$temp_path</span>/file-merge.failed <span style="color: #66cc66;">&#93;</span> &amp;&amp;
<span style="color: #000066;">echo</span> <span style="color: #ff0000;">"Some of my files failed to merge, listed in $temp_path/file-merge.failed"</span>
&nbsp;
echo&lt;&lt;close <span style="color: #ff0000;">"
The upgraded version is in $wplatest
&nbsp;
To install the new version you'll want to do something like this:
  mv $wpmine ${wpmine}.old
  mv $wplatest $wpmine
&nbsp;
Afterwards you can remove the temporary dir $temp_path
&nbsp;
If the new version provides any php upgrades scripts (to upgrade the
database), now would be a good time to run them"</span>
close
&nbsp;</pre>
<p><i>Download this code: </i><a href="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/wordpress_update_sh">wordpress_update_sh</a></p>
<p>Another option would be to <a href="http://codex.wordpress.org/Installing/Updating_WordPress_with_Subversion">use Subversion</a> and just update between stable tags, but then again I don&#8217;t have that on the server and most hosts probably don&#8217;t install it. But the Subversion method and this one are functionally equivalent, with the small exception that this upgrade is done offsite while the Subversion way would typically (but not necessarily) be a live upgrade.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.matusiak.eu/numerodix/blog/index.php/2007/09/22/wordpress-update-script/feed/</wfw:commentRss>
		<slash:comments>6</slash:comments>
		</item>
		<item>
		<title>new posts popup</title>
		<link>http://www.matusiak.eu/numerodix/blog/index.php/2007/09/15/new-posts-popup/</link>
		<comments>http://www.matusiak.eu/numerodix/blog/index.php/2007/09/15/new-posts-popup/#comments</comments>
		<pubDate>Sat, 15 Sep 2007 10:29:40 +0000</pubDate>
		<dc:creator>numerodix</dc:creator>
				<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://www.matusiak.eu/numerodix/blog/index.php/2007/09/15/new-posts-popup/</guid>
		<description><![CDATA[This is a feature I&#8217;ve wanted to have for a long time, but until now I didn&#8217;t know how to realize it. I wanted to have some kind of a notification area for new events on the blog, so that a returning visitor could immediately see what has changed since the last visit. And I [...]]]></description>
			<content:encoded><![CDATA[<p>This is a feature I&#8217;ve wanted to have for a long time, but until now I didn&#8217;t know how to realize it. I wanted to have some kind of a notification area for new events on the blog, so that a returning visitor could immediately see what has changed since the last visit. And I definitely didn&#8217;t want it on the sidebar, it had to be above the fold.</p>
<p>So the concept was in the back of my head for months, but I couldn&#8217;t figure out how to make it look good. Then I came up with the idea of making it a popup window. Not a browser window, of course, just a layer that would show if there had been new events. Otherwise it wouldn&#8217;t show up. Yes, that sounds like something. So with some digging and research, a bit of hacking and lots of debugging, here is the final result.</p>
<p style="text-align: center"><img src="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/new_posts_overlay_ss.png" alt="new_posts_overlay_ss.png" /></p>
<p>The window conveys quite a lot of information. It lists the three posts last to be published (or commented on). This way you have new posts and new comments in the same place. In the screenshot, the top entry is a post made recently. The bottom two are older posts that have received new comments.</p>
<p>In terms of appearance, I wanted to make the window active only if the user is using it, so on page load it is made partially transparent, onMouseOver it becomes more opaque, and onMouseOut it becomes more transparent again.</p>
<p>For a demo.. you have this blog. After 15 minutes of inactivity your session will expire and the window will go away. To bring it back delete your cookies from this domain (or use a different browser) and it reappears. The session is handled entirely with cookies, so for visitors who don&#8217;t accept cookies, the window will always appear as if this were their first visit.</p>
<p><strong>Compatibility</strong></p>
<p>The opacity property is new in CSS3 and isn&#8217;t uniformly supported (yet). I&#8217;ve tested the plugin with the following browsers.</p>
<ul>
<li>Firefox 1.0.1, 2.0.0.6</li>
<li>Opera <strike>8.0</strike>, 9.23</li>
<li>Safari 3.0.3</li>
<li>IE 5.0, 6.0, 7.0</li>
<li><strike>Konqueror 3.5.7</strike> (opacity support is rumored to be on the way)</li>
<li>Netscape <strike>6.0.1</strike>, <strike>7.0</strike>, 8.0.2, 9.0b3</li>
</ul>
<p>In addition, there&#8217;s a rather pesky layout bug in IE &lt;7.0 that causes the height of the window (which is floating above the other content) to be added to the top of the page. If you fix it, please send a patch. <img src='http://www.matusiak.eu/numerodix/blog/wp-includes/images/smilies/smile.png' alt=':)' class='wp-smiley' /> </p>
<p>Also, I tried very hard to make sure it only consumes one query, which unfortunately made it very complicated. If you rewrite it in simpler  terms, send a patch. <img src='http://www.matusiak.eu/numerodix/blog/wp-includes/images/smilies/smile.png' alt=':)' class='wp-smiley' /> </p>
<p>Required MySQL version: <strong>4.1+ </strong></p>
<p><strong>How to use</strong></p>
<p>Download, unzip, install, append the css to your styles. <img src='http://www.matusiak.eu/numerodix/blog/wp-includes/images/smilies/cap.png' alt=':cap:' class='wp-smiley' /> </p>
<ul>
<li><a href="http://wordpress.org/extend/plugins/new-posts-popup/">New Posts Popup plugin</a> @ wordpress.org</li>
<li><a href="http://svn.wp-plugins.org/new-posts-popup/">New Posts Popup</a> @ svn</li>
</ul>
<p>UPDATE: Added Netscape.</p>
<p>UPDATE2: MySQL compatibility.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.matusiak.eu/numerodix/blog/index.php/2007/09/15/new-posts-popup/feed/</wfw:commentRss>
		<slash:comments>17</slash:comments>
		</item>
		<item>
		<title>making the spam bots feel comfortable</title>
		<link>http://www.matusiak.eu/numerodix/blog/index.php/2007/06/01/making-the-spam-bots-feel-comfortable/</link>
		<comments>http://www.matusiak.eu/numerodix/blog/index.php/2007/06/01/making-the-spam-bots-feel-comfortable/#comments</comments>
		<pubDate>Fri, 01 Jun 2007 09:19:51 +0000</pubDate>
		<dc:creator>numerodix</dc:creator>
				<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://www.matusiak.eu/numerodix/blog/index.php/2007/06/01/making-the-spam-bots-feel-comfortable/</guid>
		<description><![CDATA[A lot of famous people have said lots of interesting things about success. Little did I know the success I was about to experience when I opened this blog in 2003. It is today what it&#8217;s always been, an outlet mostly for various gripes, observations, recent events etc., of no interest to anyone. Why blog? [...]]]></description>
			<content:encoded><![CDATA[<p>A lot of famous people have said lots of interesting things about success. Little did I know the success I was about to experience when I opened this blog in 2003. It is today what it&#8217;s always been, an outlet mostly for various gripes, observations, recent events etc., of no interest to anyone. Why blog? Because I feel like it (bad guys in movies always say &#8220;because I can&#8221;). And I also thought that in time I would find it amusing to read back old entries, relive the past so to speak, which I actually don&#8217;t really do.</p>
<p>But it turns out that this blog does have a wide appeal after all. Why is anybody&#8217;s guess. In the last 6 months or so interest has intensified to the point where I get 1,000 comments a week. The absolute majority of these are friendly, well meaning, helpful spam bots who want to make sure I hear about the best deals that can be made. Whoever said machines aren&#8217;t friendly?</p>
<p>So, as more and more spam bots have found my blog and spread the word to all their friends, it&#8217;s become increasingly important to make sure I&#8217;m a good host to this populous demographic. My spam bot friends have a lot to say, and they won&#8217;t stop at arguing points for topics that were covered here a long time ago. The Wordpress community has helped me ensure that while I don&#8217;t miss out on any spam comments, the human readers on here, who don&#8217;t know my bot friends, and don&#8217;t appreciate their intelligence and sense of humor, only see the human content.</p>
<p>Wordpress ships with Akismet,  and you want to turn it on right away. But to decrease the number of spam comments, you may want to consider the <a href="http://www.bad-behavior.ioerror.us/">Bad Behavior plugin</a> in addition. It blocks certain types of traffic outright, not just posts but also pageviews.</p>
<p>The last two weeks I experimented to see whether it makes much of a difference. First I ran Bad Behaviour for a week, counted how many spam comments I got and how many were blocked. Then I ran for a week without it and counted the spam comments.</p>
<p><strong>May 17-25</strong></p>
<p><strong>832</strong> spam comments</p>
<p><strong>866</strong> spam comments blocked by Bad Behavior (out of a total 1,196 requests blocked in total)</p>
<p><strong>May 25-June 1</strong></p>
<p><strong>1,320</strong> spam comments</p>
<p>In both cases, all spam was caught by Akismet, so nothing actually gets published. But the difference is in how much spam is submitted and ends up in Akismet&#8217;s temporary 15-day archive.</p>
<p><strong>Conclusion:</strong> Bad Behavior is worthwhile. <img src='http://www.matusiak.eu/numerodix/blog/wp-includes/images/smilies/smile.png' alt=':)' class='wp-smiley' /> </p>
]]></content:encoded>
			<wfw:commentRss>http://www.matusiak.eu/numerodix/blog/index.php/2007/06/01/making-the-spam-bots-feel-comfortable/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>random posts from category</title>
		<link>http://www.matusiak.eu/numerodix/blog/index.php/2006/12/04/random-posts-from-category/</link>
		<comments>http://www.matusiak.eu/numerodix/blog/index.php/2006/12/04/random-posts-from-category/#comments</comments>
		<pubDate>Sun, 03 Dec 2006 22:37:55 +0000</pubDate>
		<dc:creator>numerodix</dc:creator>
				<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://www.matusiak.eu/numerodix/blog/index.php/2006/12/05/random-posts-from-category/</guid>
		<description><![CDATA[The other day I was thinking it would be nice to have a little space below every blog entry that displays past entries from this same category, but in random. So this would be a cool way to explore old entries for someone who hasn&#8217;t seen the blog before, but no less for me since [...]]]></description>
			<content:encoded><![CDATA[<p>The other day I was thinking it would be nice to have a little space below every blog entry that displays past entries from this same category, but in random. So this would be a cool way to explore old entries for someone who hasn&#8217;t seen the blog before, but no less for me since I wrote that stuff at one point and forgot all about it. It was actually seeing <a href="http://www.keybi.jawnet.pl/">KeyBi&#8217;s blog</a> that inspired me to do this, cause he has a random posts feature on his.</p>
<p>I used <a href="http://www.w-a-s-a-b-i.com/archives/2004/05/27/wordpress-random-posts-plugin/">an existing plugin</a> and modified it for my needs to look exactly as you can see at the bottom of this post.</p>
<ul>
<li>Random Posts From Category plugin: <a href="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/random_posts_from_cat_1_2.tar.gz">random_posts_from_cat_1_2.tar.gz</a></li>
</ul>
<p>So now it&#8217;s easier to browse old posts, but this brought out an old problem, namely that entries posted before the migration to WordPress were not input with their comments counted, so although these old entries have comments, WordPress doesn&#8217;t seem aware of this. I fixed that with the simple script below.</p>
<pre class="php"><span style="color: #000000; font-weight: bold;">&lt;?</span>
&nbsp;
<span style="color: #0000ff;">$user</span> = <span style="color: #ff0000;">''</span>;
<span style="color: #0000ff;">$pass</span> = <span style="color: #ff0000;">''</span>;
<span style="color: #0000ff;">$db</span> = <span style="color: #ff0000;">''</span>;
<span style="color: #0000ff;">$host</span> = <span style="color: #ff0000;">''</span>;
&nbsp;
<span style="color: #0000ff;">$link</span> = <a href="http://www.php.net/mysql_connect"><span style="color: #000066;">mysql_connect</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$host</span>, <span style="color: #0000ff;">$user</span>, <span style="color: #0000ff;">$pass</span><span style="color: #66cc66;">&#41;</span> or <a href="http://www.php.net/die"><span style="color: #000066;">die</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #ff0000;">"kernel panic"</span><span style="color: #66cc66;">&#41;</span>;
<a href="http://www.php.net/mysql_select_db"><span style="color: #000066;">mysql_select_db</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$db</span><span style="color: #66cc66;">&#41;</span>;
&nbsp;
<span style="color: #0000ff;">$sql</span> = <span style="color: #ff0000;">"select ID from wp_posts where post_status = 'publish'"</span>;
<span style="color: #0000ff;">$result</span> = <a href="http://www.php.net/mysql_query"><span style="color: #000066;">mysql_query</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$sql</span><span style="color: #66cc66;">&#41;</span>;
&nbsp;
<span style="color: #0000ff;">$IDs</span> = <a href="http://www.php.net/array"><span style="color: #000066;">array</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #66cc66;">&#41;</span>;
<span style="color: #b1b100;">while</span> <span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$row</span> = <a href="http://www.php.net/mysql_fetch_row"><span style="color: #000066;">mysql_fetch_row</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$result</span><span style="color: #66cc66;">&#41;</span><span style="color: #66cc66;">&#41;</span> <span style="color: #66cc66;">&#123;</span>
	<span style="color: #0000ff;">$IDs</span><span style="color: #66cc66;">&#91;</span><span style="color: #66cc66;">&#93;</span> = <span style="color: #0000ff;">$row</span><span style="color: #66cc66;">&#91;</span><span style="color: #cc66cc;">0</span><span style="color: #66cc66;">&#93;</span>;
<span style="color: #66cc66;">&#125;</span>
&nbsp;
<span style="color: #b1b100;">foreach</span> <span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$IDs</span> <span style="color: #b1b100;">as</span> <span style="color: #0000ff;">$i</span><span style="color: #66cc66;">&#41;</span> <span style="color: #66cc66;">&#123;</span>
	<span style="color: #0000ff;">$sql</span>  = <span style="color: #ff0000;">"update wp_posts set comment_count = "</span>;
	<span style="color: #0000ff;">$sql</span> .= <span style="color: #ff0000;">"(select count(*) from wp_comments where comment_post_ID = $i "</span>;
	<span style="color: #0000ff;">$sql</span> .= <span style="color: #ff0000;">"and comment_approved = '1') "</span>;
	<span style="color: #0000ff;">$sql</span> .= <span style="color: #ff0000;">"where ID = $i"</span>;
	<a href="http://www.php.net/mysql_query"><span style="color: #000066;">mysql_query</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$sql</span><span style="color: #66cc66;">&#41;</span>;
<span style="color: #66cc66;">&#125;</span>
&nbsp;
<a href="http://www.php.net/mysql_close"><span style="color: #000066;">mysql_close</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$link</span><span style="color: #66cc66;">&#41;</span>;
&nbsp;
<a href="http://www.php.net/echo"><span style="color: #000066;">echo</span></a> <span style="color: #ff0000;">"Comments updated."</span>;
<span style="color: #000000; font-weight: bold;">?&gt;</span></pre>
<p><i>Download this code: </i><a href="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/fix_wordpress_comments_php">fix_wordpress_comments_php</a></p>
]]></content:encoded>
			<wfw:commentRss>http://www.matusiak.eu/numerodix/blog/index.php/2006/12/04/random-posts-from-category/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>fixing missing post slugs in wordpress</title>
		<link>http://www.matusiak.eu/numerodix/blog/index.php/2006/08/31/fixing-missing-post-slugs-in-wordpress/</link>
		<comments>http://www.matusiak.eu/numerodix/blog/index.php/2006/08/31/fixing-missing-post-slugs-in-wordpress/#comments</comments>
		<pubDate>Thu, 31 Aug 2006 10:34:25 +0000</pubDate>
		<dc:creator>numerodix</dc:creator>
				<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://www.matusiak.eu/numerodix/blog/index.php/2006/08/01/fixing-missing-post-slugs-in-wordpress/</guid>
		<description><![CDATA[If you&#8217;ve ever moved from one house to another, you know that it&#8217;s not just moving day that is a mess in your new house, it drags on for a while until you get things sorted out. Lots of little details escape attention for days, weeks even. But eventually you track down every last one [...]]]></description>
			<content:encoded><![CDATA[<p>If you&#8217;ve ever moved from one house to another, you know that it&#8217;s not just moving day that is a mess in your new house, it drags on for a while until you get things sorted out. Lots of little details escape attention for days, weeks even. But eventually you track down every last one and after about a month or two, you are 100% in order.</p>
<p>Now you&#8217;re probably thinking <em>what the hell does that have to do with the title of this entry?!?</em> Well, just like moving houses, migrating data from one system to the next is similar. And moving from BLOG:CMS to WordPress has not been entirely trivial, so I still spot the odd bug even though it&#8217;s been a couple of weeks. One thing I neglected to consider when migrating the blog was missing post slugs. You see, WordPress uses <em>post slugs</em> as a way to label urls more human-friendly. Instead of <code>{blog_url}?p=34</code> to open post number 34, it allows you to use urls in the form <code>{blog_url}/index.php/year/month/day/<strong>blog-entry-title</strong></code> (the part after the last slash is what WordPress calls a <em>post slug</em>) This is nice for people who link to a blog entry, because the latter url makes a lot more sense to a human than the former (which is just a number of a column in a database).</p>
<p><span id="more-409"></span>But. BLOG:CMS does not use post slugs (or didn&#8217;t), so I&#8217;ve never had them. WordPress generates them automatically for new posts, but since I imported my old entries into WordPress, those didn&#8217;t have post slugs from before. I realized all this when I migrated my blog entries, and I thought it was just inconsistent, but it wouldn&#8217;t have any repercussions. Well, it turns out some links were broken over this. So I realized today that I would have to fix this annoying little bug and put in post slugs for entries that don&#8217;t already have them.</p>
<p>And for that purpose I wrote a little script. It&#8217;s a quick and dirty fix, stripping off all non-ascii characters (this will not work well with non-English post titles), forcing all characters to lowercase and inserting hyphens between words. But for my money it works well enough.</p>
<pre class="php"><span style="color: #000000; font-weight: bold;">&lt;?</span>
&nbsp;
<span style="color: #0000ff;">$dbhost</span> = <span style="color: #ff0000;">''</span>;
<span style="color: #0000ff;">$dbuser</span> = <span style="color: #ff0000;">''</span>;
<span style="color: #0000ff;">$dbpass</span> = <span style="color: #ff0000;">''</span>;
<span style="color: #0000ff;">$dbname</span> = <span style="color: #ff0000;">''</span>;
&nbsp;
&nbsp;
<span style="color: #0000ff;">$sql</span> = <span style="color: #ff0000;">'SELECT ID, post_title'</span>
        . <span style="color: #ff0000;">' FROM `wp_posts`'</span>
        . <span style="color: #ff0000;">' WHERE post_status = <span style="color: #000099; font-weight: bold;">\\'</span>publish<span style="color: #000099; font-weight: bold;">\\'</span>'</span>
        . <span style="color: #ff0000;">' and post_name = <span style="color: #000099; font-weight: bold;">\\'</span><span style="color: #000099; font-weight: bold;">\\'</span>'</span>
        . <span style="color: #ff0000;">' order by ID asc'</span>;
&nbsp;
&nbsp;
<span style="color: #0000ff;">$db</span> = <a href="http://www.php.net/mysql_connect"><span style="color: #000066;">mysql_connect</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$dbhost</span>, <span style="color: #0000ff;">$dbuser</span>, <span style="color: #0000ff;">$dbpass</span><span style="color: #66cc66;">&#41;</span> or <a href="http://www.php.net/die"><span style="color: #000066;">die</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #ff0000;">'Could not connect: '</span> . <a href="http://www.php.net/mysql_error"><span style="color: #000066;">mysql_error</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #66cc66;">&#41;</span><span style="color: #66cc66;">&#41;</span>;
<a href="http://www.php.net/mysql_select_db"><span style="color: #000066;">mysql_select_db</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$dbname</span><span style="color: #66cc66;">&#41;</span>;
&nbsp;
&nbsp;
<span style="color: #0000ff;">$result</span> = <a href="http://www.php.net/mysql_query"><span style="color: #000066;">mysql_query</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$sql</span><span style="color: #66cc66;">&#41;</span> or <a href="http://www.php.net/die"><span style="color: #000066;">die</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #ff0000;">'Query failed: '</span> . <a href="http://www.php.net/mysql_error"><span style="color: #000066;">mysql_error</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #66cc66;">&#41;</span><span style="color: #66cc66;">&#41;</span>;
<span style="color: #b1b100;">while</span><span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$row</span> = <a href="http://www.php.net/mysql_fetch_array"><span style="color: #000066;">mysql_fetch_array</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$result</span>, MYSQL_ASSOC<span style="color: #66cc66;">&#41;</span><span style="color: #66cc66;">&#41;</span>
<span style="color: #66cc66;">&#123;</span>
	<span style="color: #0000ff;">$id</span> = <span style="color: #0000ff;">$row</span><span style="color: #66cc66;">&#91;</span><span style="color: #ff0000;">'ID'</span><span style="color: #66cc66;">&#93;</span>;
	<span style="color: #0000ff;">$title</span> = <span style="color: #0000ff;">$row</span><span style="color: #66cc66;">&#91;</span><span style="color: #ff0000;">'post_title'</span><span style="color: #66cc66;">&#93;</span>;

	<span style="color: #0000ff;">$title</span> = <a href="http://www.php.net/trim"><span style="color: #000066;">trim</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$title</span><span style="color: #66cc66;">&#41;</span>;
	<span style="color: #0000ff;">$title</span> = <a href="http://www.php.net/strtolower"><span style="color: #000066;">strtolower</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$title</span><span style="color: #66cc66;">&#41;</span>;
	<span style="color: #0000ff;">$title</span> = <a href="http://www.php.net/str_replace"><span style="color: #000066;">str_replace</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #ff0000;">" "</span>, <span style="color: #ff0000;">"-"</span>, <span style="color: #0000ff;">$title</span><span style="color: #66cc66;">&#41;</span>;
	<span style="color: #0000ff;">$title</span> = <a href="http://www.php.net/ereg_replace"><span style="color: #000066;">ereg_replace</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #ff0000;">"[^a-z0-9-]"</span>, <span style="color: #ff0000;">""</span>, <span style="color: #0000ff;">$title</span><span style="color: #66cc66;">&#41;</span>;
	<span style="color: #0000ff;">$title</span> = <a href="http://www.php.net/ereg_replace"><span style="color: #000066;">ereg_replace</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #ff0000;">"[-]+"</span>, <span style="color: #ff0000;">"-"</span>, <span style="color: #0000ff;">$title</span><span style="color: #66cc66;">&#41;</span>;

	<a href="http://www.php.net/echo"><span style="color: #000066;">echo</span></a> <span style="color: #ff0000;">"ID :{$row['ID']} &lt;br&gt;"</span> .
		<span style="color: #ff0000;">"post_title : {$row['post_title']} &lt;br&gt;"</span> .
		<span style="color: #ff0000;">"post_title : {$title} &lt;br&gt;"</span>;
&nbsp;
	<span style="color: #0000ff;">$sql_u</span> = <span style="color: #ff0000;">'UPDATE `wp_posts` SET post_name = `'</span> . <span style="color: #0000ff;">$title</span> .<span style="color: #ff0000;">'`'</span>
		.<span style="color: #ff0000;">'WHERE ID = '</span> . <span style="color: #0000ff;">$id</span>;
	<a href="http://www.php.net/echo"><span style="color: #000066;">echo</span></a> <span style="color: #ff0000;">'&lt;br&gt;'</span>.<span style="color: #0000ff;">$sql_u</span>;
	<a href="http://www.php.net/mysql_query"><span style="color: #000066;">mysql_query</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$sql_u</span><span style="color: #66cc66;">&#41;</span> or <a href="http://www.php.net/die"><span style="color: #000066;">die</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #ff0000;">'Query failed: '</span> . <a href="http://www.php.net/mysql_error"><span style="color: #000066;">mysql_error</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #66cc66;">&#41;</span><span style="color: #66cc66;">&#41;</span>;
&nbsp;
<span style="color: #66cc66;">&#125;</span>
&nbsp;
<a href="http://www.php.net/mysql_close"><span style="color: #000066;">mysql_close</span></a><span style="color: #66cc66;">&#40;</span><span style="color: #0000ff;">$db</span><span style="color: #66cc66;">&#41;</span>;
&nbsp;
<span style="color: #000000; font-weight: bold;">?&gt;</span></pre>
<p><i>Download this code: </i><a href="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/fix_missing_post_slugs_php">fix_missing_post_slugs_php</a></p>
]]></content:encoded>
			<wfw:commentRss>http://www.matusiak.eu/numerodix/blog/index.php/2006/08/31/fixing-missing-post-slugs-in-wordpress/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
		<item>
		<title>my wordpress theme</title>
		<link>http://www.matusiak.eu/numerodix/blog/index.php/2006/08/14/my-wordpress-theme/</link>
		<comments>http://www.matusiak.eu/numerodix/blog/index.php/2006/08/14/my-wordpress-theme/#comments</comments>
		<pubDate>Mon, 14 Aug 2006 13:18:02 +0000</pubDate>
		<dc:creator>numerodix</dc:creator>
				<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://www.matusiak.eu/numerodix/blog/?p=357</guid>
		<description><![CDATA[So it turns out that adding custom fields in WordPress is really easy. Just use the Custom Fields box beneath the input box and add a new field. This new field will be presented as an option for every new post as well (this I would not be brave enough to assume, but it&#8217;s so). [...]]]></description>
			<content:encoded><![CDATA[<p>So it turns out that adding custom fields in WordPress is really easy. Just use the <em>Custom Fields</em> box beneath the input box and add a new field. This new field will be presented as an option for every new post as well (this I would not be brave enough to assume, but it&#8217;s so). From there on, bringing back <em>Now Playing</em> is really simple, so I thought why not just make it a plugin while I&#8217;m at it.</p>
<p>Using the plugin requires this as part of the post in the template: <code>&lt;?php get_now_playing($post); ?&gt;</code>. Yes, it requires passing on the $post object and no I don&#8217;t know why. Why do *you* care? <img src='http://www.matusiak.eu/numerodix/blog/wp-includes/images/smilies/tongue.png' alt=':P' class='wp-smiley' /> </p>
<p>So since I made it a plugin anyway, I thought I might as well package it up on the very slight off chance that someone would want it for themselves.</p>
<p>And while we&#8217;re at it, I packed up the theme I&#8217;m using as well, get both of them below. The reason I bundle this is that the theme illustrates how to use the plugin. Not only where to call the function, but also how to style it, you&#8217;ll find that at the bottom of <code>style.css</code>.</p>
<p>One caveat, the plugin *expects* a custom field called <strong>Now Playing</strong>, nothing more, nothing less. So if you neglect to include the whitespace or you call it something else, you&#8217;ll have to hack the plugin to make it work (which is trivial, just edit the call to <code>get_post_meta</code> and you&#8217;re done).</p>
<ul>
<li>numerodixed WordPress theme: <a title="numerodixed WordPress theme" id="p355" href="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/numerodixed_1_0.tar.gz">numerodixed_1_0.tar.gz</a></li>
<li>Now Playing plugin: <a title="Now Playing WordPress Plugin" id="p356" href="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/now_playing_0_1.tar.gz">now_playing_0_1.tar.gz</a></li>
</ul>
<p>&#8220;How about a demo&#8221;, you say. Look at the bottom of this post. <img src='http://www.matusiak.eu/numerodix/blog/wp-includes/images/smilies/smile.png' alt=':)' class='wp-smiley' /> </p>
]]></content:encoded>
			<wfw:commentRss>http://www.matusiak.eu/numerodix/blog/index.php/2006/08/14/my-wordpress-theme/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>blog facelift</title>
		<link>http://www.matusiak.eu/numerodix/blog/index.php/2006/08/12/blog-facelift/</link>
		<comments>http://www.matusiak.eu/numerodix/blog/index.php/2006/08/12/blog-facelift/#comments</comments>
		<pubDate>Sun, 13 Aug 2006 01:00:26 +0000</pubDate>
		<dc:creator>numerodix</dc:creator>
				<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://www.matusiak.eu/numerodix/blog/?p=344</guid>
		<description><![CDATA[As you can see, the blog just got a bit of a facelift. &#8220;But&#8221;, you interject, &#8220;if it ain&#8217;t broketh, why fixeth&#8221;, as it were. I&#8217;ve been meaning to do this for some time, I was never 100% happy with the blog software I was using. Granted, Radek Hulán&#8217;s extensions to Nucleus in the shape [...]]]></description>
			<content:encoded><![CDATA[<p>As you can see, the blog just got a bit of a facelift. &#8220;But&#8221;, you interject, &#8220;if it ain&#8217;t broketh, why fixeth&#8221;, as it were. I&#8217;ve been meaning to do this for some time, I was never 100% happy with the blog software I was using. Granted, Radek Hulán&#8217;s extensions to <a href="http://nucleuscms.org/">Nucleus</a> in the shape of <a href="http://blogcms.com/">BLOG:CMS</a> result in a very powerful and customizable package, but it is a bit rough around the edges. It would frustrate me in certain ways, like the rich content editor being buggy and not working well with images. Like the stylesheets being as good as unintelligible &#8211; even though I modified them to my liking, I knew it would be hell to try and change at any point. Like the xml feeds not always working well. It feels quite hackish. The admin control panel, for instance, is quite rough looking and frustrating. The templates are very difficult to make out, they&#8217;re all stored in the database and it took me quite a bit of trial and error to figure out what comes out where. Basically, I felt locked into a system that worked, but I would rather use something that is more friendly to change.</p>
<p>Back in 2003, Nucleus was a good choice, but the landscape has changed somewhat. <a href="http://wordpress.org/">WordPress</a> has made great strides and over the years I&#8217;ve seen quite a few great looking WordPress blogs. What makes them stand out is the attention to <em>typography</em> that WordPress has, which is a nice quality to have for <em>publishing</em> software. WordPress blogs are always good to read, because the fonts are a certain type and size etc. They also tend to have a very clean look. And since it&#8217;s now widely used, I thought I would probably find enough plugins to satisfy my modest needs.</p>
<p>To get a general idea of what my blog could look like, I started browsing the hundreds of themes there are out there for WordPress. Surprisingly, I couldn&#8217;t find one that was actually good enough to use. To be fair, it&#8217;s not that there aren&#8217;t any usable themes, just that I couldn&#8217;t find one that would suit me. Since I don&#8217;t want my blog pink or black or the post section very narrow with two sidebars, I soon realized I would have to make my own theme. Given how many attractive WordPress sites I&#8217;ve seen in the past, it&#8217;s astounding that there isn&#8217;t one theme of the kind I was looking for (predominantly light colors) in about 200 I looked through that would actually be good looking. A lot of them look good in some ways, like good choice of fonts, but there&#8217;s always some problem, like the menu looks 1995. Or the header image along with the color scheme looks great, but the fonts are Times New Roman italic or something like that. It&#8217;s strange that someone would be competent enough to produce a professional looking design with balanced colors and images, but completely botch the choice of fonts that go on the page. I&#8217;m no designer myself, I can pick fonts that look good and with some effort find a decent color scheme. But my skills are limited, I see websites all the time that I couldn&#8217;t design, because I don&#8217;t have the eye for it.</p>
<p>So I would have to roll my own. When hacking existing code, it&#8217;s essential to start with a good base, ideally the fewer changes the better. The standard WordPress theme is a good place to start. It does look quite good, but it has a few problems. For one thing, the items on the sidebar are not ordered in a particularly inviting way. There is a page full of archives, so just about noone is going to see what&#8217;s further down. Another problems is the way the posts are presented. The space allocated to them is too narrow. In some of my posts, I have images up to 500px in width, this post area is only 450px wide. It&#8217;s also so narrow that the page looks funny, as if the post wasn&#8217;t supposed to take up any more space, even though there is nothing else to look at. And strangely, on the single page, where the sidebar doesn&#8217;t appear, it&#8217;s still just as narrow.</p>
<p style="text-align: center"><img src="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/kubrick-theme.png" alt="kubrick-theme.png" id="image345" /></p>
<p>Unlike BLOG:CMS, WordPress does not come with a rich admin control panel for changing the styles. In fact, they seem to encourage editing the actual files. At first, this felt unnatural, as I&#8217;m used to vBulletin also installing hundreds of templates that go in the database. But this is actually a better way of doing it, it&#8217;s easier [quicker] to modify files on disk than rows in a database. It also means I can use nano or vim instead of having to enter the code in a <em>textarea</em>.</p>
<p>WordPress, seemingly, is documented to death. It has so much documentation that I wouldn&#8217;t even consider starting reading it. Instead I made a copy of the default theme and started changing things. Themes are separated very cleanly and there is no need to modify anything that shouldn&#8217;t be touched (outside the theme). Basically, all you need is in there. The <a href="http://www.matusiak.eu/numerodix/blog/wp-content/themes/numerodixed/style.css">stylesheet</a> makes for a nice change of pace, it&#8217;s actually logically divided and documented. But debugging css is always a pain anyway, so I found a couple of Firefox extensions that make it hurt considerably less:</p>
<ul>
<li><a href="http://chrispederick.com/work/webdeveloper/">Web Developer</a></li>
<li><a href="https://addons.mozilla.org/firefox/655/">View Source Chart</a></li>
<li><a href="https://addons.mozilla.org/firefox/2104/">CSSViewer</a></li>
</ul>
<p>These things are a blessing when trying to make sense of things! So after a while I came up with the theme you&#8217;re looking at. It aims to preserve all the strengths of the theme I used in BLOG:CMS and I&#8217;m quite happy with it. One thing that isn&#8217;t part of a theme are the smilies. WordPress comes with its set of smilies and I wanted to use <a href="http://www.kde-look.org/content/show.php?content=43094">xtorg</a>, which I use for everything, because it&#8217;s basically the best smilies set known to man. <img src='http://www.matusiak.eu/numerodix/blog/wp-includes/images/smilies/wink.png' alt=';)' class='wp-smiley' />  This should technically be very simple, such is the hypothesis. Smilies are declared in wp-includes/vars.php, in a simple associative array. Little did I know how much effort it would take to get that array &#8220;right&#8221;. It kept breaking in strange ways (parsing totally out of whack) and finally I realized that for smilies that do *not* begin _and_ end with a colon, I need to add a space at the beginning, so for instance in the case of word <img src='http://www.matusiak.eu/numerodix/blog/wp-includes/images/smilies/biggrin.png' alt=':D' class='wp-smiley' />  , WordPress will not recognize <img src='http://www.matusiak.eu/numerodix/blog/wp-includes/images/smilies/biggrin.png' alt=':D' class='wp-smiley' />  at the end, it must be prepended with a whitespace. This little quirk isn&#8217;t documented in the source, and as far as I could see, isn&#8217;t documented on wordpress.org either. This particular example doesn&#8217;t seem to square with &#8220;code is poetry&#8221; &#8211; WordPress&#8217;s slogan &#8211; but is there not an exception to every rule? In any case, I&#8217;ve added support for WordPress to <a href="http://www.kde-look.org/content/show.php?content=43094">xtorg</a>, so anyone can now easily use those smilies in WordPress. For those just posting comments here, use either colon-text-colon or just the msn codes, those will work too.</p>
<p>One thing I thoroughly enjoyed in BLOG:CMS was the random quotes that would appear on the single post pages. I&#8217;ve ripped them off and added them on the index page. Another thing I wanted to preserve was the &#8220;Now Playing&#8221; feature, but there is no plugin for that in WordPress. Meanwhile, there is a host of plugins for pulling in data from <a href="http://www.last.fm/user/numerodix/">last.fm</a>. Well, I could use that to display the last song I listened to, but I don&#8217;t quite know where. The sidebar is quite full as it is, so for the time being, it&#8217;s off.</p>
<p>Finally (and this post isn&#8217;t quite in chronological order), with WordPress set up and configured, it was time to import my posts from BLOG:CMS. As it turns out, WordPress *still* hasn&#8217;t developed a script for that, but a few people have tried it. I tried every script I could find, but only one of them worked, and it was <a href="http://mamchenkov.net/wordpress/2005/04/26/nucleus2wordpress/">Leonid Mamchenkov&#8217;s nucleus2wordpress.perl</a>. The script ran without a hitch, actually. I realized I would have to hack it a bit, because the images weren&#8217;t showing up (and this is something WordPress is very stupid with &#8211; hardcoding image paths in posts). There was also a problem with the charset &#8211; WordPress uses utf-8, BLOG:CMS uses iso-latin-1. I had to research how to encode text in perl and surprisingly, I pulled it off with two lines of code that worked (w00t! w00t!). I say that, because I don&#8217;t actualy know perl. So now the rare post in Norwegian shows up in all its utf-8 splendor.</p>
<p>So, there it is. Without doubt, the most documented software installation in my life. <img src='http://www.matusiak.eu/numerodix/blog/wp-includes/images/smilies/biggrin.png' alt=':D' class='wp-smiley' /> </p>
<p>And here is one last look at the past:</p>
<p align="center"><img src="http://www.matusiak.eu/numerodix/blog/wp-content/uploads/blogcms.png" id="image346" alt="blogcms.png" /></p>
]]></content:encoded>
			<wfw:commentRss>http://www.matusiak.eu/numerodix/blog/index.php/2006/08/12/blog-facelift/feed/</wfw:commentRss>
		<slash:comments>7</slash:comments>
		</item>
	</channel>
</rss>

