Dell and Blogging

Dell came through, thanks to my blogging, and replaced my laptop with a brand new Inspiron 1501.

At times I think of blogging as a useless activity. Yes, it has helped me meet new and interesting people, some of whom have become good friends. Yes, blogging has made me somewhat famous in that I sometimes run into people, offline or online, who have read my weblog. And of course blogging is a way to keep a diary and express my thoughts on a variety of topics.

Then again, I recall the PhotoDude complaining on his blog about not getting software user manuals and having them delivered the next day. But he is an A-list blogger unlike me!

So I had a rant here about my problems with my Dell laptop. A few days later, I got an email from Dell HQ from a person who had read it. Lo and behold, he offered to replace my computer. That was on July 26.

Meanwhile, my old Inspiron 5150 was repaired at the depot and returned to me. Then I went about copying everything off of it so it could be returned.

On August 6, I got a package from Dell. I opened it and found a brand new Inspiron 1501. I was a little surprised since I had assumed that the replacement would be a refurbished machine. Anyway, the machine looks good. And I must thank the Dell guy who read my blog and took the initiative to get me this computer.

I now have two brand new computers, a desktop that I built and this laptop. Amber is having second thoughts about letting me buy the desktop.

Blog Rating

So how much bad language do I use on my weblog? Is my blog safe for kids?

Via Matthew Yglesias, I find out that my blog is not appropriate for kids.

Online Dating

May be I should tone it down a little.

5 Years of Blogging

It has been five years since I started blogging. Over time, my blogging has become more sporadic, but I plan to continue. So today here are some statistics about my weblog.

It was 5 years ago today that I made my first post on my blog which was then on Blogger. This post today is the 999th one I have made here and there have been 6,678 comments on these posts.

Number of Posts Every Year

According to Sitemeter, there have been about 950,000 visits and 1,410,000 page views of my weblog.

Since I have had a Google Analytics account since April 2006, I have collected some decent statistics pertaining to my weblog. Here are some of them (I am using the whole period from April 2006 to now for these stats).

The web pages on my site that have gotten the most page views since April 2006 are as follows:

  1. Week 20: Boy or Girl
  2. Arranged Marriage
  3. Women, Gays, Sex, Islam
  4. Blog main page
  5. Urdu/اردو
  6. Moth Smoke
  7. Marriage: Between Cousins
  8. My Home Page
  9. Commenters Looking for Marriage
  10. Week 21: Level 2 Diagnostic Ultrasound

So it seems like category and monthly archives do not get many visits while most visitors coming from search engines land straight on an individual post page.

The percentage of visitors to my weblog who use different web browsers is as follows:

Internet Explorer 80.0%
Firefox 15.4%
Safari 2.3%
Opera 1.2%

The most popular search terms for getting to my blog are (in no particular order, since I combined similar queries):

  • urdu sex stories
  • arranged marriages
  • level 2 ultrasound
  • procrastination
  • firefox sucks
  • harun yahya
  • am i having a boy or girl
  • gays sex
  • crvo
  • asylum in canada

This list mostly disappointed me.

The top 10 countries from which my blog received visits are:

  1. United States
  2. Pakistan
  3. United Kingdom
  4. Canada
  5. India
  6. Australia
  7. Iran
  8. United Arab Emirates
  9. Saudi Arabia
  10. Germany

Here is a world map with the countries I have had visitors from shown in red.

Visitor Countries Map

The list of more than 200 countries follows:

Continue reading “5 Years of Blogging”

Spammy Fame

I am so famous now that spammers are referring to my blogging.

Since I added the Contact link on my weblog, I have been getting all sorts of strange emails about asylum, sex, marriage and other topics. However, what made my day last weekend was an email that someone had received. Here is the email that was forwarded to me.


I got your contact from the cyberspace on my search for a sincere man who is marriage minded and have value for love and friendship and recognized the significant of having a good and sincere relationship, so I saw your profile on and decided to contact you and I hope my proposition to be your friend will not be an exemption.

