Tag Archives: Wordpress

Convert myGallery to NextGen Gallery

For a lot of web logs, photo galleries are used. The web logs in this server used to run myGallery. However, this WordPress plugin wasn’t updated for a long time. (Recently there was an update for WordPress 3. I haven’t tested this one yet). So I needed a new gallery plugin. The NextGen Gallery plugin has all the requirements that I need. And best of all, it’s reasonably compatible with myGallery. So I decided to write a script that can convert all myGallery galleries to NextGen galleries. It will also update all the pages that display the gallery. Last, it will convert the thumbnail directory, so NextGen Gallery can use them. Of course, you can also let NextGen Gallery generate new thumbnails. But since my server isn’t that fast, using existing thumbnails is a good idea.

If you are running myGallery, and want to upgrade to NextGen Gallery and perform the conversion, this are the steps to perform. First, download NextGen Gallery. Disable myGallery, and enable NextGen Gallery. Next, copy and paste the script below in a PHP file. Modify the configuration and run the script. This will give a series of SQL statements. You can run these on the MySQL database. For example, you can use phpMyAdmin to run the queries easily.


// CONFIG

// the prefix for your WordPress tables (default: wp_)
$WP_PREFIX = 'wp_';

// the directory on the server where your photos are stored
$GALLERYBASEPATH = 'wp-content/myfotos/daniel';

// username for the database
$USERNAME = 'username';

// password for the database
$PASSWORD = 'password';

// name of the database containing WordPress
$DATABASE = 'wordpress';

// host for the database (99% chance it will be localhost)
$HOST = 'localhost';

// END OF CONFIG

if (substr($GALLERYBASEPATH,-1)!='/' && $GALLERYBASEPATH!='')
{
$GALLERYBASEPATH = $GALLERYBASEPATH . '/';
}

$link = mysql_connect($HOST,$USERNAME,$PASSWORD) or die('Cannot connect to database '.$HOST);
$x = mysql_select_db($DATABASE,$link) or die('Cannot select database '.$DATABASE);

// convert the gallery
$result = mysql_query('SELECT * FROM '.$WP_PREFIX.'mygallery') or die('Cannot execure queries. Is the prefix correct?');
while ($row = mysql_fetch_assoc($result))
{
$row['longname'] = addslashes($row['longname']);
$row['galdescrip'] = addslashes($row['galdescrip']);
echo 'INSERT INTO '.$WP_PREFIX.'ngg_gallery (gid,name,path,title,galdesc,pageid,previewpic,author) VALUES ('.$row['id'].',\''.$row['name'].'\',\''.$GALLERYBASEPATH.$row['name'].'\',\''.$row['longname'].'\',\''.$row['galdescrip'].'\',\''.$row['pageid'].'\',\''.$row['previewpic'].'\',0);' . '
';
}

// convert the images
$result = mysql_query('SELECT * FROM '.$WP_PREFIX.'mypictures INNER JOIN '.$WP_PREFIX.'mygprelation ON '.$WP_PREFIX.'mypictures.id='.$WP_PREFIX.'mygprelation.pid INNER JOIN '.$WP_PREFIX.'mygallery ON '.$WP_PREFIX.'mygallery.id='.$WP_PREFIX.'mygprelation.gid');

while ($row = mysql_fetch_assoc($result))
{
$row['description'] = addslashes($row['description']);
echo 'INSERT INTO '.$WP_PREFIX.'ngg_pictures (pid,galleryid,filename,description) VALUES ('.$row['pid'].','.$row['gid'].',\''.$row['picturepath'].'\',\''.$row['description'].'\');' . '
';
}

// convert pages
$result = mysql_query('SELECT id,pageid FROM '.$WP_PREFIX.'mygallery');
while ($row = mysql_fetch_assoc($result))
{
echo 'UPDATE '.$WP_PREFIX.'posts SET post_content=\'[nggallery id='.$row['id'].']\' WHERE ID='.$row['pageid'] . ';
';
}

