# Overview

Rewardful's remote script loads asynchronously to make it as performant and reliable as possible. You can use our asynchronous JavaScript API to perform client-side conversion tracking as well as execute functions when Rewardful has initialized.

## Add the JavaScript tag + snippet

To add support for our asynchronous JavaScript API, place this code snippet onto every page of your website, ideally in the `<head>` tag:

```markup
<script>(function(w,r){w._rwq=r;w[r]=w[r]||function(){(w[r].q=w[r].q||[]).push(arguments)}})(window,'rewardful');</script>
```

This code will add a `rewardful` function to the page, which can be immediately called and passed instructions that Rewardful will execute once loaded. The general format of these method calls is `rewardful(methodName, arg1, arg2, arg3, ...)`

It's important for this snippet to appear in your HTML **before any calls to the `rewardful` function.** To make it simple, we recommend adding it immediately before the script tag that loads the remote Rewardful script from [Step #1](https://app.getrewardful.com/setup/code) in the setup instructions. Your final Step #1 snippet should look something like this:

```markup
<script>(function(w,r){w._rwq=r;w[r]=w[r]||function(){(w[r].q=w[r].q||[]).push(arguments)}})(window,'rewardful');</script>
<script async src='https://r.wdfl.co/rw.js' data-rewardful='YOUR-API-KEY'></script>
```