Well I am Vick Mazur as you may know me and I am from Russia, which my father is from Russia and my mother is from Liberia but at present I live and work in the Republic of Benin in a Charity Organization but I am a very good girl from a good family, my hobbies are playing basketball, reading the bible, working hard and watching movies. I dislike people that lies and dishonest things, i am not too fat and not too thin, i am average in height, i do not smoke nor drink, white in complexion with blonde hair and a nice eye ball and i am also a easy going lady but i will leave that for you to to judge when we start this friendship and I hope you are satisfy with this little details about me and I will also pray to God to make our friendship last longer without regretting knowing each others.
Please I will like to stop for now, kindly tell me more about yourself, your profession and country so as to march one more step towards forever, honest and sincere friendship and I will send you my picture when I hear from you.

You can also reply me at my yahoo email address: [email address removed]

Here is a blog post by the cousin of the person who received this email.

When I checked my spam folder later, I found out that Vick had sent the same email to my very spammy email address which I don’t use for my blog as well. Did I mention that the subject of the email was “I saw your profile on”.

So finally I have accomplished something with this blog. I have become famous. Spammers are now referring to my blog posts in their emails. Ain’t life grand!

Oh and do read my famous post and all the comments there.

Commenting Problems

Commenting using non-ASCII characters is not working right now. We hope to have a fix soon. Temporary fix is to revert a recent upgrade of the MTValidate plugin.

We are having some problems with comments right now. You cannot write any Urdu in the comments or even use single or double quote signs (smart or otherwise). Basically you cannot use any non-ASCII characters in comments.

This seems to be related to the recent upgrade of this weblog to Movable Type 3.34 and MTValidate 0.5. It is probably a result of this blog being the only Movable Type blog running native Unicode.

We are working on fixing this soon.

UPDATE: I have temporarily fixed it by reverting to MTValidate 0.4. So comment away!

محفل اور سیارہ کی فیڈ اپنے بلاگ پر

اگر آپ اردو محفل یا اردو سیارہ کی تازہ پوسٹس کے روابط اپنے بلاگ پر دکھانا چاہتے ہیں تو اس کا طریقہ کچھ مشکل نہیں اگر آپ موویبل ٹائپ، ورڈپریس یا ورڈپریس ڈاٹ کام پر بلاگ کرتے ہیں۔

اگر آپ میرے بلاگ کی سائیڈبار دیکھیں تو وہاں نیچے آپ کو اردو محفل اور اردو سیارہ کی تازہ‌ترین پوسٹس نظر آئیں گی۔ اس بات کی تجویز بدتمیز نے محفل پر پیش کی تھی۔ بدتمیز کی یہ تجویز مجھے پسند آئی اور میں نے سوچا کہ آپ میں سے کوئی اگر اپنے بلاگ پر محفل کی تازی تھریڈز دکھانا چاہے تو اس کا طریقہ بتا دوں۔

چونکہ میرا بلاگ موویبل ٹائپ پر ہے اس لئے پہلے اس کا طریقہ۔ اگر آپ موویبل ٹائپ کی ورژن 3.3 چلا رہے ہیں تو اس میں ایک پلگ‌ان ساتھ آتا ہے فیڈز ایپ لائٹ ۔ اسے استعمال کرنے کے لئے اپنے بلاگ کے مین مینو والے صفحے پر جائیں۔ وہاں آپ کو دائیں طرف نیچے Plugin Actions میں Create a Feed Widget کا ربط ملے گا۔ اسے کلک کریں۔ وہ آپ سے فیڈ کا یو‌آر‌ایل پوچھے گا۔ آپ درج ذیل یو‌آر‌ایل ٹائپ کریں:

خیال رہے کہ یہ وہ ر‌س‌س فیڈ نہیں ہے جو آپ محفل پر پوسٹس پڑھنے کے لئے استعمال کرتے ہیں۔ اس فیڈ میں تازہ تھریڈز کے ربط ہیں جبکہ پڑھنے والی فیڈ میں پوسٹس کے روابط۔

