Eric Nagel

Eric Nagel

CTO, PHP Programmer, Affiliate Marketer & IT Consultant

Google Affiliate Network API PHP Script

I have been, or can be if you click on a link and make a purchase, compensated via a cash payment, gift, or something else of value for writing this post. Regardless, I only recommend products or services I use personally and believe will be good for my readers.

Google Affiliate Network

I was excited when I read Google had released an API for their Affiliate Network, as I wanted to automate pulling sales data from GAN. But I quickly became disheartened when I realized how difficult it is to use.

Since this was for myself, and not a web-based service that would be used by others, the Simple API method of authorization was good enough. After getting it to work with Picasa, but not GAN, I asked for some help and was introduced to the OAuth 2.0 Playground. This showed me the headers I’d need to send, and how OAuth 2.0 works.

For the record: the Google Affiliate Network API does NOT support Simple API Access. You cannot access the service with an API Key and IP locking.

I now have a working script, and have written up step-by-step instructions on how you can pull orders from GAN automatically each day.

This script is not complete, as it’s up to you to do something with the data once you have it. You can also modify the final call to pull advertisers, instead of orders.

Copy this to a new file (double-click to select-all. I named mine gan.php)

<?php
$cPublisherID	=	'';
$cScope			=	'https://www.googleapis.com/auth/gan.readonly';
$cClientID		=	'';
$cClientSecret	=	'';
$cRedirectURI	=	'urn:ietf:wg:oauth:2.0:oob';

$cAuthCode		=	'';
$cRefreshToken	=	'';

$bRefresh = true;

if (empty($cAuthCode)) {
	$rsParams = array(
						'response_type'	=>	'code',
						'client_id'		=>	$cClientID,
						'redirect_uri'	=>	$cRedirectURI,
						'scope'			=>	$cScope
						);
	$cOauthURL = 'https://accounts.google.com/o/oauth2/auth?' . http_build_query($rsParams);
	echo("Go to\n$cOauthURL\nand enter the given value into \$cAuthCode\n");
	exit();
} // ends if (empty($cAuthCode))
elseif (empty($cRefreshToken)) {
	$cTokenURL = 'https://accounts.google.com/o/oauth2/token';
	$rsPostData = array(
						'code'			=>	$cAuthCode,
						'client_id'		=>	$cClientID,
						'client_secret'	=>	$cClientSecret,
						'redirect_uri'	=>	$cRedirectURI,
						'grant_type'	=>	'authorization_code',
						);
	$ch = curl_init();

	curl_setopt($ch, CURLOPT_URL, $cTokenURL);
	curl_setopt($ch, CURLOPT_POST, 1);
	curl_setopt($ch, CURLOPT_POSTFIELDS, $rsPostData);
	curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);

	$cTokenReturn = curl_exec($ch);
	$oToken = json_decode($cTokenReturn);
	echo("Enter the following values:\n\n");
	echo("\$cRefreshToken = '" . $oToken->refresh_token . "';\n");
} // ends
else {
	// Get a new Access Token
	$cTokenURL = 'https://accounts.google.com/o/oauth2/token';
	$rsPostData = array(
						'client_secret'	=>	$cClientSecret,
						'grant_type'	=>	'refresh_token',
						'refresh_token'	=>	$cRefreshToken,
						'client_id'		=>	$cClientID
						);
	$ch = curl_init();

	curl_setopt($ch, CURLOPT_URL, $cTokenURL);
	curl_setopt($ch, CURLOPT_POST, 1);
	curl_setopt($ch, CURLOPT_POSTFIELDS, $rsPostData);
	curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);

	$cTokenReturn = curl_exec($ch);
	$oToken = json_decode($cTokenReturn);
	$cAccessToken = $oToken->access_token;

	// Get the results
	$cGANURL = 'https://www.googleapis.com/gan/v1beta1/publishers/' . $cPublisherID . '/events';
	$cAuthHeader = "Authorization: OAuth " . $cAccessToken;

	$ch = curl_init();

	curl_setopt($ch, CURLOPT_HTTPHEADER, array($cAuthHeader));
	curl_setopt($ch, CURLOPT_URL, $cGANURL);
	curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);

	$cJsonReturn = curl_exec($ch);

	print_r(json_decode($cJsonReturn));
} // ends else from <all authenticated>

?>

Login to your GAN account and get your Publisher ID. It’s the 6-character ID under your name (or your site’s name) in the upper-right once you login. Enter that value here

$cPublisherID	=	'';

GAN API Create New ProjectNext, go to https://code.google.com/apis/console/, login, click the drop-down in the left navigation, then choose Create… and name your project. I named my project GAN Reporting

