If you are like me, you probably use UTM parameters to find your best converting traffic sources in Google Analytics. The campaign/source/medium combo tells you what marketing efforts are working.

Very useful. But we can do more.

Let’s say you have an email signup form on your blog or a landing page. Visitors come from all over the interwebs clicking on your UTM tagged URLs. Some of them signup with their email address. Google Analytics tells you how many converted (if you have goals setup), but not who converted. Your email marketing tool tells you who converted, but not where they came from. There’s a surprisingly simple way to find out where each subscriber came from.

UTM parameters? What?

If you don’t know what UTM parameters are, there are a lot of very good articles on the web about them. These experts have done an exceptional job in explaining why to use UTM parameters and how to use them. I cannot explain it any better.

Let’s get started.

1. Configure your email marketing service provider

I am going to use Mailchimp as an example, but you can do something very similar in other email marketing service providers.

Mailchimp Add UTM parameters

Add UTM Parameters to Mailchimp

  1. Go to your subscribers list. Select List fields and *|MERGE|* tags from Settings.
  2. Click Add A Field, select text. Add “UTM_SOURCE” for Field Label and “USOURCE” for Put this tag in your content. Leave the Required? checkbox unchecked.
  3. Repeat the same for each of the remaining UTM parameters. i.e. UMEDIUM, UCAMPAIGN, UCONTENT, UTERM
  4. Click Save

You might be wondering why did I use “USOURCE” instead of “UTM_SOURCE” for the tag field. It’s because Mailchimp has a 10 character limit on the tags. I’m not sure why.

Now you are done with the Mailchimp setup part. Let’s head over to your website.

2. Website setup

Since your exact website setup might be different, I am going to assume a few things.

  • There’s only one form (the email signup) on your landing page.
  • If there is more than one form, the first one will be used.

A very common approach is to have the email signup form embedded in the landing page. e.g. Terminus landing page has the following email signup code as of writing this blog post.

<div id="mc_embed_signup">
  <form action="http://terminusapp.us6.list-manage.com/subscribe/post?u=4dbf&amp;id=7" method="post" id="mc-embedded-subscribe-form" name="mc-embedded-subscribe-form" class="validate form-inline" target="_blank">
  <input type="email" value="" name="EMAIL" class="email span4" id="mce-EMAIL" placeholder="Email address">
  <input type="submit" value="Get Notified" name="subscribe" id="mc-embedded-subscribe" class="btn btn-large btn-success">
   <h5><small>We will never spam you. Unsubscribe anytime.</small></h5>
  </form>
</div>

Before you proceed, make sure you have jQuery (you most likely do) on your website. If you don’t, simply add this line before the closing head tag i.e. </head>

<script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1.7.2/jquery.min.js"></script>

When a visitor comes to a landing page with UTM parameters in the URL, we need to capture those and add them to the signup form. That’s where the ugly Javascript helps.

<script type="text/javascript" charset="utf-8">
  function getParameterByName(name) {
    name = name.replace(/[\[]/, "\\\[").replace(/[\]]/, "\\\]");
    var regexS = "[\\?&]" + name + "=([^&#]*)";
    var regex = new RegExp(regexS);
    var results = regex.exec(window.location.search);
    if(results == null) {
      return "";
    } else {
      return decodeURIComponent(results[1].replace(/\+/g, " "));
    }
  }

  $(document).ready(function () {
    function addFormElem(paramName, fieldName) {
      var paramValue = getParameterByName(paramName);
      var $utmEl = $("<input type='hidden' name='" + fieldName + "' value='" + paramValue + "'>");
      if (paramValue != "") {
        $("form").first().prepend($utmEl);
      }
    }

    // Note: Only change the values after ":" if they are different for you
    // They are the same one as you added in your email marketing provider
    var utmParams = {
      "utm_source"   : "USOURCE",
      "utm_medium"   : "UMEDIUM",
      "utm_campaign" : "UCAMPAIGN",
      "utm_content"  : "UCONTENT",
      "utm_term"     : "UTERM"
    };

    for (var param in utmParams) {
      addFormElem(param, utmParams[param]);
    }
  });