جب فیڈ کا ایڈریس دینے کے بعد آپ اگلے صفحے پر جائیں گے تو وہاں اس کا عنوان “اردو محفل” لکھا ہو گا۔ اسے ایسے ہی رہنے دیں اور یہ فیصلہ کریں کہ آپ اپنے بلاگ پر کتنی تھریڈز کے روابط چاہتے ہیں۔ میرا مشورہ ہے کہ آپ 5 یا 10 منتخب کریں۔ اب اسے سیو کر دیں۔ اس کے نتیجے میں ایک ٹمپلیٹ موڈیول بن جائے گا جس کا نام “Widget: اُردو محفل” ہو گا۔ اس ٹمپلیٹ میں یہ کوڈ ہو گا:

<div class="module-feed module">
<div class="module-content">
<MTFeed uri="">
<h2 class="module-header">اُردو محفل</h2>
<ul><MTFeedEntries lastn="5">
<li><a href="<$MTFeedEntryLink encode_html="1"$>"><$MTFeedEntryTitle$></a></li>

اب آپ اپنی Main Index ٹمپلیٹ کھولیں اور سائیڈبار کے کوڈ میں جہاں آپ محفل کے روابط چاہتے ہیں وہاں یہ کوڈ پیسٹ کر دیں:

<$MTInclude module="Widget: اُردو محفل"$>

اب اس ٹمپلیٹ کو rebuild کریں تو آپ کو اپنے بلاگ پر محفل کی تازہ پوسٹس کے روابط نظر آئیں گے۔ یہ خیال رہے کہ اگر آپ موویبل ٹائپ کی static publishing استعمال کرتے ہیں تو یہ روابط صرف اس وقت تبدیل ہونگے جب آپ کی یہ ٹمپلیٹ rebuild ہوا کرے گی۔ میں اس وجہ سے اپنی سائیڈبار کو کرون جاب کے ذریعہ ہر گھنٹے بعد rebuild کرتا ہوں۔

اب آتے ہیں ورڈپریس کی طرف کہ بہت سے اردو بلاگ ورڈپریس استعمال کرتے ہیں۔ اگرچہ ورڈپریس میں اس کام کے لئے کئی پلگ‌ان ہیں مگر مجھے سائیڈر‌س‌س آسان لگا۔ سب سے پہلے اس پلگ‌ان کو ڈاؤنلوڈ کریں اور اس کی readme.txt میں دی گئی ہدایات کے مطابق اسے نصب کر لیں۔

ورڈپریس میں سائیڈ‌ر‌س‌س کو فعال کرنے کے بعد اوپر مینو میں Presentation پر کلک کریں اور پھر سب‌مینو میں Theme Editor پر۔ اب آپ اپنے تھیم کی Sidebar کو ایڈٹ کریں۔ اگر آپ ورڈپریس میں سے اس فائل کو ایڈٹ نہیں کر سکتے تو پھر ایف‌ٹی‌پی کے ذریعہ اپنا ورڈپریس کا فولڈر کھولیں اور اس میں wp-content/themes فولڈر میں اپنے تھیم کے فولڈر سے sidebar.php ڈاؤنلوڈ کریں۔ پھر اسے نوٹپیڈ یا کسی اور ایڈیٹر میں کھول لیں۔ اس فائل میں یہ لائن تلاش کریں:

<?php wp_list_bookmarks(); ?>

اور اگر آپ ورڈپریس کی 2.1 سے پرانی ورژن استعمال کر رہے ہیں تو یہ لائن ڈھونڈیں:

<?php get_links_list(); ?>

اس لائن کے بعد مندرجہ ذیل کوڈ پیسٹ کر دیں:

<li><?php echo ujc_siderss('', 'اردو محفل', 5); ?></li>

اگر آپ ورڈپریس کے ایڈمن والے صفحے سے ایڈٹ کر رہے تھے تو فائل سیو کر لیں۔ اگر ایف‌ٹی‌پی استعمال کر رہے تھے تو فائل سیو کرنے کے بعد واپس سرور پر منتقل کر دیں۔ اب آپ کو محفل کی 5 تازہ‌ترین تھریڈز کے روابط اپنے بلاگ کی سائیڈبار پر نظر آئیں گے۔

ورڈپریس پر ایک اور بھی طریقہ ہے جو کافی کام کا ہے۔ اس کے لئے آپ وجیٹس پلگ‌ان ڈاؤنلوڈ کریں اور اس کی ہدایات کے مطابق نصب کریں۔ یہ صرف اسی صورت میں کام کرے گا اگر آپ کے بلاگ کی تھیم اس کے ساتھ موزوں ہے۔ اس پلگ‌ان کو نصب کرنے کے بعد ورڈپریس ڈاٹ کام والا نیچے دیا طریقہ استعمال کریں۔

