@callforge/tracking-client 0.7.0 → 0.7.1
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 +19 -3
- package/dist/index.d.mts +5 -0
- package/dist/index.d.ts +5 -0
- package/dist/index.js +27 -14
- package/dist/index.mjs +27 -14
- package/package.json +9 -9
package/README.md
CHANGED
|
@@ -43,7 +43,13 @@ const client = CallForge.init({
|
|
|
43
43
|
const { session, location } = client.getSessionAsync();
|
|
44
44
|
|
|
45
45
|
// Location is delivered independently (often faster than phone number assignment)
|
|
46
|
-
console.log(await location);
|
|
46
|
+
console.log(await location);
|
|
47
|
+
// {
|
|
48
|
+
// city: "Woodstock",
|
|
49
|
+
// state: "Georgia",
|
|
50
|
+
// stateCode: "GA",
|
|
51
|
+
// zipOptions: ["30188", "30189", "30066", ...] // may be []
|
|
52
|
+
// } or null
|
|
47
53
|
|
|
48
54
|
// Phone session data (deterministic token + phone number)
|
|
49
55
|
console.log(await session); // { sessionToken, leaseId, phoneNumber }
|
|
@@ -160,7 +166,16 @@ Get location data only. Returns cached data if valid, otherwise fetches from the
|
|
|
160
166
|
|
|
161
167
|
```typescript
|
|
162
168
|
const location = await client.getLocation();
|
|
163
|
-
// { city, state, stateCode } or null
|
|
169
|
+
// { city, state, stateCode, zipOptions } or null
|
|
170
|
+
```
|
|
171
|
+
|
|
172
|
+
```typescript
|
|
173
|
+
interface TrackingLocation {
|
|
174
|
+
city: string;
|
|
175
|
+
state: string;
|
|
176
|
+
stateCode: string;
|
|
177
|
+
zipOptions?: string[]; // ordered by proximity, may be []
|
|
178
|
+
}
|
|
164
179
|
```
|
|
165
180
|
|
|
166
181
|
### `client.getSessionAsync()`
|
|
@@ -172,6 +187,7 @@ const { session, location } = client.getSessionAsync();
|
|
|
172
187
|
|
|
173
188
|
location.then((loc) => {
|
|
174
189
|
// show city/state ASAP
|
|
190
|
+
// optionally render loc?.zipOptions in a ZIP picker
|
|
175
191
|
});
|
|
176
192
|
|
|
177
193
|
session.then((sess) => {
|
|
@@ -204,7 +220,7 @@ Subscribe to location ready event. Callback is called once location data is avai
|
|
|
204
220
|
|
|
205
221
|
```typescript
|
|
206
222
|
client.onLocationReady((location) => {
|
|
207
|
-
// location is { city, state, stateCode } or null
|
|
223
|
+
// location is { city, state, stateCode, zipOptions } or null
|
|
208
224
|
});
|
|
209
225
|
```
|
|
210
226
|
|
package/dist/index.d.mts
CHANGED
|
@@ -21,6 +21,8 @@ interface TrackingLocation {
|
|
|
21
21
|
state: string;
|
|
22
22
|
/** State abbreviation (e.g., "GA") */
|
|
23
23
|
stateCode: string;
|
|
24
|
+
/** Suggested ZIPs ordered by proximity (may be empty) */
|
|
25
|
+
zipOptions?: string[];
|
|
24
26
|
}
|
|
25
27
|
type TrackingLocationSource = 'google_criteria' | 'cloudflare_geo';
|
|
26
28
|
/**
|
|
@@ -70,6 +72,7 @@ interface ApiLocationResponse {
|
|
|
70
72
|
stateCode: string;
|
|
71
73
|
source: TrackingLocationSource;
|
|
72
74
|
} | null;
|
|
75
|
+
zipOptions?: string[];
|
|
73
76
|
expiresAt: number;
|
|
74
77
|
}
|
|
75
78
|
interface CallIntentResponse {
|
|
@@ -174,6 +177,8 @@ declare class CallForge {
|
|
|
174
177
|
private fetchLocationFromApi;
|
|
175
178
|
private saveToCache;
|
|
176
179
|
private saveLocationToCache;
|
|
180
|
+
private toTrackingLocation;
|
|
181
|
+
private normalizeZipOptions;
|
|
177
182
|
private formatSession;
|
|
178
183
|
private formatApiResponse;
|
|
179
184
|
private syncParamsToCallForgeIfPossible;
|
package/dist/index.d.ts
CHANGED
|
@@ -21,6 +21,8 @@ interface TrackingLocation {
|
|
|
21
21
|
state: string;
|
|
22
22
|
/** State abbreviation (e.g., "GA") */
|
|
23
23
|
stateCode: string;
|
|
24
|
+
/** Suggested ZIPs ordered by proximity (may be empty) */
|
|
25
|
+
zipOptions?: string[];
|
|
24
26
|
}
|
|
25
27
|
type TrackingLocationSource = 'google_criteria' | 'cloudflare_geo';
|
|
26
28
|
/**
|
|
@@ -70,6 +72,7 @@ interface ApiLocationResponse {
|
|
|
70
72
|
stateCode: string;
|
|
71
73
|
source: TrackingLocationSource;
|
|
72
74
|
} | null;
|
|
75
|
+
zipOptions?: string[];
|
|
73
76
|
expiresAt: number;
|
|
74
77
|
}
|
|
75
78
|
interface CallIntentResponse {
|
|
@@ -174,6 +177,8 @@ declare class CallForge {
|
|
|
174
177
|
private fetchLocationFromApi;
|
|
175
178
|
private saveToCache;
|
|
176
179
|
private saveLocationToCache;
|
|
180
|
+
private toTrackingLocation;
|
|
181
|
+
private normalizeZipOptions;
|
|
177
182
|
private formatSession;
|
|
178
183
|
private formatApiResponse;
|
|
179
184
|
private syncParamsToCallForgeIfPossible;
|
package/dist/index.js
CHANGED
|
@@ -424,18 +424,14 @@ var CallForge = class _CallForge {
|
|
|
424
424
|
return this.formatApiResponse(data);
|
|
425
425
|
}
|
|
426
426
|
async fetchLocation() {
|
|
427
|
-
var _a;
|
|
427
|
+
var _a, _b;
|
|
428
428
|
const locationId = this.getLocationId();
|
|
429
429
|
if (typeof window !== "undefined" && window.__cfTrackingLocation) {
|
|
430
430
|
try {
|
|
431
431
|
const data2 = await window.__cfTrackingLocation;
|
|
432
432
|
const dataWithExtras = data2;
|
|
433
433
|
const effectiveLocId = (_a = dataWithExtras.locId) != null ? _a : locationId;
|
|
434
|
-
const location2 = data2.location
|
|
435
|
-
city: data2.location.city,
|
|
436
|
-
state: data2.location.state,
|
|
437
|
-
stateCode: data2.location.stateCode
|
|
438
|
-
} : null;
|
|
434
|
+
const location2 = this.toTrackingLocation(data2.location, dataWithExtras.zipOptions);
|
|
439
435
|
this.saveLocationToCache(effectiveLocId, location2, data2.expiresAt);
|
|
440
436
|
return location2;
|
|
441
437
|
} catch (e) {
|
|
@@ -443,14 +439,10 @@ var CallForge = class _CallForge {
|
|
|
443
439
|
}
|
|
444
440
|
const cached = this.locationCache.get(locationId);
|
|
445
441
|
if (cached) {
|
|
446
|
-
return cached.location;
|
|
442
|
+
return this.toTrackingLocation(cached.location, (_b = cached.location) == null ? void 0 : _b.zipOptions);
|
|
447
443
|
}
|
|
448
444
|
const data = await this.fetchLocationFromApi(locationId);
|
|
449
|
-
const location = data.location
|
|
450
|
-
city: data.location.city,
|
|
451
|
-
state: data.location.state,
|
|
452
|
-
stateCode: data.location.stateCode
|
|
453
|
-
} : null;
|
|
445
|
+
const location = this.toTrackingLocation(data.location, data.zipOptions);
|
|
454
446
|
this.saveLocationToCache(locationId, location, data.expiresAt);
|
|
455
447
|
return location;
|
|
456
448
|
}
|
|
@@ -525,6 +517,27 @@ var CallForge = class _CallForge {
|
|
|
525
517
|
tokenVersion: "v1"
|
|
526
518
|
});
|
|
527
519
|
}
|
|
520
|
+
toTrackingLocation(location, zipOptions) {
|
|
521
|
+
if (!location) {
|
|
522
|
+
return null;
|
|
523
|
+
}
|
|
524
|
+
return {
|
|
525
|
+
city: location.city,
|
|
526
|
+
state: location.state,
|
|
527
|
+
stateCode: location.stateCode,
|
|
528
|
+
zipOptions: this.normalizeZipOptions(zipOptions)
|
|
529
|
+
};
|
|
530
|
+
}
|
|
531
|
+
normalizeZipOptions(value) {
|
|
532
|
+
if (!Array.isArray(value)) {
|
|
533
|
+
return [];
|
|
534
|
+
}
|
|
535
|
+
return Array.from(
|
|
536
|
+
new Set(
|
|
537
|
+
value.filter((zip) => typeof zip === "string" && /^\d{5}$/.test(zip))
|
|
538
|
+
)
|
|
539
|
+
);
|
|
540
|
+
}
|
|
528
541
|
formatSession(cached) {
|
|
529
542
|
return {
|
|
530
543
|
sessionToken: cached.sessionToken,
|
|
@@ -609,12 +622,12 @@ var lkey='cf_location_v1_'+site;
|
|
|
609
622
|
try{
|
|
610
623
|
var cl=JSON.parse(localStorage.getItem(lkey));
|
|
611
624
|
if(cl&&cl.expiresAt>Date.now()+30000){
|
|
612
|
-
if(!loc||(loc&&cl.locId===loc)){window.__cfTrackingLocation=Promise.resolve(cl)}
|
|
625
|
+
if(!loc||(loc&&cl.locId===loc)){if(cl.location&&!Array.isArray(cl.location.zipOptions))cl.location.zipOptions=[];window.__cfTrackingLocation=Promise.resolve(cl)}
|
|
613
626
|
}}catch(e){}
|
|
614
627
|
if(!window.__cfTrackingLocation){
|
|
615
628
|
var lurl='${endpoint}/v1/tracking/location';
|
|
616
629
|
if(loc)lurl+='?loc_physical_ms='+encodeURIComponent(loc);
|
|
617
|
-
window.__cfTrackingLocation=fetch(lurl,{credentials:'omit'}).then(function(r){if(!r.ok)throw new Error('tracking preload location failed');return r.json()}).then(function(d){d.locId=loc;try{localStorage.setItem(lkey,JSON.stringify({locId:loc,location:d.location?{city:d.location.city,state:d.location.state,stateCode:d.location.stateCode}:null,expiresAt:d.expiresAt,tokenVersion:'v1'}))}catch(e){}return d});
|
|
630
|
+
window.__cfTrackingLocation=fetch(lurl,{credentials:'omit'}).then(function(r){if(!r.ok)throw new Error('tracking preload location failed');return r.json()}).then(function(d){var z=Array.isArray(d.zipOptions)?d.zipOptions.filter(function(x){return /^\\d{5}$/.test(x)}):[];d.locId=loc;d.zipOptions=z;try{localStorage.setItem(lkey,JSON.stringify({locId:loc,location:d.location?{city:d.location.city,state:d.location.state,stateCode:d.location.stateCode,zipOptions:z}:null,expiresAt:d.expiresAt,tokenVersion:'v1'}))}catch(e){}return d});
|
|
618
631
|
}
|
|
619
632
|
var token=null;
|
|
620
633
|
try{
|
package/dist/index.mjs
CHANGED
|
@@ -400,18 +400,14 @@ var CallForge = class _CallForge {
|
|
|
400
400
|
return this.formatApiResponse(data);
|
|
401
401
|
}
|
|
402
402
|
async fetchLocation() {
|
|
403
|
-
var _a;
|
|
403
|
+
var _a, _b;
|
|
404
404
|
const locationId = this.getLocationId();
|
|
405
405
|
if (typeof window !== "undefined" && window.__cfTrackingLocation) {
|
|
406
406
|
try {
|
|
407
407
|
const data2 = await window.__cfTrackingLocation;
|
|
408
408
|
const dataWithExtras = data2;
|
|
409
409
|
const effectiveLocId = (_a = dataWithExtras.locId) != null ? _a : locationId;
|
|
410
|
-
const location2 = data2.location
|
|
411
|
-
city: data2.location.city,
|
|
412
|
-
state: data2.location.state,
|
|
413
|
-
stateCode: data2.location.stateCode
|
|
414
|
-
} : null;
|
|
410
|
+
const location2 = this.toTrackingLocation(data2.location, dataWithExtras.zipOptions);
|
|
415
411
|
this.saveLocationToCache(effectiveLocId, location2, data2.expiresAt);
|
|
416
412
|
return location2;
|
|
417
413
|
} catch (e) {
|
|
@@ -419,14 +415,10 @@ var CallForge = class _CallForge {
|
|
|
419
415
|
}
|
|
420
416
|
const cached = this.locationCache.get(locationId);
|
|
421
417
|
if (cached) {
|
|
422
|
-
return cached.location;
|
|
418
|
+
return this.toTrackingLocation(cached.location, (_b = cached.location) == null ? void 0 : _b.zipOptions);
|
|
423
419
|
}
|
|
424
420
|
const data = await this.fetchLocationFromApi(locationId);
|
|
425
|
-
const location = data.location
|
|
426
|
-
city: data.location.city,
|
|
427
|
-
state: data.location.state,
|
|
428
|
-
stateCode: data.location.stateCode
|
|
429
|
-
} : null;
|
|
421
|
+
const location = this.toTrackingLocation(data.location, data.zipOptions);
|
|
430
422
|
this.saveLocationToCache(locationId, location, data.expiresAt);
|
|
431
423
|
return location;
|
|
432
424
|
}
|
|
@@ -501,6 +493,27 @@ var CallForge = class _CallForge {
|
|
|
501
493
|
tokenVersion: "v1"
|
|
502
494
|
});
|
|
503
495
|
}
|
|
496
|
+
toTrackingLocation(location, zipOptions) {
|
|
497
|
+
if (!location) {
|
|
498
|
+
return null;
|
|
499
|
+
}
|
|
500
|
+
return {
|
|
501
|
+
city: location.city,
|
|
502
|
+
state: location.state,
|
|
503
|
+
stateCode: location.stateCode,
|
|
504
|
+
zipOptions: this.normalizeZipOptions(zipOptions)
|
|
505
|
+
};
|
|
506
|
+
}
|
|
507
|
+
normalizeZipOptions(value) {
|
|
508
|
+
if (!Array.isArray(value)) {
|
|
509
|
+
return [];
|
|
510
|
+
}
|
|
511
|
+
return Array.from(
|
|
512
|
+
new Set(
|
|
513
|
+
value.filter((zip) => typeof zip === "string" && /^\d{5}$/.test(zip))
|
|
514
|
+
)
|
|
515
|
+
);
|
|
516
|
+
}
|
|
504
517
|
formatSession(cached) {
|
|
505
518
|
return {
|
|
506
519
|
sessionToken: cached.sessionToken,
|
|
@@ -585,12 +598,12 @@ var lkey='cf_location_v1_'+site;
|
|
|
585
598
|
try{
|
|
586
599
|
var cl=JSON.parse(localStorage.getItem(lkey));
|
|
587
600
|
if(cl&&cl.expiresAt>Date.now()+30000){
|
|
588
|
-
if(!loc||(loc&&cl.locId===loc)){window.__cfTrackingLocation=Promise.resolve(cl)}
|
|
601
|
+
if(!loc||(loc&&cl.locId===loc)){if(cl.location&&!Array.isArray(cl.location.zipOptions))cl.location.zipOptions=[];window.__cfTrackingLocation=Promise.resolve(cl)}
|
|
589
602
|
}}catch(e){}
|
|
590
603
|
if(!window.__cfTrackingLocation){
|
|
591
604
|
var lurl='${endpoint}/v1/tracking/location';
|
|
592
605
|
if(loc)lurl+='?loc_physical_ms='+encodeURIComponent(loc);
|
|
593
|
-
window.__cfTrackingLocation=fetch(lurl,{credentials:'omit'}).then(function(r){if(!r.ok)throw new Error('tracking preload location failed');return r.json()}).then(function(d){d.locId=loc;try{localStorage.setItem(lkey,JSON.stringify({locId:loc,location:d.location?{city:d.location.city,state:d.location.state,stateCode:d.location.stateCode}:null,expiresAt:d.expiresAt,tokenVersion:'v1'}))}catch(e){}return d});
|
|
606
|
+
window.__cfTrackingLocation=fetch(lurl,{credentials:'omit'}).then(function(r){if(!r.ok)throw new Error('tracking preload location failed');return r.json()}).then(function(d){var z=Array.isArray(d.zipOptions)?d.zipOptions.filter(function(x){return /^\\d{5}$/.test(x)}):[];d.locId=loc;d.zipOptions=z;try{localStorage.setItem(lkey,JSON.stringify({locId:loc,location:d.location?{city:d.location.city,state:d.location.state,stateCode:d.location.stateCode,zipOptions:z}:null,expiresAt:d.expiresAt,tokenVersion:'v1'}))}catch(e){}return d});
|
|
594
607
|
}
|
|
595
608
|
var token=null;
|
|
596
609
|
try{
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@callforge/tracking-client",
|
|
3
|
-
"version": "0.7.
|
|
3
|
+
"version": "0.7.1",
|
|
4
4
|
"main": "dist/index.js",
|
|
5
5
|
"module": "dist/index.mjs",
|
|
6
6
|
"types": "dist/index.d.ts",
|
|
@@ -17,17 +17,17 @@
|
|
|
17
17
|
"files": [
|
|
18
18
|
"dist"
|
|
19
19
|
],
|
|
20
|
-
"devDependencies": {
|
|
21
|
-
"jsdom": "^27.4.0",
|
|
22
|
-
"tsup": "^8.0.0",
|
|
23
|
-
"typescript": "^5.3.0",
|
|
24
|
-
"vitest": "^1.6.0",
|
|
25
|
-
"@callforge/tsconfig": "0.0.0"
|
|
26
|
-
},
|
|
27
20
|
"scripts": {
|
|
28
21
|
"build": "tsup src/index.ts --format esm,cjs --dts",
|
|
29
22
|
"clean": "rm -rf dist",
|
|
30
23
|
"test": "vitest run",
|
|
31
24
|
"test:watch": "vitest"
|
|
25
|
+
},
|
|
26
|
+
"devDependencies": {
|
|
27
|
+
"@callforge/tsconfig": "workspace:*",
|
|
28
|
+
"jsdom": "^27.4.0",
|
|
29
|
+
"tsup": "^8.0.0",
|
|
30
|
+
"typescript": "^5.3.0",
|
|
31
|
+
"vitest": "^1.6.0"
|
|
32
32
|
}
|
|
33
|
-
}
|
|
33
|
+
}
|