// convert page with master gallery
$result = mysql_query('SELECT * FROM '.$WP_PREFIX.'posts WHERE post_content=\'[mygallistgal]\'');
while ($row = mysql_fetch_assoc($result))
{
echo 'UPDATE '.$WP_PREFIX.'posts SET post_content=\'[album template=extend]\' WHERE ID='.$row['ID'] . ';
';
}

There are a number of caveats you should be aware of:

  • Gallery pages are updated, so they contain the new gallery tag. If there is any other text on a page, this text is lost
  • The page looks for the master gallery page (the page with links to all galleries. It will only find it if this page does not contain any other text. If the last code block does not give any results, you have to change this page manually

If you visit your gallery pages now, the should work, only the thumbnails are not displayed. To fix this, I’ve made a second script.


error_reporting(E_ALL);
$prefix = '/home/www/wordpress_mu/wp-content/myfotos/daniel';
$dirs = scandir($prefix);

foreach ($dirs as $dirname) {
if ($dirname=='.' || $dirname=='..') continue;
$dir = $prefix.'/'.$dirname;
if (is_dir($dir)) {

if ($dh = opendir($dir)) {
echo $dir . " open
";

if (is_dir($dir.'/tumbs')) {
if ($dh2 = opendir($dir.'/tumbs')) {

while (($file = readdir($dh2)) !== false) {
if (substr($file,0,3)=='tmb') {
$newname = str_replace('tmb','thumbs',$file);
$r = rename($dir.'/tumbs/'.$file,$dir.'/tumbs/'.$newname);
echo "filename: $file to $newname : rename: $r
";
}
}
// rename tumbs dir
$r = rename($dir.'/tumbs',$dir.'/thumbs');
echo $dir . " rename " .$r."
";
}
closedir($dh2);

}
closedir($dh);
}
}
}

Just change the prefix variable, to point to the path where all galleries are located. This script will rename all thumbnail directories immediately.

A script to fix Geo Mashup update

On one of my web logs, I use a map to display the route of my travels. Each post is geo-tagged, so places can be connected with lines. It’s a very nice feature for a travel blog, thanks to the Geo Mashup plugin for WordPress. I recently updated the Geo Mashup plugin to a new version. For this version, the locations had to be converted to the new format. The result of this upgrade was that my route was no longer correct: posts seemed randomly connected to each other.

After some investigation, I found that Geo Mashup uses a special table to link posts and location to each other. This link also has a date and time connected to it. The results are ordered using this date. During the conversion, each link had the date of the conversion. Therefore, the results were displayed random.

I wrote a quick PHP script to fix this problem. This script looks at the time the original post was made, and updates the Geo Mashup table.


// CONFIG

// username for the database
$USERNAME = 'username';

// password for the database
$PASSWORD = 'password';

// name of the database containing WordPress
$DATABASE = 'wordpress';

// host for the database (99% chance it will be localhost)
$HOST = 'localhost';

// END OF CONFIG

$link = mysql_connect($HOST,$USERNAME,$PASSWORD) or die('Cannot connect to database '.$HOST);
$x = mysql_select_db($DATABASE,$link) or die('Cannot select database '.$DATABASE);

$result = mysql_query("SELECT * FROM wp_geo_mashup_location_relationships");
while($row = mysql_fetch_assoc($result)
{
$result2 = mysql_query("SELECT post_date FROM wp_posts WHERE id=".$row['object_id']);
mysql_query("UPDATE wp_geo_mashup_location_relationships SET geo_date=\'" . $row2['post_date'] . "\'");
}

After running this script, the problem was fixed, and my map displayed the correct route.

WP-super-cache on lighttpd

Because my web server does not have a lot of processing power, dynamic web pages can sometimes be a bit slow. Especially if the server is busy. Serving static HTML pages is a lot better than serving PHP pages. In fact, most of the blogs on this site are just static “copies”. Using a web site downloader, such a HTTrack, I’ve made an exact copy of the web sites. This copy is served, instead of the dynamic content.

This server blog is a live blog, so I cannot make a static copy. But with the WordPress plugin WP-super-cache you can make caches of all pages. If a specific page is available in the cache, the cached paged in served. This saves a lot of executing time; no need to go to the database and get all the content. The cache has a time-out, so at regular intervals the caches are refreshed. And if a new post or comment is made, the cache is refreshed too. So users of the site won’t see any difference.

WP-super-cache supports two modes: the mod_rewrite and PHP. PHP will always work, but pages are served via PHP. The PHP script checks if a cache file exists, and serves that. This is still a lot faster than when PHP has to contact the database to build the page. But is still uses PHP. The other mode is mod_rewrite, but this is very specific to an Apache webserver. Because this site is running lighttpd, I had to search for the correct instructions. There are sites that describe a solution. However, after some debugging, I found out the solution doesn’t actually work (although it seems to work because the PHP mode is used). Also, when running WordPress as a multiblog site, images are also served using PHP. The solution below eliminates any executing of PHP when there is a static page available.

A special module, mod_magnet, in needed for lighttpd. First, install mod_magnet for lighttpd:
sudo aptitude install lighttpd-mod-magnet
Next, enable mod_magnet by runnuing:
sudo lighty-enable-mod magnet

Next, add a magnet rule to a site. In a previous post I explained how to add a site to the lighttpd configuration. To enable magnet for a site, a line needs to be added. The complete configuration then looks like this:

$HTTP["host"] =~ "server.vijge.net" {
server.document-root = "/home/www/wordpress"
var.wp_blog = 1
magnet.attract-physical-path-to = ( server.document-root + "/rewrite.lua" )
include "wpmu-rewrite.conf"
}

As you can see, a file called rewrite.lua is used. Create a file with this name in the WordPress installation directory. Paste the following code into the file:
[code lang=”lua”]
function serve_html(cached_page)
if (lighty.stat(cached_page)) then
lighty.env[“physical.path”] = cached_page
–print(“Serving cached page: ” .. cached_page)
return true
else
return false
end
end

function serve_gzip(cached_page)
if (lighty.stat(cached_page .. “.gz”)) then
lighty.header[“Content-Encoding”] = “gzip”
lighty.header[“Content-Type”] = “”
lighty.env[“physical.path”] = cached_page .. “.gz”
–print(“Serving gzipped page: ” .. cached_page .. “.gz”)
return true
else
return false
end
end

if (lighty.env[“uri.scheme”] == “http”) then
ext = “.html”
else
ext = “-https.html”
end

cached_page = lighty.env[“physical.doc-root”] .. “/wp-content/cache/supercache/” .. lighty.request[“Host”] .. lighty.env[“request.orig-uri”] .. “/index” .. ext
cached_page = string.gsub(cached_page, “//”, “/”)

attr = lighty.stat(cached_page)

if (attr) then
query_condition = not (lighty.env[“uri.query”] and string.find(lighty.env[“uri.query”], “.*s=.*”))
user_cookie = lighty.request[“Cookie”] or “no_cookie_here”
cookie_condition = not (string.find(user_cookie, “.*comment_author.*”) or (string.find(user_cookie, “.*wordpress.*”) and not string.find(user_cookie,”wordpress_test_cookie”)) or string.find(user_cookie, “.*wp-postpass_.*”))
if (query_condition and cookie_condition) then
accept_encoding = lighty.request[“Accept-Encoding”] or “no_acceptance”
if (string.find(accept_encoding, “gzip”)) then
if not serve_gzip(cached_page) then serve_html(cached_page) end
else
serve_html(cached_page)
end
end
end

Finally, add the following line to the wp-config.php file in the WordPress directory:
define('WP_CACHE', true);
Now you can go to the WordPress admin pages and configure everything. The mode setting in the admin pages does not have any effect. The rewrite.lua is always used. I recommend setting the mode to PHP, because setting it to mod_write will give an error that mod_rewrite is not enabled.

Running WordPress with lighttpd

In most of the tutorials about WordPress, it presumes you have Apache as a web server. I use lighttpd, however. Especially on a server with not a lot of power, this can make a big difference. Getting WordPress to run on lighttpd is not very difficult. You can follow the normal installation instructions. In fact, you only need to do something special if you want to use permalinks without index.php in it, and/or want to have the multisite feature in WordPress 3 (or the older WordPress MU). The instructions below are for WordPress 3 Multisite with multi blogs.

First, configure your site in the lighttpd config file. I use the (almost) default configuration file, /etc/lighttpd/lighttpd.conf At the end of this file, I placed
include "sites.conf"
This allows to have all information about the different sites in a separate config file. To add a WordPress site, simply add
$HTTP["host"] =~ "server.vijge.net" {
server.document-root = "/home/www/wordpress"
var.wp_blog = 1
include "wpmu-rewrite.conf"
}

The host is the address of the site. The document-root is the location where WordPress is installed. var.wp_blog is the ID of the blog. The ID can be found in the Network admin section of WordPress. Click on the top-right on the Admin drop down menu and choose Network Admin. Choose All sites from the left menu. Here, all blog sites are listed. The link for each site contains the ID of the blog.
wpmu-rewrite.conf is a file that does the rewriting for permalinks and files in a multisite setup. The contents of this file is:
url.rewrite-once = (
"^/(.*)?/?files/(.*)" => "/wp-content/blogs.dir/"+var.wp_blog+"/files/$2",
"^/(wp-(content|admin|includes).*)$" => "/$1",
"^/favicon.ico$" => "$0",
"^/xmlrpc.php$" => "$0",
"^/(.*)$" => "/index.php/$1",
)


Save the files sites.conf and wpmu-rewrite.conf in the /etc/lighttpd directory and restart the web server, and it should work. The trick with setting the ID for each blog allows loading images without the need of PHP. You can also use the following code, in which case you do not need var.wp_blog:
"^/(.*)?/?files/(.*)" => "wp-includes/ms-files.php?file=$2", With this code, for every image, a PHP script is executed.

Updating WordPress and plugins with SSH

WordPress allows upgrade of itself and of plugins via a nice web interface. By default, it offers the option between FTP and FTPS. That’s very nice except that my server does not use FTP, only SSH. Fortunately, WordPress can support SSH if the correct package is installed. On a Debian server, simply run:
sudo aptitude install libssh2-php
Then restart the web server. If you now go to the upgrade page, there is an option to use SSH. You can either use a password-based login, or a public/private key-based login.

Upgrading WordPress MU to WordPress 3.0

The various site on this server are powered by WordPress. Because there are multiple sites, I use WordPress MU (multi user). This fork of WordPress allows running multiple blogs from one installation, either in sub directories, or (in my case) on sub domains.

A couple of days ago WordPress 3 was released. WordPress MU is now integrated into WordPress. This is good news, because now there is only one WordPress, and I can easily upgrade to new versions, without having to wait for an updated WordPress MU version. But the first task, upgrade WordPress MU to WordPress 3.

There is a very handy auto update feature. You simply have to click a link and the update takes place, or so is the theory. That sort-of worked, but a few changes were needed. For the upgrade to succeed, the web server must have permission to write to the the directory where WordPress is installed. By default, I disabled this, and only allow writes to certain folder. Simple (temporarily) giving every one write access solved that problem:

chmod -R o+w wordpress/

After that, the upgrade went fine. A few things were needed to make everything work. First, I do not run Apache as a web server, but lighttpd. This makes permalinks and uploaded files a bit difficult. I have the following lighttpd config to make all this work:

url.rewrite-once = (
"^/(.*)?/?files/$" => "index.php",
"^/(.*)?/?files/(.*)" => "wp-includes/ms-files.php?file=$2",
"^/(wp-.*)$" => "$1",
"^/([_0-9a-zA-Z-]+/)?(wp-.*)" => "$2",
"^/([_0-9a-zA-Z-]+/)?(.*\.php)$" => "$2",
"(\?.*)$" => "index.php$1",
"." => "index.php"
)

And a few settings had to be added to the wp-config.php file. The following must be added:

define('MULTISITE', true);
define('SUBDOMAIN_INSTALL', true);

The first setting tells WordPress that I run a “multisite”, what used to be the “MU”. The second option tells WordPress that each blog has its own subdomain, as opposed to its own sub directory. Without this last line, permalinks do no work, and all links are redirected to the main site (with no subdomain).

Other that that, the upgrade went pretty fine. Actually, I’m quite impressed with how easy the upgrade of WordPress.