track page visit as an alias - javascript

I've been trying to find a solution for this but haven't seen anything useful google'ing around. The issue might be that i'm using terminology that has other meanings.
I have a site that has utilizes the same URL's for both guests and members. In order to track visits and goals correctly i need a way to tell if the visitor is a logged in user or a guest.
The easiest way i can think of is if i just prefix my URL's with something like
/member/
I thought maybe i could do this in the google tracking code by adding this:
_gaq.push(['_trackPageview'], '/member' + window.location.pathname);
the full code is:
<script type="text/javascript">
var _gaq = _gaq || [];
_gaq.push(['_setAccount', 'xxxxxxxxxx']);
_gaq.push(['_trackPageview'], '/member' + window.location.pathname);
(function() {
var ga = document.createElement('script'); ga.type = 'text/javascript'; ga.async = true;
ga.src = ('https:' == document.location.protocol ? 'https://ssl' : 'http://www') + '.google-analytics.com/ga.js';
var s = document.getElementsByTagName('script')[0]; s.parentNode.insertBefore(ga, s);
})();
</script>
However this isn't working, also reading the google analytic docs, this seems to be a way to add an 'additional' page view.
I can update the servers code to prefix the urls with /member/ and then strip it before processing the path for the controllers, but i would rather not risk breaking a stable system thats about to go live.
Does anyone know how this can be done in JS before the normal URL is tracked?
Thanks,
Dan

