# WordPress

Add ProductLense to WordPress with a header code plugin or a wp_head action in a child theme, no ProductLense plugin required.

ProductLense needs no WordPress plugin of its own. Paste the script into a site-wide header box from a code-snippet plugin, or print it from a child theme's `functions.php`. Either way it lands in the head of every page.

## Add the script

Replace `SITE_ID` with the id from Settings → Sites in the ProductLense dashboard.

```html title="Header box of a code plugin (for example WPCode)" tab="Header code plugin" {2}
<script>window.productlense=window.productlense||function(){(window.productlense.q=window.productlense.q||[]).push(arguments)}</script>
<script defer data-site="SITE_ID" src="https://api.productlense.app/a.js"></script>
```

```php title="wp-content/themes/your-child-theme/functions.php" tab="functions.php" {4}
<?php
add_action('wp_head', function () {
    echo '<script>window.productlense=window.productlense||function(){(window.productlense.q=window.productlense.q||[]).push(arguments)}</script>' . "\n";
    echo '<script defer data-site="SITE_ID" src="https://api.productlense.app/a.js"></script>' . "\n";
});
```

Use a child theme so a theme update does not remove the snippet.

> [!NOTE]
> Caching and optimisation plugins that combine, defer or delay JavaScript can rewrite the tag. Exclude `api.productlense.app/a.js` from those features, then clear the page cache.

## Identify users

For sites with logins (memberships, WooCommerce accounts, LMS plugins), identify the signed-in user in the footer:

```php title="functions.php" {6}
<?php
add_action('wp_footer', function () {
    if (!is_user_logged_in()) return;
    $user = wp_get_current_user();
    printf(
        '<script>window.productlense("identify",%s);</script>',
        wp_json_encode((string) $user->ID)
    );
});
```

The id is passed as a string, as `identify` requires. Use the same id you store on the customer in your billing provider; see [how payments are attributed](/docs/revenue/attribution).

## Custom events

```html
<script>
  document.addEventListener('submit', (e) => {
    if (e.target.matches('.newsletter-form')) window.productlense('event', 'Newsletter signup');
  }, true);
</script>
```

See [custom events](/docs/track/custom-events) for naming rules.

## Verify your installation

1. Clear any page cache, then open your site in a normal browser window, logged out.
2. Open the Live page in the ProductLense dashboard. Your visit appears within a few seconds.
3. In the browser's developer tools, the Network tab shows a `POST` to `https://api.productlense.app/api/e` with status `204`.

A local WordPress on `localhost` sends nothing unless the tag has `data-dev="true"`. Ad blockers in your own browser may block the request. If the visit does not appear, follow [Verify your installation](/docs/install/verify).
