Installing modules for a specific Python version in your Mac OSX Lion

Note: I am using Mac OSX 10.7.3 with XCode 4.3.2

I came across this problem lately where I need a certain module to run a script that is only compatible with Python 2.6. My default Python version is 2.7. So if I install using easy_instal, the system will install the module for Python 2.7 only. So in this case, when I run Python 2.6, I don’t have the module that I just installed. Then I found out how easy it is to do it.

In your mac, you have multiple versions of Python installed:

$ cd /System/Library/Frameworks/Python.framework/Versions
$ ls
$ 2.3     2.5     2.6     2.7     Current

Which means that you also have multiple version of easy_install. So if you type easy_install and ‘double tab’. You will get:

$ easy_install
$ easy_install      easy_install-2.5  easy_install-2.6  easy_install-2.7

This represents easy_install for each version.

The obvious conclusion is:
e.g. If you want to install a module for a Python 2.6:

$ sudo easy_install-2.6 <modulename>

Simple Comet Implementation Using PHP and jQuery

I have been researching about the Comet application model recently. I stumbled upon a great article from Zeitoun.net in which their AJAX implementation example is written in PHP and ProtoType (a JavaScript Framework). I decided to modify the Classic AJAX/ProtoType Implementation to use  jQuery – my JavaScript framework of choice thus far. This is only the client side of the entire architecture when you’re dealing with huge databases and web services but at least this gets you started.

We’ll be using 3 files here:

  • backend.php
  • data.txt
  • index.html

Both backend.php and data.txt stayed the same as the original example. I only modified index.html’s JavaScript block to look  like this:

var Comet = function (data_url) {
this.timestamp = 0;
this.url = data_url;
this.noerror = true;

this.connect = function() {
var self = this;

$.ajax({
type : 'get',
url : this.url,
dataType : 'json',
data : {'timestamp' : self.timestamp},
success : function(response) {
self.timestamp = response.timestamp;
self.handleResponse(response);
self.noerror = true;
},
complete : function(response) {
// send a new ajax request when this request is finished
if (!self.noerror) {
// if a connection problem occurs, try to reconnect each 5 seconds
setTimeout(function(){ comet.connect(); }, 5000);
}else {
// persistent connection
self.connect();
}

self.noerror = false;
}
});
}

this.disconnect = function() {}

this.handleResponse = function(response) {
$('#content').append('
<div>'
+ response.msg + '</div>
'
);
}

this.doRequest = function(request) {
$.ajax({
type : 'get',
url : this.url,
data : {'msg' : request}
});
}
}

var comet = new Comet('./backend.php');
comet.connect();

For more details, check out the article where I based this from. Happy hacking!

Download:

Thoughts, moving on to mig33

Another chapter of my career is starting to unfold. After working at Yolk for 8 months, I’m moving on to mig33. My new job will commence on 17th October, 2011; which also roughly marks my 3rd year working and living in Singapore.

Father time is indeed deceiving, how he passes by so fast without noticing him. I can vividly remember my first day at my first job in Singapore when I was looking for muvee‘s office, getting lost, going to City Hall instead of Bugis. Until I finally found the office, I was then warmly welcomed by two great engineers/colleagues who inspired me (Tim and Tjerk).

Now I’m very excited to start a new job again. I’m gonna be working on exciting projects that has over 50 million users, which is something new for me. It’s about time to study and work on technologies like Hadoop, Memcached, Redis, and MongoDB. Then get my skill levels up on Python. Also, I’ll sharpen my OOP and Design Patterns knowledge.

mig33 will be my 3rd company in Singapore. I feel very blessed to be able to work again with great ex-colleagues: Tim and Ali. Good luck to me. :D

Fibonacci in Python compared to C-style Languages

I have played around with Python these past few months. Learning Python will make you realize some of the not so good things about PHP and other similar C-style Languages. But I’m not going to delve into their comparison, you can find a good article about that subject here.

What got me intrigued is how I was able to implement the classic Fibonacci function in Python without having to use an extra variable that should be present in both PHP or Javascript implementation.