اب آتے ہیں ان بلاگرز کی طرف جو ورڈپریس ڈاٹ کام استعمال کرتے ہیں۔ ان کے لئے طریقہ فرق ہے مگر کافی آسان بھی۔ اپنے بلاگ کے ایڈمن انٹرفیس میں مینو میں سے Presentation پر کلک کریں اور سب‌مینو میں Sidebar Widgets پر کلک کریں۔ وہاں آپ کو Available Widgets میں RSS 1 نامی ایک بلاک نظر آئے گا۔ اسے ماؤس سے کھینچ کر اوپر سائیڈبار والے بلاک میں لے آئیں۔ اب اس ر‌س‌س بلاک کے دائیں حصے میں کلک کریں تو اس کی آپشنز کی ونڈو کھل جائے گی۔ اس میں یو‌آر‌ایل کے خانے میں یہ لکھیں:

عنوان کے خانے میں “اردو محفل” اور تعداد کے باکس سے 5 کا انتخاب کریں۔ اب اس ونڈو کو بند کریں اور اپنی تبدیلیاں سیو کر لیں۔ اور بس!

اگر آپ محفل کے علاوہ اردو سیارہ کی نئی پوسٹس کو بھی اپنے بلاگ پر ظاہر کرنا چاہتے ہیں تو یہی ہدایات استعمال کریں مگر فیڈ کا یو‌آر‌ایل یہ ہو گا:

اگر آپ کو کوئی مشکل ہو تو اپنے تبصرے میں اس کی تفصیل بتائیں۔ میں کوشش کروں گا کہ آپ کی مدد کر سکوں۔

Movable Type Security Bug

Movable Type 3.33 has a script injection bug if the nofollow plugin is disabled. Comment text is no longer sanitized as it should be.

Last month, Jacques Distler brought to my attention that Movable Type 3.3 had a script injection problem. Basically, any Javascript entered in a comment would not be sanitized and would appear on the blog. For example, try typing this in the comment form:

<script type="text/javascript">alert('hi!');</script>

It looked like Movable Type was no longer sanitizing comments, which it did until version 3.2.

Since both our installations were heavily modified, we were not sure whether it was due to our code modifications or an inherent Movable Type problem. I checked at a number of other weblogs and found out that script injection was a problem at some but not at others.

I brought this bug to the attention of Six Apart, the company that makes Movable Type immediately. They confirmed the issue and clarified that it affected only those users who had disabled the nofollow plugin distributed with MT 3.33. They also asked me for 30 days before making the issue public so that they could work on a fix.

While there has not been any announcement by Six Apart on this matter, I expect that they would fix it in the bugfix release 3.34 currently being worked on in their code repository.

Meanwhile, if you are using Movable Type 3.3, here are your options. If you have the nofollow plugin enabled (which it is by default), you shouldn’t have a problem. Otherwise:

  1. Enable the nofollow plugin.
  2. Edit your templates by adding sanitize="1" to the MT comment tags, like this:
    <MTCommentBody sanitize="1"> and <MTCommentPreviewBody sanitize="1">.

UPDATE: It looks like the sanitize function is completely disabled when you disable the nofollow plugin as it isn’t sanitizing my entry text either.

UPDATE II: Movable Type 3.34 fixes the problem.

Movable Type and Unicode

Running Movable Type natively in Unicode was not as difficult as I thought but it still required a number of patches to the code.

I have been trying to get Movable Type to run Unicode natively for a while. When Movable Type was upgraded to version 3.3, I saw my chance. This new version has a lot of the needed code for encoding and decoding etc. and made my job much easier than before.

If you remember my previous travails, DBD::mysql module lacked UTF8 support. Almost immediately after my changes, the develper release of DBD::mysql finally included a UTF8 patch. But that was too late for me. Plus I am going to wait for it to be included in a regular release since DBD::mysql is somewhat complicated.

