/**
 * Primary controller for ScionRacing content retrieval and handling.  Main contact point for VMIX
 *
 *
 */
ContentManager = Class.create();
Object.extend(ContentManager.prototype, {

	/**
	*	define member vars for this class
	*
	*/
	initialize: function() {
		this.vmixCode = "";
		this.site = new SiteStructure();
		this.template_loaded = false;
		this.isProgramSection = false; // program sections are pages related to any of the racing programs - drag, drift, road, and the teams pages
		this.isTeamSection = false;  // team sections are specific team pages like titan or world
		this.requestQueue = new Array(); // contains the active ContentRequestDO objects
		this.sampleReq = new ContentRequestDO('', '', '', 0, '');
		this.loadTemplate('templates', {});
	},
	
	/**
	*	Handles loading and storing HTML templates that are later used to format the content
	*
	*/
	loadTemplate: function(templatesId, opts) {
		var opts = opts || {};
        var data = $(templatesId).innerHTML;
		var query = /(?:^|\n)\s*#\s*[a-z0-9_ ]+?\s*-{2,}\s*\n/ig;
		var templates = data.split(query);
		//IE's split function behaves differently in that it strips the
		//first result from the array if it is an empty string
		if(document.all){
			templates = [''].concat(templates);
		}
		//Extract template titles from separator string
		var titles = [''].concat(data.match(query).map(
			function(t){
				return t.match(/[a-z0-9_ ]+/i)[0].replace(/(?:(?:^|\n)\s+|\s+(?:$|\n))/g,'').replace(/\s+/g,'');
			}
		));
		if(!this.templates) this.templates = {};
		if(templates.length > 1){
			for(var i = 1; i < templates.length; i++){
				this.templates[titles[i]] = new Template(templates[i]);
			}
		}
		else{
			this.templates[opts.name] = data;
		}
		if(opts.onComplete){
			opts.onComplete(opts.name);
		}
	},
	
	
	/**
	*	Called any time a new page loads.  This is typically called by the NavigationManager
	*
	*/
	getInitContent: function(section, team, one, two, three) {
		// construct the appropriate requests by looking up the page object
		var requests = this.site.returnPageData(true, section, team, one, two, three);
		
		this.addRequestsToQueue(requests);
		
	},
	
	
	/**
	*	Called any time the site changes a section - moves from one 'page' to another, while 
	*	remaining within the context of the current actual HTML page.  This is typically called by the 
	*	NavigationManager
	*
	*/
	getSectionContent: function(section, team, one, two, three) {
		// construct the appropriate requests by looking up the page object
		var requests = this.site.returnPageData(false, section, team, one, two, three);
		
		this.addRequestsToQueue(requests);
	},
	
	
	/**
	*	Accepts an array of ContentRequestDO objects and adds them to the request queue, then 
	*	makes the actual AJAX requests
	*
	*/
	addRequestsToQueue: function(requests) {
	
		requests.each(function(item, index) {
			
			var queueID = index + '_' + Math.floor(Math.random() * 10000000000000);
			item.queueID = queueID;
			this.requestQueue.push(item);
			var request = item;
			this.requestAjaxContent(request, queueID);
			
		}.bind(this));
	
	},
	
	
	/**
	*	Utility.  Builds the appropriate VMIX request string
	*
	*/
	build_api_url: function(api, action, params) {
		return '/scion/proxyServletPath.do?api='+api+'&action='+action+'&params='+escape(params);
	},
	
	
	/**
	*	Simple AJAX request function.  Makes a "get" request for the content at the url designated in the 
	*	argument.  When complete, relays the response to the handleContentRequest() function
	*
	*/
	requestAjaxContent: function(request, queueID) {
		
		var url = request.url;
		// request.url = build_api_url('media', 'getMediaList', 'limit=5');
		var params = {};
		
		params.queueID = queueID;
		
		// Show loading text while fetching from server
		for(var req in this.requestQueue) { if (this.requestQueue.hasOwnProperty(req)) {
			if(this.requestQueue[req].queueID == queueID && this.requestQueue[req].dataType == this.sampleReq.DATA_TYPE_HTML) {
				$(this.requestQueue[req].contentSection).innerHTML = "<div class='loading'>Loading...</div>";
			}
		}}
		
		new Ajax.Request(url, {
			method: 'get',
			evalJS: true,
			params: params,
			onSuccess: function(transport) 
			{
				this.handleContentResponse(transport.responseText, transport.request.options.params.queueID);
			}.bind(this)
		});
		
	},
	
	
	/**
	*	The handler that is called when the AJAX request created at requestAjaxContent() is successfully completed.
	*
	*/
	handleContentResponse: function(responseText, queueID) {
	
		var contentHtml = "";
		var requestObj = {};
		var contentHtmlId = "";
		
		for(i=0; i<this.requestQueue.length; i++)
		{
			if(this.requestQueue[i].queueID == queueID)
			{
				requestObj = this.requestQueue[i];
				this.requestQueue.splice(i, 1);
				var tmpSectionString = requestObj.contentSection;
				//console.log('handleContentResponse processing request ID: ' + tmpSectionString);
				break;
			}
		}
		
		contentHtmlId = requestObj.contentSection;
		
		if(requestObj.dataType == this.sampleReq.DATA_TYPE_JSON)
		{
			switch (requestObj.template)
			{
				case "featuresImages": 
					contentHtml = this.returnFeaturesImagesContent(requestObj, responseText);
				break;
				case "featuresVideos": 
					contentHtml = this.returnFeaturesVideosContent(requestObj, responseText);
				break;
				case "whatsNew": 
					contentHtml = this.returnWhatsNewContent(requestObj, responseText);
				break;
				case "groupImages": 
					contentHtml = this.returnGroupImagesContent(requestObj, responseText);
				break;
				case "groupVideos": 
					contentHtml = this.returnGroupVideosContent(requestObj, responseText);
				break;
				case "video": 
					contentHtml = this.returnGroupImagesContent(requestObj, responseText);
				break;
				case "featuredAbout":
					contentHtml = this.returnFeaturedAboutContent(requestObj, responseText);
				break;
				case "groupImageCollectionsPassOne":
					contentHtml = this.returnGroupImageContainer(requestObj, responseText);
				break;
				case "groupVideoCollectionsPassOne":
					contentHtml = this.returnGroupVideoContainer(requestObj, responseText);
				break;
				case "groupImageCollectionsPassTwo":
					contentHtml = this.returnGroupImagesContent(requestObj, responseText);
				break;
				case "groupVideoCollectionsPassTwo":
					contentHtml = this.returnGroupVideosContent(requestObj, responseText);
				break;
			}

		}
		if (requestObj.dataType == this.sampleReq.DATA_TYPE_HTML) {
			// parse HTML Content
			contentHtml = responseText;
		}
		if (requestObj.dataType == this.sampleReq.DATA_TYPE_XML) {
			// parse XML Content
			//alert('ContentManager.handleContentResponse: Need to implement xml parsing!');
		}
		var contentHtmlEl = $(contentHtmlId);
		contentHtmlEl.innerHTML = "";
		if(contentHtml != ''){
			contentHtmlEl.insert(contentHtml);
		}
		if(contentHtmlEl.ancestors().first().select(".loading").first()) {
			contentHtmlEl.ancestors().first().select(".loading").first().hide();
		}
		
		// hooks for attaching listeners to newly included dom elements
		if(requestObj.template === "ask" || requestObj.template === "askDiary" || requestObj.template === "askArchive") {
			Paginator(contentHtmlId).init();
		}
		
		// some content goes into a carousel widget
		if(requestObj.dataType == this.sampleReq.DATA_TYPE_JSON)
		{
			if (requestObj.template == "featuresImages" || requestObj.template == "featuresVideos" || requestObj.template == "whatsNew" || requestObj.template == "groupImages" || requestObj.template == "groupVideos")
			{
				
				if($(requestObj.contentSection).select('.item').size() > 0){
				
					// init carousel
					var carouselID = requestObj.contentSection.replace(/Holder/g, "Carousel");
				
					var rotateObj = new CarouselLoader();
					if ((requestObj.template == "featuresImages") || (requestObj.template == "featuresVideos") || (requestObj.template == "whatsNew"))
					{
						rotateObj.load(carouselID, 'vertical', 216, 61);
					} else if ((requestObj.template == "groupImages") || (requestObj.template == "groupVideos")) {
						rotateObj.load(carouselID, 'horizontal', 166, 166);
					}
					
				} else {
					
					var carouselID = requestObj.contentSection.replace(/Holder/g, "Carousel");
					$(carouselID).select('.box-hdr-sub').first().select('.pagin-ctrl').style.visibility = "hidden";
					
				}
				
			}
			
			if (requestObj.template == "groupImageCollectionsPassTwo" || requestObj.template == "groupVideoCollectionsPassTwo")
			{
				
				var newContentSectionName = requestObj.contentSection.substr(0,requestObj.contentSection.indexOf("-media-"));
				if($(newContentSectionName).select('.item').size() > 0 &&
					$(newContentSectionName).select('.item').all(function(item) { return item.select('div').size() > 0; })) {
					var tempStr = requestObj.contentSection.replace(/Holder/g, "Carousel");
					var carouselID = tempStr.substr(0,tempStr.indexOf("-media-"));
					(new CarouselLoader()).load(carouselID, 'horizontal', 166, 166);
				} else {
					var tempStr = requestObj.contentSection.replace(/Holder/g, "Carousel");
					var carouselID = tempStr.substr(0,tempStr.indexOf("-media-"));
					$(carouselID).select('.carousel-ctrl')[1].select('.carousel-info').style.visibility = "hidden";
				}
			
			}
		}
		
		// look for sub requests
		if (requestObj.subRequests.length > 0)
		{
			this.addRequestsToQueue(requestObj.subRequests);
		}
		
	},
	
	
	/**
	*	Parsing specific to the 'features' content (currently the paginated side nav items such as "features video", or "what's new")
	*
	*/
	returnFeaturesImagesContent: function(requestObj, responseText) {
		// parse Vmix Content
		var responseObj = {};
		var contentHtml = '';
		var contentArray = [];
		var descMetaData = '';
		responseObj = responseText.evalJSON();
		responseObj.media.each(function(item, index) {
			var content = {};
			content.first_item_class = '';
			if(index == 0)
			{
				content.first_item_class = ' first';
			}
			content.image_path = "http://image.vmixcore.com/imgman.jpg?width=57&height=39&fill=000000000&url=" + item.thumbnail[0].url;
			
			//content.desc_copy = item.title.truncate(55);
			
			descMetaData = item.description;
			descMetaData = '<?xml version=\"1.0\"?><xml>' + descMetaData + '</xml>';
			
			if (window.DOMParser)
  			{
  				parser=new DOMParser();
  				xmlDoc=parser.parseFromString(descMetaData,"text/xml");
  			}
			else // Internet Explorer
  			{
 				if(window.VBArray && window.XMLHttpRequest) {
					xmlDoc=new ActiveXObject("MSXML2.DOMDocument"); // IE 7 - IE 8 Msxml2.DOMDocument.4.0 Msxml2.DOMDocument.3.0
				} else if(window.VBArray && window.document.implementation) {
					xmlDoc=new ActiveXObject("Microsoft.XMLDOM"); // IE 6
				} else {
					xmlDoc=new ActiveXObject("MSXML2.DOMDocument");
				}
  				xmlDoc.async="false";
  				xmlDoc.loadXML(descMetaData); 
  			}
			
			content.title = item.title;
			
			if(xmlDoc && (xmlDoc.getElementsByTagName("description").length>0)){
				var desc = xmlDoc.getElementsByTagName("description")[0].childNodes[0];
				if(desc == null){
					content.desc_copy = item.description.truncate(20);
				} else {
					content.desc_copy = desc.nodeValue.truncate(20);
				}
			} else {
				content.desc_copy = item.description.truncate(20);
			}
			
			if(xmlDoc && (xmlDoc.getElementsByTagName("internallink").length>0)){
				var mediaLink = xmlDoc.getElementsByTagName("internallink")[0].childNodes[0];
				if(mediaLink == null){
					content.media_link = 'javascript:void(0);';
				} else {
					content.media_link = mediaLink.nodeValue;
				}
			} else {
				content.media_link = 'javascript:void(0);';
			}
			
			contentArray.push(content);
		});
		
		// we have to assemble this later due to namespace binding issues
		for(i=0; i<contentArray.length; i++)
		{
			contentHtml += this.templates[requestObj.template].evaluate(contentArray[i]);
		}
		
		return contentHtml;
	},
	
	returnFeaturesVideosContent: function(requestObj, responseText) {
		// parse Vmix Content
		var responseObj = {};
		var contentHtml = '';
		var contentArray = [];
		var descMetaData = '';
		responseObj = responseText.evalJSON();
		responseObj.media.each(function(item, index) {
			var content = {};
			content.first_item_class = '';
			if(index == 0)
			{
				content.first_item_class = ' first';
			}
			content.image_path = "http://image.vmixcore.com/imgman.jpg?width=57&height=39&fill=000000000&url=" + item.thumbnail[0].url;
			
			//content.desc_copy = item.title.truncate(55);
			
			descMetaData = item.description;
			descMetaData = '<?xml version=\"1.0\"?><xml>' + descMetaData + '</xml>';
			
			if (window.DOMParser)
  			{
  				parser=new DOMParser();
  				xmlDoc=parser.parseFromString(descMetaData,"text/xml");
  			}
			else // Internet Explorer
  			{
 				if(window.VBArray && window.XMLHttpRequest) {
					xmlDoc=new ActiveXObject("MSXML2.DOMDocument"); // IE 7 - IE 8 Msxml2.DOMDocument.4.0 Msxml2.DOMDocument.3.0
				} else if(window.VBArray && window.document.implementation) {
					xmlDoc=new ActiveXObject("Microsoft.XMLDOM"); // IE 6
				} else {
					xmlDoc=new ActiveXObject("MSXML2.DOMDocument");
				}
  				xmlDoc.async="false";
  				xmlDoc.loadXML(descMetaData); 
  			}
			
			content.title = item.title;
			
			if(xmlDoc && (xmlDoc.getElementsByTagName("description").length>0)){
				var desc = xmlDoc.getElementsByTagName("description")[0].childNodes[0];
				if(desc == null){
					content.desc_copy = item.description.truncate(20);
				} else {
					content.desc_copy = desc.nodeValue.truncate(20);
				}
			} else {
				content.desc_copy = item.description.truncate(20);
			}
			
			if(xmlDoc && (xmlDoc.getElementsByTagName("internallink").length>0)){
				var mediaLink = xmlDoc.getElementsByTagName("internallink")[0].childNodes[0];
				if(mediaLink == null){
					content.media_link = 'javascript:void(0);';
				} else {
					content.media_link = mediaLink.nodeValue;
				}
			} else {
				content.media_link = 'javascript:void(0);';
			}
			
			contentArray.push(content);
		});
		
		// we have to assemble this later due to namespace binding issues
		for(i=0; i<contentArray.length; i++)
		{
			contentHtml += this.templates[requestObj.template].evaluate(contentArray[i]);
		}
		
		return contentHtml;
	},
	
	returnWhatsNewContent: function(requestObj, responseText) {
		// parse Vmix Content
		var responseObj = {};
		var contentHtml = '';
		var contentArray = [];
		responseObj = responseText.evalJSON();
		responseObj.media.each(function(item, index) {
			var content = {};
			content.first_item_class = '';
			if(index == 0)
			{
				content.first_item_class = ' first';
			}
			
			content.image_path = "http://image.vmixcore.com/imgman.jpg?width=57&height=39&fill=000000000&url=" + item.thumbnail[0].url;
			
			//content.desc_copy = item.title.truncate(55);
			
			descMetaData = item.description;
			descMetaData = '<?xml version=\"1.0\"?><xml>' + descMetaData + '</xml>';
			
			if (window.DOMParser)
  			{
  				parser=new DOMParser();
  				xmlDoc=parser.parseFromString(descMetaData,"text/xml");
  			}
			else // Internet Explorer
  			{
 				if(window.VBArray && window.XMLHttpRequest) {
					xmlDoc=new ActiveXObject("MSXML2.DOMDocument"); // IE 7 - IE 8 Msxml2.DOMDocument.4.0 Msxml2.DOMDocument.3.0
				} else if(window.VBArray && window.document.implementation) {
					xmlDoc=new ActiveXObject("Microsoft.XMLDOM"); // IE 6
				} else {
					xmlDoc=new ActiveXObject("MSXML2.DOMDocument");
				}
  				xmlDoc.async="false";
  				xmlDoc.loadXML(descMetaData); 
  			}
			
			content.title = item.title;
			
			if(xmlDoc && (xmlDoc.getElementsByTagName("description").length>0)){
				var desc = xmlDoc.getElementsByTagName("description")[0].childNodes[0];
				if(desc == null){
					content.desc_copy = item.description.truncate(20);
				} else {
					content.desc_copy = desc.nodeValue.truncate(20);
				}
			} else {
				content.desc_copy = item.description.truncate(20);
			}
			
			if(xmlDoc && (xmlDoc.getElementsByTagName("internallink").length>0)){
				var mediaLink = xmlDoc.getElementsByTagName("internallink")[0].childNodes[0];
				if(mediaLink == null){
					content.media_link = 'javascript:void(0);';
				} else {
					content.media_link = mediaLink.nodeValue;
				}
			} else {
				content.media_link = 'javascript:void(0);';
			}
			
			contentArray.push(content);
		});
		
		// we have to assemble this later due to namespace binding issues
		for(i=0; i<contentArray.length; i++)
		{
			contentHtml += this.templates[requestObj.template].evaluate(contentArray[i]);
		}
		
		return contentHtml;
	},
	
	/**
	*	Parsing specific to the 'groupImages' content (currently the images tab content for non-team pages such as "drag" -- 
	*	as opposed to "drag/titan", which is a team gallery and follows a different template)
	*
	*/
	returnGroupImagesContent: function(requestObj, responseText) {
		// parse Vmix Content
		var responseObj = {};
		var contentHtml = '';
		var thumbnailURL = '';
		responseObj = responseText.evalJSON();
			
		// we have to assemble this later due to namespace binding issues
		contentHtml = this.templates[requestObj.template].evaluate({
			collection_id: requestObj.contentSection.substr(requestObj.contentSection.indexOf("-media-") + "-media-".length,requestObj.contentSection.length),
			image_path: "http://image.vmixcore.com/imgman.jpg?width=141&height=128&fill=000000000&url=" + responseObj.media.first().thumbnail[0].url,
			copy: requestObj.collectionDesc
		});
		
		return contentHtml;
	},
	
	/**
	*	Parsing specific to the 'groupVideos' content (currently the images tab content for non-team pages such as "drag" -- 
	*	as opposed to "drag/titan", which is a team gallery and follows a different template)
	*
	*/
	returnGroupVideosContent: function(requestObj, responseText) {
		// parse Vmix Content
		var responseObj = {};
		var contentHtml = '';
		var thumbnailURL = '';
		responseObj = responseText.evalJSON();
		
		if(requestObj.thumbMediaID == "0"){
			thumbnailURL = responseObj.media.first().thumbnail[0].url;
		} else {
			
			thumbnailURL = responseObj.media.first().thumbnail[0].url;
			
			new Ajax.Request('/vmix/apis/media.php?action=getMedia&media_id=' + requestObj.thumbMediaID + '&atoken=c3d1bee0a6f3d6bdfc7750eef78595de', {
				method: 'get',
				evalJS: true,
				onSuccess: function(transport) 
				{
					
					var responseObjTwo = {};
					responseObjTwo = transport.responseText.evalJSON();
					this.thumbnailURL = responseObjTwo.url;
					
				}.bind({thumbnailURL:thumbnailURL})
			});
			
		}
		
		// we have to assemble this later due to namespace binding issues
		contentHtml = this.templates[requestObj.template].evaluate({
			collection_id: requestObj.contentSection.substr(requestObj.contentSection.indexOf("-media-") + "-media-".length,requestObj.contentSection.length),
			image_path: "http://image.vmixcore.com/imgman.jpg?width=141&height=128&fill=000000000&url=" + thumbnailURL,
			copy: requestObj.collectionDesc
		});
		
		return contentHtml;
	},
	
	returnFeaturedAboutContent: function(requestObj, responseText) {
		// parse Vmix Content
		var responseObj = {};
		var contentHtml = '';
		var contentArray = [];
		responseObj = responseText.evalJSON();
		responseObj.media.each(function(item, index) {
			var content = {};
			content.image_path = "http://image.vmixcore.com/imgman.jpg?width=483&height=317&fill=000000000&url=" + item.url;
			//content.copy = item.description;
			
			descMetaData = item.description;
			descMetaData = '<?xml version=\"1.0\"?><xml>' + descMetaData + '</xml>';
			
			if (window.DOMParser)
  			{
  				parser=new DOMParser();
  				xmlDoc=parser.parseFromString(descMetaData,"text/xml");
  			}
			else // Internet Explorer
  			{
 				if(window.VBArray && window.XMLHttpRequest) {
					xmlDoc=new ActiveXObject("MSXML2.DOMDocument"); // IE 7 - IE 8 Msxml2.DOMDocument.4.0 Msxml2.DOMDocument.3.0
				} else if(window.VBArray && window.document.implementation) {
					xmlDoc=new ActiveXObject("Microsoft.XMLDOM"); // IE 6
				} else {
					xmlDoc=new ActiveXObject("MSXML2.DOMDocument");
				}
  				xmlDoc.async="false";
  				xmlDoc.loadXML(descMetaData); 
  			}
			
			content.title = (item.title && item.title.toUpperCase());
			
			if(xmlDoc && (xmlDoc.getElementsByTagName("description").length>0)){
				var desc = xmlDoc.getElementsByTagName("description")[0].childNodes[0];
				if(desc == null){
					content.copy = item.description.truncate(200);
				} else {
					content.copy = desc.nodeValue.truncate(200);
				}
			} else {
				content.copy = item.description.truncate(200);
			}
			
			if(xmlDoc && (xmlDoc.getElementsByTagName("internallink").length>0)){
				var mediaLink = xmlDoc.getElementsByTagName("internallink")[0].childNodes[0];
				if(mediaLink == null){
					content.internal_link_js = 'javascript:void(0);';
				} else {
					content.internal_link_js = "javascript:window.location.href = '" + mediaLink.nodeValue + "';";
				}
			} else {
				content.internal_link_js = 'javascript:void(0);';
			}
			
			contentArray.push(content);
		});
		
		// we have to assemble this later due to namespace binding issues
		for(i=0; i<contentArray.length; i++)
		{
			contentHtml += this.templates[requestObj.template].evaluate(contentArray[i]);
		}
	
		return contentHtml;
	},
		
	returnGroupImageContainer: function(requestObj, responseText) {
		
		// parse Vmix Content
		var responseObj = responseText.evalJSON();
		requestObj.subRequests = [];
		$H(responseObj.collection).each(function(pair, index) {
			// The first item returned by Vmix is the collection of collections itself, so disregard.
			if(pair.value.name === "Images" || pair.value.name === "Video") {
				return; // continue (but in a function)
			}
			requestObj.subRequests.push(
				new ContentRequestDO(
					requestObj.contentSection + "-media-" + pair.value.id,
					'groupImageCollectionsPassTwo',
					"/vmix/apis/collection.php?action=getCollectionMedias&collection_id=" + pair.value.id + "&atoken=c3d1bee0a6f3d6bdfc7750eef78595de",
					0,
					requestObj.dataType,
					null,
					pair.value.description,
					null,
					pair.value.thumbnail_media_id,
					pair.value.date_created
				)
			);
		});
		requestObj.subRequests.sort(arrange.byObjectsAttribute('dateCreated'));
		
		// parse Vmix Content
		var contentHtml = '';
		// Depends on having subRequests populated, to avoid the JSON eval
		// we have to assemble this later due to namespace binding issues
		for(i=0; i < requestObj.subRequests.length; i++) {
			contentHtml += this.templates[requestObj.template].evaluate({collection_id : requestObj.subRequests[i].contentSection});
		}
	
		return contentHtml;
	},
		
	returnGroupVideoContainer: function(requestObj, responseText) {
		
		// parse Vmix Content
		var responseObj = responseText.evalJSON();
		requestObj.subRequests = [];
		requestObj.subIds = [];
		$H(responseObj.collection).each(function(pair, index) {
			// The first item returned by Vmix is the collection of collections itself, so disregard.
			if(pair.value.name === "Images" || pair.value.name === "Video") {
				return; // continue (but in a function)
			}
			requestObj.subRequests.push(
				new ContentRequestDO(
					requestObj.contentSection + "-media-" + pair.value.id,
					'groupVideoCollectionsPassTwo',
					"/vmix/apis/collection.php?action=getCollectionMedias&collection_id=" + pair.value.id + "&atoken=c3d1bee0a6f3d6bdfc7750eef78595de",
					0,
					requestObj.dataType,
					null,
					pair.value.description,
					null,
					pair.value.thumbnail_media_id,
					pair.value.date_created
				)
			);
			requestObj.subRequests.sort(arrange.byObjectsAttribute('dateCreated'));
		});
		
		
		// parse Vmix Content
		var contentHtml = '';
		// Depends on having subRequests populated, to avoid the JSON eval
		// we have to assemble this later due to namespace binding issues
		for(i=0; i < requestObj.subRequests.length; i++) {
			contentHtml += this.templates[requestObj.template].evaluate({collection_id : requestObj.subRequests[i].contentSection});
		}
	
		return contentHtml;
	}
	
});

var arrange = {

    byObjectsAttribute:function(name){
        return function(obj1,obj2){
            var n1;
            var n2;
            if(typeof obj1 === 'object' && typeof obj2 === 'object' && obj1 && obj2){
                n1 = obj1[name];
                n2 = obj2[name];
                if(n1 === n2){
                    return obj1;
                }
                if(typeof n1 === typeof n2){
                    return n2 < n1 ? -1 : 1; 
                }
            }else{
                throw{
                    name: 'Error',
                    message: 'Expected object when sorting by ' + name
                };
            }
        };
    }

};
