@callforge/tracking-client 0.3.1 → 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +24 -8
- package/dist/index.d.mts +11 -2
- package/dist/index.d.ts +11 -2
- package/dist/index.js +22 -5
- package/dist/index.mjs +22 -5
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -2,7 +2,7 @@
|
|
|
2
2
|
|
|
3
3
|
Lightweight client library for the CallForge tracking API. Handles location-aware phone number assignment with aggressive caching and preload optimization.
|
|
4
4
|
|
|
5
|
-
**v0.
|
|
5
|
+
**v0.4.0** - Added `ga4MeasurementId` config option for cleaner gtag callback instead of cookie polling.
|
|
6
6
|
|
|
7
7
|
## Installation
|
|
8
8
|
|
|
@@ -55,17 +55,31 @@ client.onReady((session) => {
|
|
|
55
55
|
|
|
56
56
|
### 3. GA4 Integration (automatic)
|
|
57
57
|
|
|
58
|
-
The client automatically captures the GA4 client ID
|
|
58
|
+
The client automatically captures the GA4 client ID and associates it with the tracking session. This enables CallForge to send call events (phone call, conversion, billable conversion) to your Google Analytics 4 property.
|
|
59
59
|
|
|
60
60
|
**Requirements:**
|
|
61
61
|
1. Google Analytics 4 must be installed on your site
|
|
62
62
|
2. Configure GA4 credentials in CallForge dashboard (Categories → Edit → GA4 tab)
|
|
63
63
|
|
|
64
|
+
**Recommended: Provide Measurement ID for callback-based capture:**
|
|
65
|
+
|
|
66
|
+
```typescript
|
|
67
|
+
const client = CallForge.init({
|
|
68
|
+
categoryId: 'your-category-id',
|
|
69
|
+
ga4MeasurementId: 'G-XXXXXXXXXX', // Enables gtag('get') callback
|
|
70
|
+
});
|
|
71
|
+
```
|
|
72
|
+
|
|
73
|
+
When `ga4MeasurementId` is provided, the client uses the official `gtag('get')` API callback to retrieve the client ID. This is cleaner and more reliable than cookie polling.
|
|
74
|
+
|
|
64
75
|
**How it works:**
|
|
65
|
-
|
|
66
|
-
-
|
|
67
|
-
-
|
|
68
|
-
|
|
76
|
+
1. **If `ga4MeasurementId` is provided AND `window.gtag` exists:**
|
|
77
|
+
- Uses `gtag('get', measurementId, 'client_id', callback)` to get the client ID
|
|
78
|
+
- No polling needed - callback fires when GA4 is ready
|
|
79
|
+
2. **Otherwise (fallback):**
|
|
80
|
+
- Checks for the `_ga` cookie immediately
|
|
81
|
+
- If not found, polls every 500ms for up to 10 seconds
|
|
82
|
+
- Handles async GA4 script loading
|
|
69
83
|
|
|
70
84
|
**Manual override:** If you need to pass a custom GA4 client ID:
|
|
71
85
|
|
|
@@ -114,8 +128,10 @@ Initialize the tracking client.
|
|
|
114
128
|
|
|
115
129
|
```typescript
|
|
116
130
|
interface CallForgeConfig {
|
|
117
|
-
categoryId: string;
|
|
118
|
-
endpoint?: string;
|
|
131
|
+
categoryId: string; // Required - which number pool to use
|
|
132
|
+
endpoint?: string; // Optional - defaults to 'https://tracking.callforge.io'
|
|
133
|
+
ga4MeasurementId?: string; // Optional - GA4 Measurement ID (e.g., "G-XXXXXXXXXX")
|
|
134
|
+
// Enables gtag callback instead of cookie polling
|
|
119
135
|
}
|
|
120
136
|
```
|
|
121
137
|
|
package/dist/index.d.mts
CHANGED
|
@@ -6,6 +6,8 @@ interface CallForgeConfig {
|
|
|
6
6
|
categoryId: string;
|
|
7
7
|
/** Optional - API endpoint. Defaults to 'https://tracking.callforge.io' */
|
|
8
8
|
endpoint?: string;
|
|
9
|
+
/** Optional - GA4 Measurement ID (e.g., "G-XXXXXXXXXX"). Enables gtag callback instead of cookie polling. */
|
|
10
|
+
ga4MeasurementId?: string;
|
|
9
11
|
}
|
|
10
12
|
/**
|
|
11
13
|
* Location data returned by the tracking API.
|
|
@@ -64,11 +66,12 @@ interface ApiResponse {
|
|
|
64
66
|
*/
|
|
65
67
|
type ReadyCallback = (session: TrackingSession) => void;
|
|
66
68
|
/**
|
|
67
|
-
* Global window extension for preload promise.
|
|
69
|
+
* Global window extension for preload promise and gtag.
|
|
68
70
|
*/
|
|
69
71
|
declare global {
|
|
70
72
|
interface Window {
|
|
71
73
|
__cfTracking?: Promise<ApiResponse>;
|
|
74
|
+
gtag?: (command: 'get', targetId: string, fieldName: string, callback: (value: string) => void) => void;
|
|
72
75
|
}
|
|
73
76
|
}
|
|
74
77
|
|
|
@@ -113,12 +116,18 @@ declare class CallForge {
|
|
|
113
116
|
*/
|
|
114
117
|
getQueuedParams(): TrackingParams;
|
|
115
118
|
private patchSession;
|
|
119
|
+
/**
|
|
120
|
+
* Start capturing the GA4 client ID.
|
|
121
|
+
* If ga4MeasurementId is configured, uses gtag('get') callback.
|
|
122
|
+
* Otherwise falls back to polling the _ga cookie.
|
|
123
|
+
*/
|
|
124
|
+
startGA4ClientIdCapture(): void;
|
|
116
125
|
/**
|
|
117
126
|
* Start polling for the GA4 _ga cookie.
|
|
118
127
|
* If found immediately, calls setParams right away.
|
|
119
128
|
* Otherwise polls every 500ms for up to 10 seconds.
|
|
120
129
|
*/
|
|
121
|
-
startGA4CookiePolling
|
|
130
|
+
private startGA4CookiePolling;
|
|
122
131
|
private stopGA4CookiePolling;
|
|
123
132
|
private fetchSession;
|
|
124
133
|
private getLocationId;
|
package/dist/index.d.ts
CHANGED
|
@@ -6,6 +6,8 @@ interface CallForgeConfig {
|
|
|
6
6
|
categoryId: string;
|
|
7
7
|
/** Optional - API endpoint. Defaults to 'https://tracking.callforge.io' */
|
|
8
8
|
endpoint?: string;
|
|
9
|
+
/** Optional - GA4 Measurement ID (e.g., "G-XXXXXXXXXX"). Enables gtag callback instead of cookie polling. */
|
|
10
|
+
ga4MeasurementId?: string;
|
|
9
11
|
}
|
|
10
12
|
/**
|
|
11
13
|
* Location data returned by the tracking API.
|
|
@@ -64,11 +66,12 @@ interface ApiResponse {
|
|
|
64
66
|
*/
|
|
65
67
|
type ReadyCallback = (session: TrackingSession) => void;
|
|
66
68
|
/**
|
|
67
|
-
* Global window extension for preload promise.
|
|
69
|
+
* Global window extension for preload promise and gtag.
|
|
68
70
|
*/
|
|
69
71
|
declare global {
|
|
70
72
|
interface Window {
|
|
71
73
|
__cfTracking?: Promise<ApiResponse>;
|
|
74
|
+
gtag?: (command: 'get', targetId: string, fieldName: string, callback: (value: string) => void) => void;
|
|
72
75
|
}
|
|
73
76
|
}
|
|
74
77
|
|
|
@@ -113,12 +116,18 @@ declare class CallForge {
|
|
|
113
116
|
*/
|
|
114
117
|
getQueuedParams(): TrackingParams;
|
|
115
118
|
private patchSession;
|
|
119
|
+
/**
|
|
120
|
+
* Start capturing the GA4 client ID.
|
|
121
|
+
* If ga4MeasurementId is configured, uses gtag('get') callback.
|
|
122
|
+
* Otherwise falls back to polling the _ga cookie.
|
|
123
|
+
*/
|
|
124
|
+
startGA4ClientIdCapture(): void;
|
|
116
125
|
/**
|
|
117
126
|
* Start polling for the GA4 _ga cookie.
|
|
118
127
|
* If found immediately, calls setParams right away.
|
|
119
128
|
* Otherwise polls every 500ms for up to 10 seconds.
|
|
120
129
|
*/
|
|
121
|
-
startGA4CookiePolling
|
|
130
|
+
private startGA4CookiePolling;
|
|
122
131
|
private stopGA4CookiePolling;
|
|
123
132
|
private fetchSession;
|
|
124
133
|
private getLocationId;
|
package/dist/index.js
CHANGED
|
@@ -147,10 +147,11 @@ var CallForge = class _CallForge {
|
|
|
147
147
|
this.sessionCreated = false;
|
|
148
148
|
this.config = {
|
|
149
149
|
categoryId: config.categoryId,
|
|
150
|
-
endpoint: config.endpoint || DEFAULT_ENDPOINT
|
|
150
|
+
endpoint: config.endpoint || DEFAULT_ENDPOINT,
|
|
151
|
+
ga4MeasurementId: config.ga4MeasurementId
|
|
151
152
|
};
|
|
152
153
|
this.cache = new TrackingCache(config.categoryId);
|
|
153
|
-
this.
|
|
154
|
+
this.startGA4ClientIdCapture();
|
|
154
155
|
}
|
|
155
156
|
/**
|
|
156
157
|
* Initialize the CallForge tracking client.
|
|
@@ -211,15 +212,31 @@ var CallForge = class _CallForge {
|
|
|
211
212
|
console.warn("[CallForge] Failed to patch session:", error);
|
|
212
213
|
}
|
|
213
214
|
}
|
|
215
|
+
/**
|
|
216
|
+
* Start capturing the GA4 client ID.
|
|
217
|
+
* If ga4MeasurementId is configured, uses gtag('get') callback.
|
|
218
|
+
* Otherwise falls back to polling the _ga cookie.
|
|
219
|
+
*/
|
|
220
|
+
startGA4ClientIdCapture() {
|
|
221
|
+
if (this.ga4PollInterval !== null || this.ga4PollTimeout !== null) {
|
|
222
|
+
return;
|
|
223
|
+
}
|
|
224
|
+
if (this.config.ga4MeasurementId && typeof window !== "undefined" && window.gtag) {
|
|
225
|
+
window.gtag("get", this.config.ga4MeasurementId, "client_id", (clientId) => {
|
|
226
|
+
if (clientId) {
|
|
227
|
+
this.setParams({ ga4ClientId: clientId });
|
|
228
|
+
}
|
|
229
|
+
});
|
|
230
|
+
return;
|
|
231
|
+
}
|
|
232
|
+
this.startGA4CookiePolling();
|
|
233
|
+
}
|
|
214
234
|
/**
|
|
215
235
|
* Start polling for the GA4 _ga cookie.
|
|
216
236
|
* If found immediately, calls setParams right away.
|
|
217
237
|
* Otherwise polls every 500ms for up to 10 seconds.
|
|
218
238
|
*/
|
|
219
239
|
startGA4CookiePolling() {
|
|
220
|
-
if (this.ga4PollInterval !== null || this.ga4PollTimeout !== null) {
|
|
221
|
-
return;
|
|
222
|
-
}
|
|
223
240
|
const clientId = getGA4ClientId();
|
|
224
241
|
if (clientId) {
|
|
225
242
|
this.setParams({ ga4ClientId: clientId });
|
package/dist/index.mjs
CHANGED
|
@@ -122,10 +122,11 @@ var CallForge = class _CallForge {
|
|
|
122
122
|
this.sessionCreated = false;
|
|
123
123
|
this.config = {
|
|
124
124
|
categoryId: config.categoryId,
|
|
125
|
-
endpoint: config.endpoint || DEFAULT_ENDPOINT
|
|
125
|
+
endpoint: config.endpoint || DEFAULT_ENDPOINT,
|
|
126
|
+
ga4MeasurementId: config.ga4MeasurementId
|
|
126
127
|
};
|
|
127
128
|
this.cache = new TrackingCache(config.categoryId);
|
|
128
|
-
this.
|
|
129
|
+
this.startGA4ClientIdCapture();
|
|
129
130
|
}
|
|
130
131
|
/**
|
|
131
132
|
* Initialize the CallForge tracking client.
|
|
@@ -186,15 +187,31 @@ var CallForge = class _CallForge {
|
|
|
186
187
|
console.warn("[CallForge] Failed to patch session:", error);
|
|
187
188
|
}
|
|
188
189
|
}
|
|
190
|
+
/**
|
|
191
|
+
* Start capturing the GA4 client ID.
|
|
192
|
+
* If ga4MeasurementId is configured, uses gtag('get') callback.
|
|
193
|
+
* Otherwise falls back to polling the _ga cookie.
|
|
194
|
+
*/
|
|
195
|
+
startGA4ClientIdCapture() {
|
|
196
|
+
if (this.ga4PollInterval !== null || this.ga4PollTimeout !== null) {
|
|
197
|
+
return;
|
|
198
|
+
}
|
|
199
|
+
if (this.config.ga4MeasurementId && typeof window !== "undefined" && window.gtag) {
|
|
200
|
+
window.gtag("get", this.config.ga4MeasurementId, "client_id", (clientId) => {
|
|
201
|
+
if (clientId) {
|
|
202
|
+
this.setParams({ ga4ClientId: clientId });
|
|
203
|
+
}
|
|
204
|
+
});
|
|
205
|
+
return;
|
|
206
|
+
}
|
|
207
|
+
this.startGA4CookiePolling();
|
|
208
|
+
}
|
|
189
209
|
/**
|
|
190
210
|
* Start polling for the GA4 _ga cookie.
|
|
191
211
|
* If found immediately, calls setParams right away.
|
|
192
212
|
* Otherwise polls every 500ms for up to 10 seconds.
|
|
193
213
|
*/
|
|
194
214
|
startGA4CookiePolling() {
|
|
195
|
-
if (this.ga4PollInterval !== null || this.ga4PollTimeout !== null) {
|
|
196
|
-
return;
|
|
197
|
-
}
|
|
198
215
|
const clientId = getGA4ClientId();
|
|
199
216
|
if (clientId) {
|
|
200
217
|
this.setParams({ ga4ClientId: clientId });
|