</script>

Copy the above code and add it before the closing body tag i.e. </body>. This script will add the UTM parameters to any form as long as it is the first form on the page. It doesn’t have to be from Mailchimp or other similar provider.

3. Now what?

So what do you really get after doing all this?

You get to see the details for each subscriber

Now when you look at the detailed view of each new subscriber, you can see the UTM parameters.

Mailchimp UTM Details

Mailchimp UTM Details

You get to segment based on the Campaign/Medium/Source

You can now send emails to people who came from a particular source e.g. Guest blog post.

Mailchimp UTM segments

Mailchimp UTM segments

Here are couple of ideas for email segments, but I am sure your mind is bubbling with new ones already:

  • Send a targeted email to people who came from Twitter asking them to follow you.
  • Offer a discount to people coming from a partner website. Maybe you have an offer for them they cannot refuse.

In short, you don’t need to pay for expensive marketing platforms to get this segmenting feature.

Thank you, giants

  • I did not come up with this idea of capturing UTM parameters. I learned this from my friend and marketing guru, Roger Kondrat (@meetroger). Hi Roger.
  • The above javascript uses some code shared by awesome developers on Stackoverflow. They complete me.

Wrap up

  • Don’t let your UTM parameters go to waste. Make them do more work for you.
  • If you have any problem with the setup, please ask me and I will do my best to help you out. Either leave a comment or email me at puru@terminusapp.com