In the list of services, turn on Google Affiliate Network API

Turn on the Google Affiliate Network API Service
Turn on the Google Affiliate Network API Service

Create an OAuth 2.0 client ID...Now click on API Access (left navigation), then click on the button Create an OAuth 2.0 client ID…

Enter “GAN Reporting” for the “Product name” then click Next

GAN API Create Client ID
GAN API Create Client ID

Choose “Installed application” for the Application type, then click “Create client ID”

GAN API Application Type
GAN API Application Type

You now have a Client ID, Client secret, and 2 Redirect URIs
GAN API OAuth Client

Enter your Client ID in the variable $cClientID and the Client secret value in $cClientSecret

$cClientID		=	'xxxxxxxxxxxx.apps.googleusercontent.com';
$cClientSecret	=	'xxxxxxxxxxxxxxxxx_xxxxxx';

Make sure $cRedirectURI is correct. Then save and upload gan.php (yes, there will be some empty variables… that’s OK!), and run it via command-line or a browser. You’ll see:

[esnagel@ec2 temp]$ php gan.php
Go to
https://accounts.google.com/o/oauth2/auth?response_type=code&client_id=xxxxxxxxxxxx.apps.googleusercontent.com&redirect_uri=urn%3Aietf%3Awg%3Aoauth%3A2.0%3Aoob&scope=https%3A%2F%2Fwww.googleapis.com%2Fauth%2Fgan.readonly
and enter the given value into $cAuthCode

Go to this URL while logged into the Google account associated with your Google Affiliate Network (usually you@gmail.com, but if you’re like me and use Google Apps, you’ll have to open an Incognito window in Chrome to login)

You’ll see a page telling you GAN Reporting (your application) wants access to your GAN data. Click Allow access.

GAN API Allow Access
GAN API Allow Access

Next, you’ll see an Auth Code.

GAN API Auth Code
GAN API Auth Code

Copy that value and paste it back into gan.php:

$cAuthCode		=	'x/x-xxxxxxxxxx-xxxxxxxxxxxxxxx';

Save, upload and run the script again. Now, you’re given the value for the Refresh Token. Copy that and put it in gan.php:

$cRefreshToken = 'x/xxx_xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx';

Save, upload, and run the script again. Now when you run the script via command-line, you’ll see:

[esnagel@ec2 temp]$ php gan.php
stdClass Object
(
    [kind] => gan#events
    [items] => Array
        (
            [0] => stdClass Object
                (
                    [kind] => gan#event
                    [modifyDate] => 2011-12-21T01:17:47.608Z
                    [eventDate] => 2011-12-21T00:46:38.185Z
                    [orderId] => xxxxxx
                    [commissionableSales] => stdClass Object
                        (
                            [amount] => xx.xx
                            [currencyCode] => USD
                        )

                    [status] => ACTIVE
                    [type] => TRANSACTION
                    [products] => Array
                        (
                            [0] => stdClass Object
                                (
                                    [sku] => @adjustment
                                    [quantity] => 1
                                    [unitPrice] => stdClass Object
                                        (
                                            [amount] => xx.xx
                                            [currencyCode] => USD
                                        )

                                )

                        )

                    [advertiserId] => xxxxxx
                    [advertiserName] => xxxxxxxxxxxxx
                    [memberId] => xxxxxxxxxx
                    [earnings] => stdClass Object
                        (
                            [amount] => xx.xxxx
                            [currencyCode] => USD
                        )

                )
...

This is the result of

print_r(json_decode($cJsonReturn));

At this point, it’s up to you to loop through the items array and do what you want with the data.

I’ll answer some technical questions in the comments, but for the complicated questions, I’ll direct you to my PHP Programmer page where you can email or call me to describe your project and receive an estimate.

Comments
  • Jhun
    Posted December 22, 2011 3:40 am 0Likes

    Hope you can help me understanding the json code response I get.
    I only get the following json code response:

    { “kind”: “gan#events” }

    upon running the code:

    —————————————————————–

    // Get the results
    $cGANURL = ‘https://www.googleapis.com/gan/v1beta1/publishers/’ . $cPublisherID . ‘/events’;
    $cAuthHeader = “Authorization: OAuth ” . $cAccessToken;

    $ch = curl_init();

    curl_setopt($ch, CURLOPT_HTTPHEADER, array($cAuthHeader));
    curl_setopt($ch, CURLOPT_URL, $cGANURL);
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);

    $cJsonReturn = curl_exec($ch);

    print_r(json_decode($cJsonReturn));

    —————————————————————–

    * But changing the “events” to “advertisers” returns advertiser data in json code format.

    Thanks you.

    • Eric Nagel
      Posted December 22, 2011 7:30 am 0Likes

      I’m pretty new to this, but my first thought is: do you have data to return? Did you have sales (orders) in the past 24 hours?

      Based on http://code.google.com/apis/gan/v1beta1/events.html, you’re getting a result, but the result is empty.

      Try setting eventDateMin and eventDateMax to extend your timeframe.

      • Brandon Carlson
        Posted January 27, 2012 5:11 pm 0Likes

        Eric,

        Google doesn’t specify the date format for eventDateMax, I’ve tried several different variations (mm/dd/YYYY, dd/mm/YYYY, mm/dd/yy, dd/mm/yy, and even unix timestamp). Do you know what format we’re supposed to use?

        • Eric Nagel
          Posted January 27, 2012 5:22 pm 0Likes

          I’d guess ISO 8601, as that’s what they return. That’s “c” in PHP’s date() function

          • Brandon Carlson
            Posted January 27, 2012 5:34 pm 0Likes

            That looks right. I tried eventDateMin=2011-09-04T19:56:22.982Z which I found in one of their python samples and that seemed to do the trick.

            Thanks for the quick reply, and the awesome post!

  • Matt
    Posted December 22, 2011 11:41 am 0Likes

    Eric,

    Thanks for posting this. This was extremely helpful.

  • R.
    Posted January 3, 2012 3:05 pm 0Likes

    Thank you a lot. I was going crazy with that… Is the first place I find useful information!

  • Trackback: Part 2: OAuth2 and Configuring Your ‘Application’ With Google » CornEmpire Software
  • Trackback: Access Your GAN (Google Affiliate Network ) with API PHP Script - Pogung177 – Not Addict Anymore
  • Charlie
    Posted January 19, 2012 1:24 pm 0Likes

    Eric,

    Any ideas as to why I’m getting a blank $cRefreshToken? After running the script with $cAuthCode added I just get:

    Enter the following values: $cRefreshToken = ”;

    Thanks for your input in advance.

  • MiniGig Custom Web Development
    Posted February 7, 2012 11:06 pm 0Likes

    To fix the empty $cRefreshToken issue you need to enable SSL by adding
    curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false);
    right before curl_exec($ch);

    Good Luck! Contact minigig.com if you need web or .NET development!

    • Eric Nagel
      Posted February 8, 2012 6:20 am 0Likes

      Thanks guys! Hope that works for those having trouble w/ this.

  • Tim
    Posted February 20, 2012 11:51 am 0Likes

    Thank you so much for this code, extremely grateful.

    I did make a couple changes to your code in order to download all transactions for a certain period, as by default there is a limit of 20 transactions, and even if you specify a number the max is 100.

    while (true) {

    $cGANURL = ‘https://www.googleapis.com/gan/v1beta1/publishers/’.$cPublisherID.’/events?maxResults=100′;

    if (isset($cJson->nextPageToken)) $cGANURL .= ‘&pageToken=’.$cJson->nextPageToken;

    $cAuthHeader = “Authorization: OAuth “.$cAccessToken;

    [existing code]

    $cJsonReturn = curl_exec($ch);
    $cJson = json_decode($cJsonReturn);

    if (!isset($cJson->nextPageToken)) break;

    }

  • Sri
    Posted March 21, 2012 5:05 am 0Likes

    Hi Eric,
    What is the validity of the refresh token?
    –Sri

  • Fahad
    Posted June 15, 2012 3:00 am 0Likes

    Hello Eric,

    I wasted lot of my time for finding a php code like this. It helped me a lot.
    Thank you very much for this code.

    Thanks,
    Fahad

  • Ajay
    Posted June 22, 2012 2:19 am 0Likes

    Is there any other way to retrieve event without refresh token?

  • Namrata Mathur
    Posted July 30, 2012 3:16 am 0Likes

    Hi,

    Thanks for useful post.

    Is there any way to automaticlly allow access when gan reporting request permission to view GAN data, through code. I want to create a cron job to fetch event list.

    Thanks in advance.
    NM

    • Eric Nagel
      Posted July 30, 2012 10:24 am 0Likes

      That’s what this script is doing. While I store the variables in the script (as I’m the only account I need to pull data from) I have used this as the basis of a script for a client of mine, and we store the GAN ids in a database.

  • Namrata Mathur
    Posted July 31, 2012 12:28 am 0Likes

    Hi Eric,

    I think my comment was not so clear. Let me explain it again.

    – When we first time run this script, it generates the URL for AuthCode.
    – Then we open that URL in our browser.
    – If we are not logged in to our GAN account then it we sow the login page,
    – and at last we saw the message to allow access (the dialog box which you have mentioned as “GAN API Allow Access”).
    – After clicking on allow access button we get the AuthCode.

    My requirement is to generate/get AuthCode at runtime without using above process. So I want to know if it is possible. If yes then how?

    Please reply, I really need help.

    Thanks,
    Namrata

    • Eric Nagel
      Posted July 31, 2012 7:37 am 0Likes

      Hi Namrata,

      No, this is not possible, as the AuthCode is specific to the Google account that you’re logged in with.

      I guess I shouldn’t say it’s not possible… in theory you could automate a Google login, hit the URL, authenticate the app then copy the AuthCode, but I’m not sure how to go about doing that. The first step would be to see if you can simulate a login w/ your GAN username / password.

  • Namrata Mathur
    Posted July 31, 2012 7:50 am 0Likes

    Hello Eric,

    Thanks for reply,

    I know how to automate the google login and I can also hit the URL through code, but don’t know how to authenticate the app at runtime. 🙁

    Please tell me if you have any idea for that.

    Thanks again!
    Namrata

  • Namrata Mathur
    Posted July 31, 2012 7:57 am 0Likes

    Hi Eric,

    Thanks again, actually I am using .NET client library for GAN API. I was lurking here coz I wanted to findout a working code so that I can use the login used in that code, and your code was very helpfull for me. I will try to implement your suggetion in my code.

    Thanks a lot.

    Regards,
    Namrata Mathur

  • Namrata Mathur
    Posted July 31, 2012 7:59 am 0Likes

    Thanks again for this helpful code.

  • Tom Harrison
    Posted August 30, 2012 6:37 pm 0Likes

    Here’s a version written as a Ruby (Rails) library, inspired by your example here. Thanks!!!!

    https://gist.github.com/3543368

  • Mack
    Posted September 27, 2012 3:39 am 0Likes

    where can i get Redirect URIs and how can i create when i want to grab coupon for my website.

    • Eric Nagel
      Posted September 27, 2012 10:13 pm 0Likes

      Hi Mark,

      I haven’t used the GAN API for this, so I’m not sure. Check the docs

  • Andrew
    Posted September 29, 2012 10:31 am 0Likes

    After inserting the $cRefreshToken into code and run the file it shows this message but when i check by below url then i am getting result https://developers.google.com/oauthplayground/?code

    stdClass Object ( [error] => stdClass Object ( [errors] => Array ( [0] => stdClass Object ( [domain] => global [reason] => authError [message] => Invalid Credentials [locationType] => header [location] => Authorization ) ) => 401 [message] => Invalid Credentials ) )

    • Eric Nagel
      Posted September 30, 2012 4:33 pm 0Likes

      Make sure you’re using the same account. For example, my GAN account is esnagel@gmail.com, but everything else I use is eric@ericnagel.com. So if you put in your publisherID for one account, then authorize the other, it won’t work.

  • Brad Moore
    Posted October 10, 2012 10:27 am 0Likes

    So I’m assuming from this discussion thread that there is no way to automate the login and authentication to GAN? I have a script that connects to each of the other networks (i.e. CJ, Linkshare, and Pepperjam) to retrieve transaction details and can automate everything with curl. This script runs with a kron job and is not user attended. I would like to add GAN access to this script, but it doesn’t sound possible.

    Am I understanding correctly? And if so, where could I go to learn how to simulate a browser session with curl? I currently use curl to send post requests to a remote site and then process the return data as json, xml, or straight text. What I don’t know how to do is how to login to google and how I would respond to an alert box on the page such as the GAN Reporting is requesting permission… popup.

    Any suggestions?

    • Eric Nagel
      Posted October 10, 2012 11:04 am 0Likes

      I’ve used this (above) method for a couple of clients. The owner of the gmail account must authenticate the app, then the rest can be automated. You can’t get around that first bit.

  • Ted
    Posted November 30, 2012 3:39 am 0Likes

    Thanks this is great, I play a little bit and is awesome 🙂

    One question, since I am not professional , how to handle stdObject, I mean how to parse row by row, tried but don’t have success…

  • Chris
    Posted December 6, 2014 11:29 am 0Likes

    I struggled with this for a week (was receiving a blank refresh token). After trying a few different scripts, I came back and found the issue with this script. In the refresh token call, you have the redirect_url spelled incorrectly with a I rather than a L.

Leave A Comment

Your email address will not be published. Required fields are marked *

This site uses Akismet to reduce spam. Learn how your comment data is processed.