{% hint style="warning" %}
Remember to replace `YOUR-API-KEY` with your **Rewardful API Key**, which can be found on the [Company settings](https://app.getrewardful.com/company/edit) page in your Rewardful dashboard.
{% endhint %}

## Client-Side Conversion Tracking

Rewardful's JavaScript API allows you to track conversions with frontend code only — no backend code is required. This can make integrating Rewardful much simpler, and enables you to use Rewardful in scenarios where you're unable to modify backend/server code, such as when using a hosted platform to sell your products.

To track a conversion client-side, use the `"convert"` function, and pass the customer's email address using the `email` parameter. This code should appear on your **thank-you** or **receipt** page (or whatever page your customers are taken to immediately after purchase).

For example:

```markup
<script>
  rewardful('convert', { email: 'joe@example.com' })
</script>
```

This code will search for the most recently created customer with the email address "<joe@example.com>" in your  Stripe account. If the customer exists and the Rewardful cookie is present (i.e. this visitor is a referral), Rewardful with associate the customer with the affiliate.

**Note:** this code only performs network requests if the current website visitor is a referral. If the visitor arrived on your website through another channel, the `convert` function does nothing.

### Requirements

In order to use Client-Side Conversion Tracking there are a few prerequisites:

1. Your Stripe account must be connected to Rewardful with [read-write permission](https://help.getrewardful.com/en/articles/2051884-connect-your-stripe-account).
2. Your platform creates Stripe Customers within your Stripe account when a purchase is made.
3. You are able to add client-side code snippets to your website & receipt/thank-you page, and access the customer's email address on these pages.

{% hint style="warning" %}
The Stripe customer must have been created within the last **24 hours** in order to be tracked with client-side conversion tracking.
{% endhint %}

## Executing code when Rewardful loads

In some cases you might want to execute code once Rewardful has fully loaded and performed any tracking/network requests.&#x20;

Pass a callback function to the `ready` handler to have it executed when Rewardful has fully loaded. This function *always* executes, whether the current visitor is a referral or not. For example:

```markup
<script>
  rewardful('ready', function() {
    console.log('Rewardful Ready!')
  });
</script>
```

If you only want code to run if the current visitor is a referral, you can check the `Rewardful.referral` property:

```markup
<script>
  rewardful('ready', function() {
    if(Rewardful.referral) {
      // The current website visitor is a referral from an affiliate.
    }
  });
</script>
```

Calls to `rewardful` are queued and executed in order once Rewardful has loaded. This means you can queue up multiple functions, and even call `rewardful` if Rewardful is loaded (which effectively calls the underlying function immediately). For example:

```markup
<script>
  rewardful('ready', function() {
    console.log('This will fire first.')
  });
  
  rewardful('ready', function() {
    console.log('This will fire second.')
  });
  
  rewardful('ready', function() {
    console.log('This will fire third.')
  });
</script>
```

{% hint style="warning" %}
**Do not run critical code  within a `ready` handler** (i.e. checkout code). If Rewardful fails to load for any reason (network issue, adblockers, etc.) then the `ready` handler will never run and your code will not execute.

If you must place critical code within a `ready` handler, use defensive programming techniques (such as `setTimeout`) to ensure your critical code will execute even if Rewardful never loads.
{% endhint %}

## Specify traffic source

It's possible to force the current visitor to be attributed to an affiliate even if the visitor didn't arrive through an affiliate link. This is useful for creating landing pages with friendly URLs for a partner promotion, or for creating URLs that are easier to share verbally (i.e. on podcasts).

```markup
<script>
  rewardful('source', AFFILIATE_LINK_TOKEN)
</script>
```

**Example:** instead of `example.com/?via=bond007` you could create a page at `example.com/bond` and include the snippet below to ensure all visitors to this page get attributed to James Bond:

```markup
<script>
  rewardful('source', 'bond007')
</script>
```

It's important to note that this operation **overwrites** any existing referral for the visitor that's stored in the cookie. Continuing our example above, if the visitor first arrived through `example.com/?via=batman` but then went on to visit `example.com/bond` (where the code above is executed) then James Bond would ultimately get credited for the conversion.

## Preloading a referral ID

Normally Rewardful will look for the `?via=token` query string parameter when attributing a visit to an affiliate. When the `via` parameter is present and valid, a new referral will be created for the affiliate and the referral ID stored in the cookie as [`Rewardful.referral`](https://developers.getrewardful.com/javascript-api/overview#referral).

However, there may be situations where you want to *preload a specific referral ID* into the cookie. This can be done by adding a `?referral=<UUID>` parameter to the URL:

```
https://www.example.com/pricing?referral=bffa8b94-b25a-45a4-97a0-1c8ecb8018b9
```

When a user browses to this URL, the existing referral with ID `bffa8b94-b25a-45a4-97a0-1c8ecb8018b0` will be loaded into the cookie. (This is actually how [Rewardful tracks across different domains](https://help.getrewardful.com/en/articles/3492319-does-rewardful-track-referred-visitors-across-domains#tracking-between-domains)).

An example of when this is relevant is when the checkout process is embedded within an iframe. If the parent URL and iframe URL both have a `via` parameter then *two* referrals will be created (one for each window) which artificially inflates visitor stats.

In this scenario, the parent window can check for an existing referral ID and pass it to the iframe by adding a `referral=<UUID>`parameter to the iframe URL before inserting the iframe into the DOM:

```javascript
rewardful('ready', function() {
  const iframe = document.createElement('iframe')

  iframe.src = 'https://checkout.example.com'

  if(Rewardful.referral) {
    iframe.src += `?referral=${Rewardful.referral}`
  }

  document.appendChild(iframe)
});
```

This will ensure the iframe is using the same referral ID as the parent window and will prevent double-tracking visitors. If using the approach above to insert your checkout `iframe`, ensure you have a fallback plan in case Rewardful never loads. See [Executing code when Rewardful loads](https://developers.getrewardful.com/javascript-api/overview#executing-code-when-rewardful-loads) for more information.

## Attributes

{% hint style="info" %}
Because Rewardful loads asynchronously, we recommend accessing these attributes within the `rewardful('ready')`handler. See [Executing code when Rewardful loads](https://developers.getrewardful.com/javascript-api/overview#executing-code-when-rewardful-loads) for details.
{% endhint %}

### Referral

`Rewardful.referral` will return the Referral ID of the current visitor if they were referred, for example: `"98288128-0d5f-45a9-88b3-ef95b229f798"`&#x20;

If the current visitor was not referred by a Rewardful affiliate, `Rewardful.referral`  will return an empty string: `""`&#x20;

```markup
<script>
  rewardful('ready', function() {
    if(Rewardful.referral) {
      console.log('Current referral ID: ', Rewardful.referral);
    } else {
      console.log('No referral present.');
    }
  });
</script>
```

### Affiliate

`Rewardful.affiliate` will return some information about who sent you a referral, for example:

```javascript
{
  id: "b533bfca-7c70-4dec-9691-e136a8d9a26c",
  name: "James Bond",
  first_name: "James",
  last_name: "Bond",
  token: "james007"
}
```

You might want to use this for personalizing your website based on who the affiliate was:

```markup
<script>
  rewardful('ready', function() {
    if(Rewardful.affiliate) {
      $('.affiliate-banner').text(
        `Hi there, friend of ${Rewardful.affiliate.first_name}!`
      ).show();
    }
  });
</script>
```

`Rewardful.affiliate` returns `false` if there is no affiliate, i.e. the current visitor was not referred.

### **Campaign**

`Rewardful.campaign` will return the ID and name of the campaign the affiliate is associated with:

```javascript
{
  "campaign": {
  "id": "1f51675a-646d-4a83-898b-16e0ceeb0373",
  "name": "Friends of Acme, Inc."
  }
}
```

### **Coupon Details**

If you've [attached a coupon to your campaign](https://help.getrewardful.com/en/articles/3024552-double-sided-incentives), the coupon object will be available through `Rewardful.coupon`. The attributes correspond directly to the [coupon object](https://stripe.com/docs/api/coupons/object) in Stripe.

For example, a 25% discount that repeats for 12 months might look like:

```javascript
{
  id: "bf-2019",
  name: "Black Friday 2019",
  duration: "repeating",
  duration_in_months: 12,
  percent_off: 25,
  amount_off: null,
  currency: null
}
```

And a one-time $25 USD discount might look like:

```javascript
{
  id: "save-25",
  name: "One-time $25 credit",
  duration: "once",
  duration_in_months: null,
  percent_off: null,
  amount_off: 2500,
  currency: "usd"
}
```

We recommend checking for the coupon's existence before attempting to access it's attributes, for example:

```markup
<script>
  rewardful('ready', function() {
    if(Rewardful.coupon) {
      showCouponBanner(Rewardful.coupon);
    }
  });
</script>
```

## Methods

### **Attaching to forms**

On page load Rewardful will **automatically** inject a hidden input into forms with a `data-rewardful` attribute. This makes it simple to get the referral ID sent to your server along with the rest of the data from your signup or payment form.

For example, your signup form might look something like this:

```markup
<form action="/signup" method="post" data-rewardful="true">
  <input type="text" name="name">
  <input type="email" name="email">
  <button>Sign Up</button>
</form>
```

If the current visitor came to your site through an affiliate link, Rewardful will detect the data-rewardful attribute and automatically insert a hidden input named `referral` with the unique click ID (UUID) as the value. For example:

```markup
<form action="/signup" method="post" data-rewardful="true">
  <input type="text" name="name">
  <input type="email" name="email">
  <button>Sign Up</button>
  
  <!-- Inserted automatically by Rewardful: -->
  <input type="hidden" name="referral" value="78476c40-0137-11eb">
</form>
```

When the form is submitted, the `POST` data sent to your server will include the `referral` parameter, along with the rest of the customer data. You can extract this value (`$_POST['referral']` in PHP, `params[:referral]` in Rails, etc) and add it to the Stripe customer's metadata or save it in your own database for future use.

### Manually attaching to forms

If your form is dynamically added to the page ([Turbolinks](https://github.com/turbolinks/turbolinks), a single-page app or a modal) you'll need to manually tell Rewardful to attach to these forms *after* they have been added to the DOM.

To attach to all forms present in the DOM with the `data-rewardful` attribute, you can call `Rewardful.Forms.attach()`&#x20;

#### Turbolinks example:

```javascript
document.addEventListener("turbolinks:load", function() {
  Rewardful.Forms.attach();
});
```

#### If your form appears inside a [Bootstrap Modal](https://getbootstrap.com/docs/4.0/components/modal/):

```javascript
$('#signup-modal').on('shown.bs.modal', function (e) {
  Rewardful.Forms.attach();
});
```

### **Attaching to specific forms**

If you'd like to manually attach the hidden referral input into a specific form, you can do so with `Rewardful.Forms.add(formElement)`, for example:

```
const signupForm = document.getElementById('signup-form');
Rewardful.Forms.add(signupForm);
```

This can be useful in circumstances where you cannot easily modify the source code of the `form` tag (for example, using a CMS or hosted service) and are unable to add the `data-rewardful` attribute.

## Troubleshooting

If you're running into issues with your JavaScript integration it's possible to inspect the data stored in the Rewardful cookie using the `Rewardful._cookie` attribute.

{% hint style="warning" %}
**IMPORTANT:** The`Rewardful._cookie` is for *debugging purposes only*. This data structure is for may change formats at any time without warning and *should not* be used for any purpose other than troubleshooting.
{% endhint %}

Here's an example of the data structure returned by `Rewardful._cookie`:

```javascript
{
  "id": "c4b3c530-3d7b-4f01-89bf-12ce7cbe1e4b",
  "created_at": "2021-01-10T13:27:16.766-07:00",
  "affiliate": {
    "id": "b533bfca-7c70-4dec-9691-e136a8d9a26c",
    "name": "James Bond",
    "first_name": "James",
    "last_name": "Bond",
    "token": "jb007"
  },
  "campaign": {
    "id": "1f51675a-646d-4a83-898b-16e0ceeb0373",
    "name": "Friends of Acme, Inc."
  },
  "coupon": null,
  "cookie": {
    "domain": "example.com"
  }
}
```

| Attribute    | Description                                                  |
| ------------ | ------------------------------------------------------------ |
| `id`         | The UUID of the referral (equivalent to`Rewardful.referral)` |
| `created_at` | Timestamp at which this referral was originally created.     |
| `affiliate`  | Equivalent to `Rewardful.affiliate`                          |
| `campaign`   | Equivalent to `Rewardful.campaign`                           |
| `coupon`     | Equivalent to `Rewardful.coupon`                             |
| `cookie`     | Additional metadata about the cookie                         |


---

# Agent Instructions: Querying This Documentation

If you need additional information that is not directly available in this page, you can query the documentation dynamically by asking a question.

Perform an HTTP GET request on the current page URL with the `ask` query parameter:

```
GET https://developers.rewardful.com/javascript-api/overview.md?ask=<question>
```

The question should be specific, self-contained, and written in natural language.
The response will contain a direct answer to the question and relevant excerpts and sources from the documentation.

Use this mechanism when the answer is not explicitly present in the current page, you need clarification or additional context, or you want to retrieve related documentation sections.
