Skip to content

Commit b6d48d2

Browse files
committed
parameterize
1 parent a7ca7ef commit b6d48d2

File tree

3 files changed

+64
-63
lines changed

3 files changed

+64
-63
lines changed

packages/script/src/base.js

Lines changed: 51 additions & 47 deletions
Original file line numberDiff line numberDiff line change
@@ -1,34 +1,54 @@
11
(function () {
2+
// Store script reference for extensions
3+
const script = document.currentScript;
4+
25
const DUB_ID_VAR = 'dub_id';
36
const COOKIE_EXPIRES = 90 * 24 * 60 * 60 * 1000; // 90 days
47
const HOSTNAME = window.location.hostname;
5-
let clientClickTracked = false;
68

7-
// Store script reference for extensions
8-
const script = document.currentScript;
9+
// Common script attributes
10+
const API_HOST = script.getAttribute('data-api-host') || 'https://api.dub.co';
11+
const COOKIE_OPTIONS = (() => {
12+
const defaultOptions = {
13+
domain:
14+
HOSTNAME === 'localhost'
15+
? undefined
16+
: `.${HOSTNAME.replace(/^www\./, '')}`,
17+
path: '/',
18+
sameSite: 'Lax',
19+
expires: new Date(Date.now() + COOKIE_EXPIRES).toUTCString(),
20+
};
21+
22+
const opts = script.getAttribute('data-cookie-options');
23+
if (!opts) return defaultOptions;
24+
25+
const parsedOpts = JSON.parse(opts);
26+
if (parsedOpts.expiresInDays) {
27+
parsedOpts.expires = new Date(
28+
Date.now() + parsedOpts.expiresInDays * 24 * 60 * 60 * 1000,
29+
).toUTCString();
30+
delete parsedOpts.expiresInDays;
31+
}
32+
33+
return { ...defaultOptions, ...parsedOpts };
34+
})();
35+
const SHORT_DOMAIN =
36+
script.getAttribute('data-short-domain') ||
37+
script.getAttribute('data-domain');
38+
const ATTRIBUTION_MODEL =
39+
script.getAttribute('data-attribution-model') || 'last-click';
940

1041
// Cookie management
11-
const cookie = {
42+
const cookieManager = {
1243
get(key) {
1344
return document.cookie
1445
.split(';')
1546
.map((c) => c.trim().split('='))
1647
.find(([k]) => k === key)?.[1];
1748
},
1849

19-
set(key, value, options = {}) {
20-
const defaultOptions = {
21-
domain:
22-
HOSTNAME === 'localhost'
23-
? undefined
24-
: `.${HOSTNAME.replace(/^www\./, '')}`,
25-
path: '/',
26-
sameSite: 'Lax',
27-
expires: new Date(Date.now() + COOKIE_EXPIRES).toUTCString(),
28-
};
29-
30-
const opts = { ...defaultOptions, ...options };
31-
const cookieString = Object.entries(opts)
50+
set(key, value) {
51+
const cookieString = Object.entries(COOKIE_OPTIONS)
3252
.filter(([, v]) => v)
3353
.map(([k, v]) => `${k}=${v}`)
3454
.join('; ');
@@ -37,22 +57,17 @@
3757
},
3858
};
3959

60+
let clientClickTracked = false;
4061
// Track click and set cookie
4162
function trackClick(identifier) {
4263
if (clientClickTracked) return;
4364
clientClickTracked = true;
4465

45-
const apiHost =
46-
script.getAttribute('data-api-host') || 'https://api.dub.co';
47-
const shortDomain =
48-
script.getAttribute('data-short-domain') ||
49-
script.getAttribute('data-domain');
50-
51-
fetch(`${apiHost}/track/click`, {
66+
fetch(`${API_HOST}/track/click`, {
5267
method: 'POST',
5368
headers: { 'Content-Type': 'application/json' },
5469
body: JSON.stringify({
55-
domain: shortDomain,
70+
domain: SHORT_DOMAIN,
5671
key: identifier,
5772
url: window.location.href,
5873
referrer: document.referrer,
@@ -61,54 +76,43 @@
6176
.then((res) => res.ok && res.json())
6277
.then((data) => {
6378
if (data) {
64-
const cookieOptions = script.getAttribute('data-cookie-options');
65-
cookie.set(
66-
DUB_ID_VAR,
67-
data.clickId,
68-
cookieOptions ? JSON.parse(cookieOptions) : null,
69-
);
79+
cookieManager.set(DUB_ID_VAR, data.clickId);
7080
}
7181
});
7282
}
7383

7484
// Initialize tracking
7585
function init() {
7686
const params = new URLSearchParams(window.location.search);
77-
const shortDomain =
78-
script.getAttribute('data-short-domain') ||
79-
script.getAttribute('data-domain');
8087
const queryParam = script.getAttribute('data-query-param') || 'via';
81-
const attributionModel =
82-
script.getAttribute('data-attribution-model') || 'last-click';
8388

8489
// Direct click ID in URL
8590
const clickId = params.get(DUB_ID_VAR);
8691
if (clickId) {
87-
const cookieOptions = script.getAttribute('data-cookie-options');
88-
cookie.set(
89-
DUB_ID_VAR,
90-
clickId,
91-
cookieOptions ? JSON.parse(cookieOptions) : null,
92-
);
92+
cookieManager.set(DUB_ID_VAR, clickId);
9393
return;
9494
}
9595

9696
// Track via query param
9797
const identifier = params.get(queryParam);
98-
if (identifier && shortDomain) {
99-
const existingCookie = cookie.get(DUB_ID_VAR);
100-
if (!existingCookie || attributionModel !== 'first-click') {
98+
if (identifier && SHORT_DOMAIN) {
99+
const existingCookie = cookieManager.get(DUB_ID_VAR);
100+
if (!existingCookie || ATTRIBUTION_MODEL !== 'first-click') {
101101
trackClick(identifier);
102102
}
103103
}
104104
}
105105

106106
// Export core functionality
107107
window._dubAnalytics = {
108+
script,
109+
cookieManager,
108110
DUB_ID_VAR,
109111
HOSTNAME,
110-
cookie,
111-
script, // Export script reference
112+
API_HOST,
113+
COOKIE_OPTIONS,
114+
SHORT_DOMAIN,
115+
ATTRIBUTION_MODEL,
112116
};
113117

114118
// Initialize

packages/script/src/extensions/outbound-domains.js

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
// Wait for base script to initialize
22
const initOutboundDomains = () => {
3-
const { DUB_ID_VAR, cookie, HOSTNAME, script } = window._dubAnalytics;
3+
const { script, cookieManager, DUB_ID_VAR, HOSTNAME } = window._dubAnalytics;
44
let outboundLinksUpdated = new Set(); // Track processed links
55

66
function addOutboundTracking(clickId) {
@@ -10,7 +10,7 @@ const initOutboundDomains = () => {
1010
const outboundDomains = outboundDomainsAttr.split(',').map((d) => d.trim());
1111
if (outboundDomains.length === 0) return;
1212

13-
const existingCookie = clickId || cookie.get(DUB_ID_VAR);
13+
const existingCookie = clickId || cookieManager.get(DUB_ID_VAR);
1414
if (!existingCookie) return;
1515

1616
const currentDomain = HOSTNAME.replace(/^www\./, '');

packages/script/src/extensions/site-visit.js

Lines changed: 11 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -1,20 +1,22 @@
11
// Wait for base script to initialize
22
const initSiteVisit = () => {
3-
const { DUB_ID_VAR, cookie, script } = window._dubAnalytics;
3+
const {
4+
script,
5+
cookieManager,
6+
DUB_ID_VAR,
7+
API_HOST, // Use shared API_HOST
8+
} = window._dubAnalytics;
9+
410
let siteVisitTracked = false;
511

612
function trackSiteVisit() {
7-
const apiHost =
8-
script.getAttribute('data-api-host') || 'https://api.dub.co';
913
const siteShortDomain = script.getAttribute('data-site-short-domain');
10-
11-
// Return early if siteShortDomain is not set or if visit already tracked
1214
if (!siteShortDomain || siteVisitTracked) return;
1315
siteVisitTracked = true;
1416

15-
// Only track if no existing cookie
16-
if (!cookie.get(DUB_ID_VAR)) {
17-
fetch(`${apiHost}/track/visit`, {
17+
if (!cookieManager.get(DUB_ID_VAR)) {
18+
fetch(`${API_HOST}/track/visit`, {
19+
// Use shared API_HOST
1820
method: 'POST',
1921
headers: { 'Content-Type': 'application/json' },
2022
body: JSON.stringify({
@@ -26,12 +28,7 @@ const initSiteVisit = () => {
2628
.then((res) => res.ok && res.json())
2729
.then((data) => {
2830
if (data.clickId) {
29-
const cookieOptions = script.getAttribute('data-cookie-options');
30-
cookie.set(
31-
DUB_ID_VAR,
32-
data.clickId,
33-
cookieOptions ? JSON.parse(cookieOptions) : null,
34-
);
31+
cookieManager.set(DUB_ID_VAR, data.clickId);
3532
}
3633
});
3734
}

0 commit comments

Comments
 (0)