# Caddy

Serve the ProductLense script from your own domain with a Caddy reverse_proxy block, keeping events correct for visitor counts and countries.

Caddy serves the script from your domain with one `handle` block. As with any reverse proxy, do not forward events to ProductLense directly: ProductLense would see your server's IP address for every visitor. Forward them through your application instead, as shown in the [proxy overview](/docs/proxy/overview#option-2-send-events-through-your-server-scale-plan).

## Serve the script

```caddy title="Caddyfile" {4-7}
example.com {
	# ... your existing configuration

	handle /js/a.js {
		rewrite * /a.js
		reverse_proxy https://api.productlense.app {
			header_up Host {upstream_hostport}
		}
	}
}
```

`header_up Host {upstream_hostport}` sends `api.productlense.app` as the host, which ProductLense needs to route the request. Then load the script from your path:

```html
<script defer data-site="SITE_ID" data-api="https://api.productlense.app" src="/js/a.js"></script>
```

## Forward events

On the Scale plan, send `/m/api/e` to your application, which adds the visitor's address before calling the [Events API](/docs/api/events):

```caddy
handle /m/api/e {
	request_body {
		max_size 8KB
	}
	reverse_proxy 127.0.0.1:3000
}
```

Caddy sets `X-Forwarded-For` to the visitor's address by default, so `req.ip` in Express with `trust proxy` enabled is correct.

## Check it works

1. Run `caddy reload`, then open `https://example.com/js/a.js`: it returns JavaScript.
2. Load a page with the developer tools open. The Network tab shows a `POST` to `api/e` with status `204`.
3. Open the Live page in the ProductLense dashboard. Your visit appears within a few seconds.
