Skip to content

Instantly share code, notes, and snippets.

@gtzilla
Created May 17, 2011 04:26
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save gtzilla/975949 to your computer and use it in GitHub Desktop.
Save gtzilla/975949 to your computer and use it in GitHub Desktop.
//
// BitsMetaMetric.js
// bitly2
//
// Created by gregory tomlinson on 2011-05-11.
// Copyright 2011 the public domain. All rights reserved.
//
/*
*/
(function(window, undefined) {
/*
Usage:
// summary page, realtime
var bmm = new BitsMetaMetric({
page_type : 0,
units : 0
});
bmm.add_event( ... )
bmm.add_event( "click", { "hash" : page_hash }, bit_metrics.click_remote_callback, bit_metrics );
bmm.phone_callback=function() {
// my method, scope to this instance of BitsMetaMetric
// runs when all _xhrs are completed via a length test.
}
// Remote URLs call -- phone!
bmm.phone();
*/
window.BitsMetaMetric=function( opts, update_settings ) {
this.__m=$.extend(true, {}, this.__m, opts );
this.clear_events();
if(update_settings) {
settings=$.extend(true, {}, settings, update_settings);
}
return this;
}
var _xhrs=[], settings={
page_types : ["SUMMARY", "INFOHASH"],
unit_types : ["REALTIME", "HOUR", "DAY", "WEEK", "MONTH", "YEAR"],
endpoint_types: ["CLICK", "COUNTRY", "DOMAIN"], // iterate here
urls : {
"SUMMARY" : {
"REALTIME" : {
"CLICK" : "/data/clicks/hourly",
"COUNTRY" : "/data/countries/hourly",
"DOMAIN" : "/data/domains/hourly"
},
"DAY" : {
"CLICK" : "/data/clicks/summary",
"COUNTRY" : "/data/countries/summary",
"DOMAIN" : "/data/domains/summary"
}
},
"INFOHASH" : {
"REALTIME" : {
"CLICK" : "/data/clicks/hashhourly",
"COUNTRY" : "/data/countries/hashhourly",
"DOMAIN" : "/data/domains/hashhourly"
},
"DAY" : {
"CLICK" : "/data/clicks/hashsummary",
"COUNTRY" : "/data/countries/hashsummary",
"DOMAIN" : "/data/domains/hashsummary"
},
"HOUR" : {
"CLICK" : "/data/metrics/links/click",
"COUNTRY" : "/data/metrics/links/country",
"DOMAIN" : "/data/metrics/links/domain"
}
}
}
};
window.BitsMetaMetric.prototype={
"constructor" : BitsMetaMetric,
page_name : function() {
return settings.page_types[ this.get("page_type") ];
},
/*
getter/setter
*/
units_by_name : function( name ) {
var pos = settings.unit_types.indexOf( name.toUpperCase() );
this.set("units", Math.max(pos, 0) );
return this.page_unit();
},
page_unit : function() {
return settings.unit_types[ this.get("units") ];
},
get : function( name ) {
return this.__m[name]
},
set : function( name, value) {
return this.__m[name]=value;
},
abort : function() {
for(var i=0; _xhrs.length; i++) {
if( _xhrs[i] && _xhrs[i].abort && typeof _xhrs[i].abort == "function" ) {
_xhrs[i].abort();
}
}
_xhrs.length = 0; // steal this from jeff, assuming it cleans out the array better than =[]
},
/*
Callbacks for the Data URLs
this.add_event( "click", { hash : "test" }, func[, scope] )
*/
add_event : function( type, params, callback, scope ) {
this._data_events.push({
'type' : type,
'params' : jQuery.extend(true, {}, params),
'method' : (callback || function(){}),
'scope' : (scope || this)
});
},
clear_events : function() {
this._data_events=null;
this._data_events=[];
},
_urls_list : function() {
var page_type_name=this.page_name() || settings.page_types[0],
page_unit_type=this.page_unit() || settings.unit_types[0];
return settings.urls[ page_type_name ][ page_unit_type ];
},
phone : function() {
var urls = this._urls_list(), evt;
for(var k in urls) {
// settings.url[PAGE NAME][ PAGE TYPE ][k==endpoint types]
this._find_phone_url( k, urls[k] );
}
},
phone_callback : function() {
// called when all xhrs are complete
// scoped to this instance
try {
console.log("completed all xhrs", (new Date).getTime(), this.page_unit());
} catch(e) {}
},
// type click|country|domain
phone_url : function( endpoint_type ) {
var urls = this._urls_list(),
ajax_url = urls[endpoint_type];
if(ajax_url) {
this._find_phone_url( endpoint_type, ajax_url );
}
},
_find_phone_url : function( type, url ) {
var self=this;
for(var i=0; i<this._data_events.length; i++) {
evt=this._data_events[i];
if(evt.type.toLowerCase() === type.toLowerCase() ) {
var token = remote_call( url, evt );
token.done( (function( obj, self ) {
return function(jo, type, xhr){
// b/c element has multiple data calls, storage isn't yet solved
obj.method.call( obj.scope || obj, jo );
var pos=_xhrs.indexOf( xhr);
if( pos > -1) {
_xhrs.splice( pos, 1 );
if(_xhrs.length === 0 ) { self.phone_callback.call(self); }
}
};
})(evt, self) );
}
}
},
"_data_events" : [],
"__data" : {},
"__m" : {
page_type : 0, // 0,1
// unit_type : "realtime", // ["realtime", "hour", "day"]
units : 0, // 0,1,2
unit : -1,
period : 60,
value : "",
active_updates : false,
"data" : null // yuck, a property..
}
}
function remote_call(ajax_url, opts) {
var dfr=$.Deferred(), params=opts.params;
params._xsrf=$.cookie.get("_xsrf"); // don't add a bunch of crap here, just the xsrf
_xhrs.push($.ajax({
url : ajax_url,
type : "POST",
dataType : "json",
'data' : params,
success : dfr.resolve
}));
return dfr.promise();
}
})(window);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment