An important part of being successful as a digital product seller is taking precautions to protect your product and keep it from being improperly downloaded. In this guide, we have several steps you can take to keep your product secure.
The following subjects are covered in this article:
General Guidance
Here are several suggestions to protect your digital product from piracy:
- If your digital product is a one-time digital product, see the Digital Product Upload article for information about having ClickBank deliver your product to customers.
- Add the following HTML code in the <HEAD> element of your Thank You Page should prevent a search engine robot from indexing that page or following links on that page:
<META name="robots" content="noindex, nofollow"/>
- Give your Thank You Page URL an obscure file name (it should not be something like thankyou.htm, which is too easy to guess).
- Consider using a third party solution. Popular third parties include DLGuard and WishList.
- If you are concerned about security and you have experience with CGI programming, you can generate a script that will verify the customer’s successful completion of the purchase process before allowing him or her access to the Thank You Page. Follow the instructions below for implementing the ClickBank Link Security Script.
Using a Link Security Setup
When the customer completes a purchase, several values are passed along to your thank you page in the query string if you have specified a secret key in your account settings. These are the ClickBank receipt number (cbreceipt), the epoch time of the order (time), the ClickBank item number (item), and the ClickBank proof of purchase (cbpop) value.
During the purchase we encrypt the receipt, time, and item using the secret key you specify in your account. We will then pass the result back to you as a query string parameter called cbpop. Use the validation script to confirm the cbpop value is correct.
Unlike prior versions of this script there is no need for a “seed” value.
The C#, VB.NET, and Ruby examples below are only a method for checking for a valid cbpop value and leave the capturing of the request parameters up to your individual implementations.
Code Samples
PHP Source:
function cbValid(){
$key='YOUR SECRET KEY';
$rcpt=$_REQUEST['cbreceipt'];
$time=$_REQUEST['time'];
$item=$_REQUEST['item'];
$cbpop=$_REQUEST['cbpop'];
$xxpop=sha1("$key|$rcpt|$time|$item");
$xxpop=strtoupper(substr($xxpop,0,8));
if ($cbpop==$xxpop){
return 1;
}
else {
return 0;
}
Perl Source:
sub cbValid { my($q,$key,$rcpt,$time,$item,$cbpop,$xxpop) $key='YOUR SECRET KEY' $q='&'.$ENV{'QUERY_STRING'} $q=~/Wcbreceipt=(w+)/; $rcpt=$1 $q=~/Wtime=(w+)/; $time=$1 $q=~/Witem=(w+)/; $item=$1 $q=~/Wcbpop=(w+)/; $cbpop=$1 use Digest::SHA1 qw(sha1_hex) $xxpop=uc(substr(sha1_hex("$key|$rcpt|$time|$item"),0,8)) return 1 if $cbpop eq $xxpop return 0 }
C# Source:
public bool cbValid(string cbreceipt, string time, string item, string cbpop)
{
string secret_key = "YOUR SECRET KEY"
byte[] data = Encoding.Default.GetBytes(secret_key + "|" + cbreceipt + "|" + time + "|" + item)
byte[] hashedData = new SHA1Managed().ComputeHash(data)
string xxpop = BitConverter.ToString(hashedData).Replace("-","").ToUpper().Substring(0, 8)
return cbpop.Equals(xxpop)
}
VB.NET Source:
Public Function cbValid(ByVal receipt As String, ByVal time As String, ByVal item AsString, ByVal cbpop As String) As Boolean
Dim key As String = "YOUR SECRET KEY"
Dim sha As New SHA1CryptoServiceProvider()
Dim mash As String = key & "|" & receipt & "|" & time & "|" & item
Dim result() As Byte = sha.ComputeHash(NewSystem.Text.ASCIIEncoding().GetBytes(mash))
Dim xxpop As String = BitConverter.ToString(result).Replace("-","").ToUpper().Substring(0, 8)
Return cbpop.Equals(xxpop)
End Function
Ruby Source:
require 'digest/sha1'
def cbValid(receipt, time, item, cbpop)
key = "YOUR SECRET KEY"
popCheck = "#{key}|#{receipt}|#{time}|#{item}"
xxpop = Digest::SHA1.hexdigest(popCheck).upcase[0,8]
cbpop == xxpop
end
Python Source:
import hashlib
def valid_cb_pop(receipt, time, item, cbpop):
secret_key = 'YOUR SECRET KEY'
data = "%s|%s|%s|%s" % (secret_key, receipt, time, item)
return cbpop == hashlib.sha1(data).hexdigest()[:8].upper()
Java Source:
import org.apache.commons.codec.digest.DigestUtils
/**
* Note: To make this method simple it uses the Apache Commons Codec library for computing the SHA value.
* This library is available at: http://commons.apache.org/codec/
**/
public class CBPopValidator {
/**
* Code to validate cbpop parameter passed from ClickBank orderform to thank-you page.
*
* @param receipt The receipt number that ClickBank generated and passed to thank-you page.
* @param time The time (unix timestamp) of the purchase, also passed to thank-you page
* @param item The item purchased, also passed to thank-you page
* @param cbpop The passed validation parameter
* @return True of passed cbpop matches the calculated cbpop using the passed parameters and secret key
**/
public static boolean validCbPop(final String receipt, final String time, final String item, final String cbpop) {
// secret key on the site of your ClickBank account
final String secretKey = "YOUR SECRET KEY"
// create sha1 of passed data with secret key
String hashedData = DigestUtils.shaHex(String.format("%s|%s|%s|%s", secretKey, receipt, time, item))
// compare hashed result to passed value
return hashedData != null && hashedData.substring(0,8).equalsIgnoreCase(cbpop)
}
}
Related Articles
- Encrypting Passed Parameters – This article explains how to encrypt the customer data in your URLs.
- How to Avoid Piracy when Selling Digital Goods