What I did was to set the UTF-8 flag for everything coming out of the database using a wrapper around the DBI module. I used Pavel Kudinov’s code for that, which is given below.

# re-implementation by Pavel Kudinov
# originally from:
package UTF8DBI    ; use base DBI    ;
package UTF8DBI::db; use base DBI::db;
package UTF8DBI::st; use base DBI::st;
sub _utf8_() {
use Encode;
if    (ref $_ eq 'ARRAY'){ &_utf8_() foreach        @$_  }
elsif (ref $_ eq 'HASH' ){ &_utf8_() foreach values %$_  }
else                     {         Encode::_utf8_on($_) };
sub fetch             { return _utf8_ for shift->SUPER::fetch            (@_)  };
sub fetchrow_arrayref { return _utf8_ for shift->SUPER::fetchrow_arrayref(@_)  };
sub fetchrow_hashref  { return _utf8_ for shift->SUPER::fetchrow_hashref (@_)  };
sub fetchall_arrayref { return _utf8_ for shift->SUPER::fetchall_arrayref(@_)  };
sub fetchall_hashref  { return _utf8_ for shift->SUPER::fetchall_hashref (@_)  };
sub fetchcol_arrayref { return _utf8_ for shift->SUPER::fetchcol_arrayref(@_)  };
sub fetchrow_array    {                 @{shift->       fetchrow_arrayref(@_)} };

With that code, I needed to replace calls to DBI module with calls to UTF8DBI module as shown in the patches below.

--- lib/MT/ObjectDriver/	2006-09-06 19:27:17.000000000 -0700
+++ lib/MT/ObjectDriver/	2006-09-06 19:23:09.000000000 -0700
@@ -7,7 +7,7 @@
package MT::ObjectDriver::DBI;
use strict;
-use DBI;
+use UTF8DBI;
use MT::Util qw( offset_time_list );
use MT::ObjectDriver;
--- lib/MT/ObjectDriver/DBI/	2006-09-06 19:26:55.000000000 -0700
+++ lib/MT/ObjectDriver/DBI/	2006-09-06 19:24:20.000000000 -0700
@@ -93,10 +93,10 @@
$dsn .= ';hostname=' . $cfg->DBHost if $cfg->DBHost;
$dsn .= ';mysql_socket=' . $cfg->DBSocket if $cfg->DBSocket;
$dsn .= ';port=' . $cfg->DBPort if $cfg->DBPort;
-    $driver->{dbh} = DBI->connect($dsn, $cfg->DBUser, $cfg->DBPassword,
+    $driver->{dbh} = UTF8DBI->connect($dsn, $cfg->DBUser, $cfg->DBPassword,
{ RaiseError => 0, PrintError => 0 })
or return $driver->error(MT->translate("Connection error: [_1]",
-             $DBI::errstr));
+             $UTF8DBI::errstr));

However, that didn’t fix all the problems. The Perl CGI module was still working in Latin1 mode. I could wrap that into a UTF8CGI module but the newer versions of CGI module support Unicode. So I just upgraded the version of CGI bundled with Movable Type. Still I needed to tell the CGI module that the character set in use was UTF-8. I could either do that every single time the CGI module was called or I could just set the default character set to UTF-8. Since this CGI module was in the Movable Type extlib folder, I decided to modify its default character set.

--- extlib/	2006-09-15 10:39:30.000000000 -0700
+++ extlib/	2006-09-15 10:39:59.000000000 -0700
@@ -517,8 +517,8 @@
$fh = to_filehandle($initializer) if $initializer;
-    # set charset to the safe ISO-8859-1
-    $self->charset('ISO-8859-1');
+    # set charset to utf-8
+    $self->charset('utf-8');

I also set the utf8 mode for writing the files to disk.

--- lib/MT/FileMgr/	2006-09-27 06:56:39.000000000 -0700
+++ lib/MT/FileMgr/	2006-09-27 06:57:36.000000000 -0700
@@ -75,6 +75,9 @@
binmode($from) if $fmgr->is_handle($from);
+    else {
+        binmode(FH, ":utf8");
+    }
## Lock file unless NoLocking specified.
flock FH, LOCK_EX unless $fmgr->{cfg}->NoLocking;
seek FH, 0, 0;

