How to Queue getURL calls to appease IE

Web analytics can be a real pain in the ass sometimes, especially with Flash. If the object you’re coding is a link then you’re required to execute two getURLs and therefore two separate calls to the browser. One link being the actual URL you’re navigating to and the other being a javascript call to an analytics function.

As I mentioned in a previous post, while Firefox is able to handle this without an issue, many times Internet Explorer will only take one. This is because Internet Explorer calls getURL() asynchronously.

Until recently I hadn’t run into the problem myself but the time inevitably came where I was saddled with the issue. The solution my coworkers have been using is to string the calls together into one javascript getURL call but that can make for some hard to read and manage code. I decided instead to write a function that would queue up the calls and send them at a specified interval.

I start off by defining the variables I’m going to need:


var linkQ:Array = new Array();
var sendInterval:Number;
var waitTime:Number = 75;

linkQ will be a multi-dimensional array that will take the link and the target. sendInterval will simply hold the setInterval id, and wait time represent the number of milliseconds to wait between sending links.

We use Hitbox so my example will be using _hbLink which takes 6 parameters: ID, Link Position (on the page), _x,_y,_width,_height. ID and Position are both strings defined by your friendly neighborhood SEO manager. I wrote a function external to the Flash app so it can be used with any site or app we host:


function hblink(linkID:String,linkPOS:String,Position:String,linkurl:String,linkurlTarget:String) {
	if (!linkQ.length) {
		linkQ.push(["javascript:_hbLink('"+linkID+"','"+linkPOS+"','"+Position+"');",""]);
		if(linkurl) {
			if(linkurlTarget) {
				linkQ.push([linkurl,linkurlTarget]);
			} else {
				linkQ.push([linkurl,"_self"]);
			};
		};
		sendInterval = setInterval(_root.sendData,waitTime);
	} else {
		linkQ.push(["javascript:_hbLink('"+linkID+"','"+linkPOS+"','"+Position+"');",""]);
		if(linkurl) {
			if(linkurlTarget) {
				linkQ.push([linkurl,linkurlTarget]);
			} else {
				linkQ.push([linkurl,"_self"]);
			};
		};

	};
};

My function takes five parameters: linkID and linkPOS coincide with _hbLink’s ID and Link Position, Position is a string I pass containing the _x,_y,_width, and _height, linkurl is the functional navigation link, and linkurlTarget is the target page. So what I would pass looks something like this:


hblink("buttonHome","navbar",String(this._x+","+this._y+","+this._width+","+this._height),'http://www.google.com','_blank');

The function separates pushes the two links (the _hbLink call and the actual URL) into the linkQ array and, if no interval is currently set, defines the interval to call the sendData function that actually executes the getURLs one at a time, waitTime seconds apart. Here’s what that function looks like:


function sendData() {
	var execCode:String = String(linkQ[0][0]);
	var execTarget:String = String(linkQ[0][1]);
	if (execTarget.length) {
		getURL(execCode,execTarget);
	} else {
		getURL(execCode);
	};
	linkQ.splice(0,1);
	if (!linkQ.length) {
		clearInterval(sendInterval);
	};
};

The sendData function only reads the first row in the array no matter how many are queued up. After it sends the getURL it removes that link from the array. This function will fire every waitTime seconds until the array is empty at which point it will clear the interval.

There’s not a lot of info out there on this topic and the few solutions I came across were overly complicated or just plain ugly. I hope this info helps somebody out.

-rG