First I’ll show you how it is implemented in both JavaScript and PHP:

JavaScript: (Copy and run in your browser’s JS console to see it in action now!)

<script type="text/javascript">
function fib(n)
{
    var a = 0, b = 1;
    while(b < n) {
        console.log(b);
        sum = a + b;
        a = b;
        b = sum;
    }
}

fib(60);
</script>

PHP:

<?php
function fib($n)
{
    $a = 0, $b = 1;
    while($b < $n) {
        echo $b . PHP_EOL;
        $sum = $a + $b;
        $a = $b;
        $b = $sum;
    }
}

fib(60);
?>

You’ll notice that both JavaScript and PHP use the following variables: n, a, b, and sum. Variable n will be the size or the limit of the series while a, b and sum are there to help determine what numbers to display.

Now it’s Python’s turn:

def fib(n):
    a, b = 0, 1
    while(b < n):
        print(b)
        a, b = b, a + b
       
fib(60)

For Python, it doesn’t need to use the extra variable sum. This is because you can assign variables simultaneously in Python just like in Ruby and Perl.

This is one of those little things that we might overlook when building applications. Yes, we only saved one variable in this Fibonacci function. But how much more when we build more complex applications? When we’ll need to strategically assign variables in large and scalable applications?

Implementing Inheritance for jQueryUI Dialog Boxes

First of all, nothing fancy here. Just want to show you a good way to implement Inheritance on jQueryUI Dialog Boxes. Here is one way to take advantage of Javascript’s Inheritance capability. We can use inheritance for jQuery UI dialog boxes – e.g. we have the parent ‘DialogBox’ which will have the basic properties like width, height, border colour, border thickness, close box, etc. Then all these basic properties of the parent ‘DialogBox’ will be inherited by its children classes like ‘MessageBox’, ‘LoginBox’, ‘EditBox’, and ‘UploadBox’. These children classes will have its own unique properties as well. Which will make the implementation look like this:

var dbox = new StatusMessageBox('message here..'); // this will initialize the message dialog box
dbox.render(); // this will render the message dialog box

Time to dissect the classes. Let’s start with the parent class ‘DialogBox’ – this is where all the basic and common properties will be set. Please refer to the code comments for more details:

var DialogBox = function(properties, attr) {
this.properties = properties;
this.attr = attr;
}
DialogBox.prototype.preRender = function() {
// do something before rendering the dialog box
}
DialogBox.prototype.postRender = function() {
// do something after the redering the dialog box
}
DialogBox.prototype.render = function(appendElt) {
//this.preRender(this.dialogContent);

var appendElt = (appendElt) ? appendElt : $('#container');
var self = this;

var defaultAttr = {
'class' : 'dialog_box'
};
var defaultProperties = {
'title' : 'Message',
'width' : '350',
'height' : 'auto',
'modal' : true,
'resizable' : true,
'buttons' : {
'OK' : function() {
$(this).dialog('close');
}
},
'open' : function() {
self.postRender();
},
'beforeClose' : function() {
//$(this).dialog('destroy');
}

};

// overwrite the default properties and attributes if necessary
$.extend(defaultProperties, this.properties);
$.extend(defaultAttr, this.attr);

// create the element
var dialog = $(document.createElement('div')).attr(defaultAttr);

this.dialogContent.appendTo(dialog);

// append the box to the parent element
dialog.appendTo(appendElt);

// apply the dialog box properties
dialog.dialog(defaultProperties);

 // make this accessible outside
this.dialogObj = dialog;
}

As you can see, the base class is setting up the possible common properties among dialog boxes. Let’s move on to the ‘StatusMessageBox’ class below. This type of dialog box will prompt for messages e.g. error or success messages. You can initialize its message property which will set the message to be prompted by the message box. ‘StatusMessageBox’ is also inheriting its basic properties from its parent: ‘DialogBox’.

/**
* Display simple status message
*
*/