If you want to consistently build URLs with accurate UTM parameters, signup at www.terminusapp.com.

  • http://www.rogerkondrat.com/ Roger Kondrat

    That’s a great article Puru! I seriously doubt I had that much impact, but I really really appreciate your mentioning me.

  • kyuumeitai

    Thank you. This was very helpful.

    • http://term.li/1eFEesN Puru Choudhary

      You are welcome. I am glad you found it useful.

  • Sikandar Shukla

    Thanks for this, very helpful. Do you have any ideas/pointers for capturing the source/medium on pages that do not directly have the utm tags in their URL?

    I.e links that are clicked on after the user has already navigated to the URL with the UTM tags?

    • http://term.li/1eFEesN Puru Choudhary

      Hi Sikandar,

      I actually was working on a blog post to cover that part, but it went on the backburner due to other stuff. I’ll definitely try to get to it.

      If you are so inclined you can parse the cookie “__utmz” that Google Analytics drops (assuming you have Google Analytics) and add the fields to the form. It might involve a bit of trial and error, but it should not be too complicated. Then your form will see the visitors the same way Google Analytics sees it.

      Sorry that I don’t have more specific answer right now. I did write some Javascript code that replaces the one in this post. You can shoot me an email at puru@terminusapp.com and I will send it to you. You might need to test it bit to make sure it works for you.

      • s6mike

        Note that this works great with classic GA – but you can’t do with universal analytics because it doesn’t use a utmz cookie, only a single cookie which captures the unique client id.

        • http://term.li/1eFEesN Puru Choudhary

          Yes, utmz cookie approach might not work, but parsing the URL in the browser (as described in the blog post) should still work.

    • http://term.li/1eFEesN Puru Choudhary

      You can find the script I mentioned earlier here: https://gist.github.com/medius/8856352

  • amir

    hi Puru, I am trying to carry forward the utm_medium to another link that leaves my site. Any idea on how to accomplish this?
    thanks

    • http://term.li/1eFEesN Puru Choudhary

      Hi Amir,

      It can definitely be done with some Javascript. If you are comfortable with it, you can capture the utm_medium in a cookie if it is present in the URL. You can then add it to the target URL when any one clicks on the link.

      Sorry, if it’s not super helpful. To be honest, I have never felt the need to do something like this and therefore don’t have a code handy.

  • Dole

    Was looking for something simple like this. Nice. If it’s a form outside of an email service, do you just add the hidden fields yourself? Basically, how would you suggest it without an email program?

    • http://term.li/1eFEesN Puru Choudhary

      Hi Dole,

      The script adds the hidden fields for you to the first form on the page. So it will work for any form even if it’s not tied to an email service. It could be a form saving data to your own server.

      – Puru

  • Scott

    Many thanks! This was exactly what I have been looking for. Quite simple, but creates powerful metrics when combined with purchase data.

    • http://term.li/1eFEesN Puru Choudhary

      You are welcome, Scott.

  • http://www.paulminors.com Paul Minors

    Is it possible to use this same technique to track sources from around my own site. i.e. I have one signup form on a page. But I’d like to track the signups from people clicking a link on a blog post separate from a link on my about page. I have tried editing the code and adding ?source=blog-post or ?source=about to my URLs but it doesn’t seem to work. I don’t think I’ve edited the code correctly. Can you please help?

    • http://term.li/1eFEesN Puru Choudhary

      Just to make sure, did you use ?source=blog-post or ?utm_source=blog-post?

      • http://www.paulminors.com Paul Minors

        I used ?source=blog-post. I’d like to use “source” not “utm_source” as it’s an internal link.

        • http://term.li/1eFEesN Puru Choudhary

          I see. In that case you need need to add another parameter SOURCE in Mailchimp and use the this modified script https://gist.github.com/medius/d36c36fb85ca244c7de0. Hopefully this will work.

          • http://www.paulminors.com Paul Minors

            Hey, thanks for your help. Unfortunately this isn’t working. I have setup the “source” field in MailChimp and have added ?source=blog-post to my URL but it isn’t tracking any source when I sign up. Do I need a hidden field as part of the form page? i.e. a hidden field for “source”? As I don’t have one at the moment.

          • http://www.paulminors.com Paul Minors

            Just to clarify – the “source” field exists on the list, but there isn’t a field to collect this in my embedded form.

          • http://term.li/1eFEesN Puru Choudhary

            The javascript should add the “source” field to the embedded form dynamically. If you added “source” fields in Mailchimp, then it should work. If you don’t mind giving me the website address, I can confirm if the script worked or not.

          • http://www.paulminors.com Paul Minors
          • http://term.li/1eFEesN Puru Choudhary

            There’s an issue with the way the script is added to the page. It should be added just before the closing body tag i.e. . Also, make sure that it does not have any additional html elements e.g. p tags, etc.

          • http://www.paulminors.com Paul Minors

            Ah, thought I might be doing it wrong. I am adding it to my MailChimp code on a WordPress page. I can’t actually see any tag. Are you talking about HTML within the script? I do have HTML elsewhere on the page.

          • http://www.paulminors.com Paul Minors

            Sorry, meant to say “Can’t see…” the tag.

          • http://term.li/1eFEesN Puru Choudhary

            Does your wordpress theme allow you to add javascript on the page?

            You can also go into “HTML mode” in wordpress editor and try pasting the code.

          • http://www.paulminors.com Paul Minors

            Yes it does. There was previously some java in the form and I pasted this just below it.

          • http://term.li/1eFEesN Puru Choudhary

            Yeah, it’s still broken. You should probably remove the broken code from your mailchimp form since it can possibly break your other scripts. Then you can try adding the script again through the ‘HTML mode’ in wordpress editor.

          • http://www.paulminors.com Paul Minors

            I have added this in HTML mode, but I’m still getting the same issue. I pasted the code right before here: ““. I can’t see any body tag so am not sure if this is the right place. Are you trustworthy? I could add you as a user to my site if you wouldn’t mind taking a look?

          • http://term.li/1eFEesN Puru Choudhary

            I’m not sure how to answer the trustworthy issue. :) I can take a look at your site and see if I can help. If you decide to add me, you can send the credentials to my email puru@terminusapp.com. Don’t want it to be publicly visible.

          • http://www.paulminors.com Paul Minors

            Haha, I’ll add you now.

          • http://www.paulminors.com Paul Minors

            Also, I pasted the code at the end of my mailchimp embedd code. In this the right place?

  • amruta

    what to do while there are two ids one in main link and another in utm code

  • Steven Cutbirth

    Thanks for this post Puru! This is exactly what I want to do. I tried to implement this on http://mdigitallife.com/physiciancommunications/ but I am having issues. Do you know if this works with Gravity Forms? Does it matter if the mail chimp field is listed as Visible or not? And does the sign up form on the page have to actually show the UTM fields or should they be included in the form but hidden somehow?

    • http://term.li/1eFEesN Puru @ Terminusapp.com

      Steven,

      I saw your website and looks like the actual code was copied in the head section. Only the jQuery part needs to be in the head. The actual script should be just before the closing body tag. Could you please make that change and see if that works?

      To answer your questions:
      1) Yes, this should work for all forms, but you’ll need to make sure that those forms are able to accept those parameters. This blog post helps you for Mailchimp forms.
      2) The Mailchimp form itself does not need to have those fields. The script will add those fields. However, Mailchimp needs to be configured to accept those fields.
      3) The signup form does not need to show the UTM parameters. They are added as hidden fields. You don’t need to add them manually. The script should add them automatically.

      Hope this helps.
      Puru

      • Steven Cutbirth

        Puru,

        Thanks for your reply! I added the query script to the head and attempted to move the rest of the script before the closing body tag.

        I am using the genesis framework and I am not completely certain what is the best way to add the code before the body. I ended up using the Genesis > Theme Settings > Footer Scripts field to add the script just before the body.

        I am using mailchimp and I created all of the UTM parameters as fields in mailchimp exactly as you instructed in your post. I am using gravity forms and their integration with mailchimp to send my submissions to our mailchimp list.

        After making all of the changes and running a few tests, the UTM fields are still showing up blank in the corresponding entries on my mailchimp list. I did see that there was a Syntax Error in the code when I viewed my page source (See attached image). Could this have something to do with my problem? Or do you think it is an issue with gravity forms not accepting the parameters? (I also tried creating fields visible only to admin on my form for each UTM and allowing them to be populated dynamically but still no luck.)

        Thanks again for your help!!
        Steven

        • Guest

          image didn’t show up. Here ya go.

        • http://term.li/1eFEesN Puru @ Terminusapp.com

          Hi Steven,

          Looks like that line did not get copied correctly. It has a missing before +. The correct line is

          return decodeURIComponent(results[1].replace(/+/g, ” “));

          That should make it work. The rest of the code seems to be added correctly.

          • Steven Cutbirth

            Puru,

            Thanks again for your response. It took quite a bit of playing around but I was finally able to make it work (with the help of my friend and his javascript knowledge). For some reason my genesis framework was pulling that “” out of the Javascript every time I submitted it. So I had to create a separate .JS file for the javascript and then use a wp_enqueue_script in my functions.php file to call the .JS file.

            This worked for calling the javascript and it was clearly capturing the value but it was not submitting the value to mailchimp. So I ended up creating hidden fields through gravity forms and mapping them to the UTM fields with the mailchimp to gravity integration. My friend then helped me to edit the javascript to just grab the UTM parameters and populate the hidden fields with them. After some final tweaking we were able to get it to work properly!

            I attached a screenshot of the altered code below in case anyone else is using Gravity Forms and runs into the same problem.

            Thanks again for your help Puru!

          • http://term.li/1eFEesN Puru @ Terminusapp.com

            Hi Steven,

            I’m glad you were able to make it work. I hope this additional information will be valuable to you.

            I’m actually working on making this script more robust and easy to integrate. The new script will even capture the UTM information (in a cookie) when a visitor lands on a different page on your website. Also, it will add first referrer information too which goes missing in Google Analytics when UTMs are present.

            Best,
            Puru