You have a minor syntax error with your _trackPageview call.
It should just be this:
_gaq.push(['_trackPageview', '/member' + window.location.pathname]);
Note that the /member+ part is now within the array, not outside of it.
What you were doing was passing the _trackPageview function name without a second parameter to be its argument (which, by default, tracks the pageview as location.pathname+location.search, and then passing a string /member+window.location.pathname to the array, which did nothing.
Passing the custom URL as a 2nd item in an array will make it work just fine.

Aside from the fact that you probably shouldn't use the same URL structure for goal tracking in Google Analytics, I can suggest a couple of ways to solve the problem. Note that this doesn't address the alias-tracking question you asked, but offers some alternatives.
1. Append a querystring parameter to goal pages for members or guests
Bit of a hack, but it should be trivial to append a ?guest=true param if your users are not logged in. This would be a minor change that should not affect your business logic or website operation.
You can then set different goals in GA that look for the success page with or without the URL param.
2. Set custom variables in Google Analytics for members and guests
This is the more correct solution.
Use session-level custom variables to distinguish different visitor experiences across sessions.
For example, if your website offers users the ability to login, you can use a custom variable scoped to the session level for user login status. In that way, you can segment visits by those from logged in members versus anonymous visitors.
http://code.google.com/apis/analytics/docs/tracking/gaTrackingCustomVariables.html#sessionLevel
Then you can segment your goal starts and completions using your advanced segments, segmenting on user login status:
http://www.lunametrics.com/blog/2010/10/07/visitor-signed-in/

Related

Angular: redirecting /#%21/ to /#!/

In emails that we send to users, we include links to Angular app like the following:
http://example.com/#!/mypage
We've noticed that some email clients or browsers, for one reason or another, upon click direct the user to this instead:
http://example.com/#%21/mypage
Angular then throws the following error:
Uncaught Error: [$location:ihshprfx] Invalid url "http://example.com/#%21/mypage", missing hash prefix "#!".
http://errors.angularjs.org/1.3.0-beta.10/$location/ihshprfx
We are using $locationProvider.hashPrefix('!');. I'm trying to find a way to detect instances where $location is /#%21/ rather than /#!/ and then redirect properly, but I can't find a way to detect and/or get Angular to do this. What is the proper way to do this?
Ended up finding a better answer here:
Adding a hash prefix at the config phase if it's missing
Using $locationChangeStart didn't work because angular threw the error during initialization, so $locationChangeStart was never tripped.
Instead, I went with the following approach:
<head>
<!-- Change #%21 to #! on first load -->
<script type="text/javascript">
var loc = window.location.href;
if (loc.indexOf('#%21') > -1 && loc.indexOf('#!') === -1 ) {
window.location.href = loc.replace("#%21", "#!");
}
</script>
<!-- More stuff ... -->
</head>
<body>...
This (a) allows me to rewrite the URL before we ever hit Angular, and (b) makes sure we only rewrite it the first time the app is loaded, rather than any time there's a location change--just in case at some point in the future we deliberately write a change that includes a #%21.
Might not be the most elegant way to go about solving your problem, but you could catch the $locationChangeStart event and then conditionally redirect the user with the $location service based on what the nature of the URL is.
For example:
$rootScope.$on('$locationChangeStart', function(event, newUrl, oldUrl) {
// ...
});

Making a Same Domain iframe Secure

tl;dr Can I execute un-trusted scripts on an iframe safely?
Back story:
I'm trying to make secure JSONP requests. A lot of older browsers do not support Web Workers which means that the current solution I came up with is not optimal.
I figured I could create an <iframe> and load a script inside it. That script would perform a JSONP request (creating a script tag), which would post a message to the main page. The main page would get the message, execute the callback and destroy the iframe. I've managed to do this sort of thing.
function jsonp(url, data, callback) {
var iframe = document.createElement("iframe");
iframe.style.display = "none";
document.body.appendChild(iframe);
var iframedoc = iframe.contentDocument || iframe.contentWindow.document;
sc = document.createElement("script");
sc.textContent = "(function(p){ cb = function(result){p.postMessage(result,'http://fiddle.jshell.net');};})(parent);";
//sc.textContent += "alert(cb)";
iframedoc.body.appendChild(sc);
var jr = document.createElement("script");
var getParams = ""; // serialize the GET parameters
for (var i in data) {
getParams += "&" + i + "=" + data[i];
}
jr.src = url + "?callback=cb" + getParams;
iframedoc.body.appendChild(jr);
window.onmessage = function (e) {
callback(e.data);
document.body.removeChild(iframe);
}
}
jsonp("http://jsfiddle.net/echo/jsonp/", {
foo: "bar"
}, function (result) {
alert("Result: " + JSON.stringify(result));
});
The problem is that since the iframes are on the same domain, the injected script still has access to the external scope through .top or .parent and such.
Is there any way to create an iframe that can not access data on the parent scope?
I want to create an iframe where scripts added through script tags will not be able to access variables on the parent window (and the DOM). I tried stuff like top=parent=null but I'm really not sure that's enough, there might be other workarounds. I tried running a for... in loop, but my function stopped working and I was unable to find out why.
NOTE:
I know optimally WebWorkers are a better isolated environment. I know JSONP is a "bad" technique (I even had some random guy tell me he'd never use it today). I'm trying to create a secure environment for scenarios where you have to perform JSONP queries.
You can't really delete the references, setting null will just silently fail and there is always a way to get the reference to the parent dom.
References like frameElement and frameElement.defaultView etc. cannot be deleted. Attempting to do so will either silently fail or throw exception depending on browser.
You could look into Caja/Cajita though.
tl;dr no
Any untrusted script can steal cookies (like a session id!) or read information from the DOM like the value of a credit card input field.
JavaScript relies on the security model that all code is trusted code. Any attempts at access from another domain requires explicit whitelisting.
If you want to sandbox your iframe you can serve the page from another domain. This does mean that you can't share a session or do any kind of communication because it can be abused. It's just like including an unrelated website. Even then there are possibilities for abuse if you allow untrusted JavaScript. You can for instance do: window.top.location.href = 'http://my.phishing.domain/';, the user might not notice the redirect.

Pull links from incoming visitors (referrals) via Javascript or jQuery

Is there a way to pull links from incoming visitors on a page (referrals)? I essentially want to do some if statements.
if user is from Nextag.com {do some javacode} else from Pricegrabber.com {do some javacode}.
Before I can do the if statements I need to find out how that user got on our page (where did they come from). I know google analytics does this but is there a way to hard code it on one page so I can do the above?
You can get the referer URL with document.referrer, it is supported cross-browser.
It might not be set though based on the user's privacy preferences, firewall, etc. Some proxies also clear or fake it.
You can run some Regexes on the value or use indexOf, and do some actions based on them.
For example (not final code):
if (document.referrer.indexOf('nextag.com') != -1) {
//user came from nextag.com
}
MDC Docs on document.referrer
You can use document.referrer (assuming it is populated by the user's browser).
Use the document.referrer property to get the originating URL, plus some basic pattern matching for validation:
var reURL = new RegExp("^https?:\/\/(www.)?nextag.com\/", "i");
if (document.referrer.length && reURL.test(document.referrer)) {
alert("Hello, nextag.com!");
} else {
alert("Hello, world!");
}

disqus api for dynamic page

I developing a web application where each user can create the his own pages using the widgets provided and disqus api is one of the widgets. I trying to use the disqus api http://docs.disqus.com/developers/universal/ for the web site, but I am little confused or I can say not able to do few things,let me explain u with a scenario. Suppose user A comes and adds disqus widget in his page and he can access his page through this url say "www.domain.com/xxx" where he can use his disqus widget, I am using the universal api but I guess I need to dynamically update the disqus_identifier and also disqus_url. How do I do it dynamically for different users or multiple users.
Kindly help me out
The disqus_identifier and disqus_url parameters are not required for Disqus to embed. However, depending on the functionality you are looking for (which is not clear from your question) you may need them to satisfy your requirements.
Since your page is composed of widgets, I assume there is no "permalink" URL that links to just the Disqus widget. For that reason, I would recommend you do not set the disqus_url parameter at all. (By not setting this parameter, disqus will figure out the appropriate URL on its own.)
The method you use to set the disqus_identifier will determine how and when a new disqus thread appears in the widget. If you want each user to see a unique disqus thread in their widget, set disqus_identifier to that user's ID. In JSP, this might look something like the following (but the actual implementation completely depends on your unique application).
// ...
%>
<div id="disqus_thread"></div>
<script type="text/javascript">
/* * * CONFIGURATION VARIABLES: EDIT BEFORE PASTING INTO YOUR WEBPAGE * * */
var disqus_shortname = 'example'; // required: replace example with your forum shortname
// The following are highly recommended additional parameters. Remove the slashes in front to use.
var disqus_identifier = '<%=currentUser.getID()%>';
// var disqus_url = 'http://example.com/permalink-to-page.html';
/* * * DON'T EDIT BELOW THIS LINE * * */
(function() {
var dsq = document.createElement('script'); dsq.type = 'text/javascript'; dsq.async = true;
dsq.src = 'http://' + disqus_shortname + '.disqus.com/embed.js';
(document.getElementsByTagName('head')[0] || document.getElementsByTagName('body')[0]).appendChild(dsq);
})();
</script>
<%

Adding Google Analytics to Adobe Air HTML/Javascript App

I am attempting to add google analytics tracking to an Adobe Air app created with HTML and javascript.
I have tried adding the ga.js file and using it like I would in a webpage:
<script type="text/javascript" src="lib/js/ga.js"></script>
<script type="text/javascript">
var pageTracker = _gat._getTracker("UA-********-1");
pageTracker._initData();
pageTracker._trackPageview('/test');
</script>
But this doesn't seem to register anything on the analytics dashboard.
Have also tried using the GA for flash actionscript library but I can't seem to create an instance of the GATracker as it needs a DisplayObject?
EDIT
using the information from grapefrukt I tried the following:
air.Sprite = window.runtime.flash.display.Sprite;
air.GATracker = window.runtime.com.google.analytics.GATracker;
var tracker = new air.GATracker( new air.Sprite(), "UA-XXXXXXX-X", "AS3", false );
but I get the following error:
TypeError: Error #1009: Cannot access a property or method of a null object reference
NOTE: I originally misread your question to be about how to use gaforflash, but I'll post this anyway since I've already typed it up and it might be of some use.
You can the constructor whatever DisplayObject you like, normally you'd use your document class, but anything will work. As far as I can understand it's only really used for displaying debug info.
var tracker:AnalyticsTracker = new GATracker( new Sprite, "UA-XXXXXXX-X", TrackerMode.AS3, false );
Setting the TrackerMode to AS3 let's the flash communicate directly with the tracking servers, so you don't need the javascript from google's servers.
I can't help you with the communication between js/as3, but that should be fairly easy.
Probably not useful to the OP, but just spent the whole day working around this so hopefully my solution will save someone else that time.
So the reason the ga.js code can't be used directly from an AIR app written in javascript is that AIR won't set the cookie for pages that are stored within the application itself. To work around this, I downloaded ga.js to the application and modified it so that it doesn't rely on the document.cookie function.
In the application, I have:
<script type="text/javascript">
var cookies = {};
document.__defineSetter__('_cookie', function(c) {
var epos = c.indexOf('=');
var spos = c.indexOf(';', Math.max(0, epos));
if (epos == -1 || spos == -1) { return; }
var name = c.substring(0, epos);
var value = c.substring(epos + 1, spos);
cookies[name] = value;
});
document.__defineGetter__('_cookie', function() {
var a = [];
for (var name in cookies) {
a.push(name + '=' + cookies[name]);
}
return a.join('; ');
});
var _gaq = _gaq || [];
_gaq.push(['_setAccount', 'UA-XXXXXX-1']);
_gaq.push(['_trackPageview', path])
(function() {
var ga = document.createElement('script');
ga.type = 'text/javascript';
ga.async = true;
// custom GA code which uses document._cookie instead of
// document.cookie
ga.src = 'js/ga.js';
var s = document.getElementsByTagName('script')[0];
s.parentNode.insertBefore(ga, s);
})();
</script>
Ideally, we'd be able to override the cookie method, but unfortunately, it doesn't seem possible in webkit as implemented for AIR. So in ga.js, I replaced all instances of J.cookie with J._cookie. Once that's done, ga.js should believe that it's writing cookies and function normally.
In the interest of full disclosure, I actually access the above analytics code through an iframe, but since ga.js is being served locally, I suspect it's no longer necessary and didn't want to complicate the solution by adding the bridge logic.

Categories

Resources