var StatusMessageBox = function(msg) {
// create the dialog box content
var defaultMsg = (msg) ? msg : 'default message';
this.dialogContent = $(document.createElement('p')).html(defaultMsg);
}
/**
* inherit from DialogBox
*/

StatusMessageBox.prototype = new DialogBox();
StatusMessageBox.prototype.constructor = StatusMessageBox;

Concept is the same with the rest of DialogBox’s children like: ‘LoginBox’, ‘EditBox’, and ‘UploadBox’. Please take note that ‘UploadBox’ in the demo is dependent on uploadify and swfobject.

Suggestions and ideas for improvement will be greatly appreciated.

Time to play:

The class itself.
Live demo.

Fix for pinify’s createThumbbarButtons function bug

If you are using pinify‘s createThumbbarButtons function, and you got stuck finding ways to make it work. Then this article is for you. I’m dealing with jQuery pinify version 1.2 here.

First of all, they did a great job with pinify – it makes life easier for web developers who want or who are required to make use if IE9′s browser pinning feature. My task was to implement thumbnail preview controls in one of the sites I’m working on.

After diligently following the documentation and pinify’s example, I found myself stuck in getting it to work. Until I finally decided to dissect jquery.pinify.js. I looked for the createThumbbarButtons function and I found it with a try/catch statement. With catch statement left empty, I inserted console.log(‘createThumbbarButtons error: ‘ + e.description); under the catch(e) declaration. It ended up spitting a “Object doesn’t support property or method ‘addEventListener’” error.

Stupid IE as usual, it’s having problems with addEventListener. This error is caused by document.addEventListener(‘msthumbnailclick’, clickCurrent, false); which is only found within the createThumbbarButtons function. The solution is to replace the addEventListener statement with a good old jQuery bind:

$(document).bind(‘msthumbnailclick’, clickCurrent);

Update: Okay, the correct solution for this is to add the following tag within your head tag:

<meta http-equiv="X-UA-Compatible" content="IE=9" />

This will force the browser to use IE9 compatibility mode if it is available. And this will recognize addEventListener without any errors.

Finally it worked. =)

A weird PHP behavior

This post about the oddity on how PHP converts float to integer. This is not new to most of the PHP geeks out there, but I just want to point this out to those who are not aware of this yet. You may or may not tackle this in the future, but it’s worth knowing about.

See the PHP code below:

echo (int)((0.7 + 0.1) * 10);

At first look, what’ll come to your mind is that the output will be ’8′. But that’s not the actual output. If you’ll try to run it – the output is ’7′.
That’s not all, try:

echo (int)((0.6 + 0.1) * 10);  //outputs 7
echo (int)((0.8 + 0.1) * 10); //outputs 9

See the result? Okay, so that sums it up. ;)

My YoutubePlayer jQuery Class with Event Tracking

This Javascript class will simplify the embedding and event tracking of YouTube videos on your website.  It utilizes and requires the jQuery library (for better implementation), Google Analytics library (for event tracking) and swfobject (for YouTube embedding). So the basic Javascript implementation will be something like:

<div id="ytplayer"></div>

<script>
$(function() {
   var ytplayer = new YouTubePlayer('lNdljbYy0qk', 'ytplayer', '560', '340');    
   ytplayer.embed();
});
</script>

Where ‘lNdljbYy0qk’ is the YouTube Video ID, ‘youtube_player’ is the HTML element ID where you want to embed your video, ’560′ and ’340′ are the width and the height respectively.

Below is the code of the class itself:

//need to make this global so that onYouTubePlayerReady can easily access it
var YT_ATT_ID;

