### Install @counterscale/tracker
Source: https://github.com/benvinegar/counterscale/blob/main/packages/tracker/README.md
Install the tracker library using npm. This is the first step before initializing the tracker in your project.
```bash
npm install @counterscale/tracker
```
--------------------------------
### Install Project Dependencies
Source: https://github.com/benvinegar/counterscale/blob/main/CONTRIBUTING.md
Run this command to install all necessary project dependencies using pnpm.
```bash
pnpm install
```
--------------------------------
### Install Counterscale CLI
Source: https://github.com/benvinegar/counterscale/blob/main/README.md
Run the Counterscale installer script to deploy the server application. This script will prompt for necessary Cloudflare API tokens and configuration details.
```bash
npx @counterscale/cli@latest install
```
--------------------------------
### Install Playwright Browsers
Source: https://github.com/benvinegar/counterscale/blob/main/CONTRIBUTING.md
Navigate to the tracker package directory and install Playwright browsers. This is necessary for end-to-end testing.
```bash
cd packages/tracker && pnpm playwright install
```
--------------------------------
### Run Development Server (Cloudflare Miniflare)
Source: https://github.com/benvinegar/counterscale/blob/main/CONTRIBUTING.md
Starts the Cloudflare Miniflare server with a build of the Remix files. This more closely matches the production environment but does not auto-rebuild.
```bash
pnpm turbo preview
```
--------------------------------
### Run Development Server (Node.js)
Source: https://github.com/benvinegar/counterscale/blob/main/CONTRIBUTING.md
Starts the Vite development server in Node.js. This server supports hot-reloading for faster development cycles.
```bash
pnpm turbo dev
```
--------------------------------
### Browser Client Initialization
Source: https://context7.com/benvinegar/counterscale/llms.txt
Initializes the browser tracker with basic setup. Automatically tracks pageviews on navigation.
```APIDOC
## init(opts: ClientOpts): void — Initialize the browser tracker
Creates a singleton client instance. Automatically begins tracking pageviews unless `autoTrackPageviews` is set to `false`. Subsequent calls to `init` are no-ops if the client already exists.
### Description
Initializes the browser tracker with essential configuration like `siteId` and `reporterUrl`.
### Parameters
#### Path Parameters
None
#### Query Parameters
None
#### Request Body
None
### Request Example
```typescript
import * as Counterscale from "@counterscale/tracker";
Counterscale.init({
siteId: "my-blog",
reporterUrl: "https://analytics.myworkers.dev/collect",
});
if (Counterscale.isInitialized()) {
console.log("Tracker is live");
const client = Counterscale.getInitializedClient();
}
Counterscale.cleanup();
```
### Response
None (void function)
#### Success Response (200)
N/A
#### Response Example
N/A
```
--------------------------------
### Express.js Middleware Example
Source: https://github.com/benvinegar/counterscale/blob/main/packages/tracker/SERVER.md
Example of integrating Counterscale tracking into an Express.js application using middleware.
```APIDOC
```javascript
import express from "express";
import * as Counterscale from "@counterscale/tracker/server";
const app = express();
// Initialize tracker
Counterscale.init({
siteId: "your-site-id",
reporterUrl: "https://your-analytics-domain.com/collect",
});
// Track all requests
app.use(async (req, res, next) => {
try {
await Counterscale.trackPageview({
url: req.originalUrl,
hostname: req.get("Host"),
referrer: req.get("Referer"),
});
} catch (error) {
// Tracking errors shouldn't break your app
console.error("Tracking error:", error);
}
next();
});
```
```
--------------------------------
### Install Counterscale CLI to Cloudflare Workers
Source: https://context7.com/benvinegar/counterscale/llms.txt
Use this command to deploy Counterscale to Cloudflare Workers. It guides you through authentication, `wrangler.json` setup, secret configuration, and deployment. Use `--advanced` for custom worker names and dataset names, and `--verbose` for detailed output.
```bash
# Prerequisites: log in to Cloudflare CLI first
npx wrangler login
# Run the installer (latest release)
npx @counterscale/cli@latest install
# Advanced mode: customize worker name and dataset
npx @counterscale/cli@latest install --advanced
# Verbose mode: show internal deployment steps
npx @counterscale/cli@latest install --verbose
# Upgrade an existing deployment
npx @counterscale/cli@latest install
# → Re-deploys without prompting for API key if already set
# → Data carries forward (Analytics Engine dataset unchanged)
```
--------------------------------
### npx @counterscale/cli@latest install
Source: https://context7.com/benvinegar/counterscale/llms.txt
Deploys Counterscale to Cloudflare Workers using an interactive wizard.
```APIDOC
## npx @counterscale/cli@latest install
### Description
Deploy to Cloudflare Workers. Interactive wizard that authenticates with Cloudflare, stages a `wrangler.json`, sets Worker secrets, and runs `wrangler deploy`. Supports `--advanced` to customize worker name and analytics dataset name; `--verbose` for detailed output.
### Method
`install`
### Endpoint
`npx @counterscale/cli@latest install`
### Parameters
#### Path Parameters
None
#### Query Parameters
- **--advanced** (flag) - Optional - Customize worker name and analytics dataset name.
- **--verbose** (flag) - Optional - Show detailed output.
### Request Example
```bash
npx @counterscale/cli@latest install
npx @counterscale/cli@latest install --advanced
npx @counterscale/cli@latest install --verbose
```
### Response
#### Success Response
Deployment to Cloudflare Workers is successful.
```
--------------------------------
### Standard ESLint Configuration
Source: https://github.com/benvinegar/counterscale/blob/main/packages/eslint-config/README.md
Use this for a straightforward setup of ESLint. It requires specifying the base directory and can be configured for React and TypeScript projects, along with custom global variables.
```javascript
import { createConfig } from "@counterscale/eslint-config";
import path from "node:path";
import { fileURLToPath } from "node:url";
const __filename = fileURLToPath(import.meta.url);
const __dirname = path.dirname(__filename);
export default createConfig({
baseDirectory: __dirname,
ignores: [
"build/*",
"node_modules",
"dist/*",
// Add any package-specific ignores
],
// Configure based on package type
includeReact: true, // Set to true for React packages
includeTypeScript: true, // Set to true for TypeScript packages
tsconfigRootDir: "./",
project: "./tsconfig.json", // Path to your tsconfig.json
additionalGlobals: {
// Add any package-specific globals
counterscale: true,
},
});
```
--------------------------------
### Express.js Middleware for Tracking
Source: https://github.com/benvinegar/counterscale/blob/main/packages/tracker/SERVER.md
Integrate server-side tracking into an Express.js application using middleware. This example tracks all incoming requests, capturing URL, hostname, and referrer.
```javascript
import express from "express";
import * as Counterscale from "@counterscale/tracker/server";
const app = express();
// Initialize tracker
Counterscale.init({
siteId: "your-site-id",
reporterUrl: "https://your-analytics-domain.com/collect",
});
// Track all requests
app.use(async (req, res, next) => {
try {
await Counterscale.trackPageview({
url: req.originalUrl,
hostname: req.get("Host"),
referrer: req.get("Referer"),
});
} catch (error) {
// Tracking errors shouldn't break your app
console.error("Tracking error:", error);
}
next();
});
```
--------------------------------
### HTML Script Tag Embed
Source: https://context7.com/benvinegar/counterscale/llms.txt
Embeds the Counterscale tracker directly into an HTML page using a script tag for a zero-dependency setup.
```APIDOC
## HTML script tag embed — CDN / no-build setup
The server serves `tracker.js` as a static asset. Embed it directly in HTML for zero-dependency tracking. The `data-site-id` attribute replaces the programmatic `siteId` option.
### Description
Provides instructions for embedding the Counterscale tracker via a CDN script tag, simplifying integration without a build process.
### Parameters
None
### Request Example
```html
```
### Response
None (This is an embeddable script)
#### Success Response (200)
N/A
#### Response Example
N/A
```
--------------------------------
### Get Top Pages by Visitor Count
Source: https://context7.com/benvinegar/counterscale/llms.txt
Returns a list of pages ranked by visitor count, along with their respective visitor and view counts. Data is sorted in descending order of visitors.
```typescript
const topPages = await ae.getCountByPath("my-blog", "30d", "UTC", {}, 1);
// → [
// ["/", 1820, 4301],
// ["/blog/post-1", 412, 890],
// ["/about", 204, 320],
// ]
```
--------------------------------
### Embed Counterscale Tracking Script
Source: https://github.com/benvinegar/counterscale/blob/main/README.md
Include this HTML snippet in your website's code to start reporting traffic to your Counterscale deployment. Ensure the `data-site-id` is unique for each website and the `src` URL points to your deployed Counterscale worker.
```html
```
--------------------------------
### Get Visitor Counts by Referrer, Country, Browser, and Device Type
Source: https://context7.com/benvinegar/counterscale/llms.txt
Use these functions to retrieve top N results for specific dimensions. They share a common signature and return arrays of dimension-visitor/view counts.
```typescript
const referrers = await ae.getCountByReferrer("my-blog", "7d", "UTC", {}, 1);
// → [["https://news.ycombinator.com", 510, 620], ["https://google.com", 300, 380]]
```
```typescript
// Country breakdown: [country, visitors][]
const countries = await ae.getCountByCountry("my-blog", "7d");
// → [["US", 1200], ["GB", 340], ["DE", 210]]
```
```typescript
// Browser breakdown
const browsers = await ae.getCountByBrowser("my-blog", "30d");
// → [["Chrome", 2100], ["Safari", 980], ["Firefox", 340]]
```
```typescript
// Device type
const devices = await ae.getCountByDeviceType("my-blog", "30d");
// → [["desktop", 2800], ["mobile", 1400], ["tablet", 120]]
```
--------------------------------
### Get Sites Ordered by Hits
Source: https://context7.com/benvinegar/counterscale/llms.txt
This function lists all site IDs tracked in the dataset, ordered by total hit count. It's useful for multi-site deployments and accepts an interval and an optional limit.
```typescript
const sites = await ae.getSitesOrderedByHits("1d", 5);
// → [
// ["marketing-site", 4800],
// ["docs-site", 920],
// ["blog", 540],
// ]
```
--------------------------------
### collectRequestHandler
Source: https://context7.com/benvinegar/counterscale/llms.txt
Ingests a pageview hit by processing query parameters from a GET request, resolving session state, parsing the user agent, and writing data to the Cloudflare Analytics Engine. It returns a 1x1 transparent GIF.
```APIDOC
## collectRequestHandler(request, env, extra) — Ingest a pageview hit
### Description
The core data ingestion function. Reads query parameters from a pixel GET request, resolves cookieless session state from `If-Modified-Since` / `Last-Modified` headers (or an explicit `ht` hit-type param), parses the user agent, and writes a data point to the Cloudflare Analytics Engine binding (`WEB_COUNTER_AE`). Returns a 1x1 transparent GIF.
### Query String Parameters
- **sid** (string) - Required - Site ID
- **h** (string) - Optional - Hostname
- **p** (string) - Optional - Path
- **r** (string) - Optional - Referrer
- **ht** (integer) - Optional - Hit type (1=new visit, 2=anti-bounce, 3=repeat hit)
- **us** (string) - Optional - UTM Source
- **um** (string) - Optional - UTM Medium
- **uc** (string) - Optional - UTM Campaign
- **ut** (string) - Optional - UTM Term
- **uco** (string) - Optional - UTM Content
### Request Example (Tracker)
```
GET /collect?sid=my-blog&h=example.com&p=/post-1&r=https://google.com&us=organic
Headers:
If-Modified-Since: Mon, 13 Jan 2025 00:00:01 GMT ← session cookie substitute
```
### Response Example
```
HTTP/2 200
Content-Type: image/gif
Last-Modified: Mon, 13 Jan 2025 00:00:02 GMT ← increments hit count
```
### Direct curl test (new visit, no prior session):
```bash
curl -s -o /dev/null -D - \
"https://analytics.myworkers.dev/collect?sid=test-site&h=example.com&p=/test&r="
```
### Direct curl test response:
```
HTTP/2 200
content-type: image/gif
last-modified: Mon, 13 Jan 2025 00:00:01 GMT
tk: N
```
```
--------------------------------
### Track Server-Side Pageviews with Express Middleware
Source: https://context7.com/benvinegar/counterscale/llms.txt
Integrate this middleware into your Express application to automatically track pageviews for every incoming GET request. UTM parameters are extracted from the URL, but explicit parameters will override them. Errors are handled internally and do not throw exceptions.
```typescript
import express from "express";
import * as Counterscale from "@counterscale/tracker/server";
const app = express();
Counterscale.init({
siteId: "my-ssr-app",
reporterUrl: "https://analytics.myworkers.dev/collect",
});
// Middleware: track every incoming GET request
app.use(async (req, res, next) => {
// Non-blocking — errors are swallowed internally
void Counterscale.trackPageview({
url: req.originalUrl, // e.g. "/products/widget?utm_source=email"
hostname: req.hostname, // required when url is relative
referrer: req.get("Referer"), // optional
// UTM params can be passed explicitly or extracted from url automatically
utmSource: "email",
utmMedium: "newsletter",
utmCampaign: "spring-sale",
utmTerm: "widget",
utmContent: "header-cta",
});
next();
});
// Expected: fires POST to /collect with all UTM + path data; never throws
```
--------------------------------
### Ingest Pageview Hit with collectRequestHandler
Source: https://context7.com/benvinegar/counterscale/llms.txt
The core data ingestion function. Reads query parameters from a pixel GET request, resolves cookieless session state, parses the user agent, and writes a data point to the Cloudflare Analytics Engine binding. Returns a 1x1 transparent GIF.
```typescript
// Query string parameters understood by /collect:
// sid = site ID (required)
// h = hostname
// p = path
// r = referrer
// ht = hit type (1=new visit, 2=anti-bounce, 3=repeat hit)
// us = utm_source
// um = utm_medium
// uc = utm_campaign
// ut = utm_term
// uco = utm_content
// Example raw request (sent automatically by the tracker):
// GET /collect?sid=my-blog&h=example.com&p=/post-1&r=https://google.com&us=organic
// Headers:
// If-Modified-Since: Mon, 13 Jan 2025 00:00:01 GMT ← session cookie substitute
// Response:
// 200 OK Content-Type: image/gif
// Last-Modified: Mon, 13 Jan 2025 00:00:02 GMT ← increments hit count
// Direct curl test (new visit, no prior session):
curl -s -o /dev/null -D - \
"https://analytics.myworkers.dev/collect?sid=test-site&h=example.com&p=/test&r="
# HTTP/2 200
# content-type: image/gif
# last-modified: Mon, 13 Jan 2025 00:00:01 GMT
# tk: N
```
--------------------------------
### Initialization
Source: https://github.com/benvinegar/counterscale/blob/main/packages/tracker/SERVER.md
Initializes the server-side tracker with essential configuration options.
```APIDOC
## init(options)
Initialize the server-side tracker.
### Parameters
#### Options
- **siteId** (string, required): Your site ID
- **reporterUrl** (string, required): The analytics collection endpoint
- **reportOnLocalhost** (boolean, optional): Whether to track localhost requests
- **timeout** (number, optional): Request timeout in milliseconds
### Request Example
```typescript
import * as Counterscale from "@counterscale/tracker/server";
Counterscale.init({
siteId: "your-site-id",
reporterUrl: "https://your-counterscale-domain.com/collect",
reportOnLocalhost: false, // optional, defaults to false
timeout: 2000, // optional, defaults to 1000ms
});
```
```
--------------------------------
### Initialize Counterscale Tracker (Client-Side)
Source: https://github.com/benvinegar/counterscale/blob/main/README.md
Initialize the Counterscale client with your site ID and reporter URL. This creates a global client instance.
```typescript
import * as Counterscale from "@counterscale/tracker";
Counterscale.init({
siteId: "your-unique-site-id",
reporterUrl: "https://{subdomain-emitted-during-deploy}.workers.dev/collect",
});
```
--------------------------------
### Publish New Version
Source: https://github.com/benvinegar/counterscale/blob/main/CONTRIBUTING.md
Execute this script to publish a new version of the project. Replace `` with the desired version number.
```bash
./bump.sh
```
--------------------------------
### Legacy CounterScale Initialization
Source: https://github.com/benvinegar/counterscale/blob/main/packages/tracker/integration/01_legacyInit/index.html
Use this method to queue commands before the CounterScale script is loaded. Ensure 'your-unique-site-id' is replaced with your actual site ID.
```javascript
01 Legacy Init (function () { window.counterscale = { q: [
["set", "siteId", "your-unique-site-id"],
["trackPageview"],
],
}; })();
```
--------------------------------
### Server-Side Tracker Initialization
Source: https://context7.com/benvinegar/counterscale/llms.txt
Initializes the server-side tracking singleton using the native `fetch` API.
```APIDOC
## init(opts: ServerClientOpts): void — Initialize server tracker
Initializes the server-side singleton. The server module does not use DOM APIs; it uses the native `fetch` API (Node.js 18+). Tracking is fire-and-forget and will never throw.
### Description
Initializes the server-side tracker, allowing for tracking from Node.js environments. It uses the native `fetch` API and is designed to be non-throwing.
### Parameters
#### Path Parameters
None
#### Query Parameters
None
#### Request Body
None
### Request Example
```typescript
import * as Counterscale from "@counterscale/tracker/server";
Counterscale.init({
siteId: "my-ssr-app",
reporterUrl: "https://analytics.myworkers.dev/collect",
reportOnLocalhost: false, // optional, default false
timeout: 2000, // optional, default 1000 ms
});
```
### Response
None (void function)
#### Success Response (200)
N/A
#### Response Example
N/A
```
--------------------------------
### Initialize and Track Pageview (Server-Side)
Source: https://github.com/benvinegar/counterscale/blob/main/README.md
Initialize the server-side tracker with configuration options and track a pageview event. Requires explicit URL and hostname.
```typescript
import * as Counterscale from "@counterscale/tracker/server";
// Initialize the tracker
Counterscale.init({
siteId: "your-unique-site-id",
reporterUrl:
"https://{subdomain-emitted-during-deploy}.workers.dev/collect",
reportOnLocalhost: false, // optional, defaults to false
timeout: 2000, // optional, defaults to 1000ms
});
// Track a pageview
await Counterscale.trackPageview({
url: "https://example.com/page", // or relative: '/page'
hostname: "example.com", // required for relative URLs
referrer: "https://google.com",
utmSource: "social",
utmMedium: "twitter",
});
```
--------------------------------
### Initialize Server-Side Tracker
Source: https://github.com/benvinegar/counterscale/blob/main/packages/tracker/SERVER.md
Initialize the server-side tracker with your site ID and reporter URL. Optional parameters include `reportOnLocalhost` and `timeout`.
```typescript
import * as Counterscale from "@counterscale/tracker/server";
// Initialize the tracker
Counterscale.init({
siteId: "your-site-id",
reporterUrl: "https://your-counterscale-domain.com/collect",
reportOnLocalhost: false, // optional, defaults to false
timeout: 2000, // optional, defaults to 1000ms
});
```
--------------------------------
### Get Time-Series Analytics Data
Source: https://context7.com/benvinegar/counterscale/llms.txt
Returns time-series data for views, visitors, and bounces, grouped by a specified interval (DAY or HOUR). Data is sorted chronologically, with empty buckets filled in.
```typescript
const start = new Date("2025-01-06T00:00:00");
const end = new Date("2025-01-13T00:00:00");
const series = await ae.getViewsGroupedByInterval(
"my-blog",
"DAY", // "DAY" | "HOUR"
start,
end,
"UTC",
{},
);
// → [
// ["2025-01-06 00:00:00", { views: 320, visitors: 210, bounces: 88 }],
// ["2025-01-07 00:00:00", { views: 415, visitors: 274, bounces: 102 }],
// ...
// ]
```
--------------------------------
### Get Aggregate Site Counts
Source: https://context7.com/benvinegar/counterscale/llms.txt
Retrieves total views, unique visitors, and net bounce count for a specified site ID over a named time interval. Supports optional timezone and filters.
```typescript
const counts = await ae.getCounts(
"my-blog",
"7d", // "today" | "yesterday" | "1d" | "7d" | "30d" | "90d"
"America/New_York",
{ path: "/blog" }, // optional SearchFilters
);
// → { views: 14230, visitors: 3812, bounces: 1204 }
const bounceRate = counts.visitors > 0
? (counts.bounces / counts.visitors * 100).toFixed(1) + "%"
: "n/a";
// → "31.6%"
```
--------------------------------
### Initialize Counterscale Tracker
Source: https://github.com/benvinegar/counterscale/blob/main/packages/tracker/README.md
Initialize the Counterscale tracker with your site ID and deployment URL. This enables automatic page view tracking.
```typescript
import * as Counterscale from "@counterscale/tracker";
Counterscale.init({
siteId: "your-unique-site-id",
deploymentUrl: "https://{subdomain-emitted-during-deploy}.pages.dev/",
});
```
--------------------------------
### Importing Server and Client Modules
Source: https://github.com/benvinegar/counterscale/blob/main/packages/tracker/SERVER.md
Demonstrates how to import the server-side module separately from the client-side module for distinct usage.
```typescript
import * as Counterscale from "@counterscale/tracker"; // Client-side
import * as CounterscaleServer from "@counterscale/tracker/server"; // Server-side
```
--------------------------------
### Server-Side Tracker Methods
Source: https://github.com/benvinegar/counterscale/blob/main/README.md
Provides methods for checking initialization status, retrieving the initialized client, tracking pageviews, and cleaning up the client instance for the server-side tracker.
```APIDOC
## isInitialized()
### Description
Checks if the tracker has been initialized.
### Method
None (function call)
### Parameters
None
### Response
#### Success Response (boolean)
- **true** if the tracker is initialized, **false** otherwise.
## getInitializedClient()
### Description
Returns the initialized server client instance or undefined if not initialized.
### Method
None (function call)
### Parameters
None
### Response
#### Success Response (ServerClient | undefined)
- The initialized server client instance or undefined.
## trackPageview(opts)
### Description
Tracks a pageview event. Requires explicit URL and hostname parameters.
### Method
None (function call)
### Parameters
#### Path Parameters
None
#### Query Parameters
None
#### Request Body
- **opts** (TrackPageviewOpts) - Required - Options for tracking a pageview.
- **url** (string) - Required - The URL of the pageview.
- **hostname** (string) - Required - The hostname for the pageview (required for relative URLs).
- **referrer** (string) - Optional - The referrer URL.
- **utmSource** (string) - Optional - The UTM source parameter.
- **utmMedium** (string) - Optional - The UTM medium parameter.
### Request Example
```typescript
await Counterscale.trackPageview({
url: "https://example.com/page",
hostname: "example.com",
referrer: "https://google.com",
utmSource: "social",
utmMedium: "twitter"
});
```
### Response
#### Success Response (Promise)
This method returns a promise that resolves when the pageview event has been tracked.
## cleanup()
### Description
Cleans up the server client instance.
### Method
None (function call)
### Parameters
None
### Response
#### Success Response (void)
This method does not return a value.
```
--------------------------------
### Client-Side Tracker Methods
Source: https://github.com/benvinegar/counterscale/blob/main/README.md
Provides methods for checking initialization status, retrieving the initialized client, tracking pageviews, and cleaning up the client instance for the client-side tracker.
```APIDOC
## isInitialized()
### Description
Checks if the Counterscale client has been initialized.
### Method
None (function call)
### Parameters
None
### Response
#### Success Response (boolean)
- **true** if client exists, **false** otherwise.
## getInitializedClient()
### Description
Returns the initialized client instance or undefined if not initialized.
### Method
None (function call)
### Parameters
None
### Response
#### Success Response (Client | undefined)
- The initialized client instance or undefined.
## trackPageview(opts?)
### Description
Tracks a pageview event. Requires client to be initialized first. Automatically detects URL and referrer if not provided.
### Method
None (function call)
### Parameters
#### Path Parameters
None
#### Query Parameters
None
#### Request Body
- **opts** (TrackPageviewOpts?) - Optional - Options for tracking a pageview.
- **url** (string) - Optional - The URL of the pageview. Defaults to the current URL.
- **referrer** (string) - Optional - The referrer URL. Defaults to the current referrer.
### Response
#### Success Response (void)
This method does not return a value.
## cleanup()
### Description
Cleans up the client instance and removes event listeners. Sets global client to undefined.
### Method
None (function call)
### Parameters
None
### Response
#### Success Response (void)
This method does not return a value.
```
--------------------------------
### Client-Side Tracker Initialization
Source: https://github.com/benvinegar/counterscale/blob/main/README.md
Initializes the Counterscale client for browser-based tracking. This method creates a global client instance if one does not already exist.
```APIDOC
## init(opts)
### Description
Initializes the Counterscale client with site configuration. Creates a global client instance if one doesn't exist.
### Parameters
#### Path Parameters
None
#### Query Parameters
None
#### Request Body
- **opts** (ClientOpts) - Required - Client configuration options.
- **siteId** (string) - Required - Your unique site ID.
- **reporterUrl** (string) - Required - The URL of your deployed reporting endpoint.
- **autoTrackPageviews** (boolean) - Optional - If true, automatically tracks pageviews. Defaults to true.
### Request Example
```typescript
import * as Counterscale from "@counterscale/tracker";
Counterscale.init({
siteId: "your-unique-site-id",
reporterUrl: "https://{subdomain-emitted-during-deploy}.workers.dev/collect",
autoTrackPageviews: false
});
```
### Response
#### Success Response (void)
This method does not return a value.
```
--------------------------------
### Initialize Server-Side Tracker
Source: https://context7.com/benvinegar/counterscale/llms.txt
Initializes the server-side tracker singleton. Uses the native `fetch` API and does not rely on DOM APIs. Tracking is fire-and-forget and will not throw errors. `timeout` defaults to 1000 ms.
```typescript
import * as Counterscale from "@counterscale/tracker/server";
Counterscale.init({
siteId: "my-ssr-app",
reporterUrl: "https://analytics.myworkers.dev/collect",
reportOnLocalhost: false, // optional, default false
timeout: 2000, // optional, default 1000 ms
});
```
--------------------------------
### Manage Counterscale Storage
Source: https://github.com/benvinegar/counterscale/blob/main/README.md
Manages long-term storage settings for your Counterscale deployment. Use enable to turn on storage and disable to turn it off.
```bash
npx @counterscale/cli@latest storage [subcommand]
```
```bash
npx @counterscale/cli@latest storage enable
```
```bash
npx @counterscale/cli@latest storage disable
```
--------------------------------
### Login to Cloudflare CLI
Source: https://github.com/benvinegar/counterscale/blob/main/README.md
Authorize the Cloudflare CLI (Wrangler) to interact with your Cloudflare account. This is a prerequisite for deploying Counterscale.
```bash
npx wrangler login
```
--------------------------------
### Advanced ESLint Configuration with Granular Control
Source: https://github.com/benvinegar/counterscale/blob/main/packages/eslint-config/README.md
Import individual configurations for fine-grained control over ESLint settings. This allows combining base, TypeScript, and React configurations, plus custom rules for specific file types.
```javascript
import {
createBaseConfig,
createTypeScriptConfig,
createReactConfig,
} from "@counterscale/eslint-config";
import path from "node:path";
import { fileURLToPath } from "node:url";
const __filename = fileURLToPath(import.meta.url);
const __dirname = path.dirname(__filename);
export default [
...createBaseConfig({
baseDirectory: __dirname,
ignores: ["build/*", "node_modules", "dist/*"],
additionalGlobals: { counterscale: true },
}),
...createReactConfig({ baseDirectory: __dirname }),
...createTypeScriptConfig({
baseDirectory: __dirname,
tsconfigRootDir: "./",
project: "./tsconfig.json",
}),
// Add any package-specific rules
{
files: ["**/*.{ts,tsx}"],
rules: {
// Your custom rules here
},
},
];
```
--------------------------------
### Server-Side Tracker Initialization
Source: https://github.com/benvinegar/counterscale/blob/main/README.md
Initializes the Counterscale tracker for server-side analytics. Allows configuration of reporting options like `reportOnLocalhost` and `timeout`.
```APIDOC
## init(opts)
### Description
Initializes the server-side tracker.
### Parameters
#### Path Parameters
None
#### Query Parameters
None
#### Request Body
- **opts** (ServerClientOpts) - Required - Server-side client configuration options.
- **siteId** (string) - Required - Your unique site ID.
- **reporterUrl** (string) - Required - The URL of your deployed reporting endpoint.
- **reportOnLocalhost** (boolean) - Optional - Whether to report on localhost. Defaults to false.
- **timeout** (number) - Optional - The timeout in milliseconds for reporting. Defaults to 1000ms.
### Request Example
```typescript
import * as Counterscale from "@counterscale/tracker/server";
Counterscale.init({
siteId: "your-unique-site-id",
reporterUrl: "https://{subdomain-emitted-during-deploy}.workers.dev/collect",
reportOnLocalhost: false,
timeout: 2000
});
```
### Response
#### Success Response (void)
This method does not return a value.
```
--------------------------------
### Initialize Browser Tracker
Source: https://context7.com/benvinegar/counterscale/llms.txt
Initializes the browser tracker singleton. Automatically tracks pageviews unless disabled. Subsequent calls are no-ops. Use `getInitializedClient` to access the client instance.
```typescript
import * as Counterscale from "@counterscale/tracker";
// Basic setup — auto-tracks every navigation automatically
Counterscale.init({
siteId: "my-blog",
reporterUrl: "https://analytics.myworkers.dev/collect",
});
// Check initialization state
if (Counterscale.isInitialized()) {
console.log("Tracker is live");
const client = Counterscale.getInitializedClient();
// client.siteId === "my-blog"
}
// Teardown (e.g., in SPA unmount or test cleanup)
Counterscale.cleanup();
```
--------------------------------
### npx @counterscale/cli@latest storage enable / disable
Source: https://context7.com/benvinegar/counterscale/llms.txt
Controls long-term R2 storage for daily Analytics Engine rollups.
```APIDOC
## npx @counterscale/cli@latest storage [enable|disable]
### Description
Controls whether the scheduled cron (`0 2 * * *`) persists daily Analytics Engine rollups to the `counterscale-daily-rollups` R2 bucket as Apache Arrow files.
### Method
`storage` with subcommands `enable`, `disable`
### Endpoint
`npx @counterscale/cli@latest storage [enable|disable]`
### Parameters
#### Path Parameters
None
#### Query Parameters
None
### Request Example
```bash
# Enable long-term storage
npx @counterscale/cli@latest storage enable
# Disable long-term storage
npx @counterscale/cli@latest storage disable
```
### Response
#### Success Response
Long-term storage setting is updated successfully.
```
--------------------------------
### ServerTrackPageviewOpts Type Reference
Source: https://context7.com/benvinegar/counterscale/llms.txt
Defines the structure for options when tracking a server-side pageview. Ensure 'hostname' is provided for relative URLs. User-Agent, IP, and UTM parameters are optional but recommended for detailed tracking.
```typescript
import type { ServerTrackPageviewOpts } from "@counterscale/tracker/server";
const opts: ServerTrackPageviewOpts = {
url: "https://example.com/blog/post-1", // full URL or relative path
hostname: "example.com", // required for relative URLs
referrer: "https://news.ycombinator.com", // optional
userAgent: req.get("User-Agent"), // optional; for server-proxied UA
ip: req.ip, // optional
utmSource: "hn",
utmMedium: "social",
utmCampaign: "launch",
utmTerm: undefined,
utmContent: undefined,
};
```
--------------------------------
### Manage Counterscale Authentication
Source: https://github.com/benvinegar/counterscale/blob/main/README.md
Manages authentication settings for your Counterscale deployment. Available subcommands include enable, disable, and roll (for password updates).
```bash
npx @counterscale/cli@latest auth [subcommand]
```
```bash
npx @counterscale/cli@latest auth enable
```
```bash
npx @counterscale/cli@latest auth disable
```
```bash
npx @counterscale/cli@latest auth roll
```
--------------------------------
### Manual Pageview Tracking
Source: https://context7.com/benvinegar/counterscale/llms.txt
Initializes the browser tracker with `autoTrackPageviews` set to `false`, allowing for manual pageview tracking.
```APIDOC
## init(opts) with `autoTrackPageviews: false` — Manual pageview tracking
Disables automatic navigation instrumentation. Call `trackPageview()` explicitly at the point you want to record a hit (e.g., after a route change resolves in a SPA).
### Description
Configures the tracker to disable automatic pageview tracking, requiring explicit calls to `trackPageview()` for each event.
### Parameters
#### Path Parameters
None
#### Query Parameters
None
#### Request Body
None
### Request Example
```typescript
import * as Counterscale from "@counterscale/tracker";
Counterscale.init({
siteId: "my-spa",
reporterUrl: "https://analytics.myworkers.dev/collect",
autoTrackPageviews: false, // disable auto-tracking
reportOnLocalhost: false, // default; suppress local dev hits
});
function onRouteChange(path: string) {
Counterscale.trackPageview({ url: path });
}
onRouteChange("/products/widget-a");
// → fires GET https://analytics.myworkers.dev/collect?sid=my-spa&p=/products/widget-a&h=...
```
### Response
None (void function)
#### Success Response (200)
N/A
#### Response Example
N/A
```
--------------------------------
### Upgrade Counterscale CLI
Source: https://github.com/benvinegar/counterscale/blob/main/README.md
Upgrade the Counterscale CLI to the latest version using npx. This command helps manage your deployment.
```bash
npx @counterscale/cli@latest install
# OR
# npx @counterscale/cli@VERSION install
```
--------------------------------
### Initialize Counterscale with UTM Tracking
Source: https://github.com/benvinegar/counterscale/blob/main/packages/tracker/integration/04_utmTracking/index.html
This snippet initializes the counterscale object with a site ID and triggers a page view event, which is essential for UTM parameter tracking.
```javascript
(function () { window.counterscale = { q: [
["set", "siteId", "utm-test-site-id"],
["trackPageview"],
],
}; })();
```
--------------------------------
### trackPageview
Source: https://context7.com/benvinegar/counterscale/llms.txt
Records a pageview from server context. UTM parameters embedded in the URL are auto-extracted; explicitly passed UTM fields override them.
```APIDOC
## trackPageview(opts: ServerTrackPageviewOpts): Promise
### Description
Records a pageview from server context. UTM parameters embedded in the URL are auto-extracted; explicitly passed UTM fields override them.
### Method
`trackPageview`
### Parameters
#### Path Parameters
None
#### Query Parameters
None
#### Request Body
- **url** (string) - Required - The URL of the pageview. Can be a full URL or a relative path.
- **hostname** (string) - Required for relative URLs - The hostname of the pageview.
- **referrer** (string) - Optional - The referrer URL.
- **userAgent** (string) - Optional - The User-Agent string.
- **ip** (string) - Optional - The IP address of the client.
- **utmSource** (string) - Optional - The UTM source parameter.
- **utmMedium** (string) - Optional - The UTM medium parameter.
- **utmCampaign** (string) - Optional - The UTM campaign parameter.
- **utmTerm** (string) - Optional - The UTM term parameter.
- **utmContent** (string) - Optional - The UTM content parameter.
### Request Example
```typescript
Counterscale.trackPageview({
url: req.originalUrl,
hostname: req.hostname,
referrer: req.get("Referer"),
utmSource: "email",
utmMedium: "newsletter",
utmCampaign: "spring-sale",
utmTerm: "widget",
utmContent: "header-cta",
});
```
### Response
#### Success Response (void)
This method returns a Promise that resolves to void upon successful tracking.
```
--------------------------------
### Instantiate AnalyticsEngineAPI Query Client
Source: https://context7.com/benvinegar/counterscale/llms.txt
Wraps Cloudflare's Analytics Engine SQL HTTP API. All query methods build SQL strings and POST them to the Cloudflare API endpoint. Requires Cloudflare Account ID and API Token.
```typescript
import { AnalyticsEngineAPI } from "~/analytics/query";
const ae = new AnalyticsEngineAPI(
process.env.CF_ACCOUNT_ID!,
process.env.CF_BEARER_TOKEN!,
);
```
--------------------------------
### Wrangler Configuration for Counterscale
Source: https://context7.com/benvinegar/counterscale/llms.txt
This JSON configuration sets up a Cloudflare Worker with bindings for Analytics Engine and R2 buckets, and defines a cron trigger for daily rollups. Ensure secrets are set via the CLI.
```json
{
"name": "counterscale",
"main": "./workers/app.ts",
"compatibility_flags": ["nodejs_compat_v2"],
"compatibility_date": "2024-12-13",
"assets": {
"binding": "ASSETS",
"directory": "./build/client"
},
"analytics_engine_datasets": [
{
"binding": "WEB_COUNTER_AE",
"dataset": "metricsDataset"
}
],
"r2_buckets": [
{
"bucket_name": "counterscale-daily-rollups",
"preview_bucket_name": "counterscale-daily-rollups-dev",
"binding": "DAILY_ROLLUPS"
}
],
"triggers": {
"crons": ["0 2 * * *"]
}
}
```
--------------------------------
### Initialize Counterscale Tracker with Manual Pageview Tracking
Source: https://github.com/benvinegar/counterscale/blob/main/packages/tracker/README.md
Initialize the Counterscale tracker with automatic page view tracking disabled. You will need to manually call `Counterscale.trackPageview()` when a page view occurs.
```typescript
import * as Counterscale from "@counterscale/tracker";
Counterscale.init({
siteId: "your-unique-site-id",
deploymentUrl: "https://{subdomain-emitted-during-deploy}.pages.dev/",
autoTrackPageviews: false, // <- don't forget this
});
// ... when a pageview happens
Counterscale.trackPageview();
```
--------------------------------
### Manually Track Pageviews (Client-Side)
Source: https://github.com/benvinegar/counterscale/blob/main/README.md
Initialize the client-side tracker with auto-tracking disabled and then manually call `trackPageview()` when needed. This provides more control over when pageviews are recorded.
```typescript
import * as Counterscale from "@counterscale/tracker";
Counterscale.init({
siteId: "your-unique-site-id",
reporterUrl: "https://{subdomain-emitted-during-deploy}.workers.dev/collect",
autoTrackPageviews: false, // <- don't forget this
});
// ... when a pageview happens
Counterscale.trackPageview();
```
--------------------------------
### Manage Long-Term R2 Storage with Counterscale CLI
Source: https://context7.com/benvinegar/counterscale/llms.txt
Enable or disable the daily persistence of Analytics Engine rollups to an R2 bucket as Apache Arrow files. This is controlled by the `CF_STORAGE_ENABLED` Worker secret. The default cron schedule is `0 2 * * *`.
```bash
# Enable long-term storage (default after install)
npx @counterscale/cli@latest storage enable
# → Sets CF_STORAGE_ENABLED=true on the Worker
# Disable long-term storage
npx @counterscale/cli@latest storage disable
# → Sets CF_STORAGE_ENABLED=false; existing R2 data is preserved
```
--------------------------------
### AnalyticsEngineAPI
Source: https://context7.com/benvinegar/counterscale/llms.txt
A client for querying Cloudflare's Analytics Engine SQL API.
```APIDOC
## AnalyticsEngineAPI — Query Class
### `new AnalyticsEngineAPI(cfAccountId, cfApiToken)` — Instantiate the query client
Wraps Cloudflare's Analytics Engine SQL HTTP API. All query methods build SQL strings and POST them to `https://api.cloudflare.com/client/v4/accounts/{accountId}/analytics_engine/sql`.
### Parameters
- **cfAccountId** (string) - Your Cloudflare Account ID.
- **cfApiToken** (string) - Your Cloudflare API Token with Analytics Engine read access.
### Request Example
```typescript
import { AnalyticsEngineAPI } from "~/analytics/query";
const ae = new AnalyticsEngineAPI(
process.env.CF_ACCOUNT_ID!,
process.env.CF_BEARER_TOKEN!,
);
```
```
--------------------------------
### Track a Pageview Server-Side
Source: https://github.com/benvinegar/counterscale/blob/main/packages/tracker/SERVER.md
Track a pageview event with URL, hostname, and referrer details. UTM parameters can be automatically extracted from the URL or passed explicitly.
```typescript
// Track a pageview
await Counterscale.trackPageview({
url: "https://example.com/page", // or relative: '/page'
hostname: "example.com", // required for relative URLs
referrer: "https://google.com",
utmSource: "social",
utmMedium: "twitter",
});
```
--------------------------------
### Manage Dashboard Authentication with Counterscale CLI
Source: https://context7.com/benvinegar/counterscale/llms.txt
Control access to your Counterscale dashboard using Cloudflare Worker secrets. This command manages `CF_AUTH_ENABLED`, `CF_PASSWORD_HASH` (bcrypt), and `CF_JWT_SECRET`. Enabling prompts for a password, disabling makes the dashboard public, and rolling rotates the password hash.
```bash
# Enable password protection (prompts for password → bcrypt hash stored as secret)
npx @counterscale/cli@latest auth enable
# → Sets CF_AUTH_ENABLED=true, CF_PASSWORD_HASH=, CF_JWT_SECRET=
# Disable password protection (dashboard becomes public)
npx @counterscale/cli@latest auth disable
# → Sets CF_AUTH_ENABLED=false; hash + JWT secret remain intact
# Rotate the dashboard password (prompts for new password)
npx @counterscale/cli@latest auth roll
# → Updates CF_PASSWORD_HASH; existing sessions remain valid until JWT expiry (30 days)
```
--------------------------------
### npx @counterscale/cli@latest auth enable / disable / roll
Source: https://context7.com/benvinegar/counterscale/llms.txt
Manages dashboard authentication secrets for Cloudflare Workers.
```APIDOC
## npx @counterscale/cli@latest auth [enable|disable|roll]
### Description
Manages the three Cloudflare Worker secrets that gate access to the dashboard: `CF_AUTH_ENABLED`, `CF_PASSWORD_HASH` (bcrypt), and `CF_JWT_SECRET`.
### Method
`auth` with subcommands `enable`, `disable`, `roll`
### Endpoint
`npx @counterscale/cli@latest auth [enable|disable|roll]`
### Parameters
#### Path Parameters
None
#### Query Parameters
None
### Request Example
```bash
# Enable password protection
npx @counterscale/cli@latest auth enable
# Disable password protection
npx @counterscale/cli@latest auth disable
# Rotate the dashboard password
npx @counterscale/cli@latest auth roll
```
### Response
#### Success Response
Authentication secrets are updated successfully.
```