These changes caused problems with file uploads through the Movable Type interface. I expected this since I have run into this problem with PHP and mbstring as well. The following patch fixed this issue.

--- lib/MT/App/	2006-10-08 21:17:11.000000000 -0700
+++ lib/MT/App/	2006-10-08 21:17:37.000000000 -0700
@@ -8334,6 +8334,7 @@
$app->validate_magic() or return;
my $q = $app->param;
+    $q->charset('iso-8859-1');
my($fh, $no_upload);
if ($ENV{MOD_PERL}) {
my $up = $q->upload('file');

Then it was time to comment out the liberally sprinkled code to switch off the utf8 flag in Movable Type.

--- lib/MT/I18N/	2006-09-16 20:22:22.000000000 -0700
+++ lib/MT/I18N/	2006-09-16 20:23:26.000000000 -0700
@@ -292,7 +292,7 @@
$text = $class->_conv_to_utf8($text, $enc) if $enc ne 'utf-8';
$text = substr($text, $startpos, $length);
-    Encode::_utf8_off($text);
+#    Encode::_utf8_off($text);
$text = $class->_conv_from_utf8($text, $enc) if $enc ne 'utf-8';
@@ -322,7 +322,7 @@
-    Encode::_utf8_off($text) if $to eq 'utf-8';
+#    Encode::_utf8_off($text) if $to eq 'utf-8';

Finally I had to make changes to the MTHash plugin that I use to force comment previews. The Digest::SHA1 module only accepts bytes, therefore, the UTF-8 characters had to be encoded as bytes before being passed to any functions in the module. Here is my patch:

--- lib/MT/App/	2006-09-16 21:01:21.000000000 -0700
+++ lib/MT/App/	2006-09-16 21:03:08.000000000 -0700
@@ -266,9 +266,10 @@
require Digest::SHA1;
my $sha1 = Digest::SHA1->new;
-     $sha1->add($q->param('text') . $q->param('entry_id') . $app->remote_ip
-                . $q->param('author') . $q->param('email') . $q->param('url')
-                . $q->param('convert_breaks'));
+     my $octets = Encode::encode_utf8($q->param('text') . $q->param('entry_id') . $app->remote_ip
+                                      . $q->param('author') . $q->param('email') . $q->param('url')
+                                      . $q->param('convert_breaks'));
+     $sha1->add($octets);
my $salt_file = MT::ConfigMgr->instance->PluginPath .'/salt.txt';
my $FH;
open($FH, $salt_file) or die "cannot open file <$salt_file> ($!)";
--- plugins/	2006-09-16 20:29:22.000000000 -0700
+++ plugins/	2006-09-16 20:57:22.000000000 -0700
@@ -32,7 +32,8 @@
or return $ctx->error($ctx->errstr);
my $sha1 = Digest::SHA1->new;
-  $sha1->add($content);
+  my $octets = Encode::encode_utf8($content);
+  $sha1->add($octets);
my $salt_file = MT::ConfigMgr->instance->PluginPath .'/salt.txt';
open(FH, $salt_file) or die "cannot open file <$salt_file> ($!)";

One thing that I still need to do is to fix the Serializer and Un-serializer used by Movable Type plugins.

Awards and Carnivals

Go nominate blogs for Brass Cresecent awards. Also, contribute to Carnival of Islam in the West. Include the real-time Carnival of Brass in your blog sidebar and read Muslims in the West blogs together in your feed reader.

Since the end of the year is near, it is again time for the Brass Crescent Awards for the Islamicate blogosphere.

Brass Crescent Awards Nominations

Right now they are taking nominations for a bunch of categories until November 17. So go and nominate your favorite weblogs. Do note that a blogger does not need to be a Muslim to be nominated (and definitely not necessary for those nominating or voting).

In defining the Islamsphere, we are not relying solely on adherence to the faith, but an affinity for parts of the diverse cultural fabric that Islam embraces and is embraced by worldwide.

Abu Sahajj, the owner of the Wa Salaam blog, started the Carnival of Islam in the West a few months ago. You can read the first and second editions of the carnival. Now it is time for the 3rd edition being hosted by Travellers on the Path of Knowledge. Do submit if you have any blog posts realting to the experience of Muslims in the West in these areas:

  • Religion and Worship
  • Marriage and Family
  • Education and Life
  • Business and Careers
  • News and Politics
  • The State of the Ummah

While on the subject of carnivals, Aziz has created a sort of “real-time” carnival called the Carnival of Brass where you can submit blog posts and media stories and there is an output feed which you can include on your blog which includes the items posted to the carnival. It updates at about one new item per day. I have included both the media and blog ones on my sidebar. If you want to include Carnival of Brass in your blog sidebar, please read Aziz’s FAQ.

Abu Sahajj also has an Islam in the West feed which aggregates quite a few Muslim blogs in the West. Just subscribe to the feed using your favorite feed aggregator and you can read a lot of Muslim blogs.

UPDATE: This month’s edition of the Carnival of Islam in the West is now up.

Geotagging Photos

Armed with a GPS and a digital camera with a love of hiking, it is time to store the location I take my photos into the images and then show them on a map. I review several software which can do this and present my workflow.

Now that I have a GPS, I can have some fun with hiking and photography. The idea is to record my position on the GPS while hiking (i.e., the tracklog). This will provide me (and others) with a good record of different hikes. In addition, I can pinpoint the location where I took photographs and hence tag the photos with those coordinates (i.e., geotagging).

Here is the procedure I use for the purpose:

  1. Set the GPS tracklog setting. My GPS allows time, distance and auto. Time and distance options are for specifying the time or distance respectively after which the GPS position should be recorded in the tracklog. Auto mode tries to determine the optimal interval automatically, though Garmin does not provide any information about how it determines the optimum interval. The preferable mode is specifying the time interval. If you are walking, then a time interval of 6 seconds should give you maximum accuracy and in my case the tracklog won’t fill up to its maximum of 10,000 points for about 17 hours. This just needs to be decided on once.
  2. At the start of the hike, set the camera clock to the time from the GPS. You can either use UTC (popularly known as GMT) or your local time zone. I prefer to set the camera to UTC since then I don’t have to get into the hassle of changing camera time at the end of daylight savings or when I travel.
  3. Sometimes, I also like to take a photograph of the GPS screen with the time showing so that I can later compare the difference in their clocks.
  4. Reset the tracklog.
  5. Mark waypoints on the hike for features, like parking, trailhead, scenic view, waterfall, etc. Write some shorthand in the waypoint name on the GPS to remember the reason later.
  6. Take photographs whenever I feel like it.
  7. Go home and upload the waypoints and tracklog from the GPS to my computer.
  8. Upload the photographs from my camera.
  9. Run RoboGEO to geotag the images and create a Google map.
  10. Use GPS Visualizer to create an elevation profile for a hike.
  11. Upload everything to my web server.

One thing I also want to do is to create a database of the tracklogs of trails which I hike. For this purpose, I will be providing you the GPX file for my hikes here. However, it would probably be a good idea to upload them to public repositories of trails. Does anyone know any such good sites?

Before using this technique on a hike, I decided to test it with a walk locally. I set my GPS tracklog setting to “auto”. With this setting the average time between tracklog points was 12 seconds but there was one interval of 2minutes and 57seconds, probably when I was sitting.

I tried several software solutions for geotagging and creating maps with the photos. Here is my review of them.


Rich Owings told me about TopoFusion which is a great software with lots of features. But their PhotoFusion is not up to par. It is super-easy to use. All you do is load the tracklog either directly from your GPS or from a GPX file on your computer, point PhotoFusion to the folder where the photographs are and voila!

However, it does not output the coordinates of the photo locations in any form (EXIF data of the images or as waypoints in a GPX file). Hence, we are limited to its own output which shows the locations on USGS aerial and topographic maps with camera icons.

Another problem is that the camera icons do not stand out and can be difficult to spot in the web page output. We also have no options to set the size of the map image for the web output, so we have to set the size of the main TopoFusion window to whatever size we want the final map image to be.

if I provide an output folder in the options for PhotoFusion, thumbnails and all other files are created there. But the original photos are not copied. However the link to full photos in the web page is to the output directory, so those links don’t work without copying the original images yourself.

Also, thumbnails are created but you have to specify both width and height and so there might be a black band if the aspect ratio is not correct. You can see that in the one landspace format thumbnail in my test scenario.

Finally, the output of PhotoFusion is a static map image and the user cannot pan, zoom out or do other interesting things with the map like you can with Google Maps.

One good thing about it is that the output includes an elevation profile and other useful info (like distance travelled etc.)

Here is my test of TopoFusion.

WWMX and GPS Visualizer

Let’s now look at some free solutions. While there are several free solutions, none of them are as easy to use or as complete for this task. One has to use multiple software: one for geotagging the photos and another for creating maps.

The best solution for the map creation is GPS Visualizer, an online tool that does almost anything you could think of.

But before using that, I needed to geotag the photos using my tracklog. I checked two programs for that.

WWMX Location Stamper is a Windows-based application which is simple to use but does not have many features. For example, the camera must be set to the same time as your computer and you cannot specify any difference in the clocks of the GPS and your camera. It needs a GPX file with a tracklog as input unless you use WWMX TrackDownload which can get the tracklog directly from a GPS. It shows the track and photo locations on a map within the application (I think the map requires you to be connected to the Internet) and then stores the location info in the image EXIF.

Another program for geotagging is, a command-line Perl tool to extract location info from a tracklog and write to EXIF. It has a lot of options. However, it is command-line and requires Perl installation on your computer. Also, you can’t check the results in a map. One pro for this tool is that it is OS-independent.

Once I had the images with their coordinates in the EXIF info, I had to get it in a format that would be acceptable for GPS Visualizer. For the tracklog, I could use the GPX format, but for the photo information, I needed CSV as described here and here. I wrote a short Perl script to do that using Image::ExifTool.

Now comes the time to get GPS Visualizer’s Google Maps form to generate the map. If you are going to fill out the same form again and again, it helps to use the Firefox extension Form Saver to store the form data so you don’t have to select the same options every time.

And finally using the GPX file, I created an elevation profile of my walk.

Here is the page with all the results.

So you might be thinking why go through all this hassle. First, it is free. Second, GSP Visualizer has lots of options and can do almost anything: Google Maps, Google Earth, SVG or JPEG maps, topographic, aerial, street maps, all kinds of profile graphs, etc. And you can control the presentation in detail. Take a look at the map linked to above. In addition to the Google maps, it also has USGS topographic and aerial maps as well as some imagery from NASA.

The downside is the amount fo time/effort used to create a map every time. Also, I would be dependent on another website to create and display my maps.

I do plan to use GPS Visualizer to create elevation profiles and other special maps, but it is too much work for regular stuff.


RoboGEO looks good and does lots of stuff related to geotagging. You can set the location of your photos manually using Google Earth, or set it using GPS waypoints or use the tracklog. It stores the location info in the EXIF fields or can even stamp the location on the image itself. The output can also be in several formats: Google Maps, Google Earth, GPX/CSV, Flickr, ESRI shapefiles, etc.

For Google maps, the output is in the form of a web page, but it also creates an XML file with all the data in case you want to use XSLT to create your own web page. There is also an option for string substitutions in the generated web files if you want to customize. These options are not as good as having a templating system for web page generation, but they do provide ways to customize the web page code.

I used the string substitution option to add USGS topographic and aerial maps to my map pages. I got the required code to do this from GPS Visualizer and Acme Mapper.

The demo version of RoboGEO is sort-of crippleware as it adds big random error to photo locations and tracklog points. However, I liked it enough after trying it out that I immediately bought it.

Another gripe I have with RoboGEO is that it stores output files in the Program Files folder.

One feature I would really like to see in RoboGEO is to be able to put the waypoints in my GPX files on the map as well. This would help by pointing out parking, trailhead, scenic view, waterfalls, or other features on a hike on the map. I emailed Tim Helton about this and he’s agreed to put it on his to-do list.

Before I show you the map from my test created using RoboGEO, if you are overwhelmed with signing up for a Google Maps API key etc., you can simply create a Google Earth KMZ file embedded with the photographs using RoboGEO and put it online (example). Then just enter the URL of this file in Google Maps like this and voila!

Continue reading “Geotagging Photos”