(function($) {
YouTubePlayer = function(vid, id, w, h, params, atts) {
    this.vid = vid;
    this.id = id;
    this.width = w;
    this.height = h;
    this.playerApiId = id + '_apiid';
   
    //the global variable, i should find a better way to pass the value
    YT_ATT_ID = id + '_attid';
   
    var defaultParams = {
            allowScriptAccess: "always",  allowFullScreen: "true", allowScriptAccess: "always", wmode: "opaque"
    };
   
    var defaultAtts = {
            id: YT_ATT_ID
    };
       
    this.params = $.extend(defaultParams, params);
    this.atts = $.extend(defaultAtts, atts);
}

var yto = YouTubePlayer.prototype;

yto.embed = function() {
    // we need swfobject
    try {
        swfobject.embedSWF('http://www.youtube.com/v/' + this.vid + '?fs=1&hl=en_US&enablejsapi=1&playerapiid=' + this.playerApiId,
                this.id, this.width, this.height, "8", null, null, this.params, this.atts);    
    }catch(e) {
        var txt = "javascript error";
        txt += "error description: " + err.description + "\n\n";
        txt += "click OK to continue.\n\n";
       
        alert(txt);    
    }
   
}

YouTubeTracker = {
    player: {
        state: {
            '-1':   'unstarted',
            '0':    'ended',
            '1':    'playing',
            '2':    'paused',
            '3':    'buffering',
            '5':    'cued'
        },
        obj: null,
        events: [],
        elapsedTime: 0, //the longest elapsed time
        hasEnded: false
    },
    init: function(player) {
        this.player.obj = player;
        player.addEventListener('onStateChange', 'onPlayerStateChange');       
    },
    track: function(stateNum) {    
        this.getTimeInTens(this.player.elapsedTime);
        switch(this.player.state[stateNum]) {
            case 'playing':
                // get the longest elapsed time
                this.player.elapsedTime = (this.player.obj.getCurrentTime() > this.player.elapsedTime) ? this.player.obj.getCurrentTime() : this.player.elapsedTime;
                if(-1 == $.inArray(this.player.state[stateNum], this.player.events))
                    this.player.events.push(this.player.state[stateNum]);              
                   
                break;
            case 'paused': // we don't really care about pause at this time.               
                // get the longest elapsed time
                this.player.elapsedTime = (this.player.obj.getCurrentTime() > this.player.elapsedTime) ? this.player.obj.getCurrentTime() : this.player.elapsedTime;               
                break;
            case 'cued':
                this.player.events.push(this.player.state[stateNum]);
                break;
            case 'ended':
                //this.player.events.push(this.player.state[stateNum]);
                this.player.hasEnded = true;
                break;
        }
    },
    getTimeInTens: function(elapsedTime) {     
        var res = elapsedTime / 10;
        var estimatedTime = Math.ceil(res) * 10;
        return estimatedTime;      
    },
    constructAction: function() {
        var action = location.pathname.replace(/\/+$/,"");
       
        this.player.events.push(this.getTimeInTens(this.player.elapsedTime));
        action += '#' + this.player.events.join(',');
       
        return action += this.player.hasEnded == true ? ',ended' : '';     
    }
}


})(jQuery)

// track the number of seconds, get the longest time
$(window).bind('unload', function(){
    // don't forget your GA library
    var action = YouTubeTracker.constructAction();
    try {
            // at this point be sure that you have your analytics code embedded
            pageTracker._trackEvent(YT_ATT_ID, action, 'YT_elapsedTime10secInterval');
        }catch(e) {
            //put something here
        }
});

// youtube api's primitive functions
function onYouTubePlayerReady(playerId) {
    ytplayer = document.getElementById(YT_ATT_ID);
    YouTubeTracker.init(ytplayer); 
}
function onPlayerStateChange(state) {
    YouTubeTracker.track(state);
}

There are a lot of things we can do to improve this class. But this works well for me so far.
Please don’t forget to reference your jquery, swfobject, and google analytics code. Enjoy! :D

A simple jQuery implementation of event tracking in Google Analytics

Here’s a fast and easy way to implement GA’s event tracking on your website using jQuery:
First thing we need to do is set the “rel” and “rev” attributes of the anchor tags where we we’ll implement event tracking. In this example we’ll use rel as the Category and rev as the Label (see Event Tracking guide for details about its parameters):

<a rel=”ExternalLink” rev=”WebscpeterBlog” href=”http://webscepter.com/a-simple-jquery-implementation-of-event-tracking-in-google-analytics”>easy event tracking</a>

