@brainfish-ai/web-tracker 0.0.4-aplha.19 → 0.0.5-beta.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/dist/index.cjs.js +30 -0
- package/dist/index.cjs.js.gz +0 -0
- package/dist/index.cjs.js.map +1 -0
- package/dist/index.d.ts +2 -0
- package/dist/index.js +2849 -967
- package/dist/index.js.gz +0 -0
- package/dist/index.js.map +1 -0
- package/dist/src/common/isLocal.d.ts +1 -0
- package/dist/src/index.d.ts +24 -0
- package/dist/src/record/eventBuffer.d.ts +7 -0
- package/dist/src/record/index.d.ts +18 -0
- package/dist/src/record/recorder.d.ts +41 -0
- package/dist/src/record/recordingManager.d.ts +17 -0
- package/dist/src/record/sender.d.ts +11 -0
- package/dist/src/record/stasher.d.ts +23 -0
- package/dist/src/record/timer.d.ts +11 -0
- package/dist/src/redact/built-ins/NameRedactor.d.ts +6 -0
- package/dist/src/redact/built-ins/SimpleRegexpRedactor.d.ts +10 -0
- package/dist/src/redact/built-ins/simple-regexp-patterns.d.ts +12 -0
- package/dist/src/redact/built-ins/well-known-names.d.ts +2 -0
- package/dist/src/redact/composition.d.ts +2 -0
- package/dist/src/redact/index.d.ts +10 -0
- package/{src/redact/types.ts → dist/src/redact/types.d.ts} +15 -22
- package/dist/src/redact/utils.d.ts +4 -0
- package/dist/src/screenshot/capture.d.ts +2 -0
- package/dist/src/screenshot/redact.d.ts +3 -0
- package/dist/src/screenshot/snapshot.d.ts +2 -0
- package/dist/src/setupTests.d.ts +0 -0
- package/dist/src/tracker.d.ts +9 -0
- package/dist/tracker.cjs.js +2 -0
- package/dist/tracker.cjs.js.map +1 -0
- package/dist/tracker.d.ts +1 -0
- package/dist/tracker.js +15 -0
- package/dist/tracker.js.map +1 -0
- package/package.json +10 -6
- package/index.ts +0 -2
- package/postcss.config.cjs +0 -6
- package/set-version.js +0 -13
- package/src/index.ts +0 -192
- package/src/redact/built-ins/NameRedactor.ts +0 -41
- package/src/redact/built-ins/SimpleRegexpRedactor.ts +0 -22
- package/src/redact/built-ins/simple-regexp-patterns.ts +0 -20
- package/src/redact/built-ins/well-known-names.ts +0 -11543
- package/src/redact/composition.ts +0 -54
- package/src/redact/index.ts +0 -21
- package/src/redact/utils.ts +0 -15
- package/src/screenshot/capture.test.ts +0 -83
- package/src/screenshot/capture.ts +0 -51
- package/src/screenshot/redact.test.ts +0 -74
- package/src/screenshot/redact.ts +0 -57
- package/src/screenshot/snapshot.ts +0 -35
- package/src/setupTests.ts +0 -1
- package/src/tracker.ts +0 -31
- package/src/types.d.ts +0 -31
- package/src/vite-env.d.ts +0 -7
- package/tailwind.config.cjs +0 -9
- package/tsconfig.json +0 -16
- package/vite.config.ts +0 -55
|
@@ -1,54 +0,0 @@
|
|
|
1
|
-
import { NameRedactor } from './built-ins/NameRedactor';
|
|
2
|
-
import * as simpleRegexpBuiltIns from './built-ins/simple-regexp-patterns';
|
|
3
|
-
import { SimpleRegexpRedactor } from './built-ins/SimpleRegexpRedactor';
|
|
4
|
-
import {
|
|
5
|
-
AsyncCustomRedactorConfig,
|
|
6
|
-
IAsyncRedactor,
|
|
7
|
-
CompositeRedactorOptions,
|
|
8
|
-
SyncCustomRedactorConfig,
|
|
9
|
-
ISyncRedactor,
|
|
10
|
-
} from './types';
|
|
11
|
-
import { isSimpleRegexpCustomRedactorConfig, snakeCase } from './utils';
|
|
12
|
-
|
|
13
|
-
function normalizeCustomRedactorConfig(redactorConfig: any) {
|
|
14
|
-
return isSimpleRegexpCustomRedactorConfig(redactorConfig)
|
|
15
|
-
? new SimpleRegexpRedactor({
|
|
16
|
-
regexpPattern: redactorConfig.regexpPattern,
|
|
17
|
-
replaceWith: redactorConfig.replaceWith,
|
|
18
|
-
})
|
|
19
|
-
: redactorConfig;
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
export function composeChildRedactors<T extends AsyncCustomRedactorConfig>(opts: CompositeRedactorOptions<T> = {}) {
|
|
23
|
-
const childRedactors: T extends SyncCustomRedactorConfig
|
|
24
|
-
? Array<ISyncRedactor>
|
|
25
|
-
: Array<IAsyncRedactor | ISyncRedactor> = [] as any;
|
|
26
|
-
|
|
27
|
-
if (opts.customRedactors && opts.customRedactors.before) {
|
|
28
|
-
opts.customRedactors.before.map(normalizeCustomRedactorConfig).forEach((redactor) => childRedactors.push(redactor));
|
|
29
|
-
}
|
|
30
|
-
|
|
31
|
-
for (const regexpName of Object.keys(simpleRegexpBuiltIns)) {
|
|
32
|
-
if (
|
|
33
|
-
!opts.builtInRedactors ||
|
|
34
|
-
!(opts.builtInRedactors as any)[regexpName] ||
|
|
35
|
-
(opts.builtInRedactors as any)[regexpName].enabled !== false
|
|
36
|
-
) {
|
|
37
|
-
childRedactors.push(
|
|
38
|
-
new SimpleRegexpRedactor({
|
|
39
|
-
regexpPattern: (simpleRegexpBuiltIns as any)[regexpName],
|
|
40
|
-
replaceWith: opts.globalReplaceWith || snakeCase(regexpName).toUpperCase(),
|
|
41
|
-
})
|
|
42
|
-
);
|
|
43
|
-
}
|
|
44
|
-
}
|
|
45
|
-
|
|
46
|
-
if (!opts.builtInRedactors || !opts.builtInRedactors.names || opts.builtInRedactors.names.enabled !== false) {
|
|
47
|
-
childRedactors.push(new NameRedactor(opts.globalReplaceWith));
|
|
48
|
-
}
|
|
49
|
-
|
|
50
|
-
if (opts.customRedactors && opts.customRedactors.after) {
|
|
51
|
-
opts.customRedactors.after.map(normalizeCustomRedactorConfig).forEach((redactor) => childRedactors.push(redactor));
|
|
52
|
-
}
|
|
53
|
-
return childRedactors;
|
|
54
|
-
}
|
package/src/redact/index.ts
DELETED
|
@@ -1,21 +0,0 @@
|
|
|
1
|
-
import { composeChildRedactors } from './composition';
|
|
2
|
-
import { CompositeRedactorOptions, ISyncRedactor, SyncCustomRedactorConfig } from './types';
|
|
3
|
-
|
|
4
|
-
/** @public */
|
|
5
|
-
export interface SyncCompositeRedactorOptions extends CompositeRedactorOptions<SyncCustomRedactorConfig> {}
|
|
6
|
-
|
|
7
|
-
/** @public */
|
|
8
|
-
export class SyncRedactor implements ISyncRedactor {
|
|
9
|
-
private childRedactors: ISyncRedactor[] = [];
|
|
10
|
-
|
|
11
|
-
constructor(opts?: SyncCompositeRedactorOptions) {
|
|
12
|
-
this.childRedactors = composeChildRedactors(opts);
|
|
13
|
-
}
|
|
14
|
-
|
|
15
|
-
redact = (textToRedact: string) => {
|
|
16
|
-
for (const redactor of this.childRedactors) {
|
|
17
|
-
textToRedact = redactor.redact(textToRedact);
|
|
18
|
-
}
|
|
19
|
-
return textToRedact;
|
|
20
|
-
};
|
|
21
|
-
}
|
package/src/redact/utils.ts
DELETED
|
@@ -1,15 +0,0 @@
|
|
|
1
|
-
import { SimpleRegexpCustomRedactorConfig, AsyncCustomRedactorConfig, ISyncRedactor, IRedactor } from './types';
|
|
2
|
-
|
|
3
|
-
export function isSimpleRegexpCustomRedactorConfig(
|
|
4
|
-
redactor: AsyncCustomRedactorConfig
|
|
5
|
-
): redactor is SimpleRegexpCustomRedactorConfig {
|
|
6
|
-
return typeof (redactor as SimpleRegexpCustomRedactorConfig).regexpPattern !== 'undefined';
|
|
7
|
-
}
|
|
8
|
-
|
|
9
|
-
export function isSyncRedactor(redactor: IRedactor): redactor is ISyncRedactor {
|
|
10
|
-
return typeof (redactor as ISyncRedactor).redact === 'function';
|
|
11
|
-
}
|
|
12
|
-
|
|
13
|
-
export function snakeCase(str: string) {
|
|
14
|
-
return str.replace(/[A-Z]/g, (letter, index) => (index !== 0 ? `_${letter.toLowerCase()}` : letter.toLowerCase()));
|
|
15
|
-
}
|
|
@@ -1,83 +0,0 @@
|
|
|
1
|
-
import { describe, it, expect, vi, beforeEach, afterEach } from 'vitest';
|
|
2
|
-
import { captureScreenshot } from './capture';
|
|
3
|
-
import { toPng } from 'html-to-image';
|
|
4
|
-
|
|
5
|
-
// Mock the html-to-image module
|
|
6
|
-
vi.mock('html-to-image', () => ({
|
|
7
|
-
toPng: vi.fn(),
|
|
8
|
-
}));
|
|
9
|
-
|
|
10
|
-
describe('captureScreenshot', () => {
|
|
11
|
-
let mockDomBody: HTMLElement;
|
|
12
|
-
|
|
13
|
-
beforeEach(() => {
|
|
14
|
-
// Create a mock DOM body
|
|
15
|
-
mockDomBody = document.createElement('div');
|
|
16
|
-
document.body.appendChild(mockDomBody);
|
|
17
|
-
|
|
18
|
-
// Mock document properties
|
|
19
|
-
vi.spyOn(document.documentElement, 'scrollHeight', 'get').mockReturnValue(1000);
|
|
20
|
-
vi.spyOn(document.documentElement, 'scrollWidth', 'get').mockReturnValue(800);
|
|
21
|
-
|
|
22
|
-
// Mock styleSheets
|
|
23
|
-
Object.defineProperty(document, 'styleSheets', {
|
|
24
|
-
value: [
|
|
25
|
-
{
|
|
26
|
-
cssRules: [
|
|
27
|
-
{ cssText: 'body { background-color: white; }' },
|
|
28
|
-
{ cssText: 'h1 { color: black; }' },
|
|
29
|
-
],
|
|
30
|
-
},
|
|
31
|
-
],
|
|
32
|
-
configurable: true,
|
|
33
|
-
});
|
|
34
|
-
|
|
35
|
-
// Mock toPng function
|
|
36
|
-
vi.mocked(toPng).mockResolvedValue('mock-image-data');
|
|
37
|
-
});
|
|
38
|
-
|
|
39
|
-
afterEach(() => {
|
|
40
|
-
document.body.removeChild(mockDomBody);
|
|
41
|
-
vi.restoreAllMocks();
|
|
42
|
-
});
|
|
43
|
-
|
|
44
|
-
it('should capture a screenshot of the entire page', async () => {
|
|
45
|
-
const result = await captureScreenshot(mockDomBody);
|
|
46
|
-
|
|
47
|
-
expect(result).toBe('mock-image-data');
|
|
48
|
-
expect(toPng).toHaveBeenCalledWith(mockDomBody, expect.objectContaining({
|
|
49
|
-
quality: 0.7,
|
|
50
|
-
width: 800,
|
|
51
|
-
height: 1000,
|
|
52
|
-
style: { transform: 'scale(1)' },
|
|
53
|
-
skipFonts: true,
|
|
54
|
-
cacheBust: true,
|
|
55
|
-
backgroundColor: 'white',
|
|
56
|
-
fetchRequestInit: { mode: 'cors' },
|
|
57
|
-
}));
|
|
58
|
-
});
|
|
59
|
-
|
|
60
|
-
it('should handle errors when accessing stylesheet rules', async () => {
|
|
61
|
-
const consoleLogSpy = vi.spyOn(console, 'log').mockImplementation(() => {});
|
|
62
|
-
|
|
63
|
-
// Mock styleSheets to throw an error
|
|
64
|
-
Object.defineProperty(document, 'styleSheets', {
|
|
65
|
-
get: () => ({
|
|
66
|
-
[Symbol.iterator]: function* () {
|
|
67
|
-
yield {
|
|
68
|
-
cssRules: {
|
|
69
|
-
[Symbol.iterator]: function* () {
|
|
70
|
-
throw new Error('Access denied');
|
|
71
|
-
},
|
|
72
|
-
},
|
|
73
|
-
};
|
|
74
|
-
},
|
|
75
|
-
}),
|
|
76
|
-
configurable: true,
|
|
77
|
-
});
|
|
78
|
-
|
|
79
|
-
await captureScreenshot(mockDomBody);
|
|
80
|
-
|
|
81
|
-
expect(consoleLogSpy).toHaveBeenCalledWith('Error accessing stylesheet rules:', expect.any(Error));
|
|
82
|
-
});
|
|
83
|
-
});
|
|
@@ -1,51 +0,0 @@
|
|
|
1
|
-
import { toPng } from 'html-to-image';
|
|
2
|
-
|
|
3
|
-
// Function to capture a screenshot of the entire page
|
|
4
|
-
async function captureScreenshot(domBody: HTMLElement): Promise<string> {
|
|
5
|
-
const height = document.documentElement.scrollHeight;
|
|
6
|
-
const width = document.documentElement.scrollWidth;
|
|
7
|
-
|
|
8
|
-
// Collect all stylesheet rules
|
|
9
|
-
const styles = Array.from(document.styleSheets)
|
|
10
|
-
.map(styleSheet => {
|
|
11
|
-
try {
|
|
12
|
-
return Array.from(styleSheet.cssRules)
|
|
13
|
-
.map(rule => rule.cssText)
|
|
14
|
-
.join('');
|
|
15
|
-
} catch (e) {
|
|
16
|
-
console.log('Error accessing stylesheet rules:', e);
|
|
17
|
-
return '';
|
|
18
|
-
}
|
|
19
|
-
})
|
|
20
|
-
.join('\n');
|
|
21
|
-
|
|
22
|
-
// Create a new style element with all the rules
|
|
23
|
-
const styleElement = document.createElement('style');
|
|
24
|
-
styleElement.textContent = styles;
|
|
25
|
-
domBody.appendChild(styleElement);
|
|
26
|
-
|
|
27
|
-
// Capture the screenshot
|
|
28
|
-
const image = await toPng(domBody, {
|
|
29
|
-
quality: 0.7, // Set quality to 0.7
|
|
30
|
-
width, // Set width to the scroll width
|
|
31
|
-
height, // Set height to the scroll height
|
|
32
|
-
style: {
|
|
33
|
-
transform: 'scale(1)', // Set scale to 1 to avoid scaling
|
|
34
|
-
},
|
|
35
|
-
skipFonts: true, // Avoid embedding web fonts to bypass SecurityError
|
|
36
|
-
cacheBust: true, // Prevent caching
|
|
37
|
-
backgroundColor: 'white', // Set background color to white
|
|
38
|
-
fetchRequestInit: {
|
|
39
|
-
mode: 'cors', // Enable CORS
|
|
40
|
-
},
|
|
41
|
-
})
|
|
42
|
-
|
|
43
|
-
// Remove the style element
|
|
44
|
-
domBody.removeChild(styleElement);
|
|
45
|
-
|
|
46
|
-
return image;
|
|
47
|
-
}
|
|
48
|
-
|
|
49
|
-
export { captureScreenshot };
|
|
50
|
-
|
|
51
|
-
|
|
@@ -1,74 +0,0 @@
|
|
|
1
|
-
import { redactTextContent, redactPIIInDOM } from './redact';
|
|
2
|
-
import { describe, it, expect, beforeEach } from 'vitest';
|
|
3
|
-
|
|
4
|
-
describe('redactTextContent', () => {
|
|
5
|
-
it('should redact email addresses', () => {
|
|
6
|
-
const text = 'Contact me at john.doe@example.com';
|
|
7
|
-
const redacted = redactTextContent(text);
|
|
8
|
-
expect(redacted).toBe('Contact me at EMAIL_ADDRESS');
|
|
9
|
-
});
|
|
10
|
-
|
|
11
|
-
it('should redact phone numbers', () => {
|
|
12
|
-
const text = 'My phone number is 123-456-7890';
|
|
13
|
-
const redacted = redactTextContent(text);
|
|
14
|
-
expect(redacted).toBe('My phone number is PHONE_NUMBER');
|
|
15
|
-
});
|
|
16
|
-
|
|
17
|
-
it('should redact SSNs', () => {
|
|
18
|
-
const text = 'SSN: 123-45-6789';
|
|
19
|
-
const redacted = redactTextContent(text);
|
|
20
|
-
expect(redacted).toBe('SSN: US_SOCIAL_SECURITY_NUMBER');
|
|
21
|
-
});
|
|
22
|
-
|
|
23
|
-
it('should redact passport numbers', () => {
|
|
24
|
-
const text = 'Passport number: A1234567';
|
|
25
|
-
const redacted = redactTextContent(text);
|
|
26
|
-
expect(redacted).toBe('Passport number: PASSPORT_NUMBER');
|
|
27
|
-
});
|
|
28
|
-
|
|
29
|
-
it('should return the original text if no PII is found', () => {
|
|
30
|
-
const text = 'No PII here';
|
|
31
|
-
const redacted = redactTextContent(text);
|
|
32
|
-
expect(redacted).toBe(text);
|
|
33
|
-
});
|
|
34
|
-
|
|
35
|
-
it('should redact credit card numbers', () => {
|
|
36
|
-
const text = 'Credit Card: 1234-5678-1234-5678';
|
|
37
|
-
const redacted = redactTextContent(text);
|
|
38
|
-
expect(redacted).toBe('Credit Card: CREDIT_CARD_NUMBER');
|
|
39
|
-
});
|
|
40
|
-
});
|
|
41
|
-
|
|
42
|
-
describe('redactPIIInDOM', () => {
|
|
43
|
-
beforeEach(() => {
|
|
44
|
-
document.body.innerHTML = `
|
|
45
|
-
<div id="content">
|
|
46
|
-
<p>Email: john.doe@example.com</p>
|
|
47
|
-
<p>Phone: 123-456-7890</p>
|
|
48
|
-
<p>SSN: 123-45-6789</p>
|
|
49
|
-
<p>Passport: A1234567</p>
|
|
50
|
-
<p>No PII here</p>
|
|
51
|
-
</div>
|
|
52
|
-
`;
|
|
53
|
-
});
|
|
54
|
-
|
|
55
|
-
it('should redact PII in text nodes', () => {
|
|
56
|
-
const element = document.getElementById('content') as Element;
|
|
57
|
-
redactPIIInDOM(element);
|
|
58
|
-
|
|
59
|
-
expect(element.innerHTML).toContain('Email: EMAIL_ADDRESS');
|
|
60
|
-
expect(element.innerHTML).toContain('Phone: PHONE_NUMBER');
|
|
61
|
-
expect(element.innerHTML).toContain('SSN: US_SOCIAL_SECURITY_NUMBER');
|
|
62
|
-
expect(element.innerHTML).toContain('Passport: PASSPORT_NUMBER');
|
|
63
|
-
expect(element.innerHTML).toContain('No PII here');
|
|
64
|
-
});
|
|
65
|
-
|
|
66
|
-
it('should not change text content without PII', () => {
|
|
67
|
-
const element = document.querySelector('p:last-child') as Element;
|
|
68
|
-
const originalText = element.textContent;
|
|
69
|
-
|
|
70
|
-
redactPIIInDOM(element);
|
|
71
|
-
|
|
72
|
-
expect(element.textContent).toBe(originalText);
|
|
73
|
-
});
|
|
74
|
-
});
|
package/src/screenshot/redact.ts
DELETED
|
@@ -1,57 +0,0 @@
|
|
|
1
|
-
import { SyncRedactor } from "./../redact/index";
|
|
2
|
-
|
|
3
|
-
const customRedactors = {
|
|
4
|
-
before: [
|
|
5
|
-
{
|
|
6
|
-
regexpPattern: /\b[A-Z]\d{7}\b/g,
|
|
7
|
-
replaceWith: 'PASSPORT_NUMBER'
|
|
8
|
-
},
|
|
9
|
-
{
|
|
10
|
-
regexpPattern: /(?<=password: )(.*)/gi,
|
|
11
|
-
replaceWith: '[REDACTED]'
|
|
12
|
-
}
|
|
13
|
-
],
|
|
14
|
-
};
|
|
15
|
-
|
|
16
|
-
// Function to redact PII in text content
|
|
17
|
-
function redactTextContent(text: string): string {
|
|
18
|
-
const redactor = new SyncRedactor({
|
|
19
|
-
builtInRedactors: {
|
|
20
|
-
names: {
|
|
21
|
-
replaceWith: 'ANONYMOUS_PERSON'
|
|
22
|
-
}
|
|
23
|
-
},
|
|
24
|
-
customRedactors
|
|
25
|
-
});
|
|
26
|
-
return redactor.redact(text);
|
|
27
|
-
}
|
|
28
|
-
|
|
29
|
-
// Function to recursively find and redact PII in text nodes
|
|
30
|
-
function redactPIIInDOM(element: Element) {
|
|
31
|
-
const treeWalker = document.createTreeWalker(element, NodeFilter.SHOW_TEXT, null);
|
|
32
|
-
let currentNode;
|
|
33
|
-
|
|
34
|
-
while ((currentNode = treeWalker.nextNode())) {
|
|
35
|
-
const originalText = currentNode.nodeValue as string;
|
|
36
|
-
const redactedText = redactTextContent(originalText);
|
|
37
|
-
|
|
38
|
-
if (originalText !== redactedText) {
|
|
39
|
-
currentNode.nodeValue = redactedText;
|
|
40
|
-
}
|
|
41
|
-
}
|
|
42
|
-
|
|
43
|
-
// Redact PII in input fields
|
|
44
|
-
redactPIIInInputs(element);
|
|
45
|
-
}
|
|
46
|
-
|
|
47
|
-
// Function to redact PII from passwords in input fields
|
|
48
|
-
function redactPIIInInputs(element: Element) {
|
|
49
|
-
const inputs = Array.from(element.querySelectorAll('input[type="password"]'));
|
|
50
|
-
inputs.forEach(input => {
|
|
51
|
-
const passwordInput = input as HTMLInputElement;
|
|
52
|
-
passwordInput.value = '[REDACTED]';
|
|
53
|
-
});
|
|
54
|
-
}
|
|
55
|
-
|
|
56
|
-
export { redactPIIInDOM, redactTextContent };
|
|
57
|
-
|
|
@@ -1,35 +0,0 @@
|
|
|
1
|
-
import { captureScreenshot } from "./capture";
|
|
2
|
-
import { redactPIIInDOM } from "./redact";
|
|
3
|
-
|
|
4
|
-
async function screenshot() {
|
|
5
|
-
try {
|
|
6
|
-
// Wait for page to load
|
|
7
|
-
await new Promise((resolve) => {
|
|
8
|
-
if (document.readyState === 'complete') {
|
|
9
|
-
resolve(null);
|
|
10
|
-
} else {
|
|
11
|
-
window.addEventListener('load', resolve);
|
|
12
|
-
}
|
|
13
|
-
});
|
|
14
|
-
|
|
15
|
-
// Clone the document body to avoid modifying the original
|
|
16
|
-
const clonedBody = document.body.cloneNode(true) as HTMLElement;
|
|
17
|
-
|
|
18
|
-
// Redact PII in text content
|
|
19
|
-
redactPIIInDOM(clonedBody);
|
|
20
|
-
|
|
21
|
-
// Capture the screenshot
|
|
22
|
-
const imageDataUrl = await captureScreenshot(clonedBody);
|
|
23
|
-
|
|
24
|
-
// if local env, print the imageDataUrl to the console
|
|
25
|
-
if (window.location.hostname === 'localhost') {
|
|
26
|
-
console.log(imageDataUrl);
|
|
27
|
-
}
|
|
28
|
-
|
|
29
|
-
return imageDataUrl;
|
|
30
|
-
} catch (error) {
|
|
31
|
-
console.error('An error occurred:', error);
|
|
32
|
-
}
|
|
33
|
-
}
|
|
34
|
-
|
|
35
|
-
export { screenshot };
|
package/src/setupTests.ts
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
// Setup for Jest tests
|
package/src/tracker.ts
DELETED
|
@@ -1,31 +0,0 @@
|
|
|
1
|
-
import { Tracker } from './index';
|
|
2
|
-
|
|
3
|
-
declare global {
|
|
4
|
-
interface Window {
|
|
5
|
-
BrainfishAnalytics: {
|
|
6
|
-
q?: [string, ...any[]];
|
|
7
|
-
(method: string, ...args: any[]): void;
|
|
8
|
-
};
|
|
9
|
-
}
|
|
10
|
-
}
|
|
11
|
-
|
|
12
|
-
((window) => {
|
|
13
|
-
if (window.BrainfishAnalytics && 'q' in window.BrainfishAnalytics) {
|
|
14
|
-
const queue = window.BrainfishAnalytics.q || [];
|
|
15
|
-
const tracker = new Tracker(queue.shift()[1]) as any;
|
|
16
|
-
queue.forEach((item) => {
|
|
17
|
-
if (item[0] in tracker) {
|
|
18
|
-
tracker[item[0]](...item.slice(1));
|
|
19
|
-
}
|
|
20
|
-
});
|
|
21
|
-
|
|
22
|
-
window.BrainfishAnalytics = (t, ...args) => {
|
|
23
|
-
const fn = tracker[t] ? tracker[t].bind(tracker) : undefined;
|
|
24
|
-
if (typeof fn === 'function') {
|
|
25
|
-
fn(...args);
|
|
26
|
-
} else {
|
|
27
|
-
console.warn(`Method ${t} does not exist on BrainfishAnalytics`);
|
|
28
|
-
}
|
|
29
|
-
};
|
|
30
|
-
}
|
|
31
|
-
})(window);
|
package/src/types.d.ts
DELETED
|
@@ -1,31 +0,0 @@
|
|
|
1
|
-
import type { Tracker, TrackerOptions, TrackProperties } from "./index";
|
|
2
|
-
|
|
3
|
-
type ExposedMethodsNames =
|
|
4
|
-
| 'track'
|
|
5
|
-
| 'identify'
|
|
6
|
-
| 'setGlobalProperties'
|
|
7
|
-
| 'alias'
|
|
8
|
-
| 'increment'
|
|
9
|
-
| 'decrement'
|
|
10
|
-
| 'clear';
|
|
11
|
-
|
|
12
|
-
export type ExposedMethods = {
|
|
13
|
-
[K in ExposedMethodsNames]: Tracker[K] extends (...args: any[]) => any
|
|
14
|
-
? [K, ...Parameters<Tracker[K]>]
|
|
15
|
-
: never;
|
|
16
|
-
}[ExposedMethodsNames];
|
|
17
|
-
|
|
18
|
-
export type TrackerMethodNames = ExposedMethodsNames | 'init' | 'screenView';
|
|
19
|
-
export type TrackerMethods =
|
|
20
|
-
| ExposedMethods
|
|
21
|
-
| ['init', TrackerOptions]
|
|
22
|
-
| ['screenView', string | TrackProperties, TrackProperties];
|
|
23
|
-
|
|
24
|
-
declare global {
|
|
25
|
-
interface Window {
|
|
26
|
-
BrainfishAnalytics: {
|
|
27
|
-
q?: [string, ...any[]];
|
|
28
|
-
(method: string, ...args: any[]): void;
|
|
29
|
-
};
|
|
30
|
-
}
|
|
31
|
-
}
|
package/src/vite-env.d.ts
DELETED
package/tailwind.config.cjs
DELETED
package/tsconfig.json
DELETED
|
@@ -1,16 +0,0 @@
|
|
|
1
|
-
{
|
|
2
|
-
"compilerOptions": {
|
|
3
|
-
"strict": true,
|
|
4
|
-
"target": "ESNext",
|
|
5
|
-
"module": "ESNext",
|
|
6
|
-
"moduleResolution": "node",
|
|
7
|
-
"allowSyntheticDefaultImports": true,
|
|
8
|
-
"esModuleInterop": true,
|
|
9
|
-
"types": ["vite/client", "jest"],
|
|
10
|
-
"baseUrl": ".",
|
|
11
|
-
"declaration": true,
|
|
12
|
-
"resolveJsonModule": true
|
|
13
|
-
},
|
|
14
|
-
"include": ["src", "./package.json"],
|
|
15
|
-
"exclude": ["src/**/*.test.ts", "src/**/*.spec.ts", "src/**/tests/**"]
|
|
16
|
-
}
|
package/vite.config.ts
DELETED
|
@@ -1,55 +0,0 @@
|
|
|
1
|
-
import { defineConfig } from 'vite';
|
|
2
|
-
import { terser } from 'rollup-plugin-terser';
|
|
3
|
-
import dts from 'vite-plugin-dts';
|
|
4
|
-
import compression from 'vite-plugin-compression';
|
|
5
|
-
import { visualizer } from 'rollup-plugin-visualizer';
|
|
6
|
-
import tsconfigPaths from 'vite-tsconfig-paths';
|
|
7
|
-
import { version } from './package.json';
|
|
8
|
-
|
|
9
|
-
export default defineConfig({
|
|
10
|
-
plugins: [
|
|
11
|
-
tsconfigPaths(),
|
|
12
|
-
dts({
|
|
13
|
-
tsconfigPath: './tsconfig.json',
|
|
14
|
-
insertTypesEntry: true,
|
|
15
|
-
include: ['src'],
|
|
16
|
-
}),
|
|
17
|
-
compression(),
|
|
18
|
-
visualizer(),
|
|
19
|
-
],
|
|
20
|
-
build: {
|
|
21
|
-
target: 'es2015',
|
|
22
|
-
sourcemap: true,
|
|
23
|
-
lib: {
|
|
24
|
-
entry: 'index.ts',
|
|
25
|
-
name: 'BrainfishAnalytics',
|
|
26
|
-
formats: ['es', 'cjs'],
|
|
27
|
-
fileName: (format, entry) => `${entry}${format === 'es' ? '' : '.cjs'}.js`,
|
|
28
|
-
},
|
|
29
|
-
minify: true,
|
|
30
|
-
terserOptions: {
|
|
31
|
-
compress: {
|
|
32
|
-
drop_console: true,
|
|
33
|
-
drop_debugger: true,
|
|
34
|
-
},
|
|
35
|
-
},
|
|
36
|
-
rollupOptions: {
|
|
37
|
-
treeshake: true,
|
|
38
|
-
plugins: [terser()],
|
|
39
|
-
external: ['@google-cloud/dlp'],
|
|
40
|
-
output: {
|
|
41
|
-
inlineDynamicImports: true, // Ensures all imports are inlined into the main bundle
|
|
42
|
-
manualChunks: undefined, // Disables code splitting
|
|
43
|
-
},
|
|
44
|
-
},
|
|
45
|
-
},
|
|
46
|
-
test: {
|
|
47
|
-
environment: 'jsdom',
|
|
48
|
-
},
|
|
49
|
-
define: {
|
|
50
|
-
'import.meta.env.PACKAGE_VERSION': JSON.stringify(version),
|
|
51
|
-
},
|
|
52
|
-
optimizeDeps: {
|
|
53
|
-
include: ['@brainfish-ai/tracker-sdk'],
|
|
54
|
-
},
|
|
55
|
-
});
|