Web Site Measurment HacksThis article can also be found in the book Web Site Measurement Hacks by Eric T. Peterson.

Hack #18

The following details a simple system for identifying a user who has deleted their cookies through the storage of a flash local shared object. The object keeps within it the value of the original unique id cookie value and the time it was stored. The system also sets a secondary cookie to be passed through page requests and to provide an indicator of when the flash should be embedded in the page through it’s absence.

Test Results

*The results of a working example will appear here once I get it working in Wordpress.

If the two cookie values are the same it means you currently have the same UID Cookie used when the Flash local shared object was stored. Clear your cookies and hard reload the page to see how they will differ.

You can also see the difference by looking at your Apache and FlashID cookies for www.visioactive.com.

The Javascript

The script below tests for when the flash movie should be embedded in the page and provides a function for setting the secondary cookie. There are three main configuration parameters:

  • myUIDCookie - The name of the unique id cookie employed on your site. The default for Apache’s mod_usertrack module is “Apache”.
  • myUIDFlashCookie - The name you wish to be used for the secondary cookie created by this system.
  • myTrackingURL - The url on your tracking server where the set and recover events are to be recorded.

Additionally you will need to specify the location of the flash in the object and embed tags written into the page by the script. Be sure to change the URL in both locations.

// A simple system for testing the ability to recover

// from deleted user cookie using Flash's local

// shared objects.

// Configure Cookies to use. The first is the normal

// user cookie name employed on the site. The second

// is an additional cookie to be used for identification

// of cookie removal and cross deletion tracking.

var myUIDCookie = "Apache";

var myUIDFlashCookie = "FlashID";

// Configure a trackable image request that can be

// used to count the resets. The URL must end with

// a ? or an & as the flash will be appending a few

// name value pairs.

var myTrackingURL = escape('http://www.yoursite.com/some/tracking/call?');

// Test if the Cookie set by the flash movie exists and

// if it doesn't embed it while passing it TrackingURL and

// the value of the myUIDCookie cookie.

var Cookies = document.cookie;

if (Cookies.indexOf(myUIDCookie + "=") != -1) {

// myUIDCookie does exist - system requires it even if it is a new one

var CookieStart = Cookies.indexOf(myUIDCookie + "=") + myUIDCookie.length + 1;

var CookieEnd = Cookies.indexOf(";", CookieStart);

if (CookieEnd == -1) CookieEnd = Cookies.length;

var myUIDCookieValue = Cookies.substring(CookieStart, CookieEnd);

if (Cookies.indexOf(myUIDFlashCookie + "=") == -1) {

// myUIDFlashCookie doesn't exist embed the flash

document.write('<object classid="clsid:d27cdb6e-ae6d-11cf-96b8-444553540000" codebase="http://fpdownload.macromedia.com/pub/shockwave /cabs/flash/swflash.cab#version=6,0,0,0" width="1" height="1" id="flashtrack" align="middle">');

document.write('<param name="allowScriptAccess" value="sameDomain" />');

document.write('<param name="movie" value="/scripts/flashtrack/flashtrack.swf?UIDCookieValue=' + myUIDCookieValue + '&TrackingURL=' + myTrackingURL + '" />');

document.write('<param name="loop" value="false" />');

document.write('<param name="menu" value="false" />');

document.write('<param name="quality" value="best" />');

document.write('<param name="scale" value="noscale" />');

document.write('<param name="wmode" value="transparent" />');

document.write('<param name="bgcolor" value="#ffffff" />');

document.write('<embed src="/scripts/flashtrack/flashtrack.swf?UIDCookieValue=' + myUIDCookieValue + '&TrackingURL=' + myTrackingURL + '" loop="false" menu="false" quality="best" scale="noscale" wmode="transparent" bgcolor="#ffffff" width="1" height="1" name="flashtrack" align="middle" allowScriptAccess="sameDomain" type="application/x-shockwave-flash" pluginspage="http://www.macromedia.com/go/getflashplayer" />');

document.write('</object>');

} else {

// Code may be placed here to do something with the value of

// the flash set cookie when it already exists.

}

}

// A special function is called by the flash to set

// the cookie that returns the user id stored

function setFlashCookie(value) {

var expiration = new Date();

expiration.setTime(expiration.getTime() + (365*86400000));

document.cookie = myUIDFlashCookie + "=" + value + "; expires=" + expiration.toGMTString() + ";path=/;";

}

The Action Script

To create the flash movie to store and read from the local object first create a blank flash document and set the stage size to 1 by 1 pixels. The movie should contain nothing more than a single blank key frame with the following action script:

// FlashTrack Flash Actionscript

stop();

// create the local Shared Object to store the uid

myLocalSO = sharedobject.getLocal("flashtrack" );

// initialize the time variables that will be used

myDate = new Date();

myTime = myDate.getTime();

// test that the required TrackingURL UIDCookieValue parameters were passed and aren't null

if ((UIDCookieValue != null) && (FlashCookieName != null) && (TrackingURL != null)) {

// test if the local shared object exists and create the appended

// tracking url with a name value at the end to illustrate it is being

// recovered.

if (myLocalSO.data.uid != null) {

myTrackingURL = unescape(TrackingURL) + "&uidvalue=" + UIDCookieValue + "&flashvalue=" + myLocalSO.data.uid + "&origination=" + myLocalSO.data.origination + "&action=recover";

}

// else set local shared object data if it didn't exist and then the

// appended tracking url with a name value at the end to illustrate

// it is being set for the first time.

else {

myLocalSO.data.uid = UIDCookieValue;

myLocalSO.data.origination = myTime;

myTrackingURL = unescape(TrackingURL) + "&uidvalue=" + UIDCookieValue + "&flashvalue=" + myLocalSO.data.uid + "&origination=" + myLocalSO.data.origination + "&action=set";

}

// define and call the special javascript function that sets the cookie

myCookieURL = "javascript:setFlashCookie('"+myLocalSO.data.uid+"')";

getURL(myCookieURL);

// use loadMovie to call the tracking url from the server to log the event

loadMovie(myTrackingURL,_root);

}

NOTE: The actual code used by this page contains extra funtionality to provide the test results output. For best results use the generic code as documented in the text boxes.

NOTE: The code on this page represents a simple proof of concept based on statements made in a recent Jupiter Reseach Report on the percentage of users who delete cookies. It is no way representative of a finished product.


Add to Technorati Favorites
View blog top tags