We need to create the jQuery function that will track the click events. In this case, all anchor tag clicks are being tracked.

$(function() {
$("a").click(function() {
// the action parameter in this example is the current page url, you can change it according to your preference.
pageTracker._trackEvent(/*category*/$(this).attr("rel"), /*action*/ location.href, /*label*/, $(this).attr("rev"));
})
});

So that’s it. Simple, right? Please don’t forget your jQuery library as well as your Google Analytics code, well obviously.

Using PHP PDO with jQuery Flexigrid Plugin

Flexigrid by Paulo Mariñas in my opinion is the best data grid plugin for jQuery. It’s professional-looking, easy to implement, and straightforward. But one of the drawbacks that I encounter when implementing it in some of my projects is its use of the native PHP mysql functions. So I decided to create a PDO class for it to enhance its portability and ease of use. In this tutorial, I’m using version 1.4.2 1.2.3.

First of all, I needed to edit the main javascript plugin file itself: flexigrid.js. I added colsNameArray as seen below in line 19 of the javascript file:

p = $.extend({
colNamesArray: [],
height: 200, //default height
width: 'auto', //auto width
striped: true, //apply odd even stripes
novstripe: false,

And on line 607, so that we can easily pass the column names (‘colnames’) without needing to set it again in our server side script. Just make sure that you specify the correct column names:

var param = [
{ name : 'page', value : p.newp }
,{ name : 'rp', value : p.rp }
,{ name : 'sortname', value : p.sortname}
,{ name : 'sortorder', value : p.sortorder }
,{ name : 'query', value : p.query}
,{ name : 'qtype', value : p.qtype}
,{ name : 'colnames', value : p.colNamesArray} //this is the column names variable
];

So we’re done with flexigrid.js. Next will be the html file where we desire to display our cool flexigrid plugin.
Not much work here though, we’ll just need to make sure that all the parameters we need are there. Let’s focus on
its javascript section where we initialize our data grid. Please refer to the code comments:

$("#flex1").flexigrid
(
{
url: 'post3.php',
dataType: 'json',
colModel : [ //all of the table column names that we set here will be automatically detected without having to set them in our server-side script again
{display: 'ISO', name : 'iso', width : 40, sortable : true, align: 'center'},
{display: 'Name', name : 'name', width : 180, sortable : true, align: 'left'},
{display: 'Printable Name', name : 'printable_name', width : 120, sortable : true, align: 'left'},
{display: 'ISO3', name : 'iso3', width : 130, sortable : true, align: 'left', hide: true},
{display: 'Number Code', name : 'numcode', width : 80, sortable : true, align: 'right'}
],
searchitems : [
{display: 'ISO', name : 'iso'},
{display: 'Name', name : 'name', isdefault: true}
],
sortname: "iso", //make sure that this is set, this will determine the sortname
sortorder: "asc",
usepager: true,
title: 'Countries',
useRp: true,
rp: 15,
showTableToggleBtn: true,
width: 700,
onSubmit: addFormData,
height: 200
}
);

And on post3.php:

include_once("FlexiPDO.php");
//change me -------
$host = "localhost";
$db = "test";
$user = "root";
$pass = "";
//-----------------

try {
    $dbh = new PDO("mysql:host=$host;dbname=$db", $user, $pass);   
}catch(PDOException $e) {
    echo $e->getMessage();
}

$table = "country";

$flxPDO = new FlexiPDO();

//only 2 parameters are required
//sortname and sortorder are both initialized in the flexigrid javascript call
//implement($table, $dbh, $sortname=null, $sortorder=null, $id=null)

$flxPDO->implement($table, $dbh);

As you can see above, we’ll only need to specify the table name and set the PDO parameters needed for the database connection.
The FlexiPDO.php class takes care of business, I know some sections of it need more cleanup, but hey it’s version 1.0.

Download:

SQL file for the sample:

See Demo – nothing different from the original. Just wanted to show you that it works. :p