@fuul/sdk 0.5.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 ADDED
@@ -0,0 +1,99 @@
1
+ # Getting started with Fuul SDK
2
+
3
+ **Setting up the Fuul SDK**
4
+
5
+ ## **1. Install the Fuul SDK**
6
+
7
+ Run one of the following commands to add Fuul SDK to your project:
8
+
9
+ ### npm
10
+
11
+ ```bash
12
+ npm install fuul-sdk
13
+ ```
14
+
15
+ ### yarn
16
+
17
+ ```bash
18
+ yarn add fuul-sdk
19
+ ```
20
+
21
+ ## 2**. Set up the Fuul SDK**
22
+
23
+ In order to authenticate to full with your project, you must execute the following in the root file of your app.
24
+
25
+ ```tsx
26
+ // App.tsx
27
+
28
+ // Settings config object
29
+ const settings = {
30
+ projectId: "myprojectid", // Replace with your Fuul Project Id.
31
+ };
32
+
33
+ const fuul = new Fuul(settings);
34
+ ```
35
+
36
+ By this way, you’ll be available to use Fuul as a global object in any of your files, so you don’t have to create a new instance every time.
37
+
38
+ - Please note that `projectId` is not required when you initialize Fuul sdk, but it is mandatory in order to send a `“connect_wallet”` event. But don’t worry, you can send it later as an argument using the `Fuul.sendEvent()` method if needed (please refer to section 3 of this guide)
39
+
40
+ ## 3**. Verifying the connection to Fuul SDK**
41
+
42
+ You can verify that everything was set up successfully with the following method
43
+
44
+ ```tsx
45
+ Fuul.verifyConnection()
46
+ ```
47
+
48
+ If everything is ok, you will see a prompt as below:
49
+
50
+ ![Untitled](Getting%20started%20with%20Fuul%20SDK%205855c088f6d14fcf9dca9d3a13e9bd86/Untitled.png)
51
+
52
+ ## 4**. Sending events**
53
+
54
+ In order to send events such as `pageview` or `connect_wallet` you must do the following
55
+
56
+ ```tsx
57
+ // Sending a pageview event does not need any parameters, just the event name
58
+ const handlePageView = async () => {
59
+ await Fuul.sendEvent("pageview");
60
+ }
61
+
62
+ // You can also send additional event arguments as follows:
63
+ const handlePageView = async () => {
64
+ await Fuul.sendEvent("pageview", {
65
+ foo,
66
+ bar,
67
+ ...myWonderfulArguments
68
+ });
69
+ }
70
+
71
+ // For connect_wallet events, you must send the address that is being connected as an argument
72
+ const handlePageView = async () => {
73
+ await Fuul.sendEvent("connect_wallet", {
74
+ address: "0x3Ec0590BC79c74B0145f94C0bE1C5d63E491569f"
75
+ });
76
+ }
77
+
78
+ // Sending projectId as an event argument (please note that you must send it as project_id)
79
+ const handlePageView = async () => {
80
+ await Fuul.sendEvent("pageview", {
81
+ project_id: "my-wonderful-project-id"
82
+ });
83
+ }
84
+ ```
85
+
86
+ ## 5**. Generating tracking links**
87
+
88
+ You can also generate the tracking link for a given wallet `address` and `campaign id`
89
+
90
+ ```tsx
91
+ // Let's assume you are testing in localhost:3000
92
+
93
+ const myWonderfulReferrerAddress: string = "0xE8BF39dCd16CF20d39006ba3C722A02e701bf0eE"
94
+ const campaignId: string = "79e72760-c730-4422-9e7b-3b730e8800dc"
95
+
96
+ const myTrackingId: string = Fuul.generateTrackingLink(myWonderfulReferrerAddress, campaignId);
97
+
98
+ console.log(myTrackingId) // http://localhost:3000?c=79e72760-c730-4422-9e7b-3b730e8800dc&origin=fuul&r=0xE8BF39dCd16CF20d39006ba3C722A02e701bf0eE
99
+ ```
@@ -0,0 +1,8 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.SENT_EVENT_ID_KEY = exports.REFERRER_ID_KEY = exports.CAMPAIGN_ID_KEY = exports.TRACKING_ID_KEY = exports.SESSION_ID_KEY = void 0;
4
+ exports.SESSION_ID_KEY = "fuul.session_id";
5
+ exports.TRACKING_ID_KEY = "fuul.tracking_id";
6
+ exports.CAMPAIGN_ID_KEY = "fuul.campaign_id";
7
+ exports.REFERRER_ID_KEY = "fuul.referrer_id";
8
+ exports.SENT_EVENT_ID_KEY = "fuul.sent";
@@ -0,0 +1,185 @@
1
+ "use strict";
2
+ var __createBinding = (this && this.__createBinding) || (Object.create ? (function(o, m, k, k2) {
3
+ if (k2 === undefined) k2 = k;
4
+ var desc = Object.getOwnPropertyDescriptor(m, k);
5
+ if (!desc || ("get" in desc ? !m.__esModule : desc.writable || desc.configurable)) {
6
+ desc = { enumerable: true, get: function() { return m[k]; } };
7
+ }
8
+ Object.defineProperty(o, k2, desc);
9
+ }) : (function(o, m, k, k2) {
10
+ if (k2 === undefined) k2 = k;
11
+ o[k2] = m[k];
12
+ }));
13
+ var __setModuleDefault = (this && this.__setModuleDefault) || (Object.create ? (function(o, v) {
14
+ Object.defineProperty(o, "default", { enumerable: true, value: v });
15
+ }) : function(o, v) {
16
+ o["default"] = v;
17
+ });
18
+ var __importStar = (this && this.__importStar) || function (mod) {
19
+ if (mod && mod.__esModule) return mod;
20
+ var result = {};
21
+ if (mod != null) for (var k in mod) if (k !== "default" && Object.prototype.hasOwnProperty.call(mod, k)) __createBinding(result, mod, k);
22
+ __setModuleDefault(result, mod);
23
+ return result;
24
+ };
25
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
26
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
27
+ return new (P || (P = Promise))(function (resolve, reject) {
28
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
29
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
30
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
31
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
32
+ });
33
+ };
34
+ var __importDefault = (this && this.__importDefault) || function (mod) {
35
+ return (mod && mod.__esModule) ? mod : { "default": mod };
36
+ };
37
+ Object.defineProperty(exports, "__esModule", { value: true });
38
+ exports.Fuul = void 0;
39
+ const axios_1 = __importDefault(require("axios"));
40
+ const date_1 = require("./utils/date");
41
+ const localStorage_1 = require("./utils/localStorage");
42
+ const constants_1 = require("./constants");
43
+ const saveSentEvent = (eventName, params) => {
44
+ const timestamp = Date.now();
45
+ const SENT_EVENT_KEY = `${constants_1.SENT_EVENT_ID_KEY}_${eventName}`;
46
+ const eventParams = Object.assign(Object.assign({}, params), { timestamp });
47
+ localStorage.setItem(SENT_EVENT_KEY, JSON.stringify(eventParams));
48
+ };
49
+ const isEventAlreadySentAndInValidTimestamp = (eventName, params) => {
50
+ const SENT_EVENT_KEY = `${constants_1.SENT_EVENT_ID_KEY}_${eventName}`;
51
+ const storedEvent = localStorage.getItem(SENT_EVENT_KEY);
52
+ if (!storedEvent)
53
+ return false;
54
+ const parsedEvent = JSON.parse(storedEvent);
55
+ const isSameDay = (0, date_1.datesAreOnSameDay)(new Date(Date.now()), new Date(parsedEvent.timestamp));
56
+ if (eventName === "connect_wallet") {
57
+ return parsedEvent["tracking_id"] === params.tracking_id && isSameDay;
58
+ }
59
+ else {
60
+ return (parsedEvent["tracking_id"] === params.tracking_id &&
61
+ parsedEvent["campaign_id"] === params.campaign_id &&
62
+ parsedEvent["referrer_id"] === params.referrer_id &&
63
+ isSameDay);
64
+ }
65
+ };
66
+ const generateRandomId = () => __awaiter(void 0, void 0, void 0, function* () {
67
+ const nanoid = yield Promise.resolve().then(() => __importStar(require("nanoid"))).then((m) => m.nanoid);
68
+ return nanoid();
69
+ });
70
+ const saveSessionId = () => __awaiter(void 0, void 0, void 0, function* () {
71
+ if (typeof window === "undefined")
72
+ return;
73
+ localStorage.setItem(constants_1.SESSION_ID_KEY, yield generateRandomId());
74
+ });
75
+ const saveTrackingId = () => __awaiter(void 0, void 0, void 0, function* () {
76
+ var _a, _b;
77
+ if (typeof window === "undefined" || typeof document === "undefined")
78
+ return;
79
+ const queryParams = new URLSearchParams(window.location.search);
80
+ if (!queryParams.has("c") ||
81
+ !queryParams.has("origin") ||
82
+ !queryParams.has("r"))
83
+ return;
84
+ const isFuulOrigin = queryParams.get("origin") === "fuul";
85
+ if (!isFuulOrigin)
86
+ return;
87
+ if (!(0, localStorage_1.getTrackingId)()) {
88
+ localStorage.setItem(constants_1.TRACKING_ID_KEY, yield generateRandomId());
89
+ }
90
+ localStorage.setItem(constants_1.CAMPAIGN_ID_KEY, (_a = queryParams.get("c")) !== null && _a !== void 0 ? _a : "");
91
+ localStorage.setItem(constants_1.REFERRER_ID_KEY, (_b = queryParams.get("r")) !== null && _b !== void 0 ? _b : "");
92
+ });
93
+ const buildTrackingLinkQueryParams = (r, c) => {
94
+ return `c=${c}&origin=fuul&r=${r}`;
95
+ };
96
+ class Fuul {
97
+ constructor(projectId) {
98
+ this.BASE_API_URL = "https://api.fuul.xyz/api/v1";
99
+ this.projectId = projectId;
100
+ saveSessionId();
101
+ saveTrackingId();
102
+ globalThis.Fuul = this;
103
+ }
104
+ /**
105
+ * @param {EventType} name Event name.
106
+ * @param {EventArgsType} args Event additional arguments.
107
+ * ```js
108
+ * import { Fuul } from 'fuul-sdk'
109
+ *
110
+ * // Initialize Fuul in your app root file
111
+ * new Fuul('your-project-id')
112
+ *
113
+ * // Then you can send an event as follows:
114
+ * fuul.sendEvent('connect_wallet', {
115
+ * address,
116
+ * ...args
117
+ * })
118
+ * ```
119
+ */
120
+ sendEvent(name, args) {
121
+ var _a;
122
+ return __awaiter(this, void 0, void 0, function* () {
123
+ const session_id = (0, localStorage_1.getSessionId)();
124
+ const tracking_id = (0, localStorage_1.getTrackingId)();
125
+ const campaign_id = (0, localStorage_1.getCampaignId)();
126
+ const referrer_id = (0, localStorage_1.getReferrerId)();
127
+ if (!tracking_id)
128
+ return;
129
+ let params = {
130
+ tracking_id,
131
+ };
132
+ let reqBody = {};
133
+ if (name === "connect_wallet") {
134
+ reqBody = {
135
+ name,
136
+ session_id,
137
+ event_args: Object.assign(Object.assign({}, args), { tracking_id }),
138
+ };
139
+ }
140
+ else {
141
+ if (!campaign_id || !referrer_id)
142
+ return;
143
+ params = Object.assign(Object.assign({}, params), { referrer_id,
144
+ campaign_id });
145
+ reqBody = {
146
+ name,
147
+ session_id,
148
+ project_id: (_a = this.projectId) !== null && _a !== void 0 ? _a : args === null || args === void 0 ? void 0 : args.project_id,
149
+ event_args: Object.assign(Object.assign({}, args), { referrer: referrer_id, campaign_id,
150
+ tracking_id }),
151
+ };
152
+ }
153
+ if (isEventAlreadySentAndInValidTimestamp(name, params))
154
+ return;
155
+ const url = `${this.BASE_API_URL}/events`;
156
+ try {
157
+ const response = yield axios_1.default.post(url, reqBody);
158
+ saveSentEvent(name, params);
159
+ return response.data;
160
+ }
161
+ catch (error) {
162
+ return error;
163
+ }
164
+ });
165
+ }
166
+ verifyConnection() {
167
+ if (window !== undefined && globalThis.Fuul) {
168
+ window.alert("You are successfully connected to Fuul SDK! ✅");
169
+ }
170
+ }
171
+ /**
172
+ * Generates a tracking link for a referrer
173
+ * @param {string} address referrer address
174
+ * @param {string} cid campaign id you want to refer the user
175
+ * @param {string} baseUrl base url of your app
176
+ * @returns {string} tracking link
177
+ */
178
+ generateTrackingLink({ address, cid, baseUrl, }) {
179
+ return `${baseUrl !== null && baseUrl !== void 0 ? baseUrl : window.location.href}?${buildTrackingLinkQueryParams(address, cid)}`;
180
+ }
181
+ }
182
+ exports.Fuul = Fuul;
183
+ exports.default = {
184
+ Fuul,
185
+ };
@@ -0,0 +1,6 @@
1
+ export declare const SESSION_ID_KEY = "fuul.session_id";
2
+ export declare const TRACKING_ID_KEY = "fuul.tracking_id";
3
+ export declare const CAMPAIGN_ID_KEY = "fuul.campaign_id";
4
+ export declare const REFERRER_ID_KEY = "fuul.referrer_id";
5
+ export declare const SENT_EVENT_ID_KEY = "fuul.sent";
6
+ //# sourceMappingURL=constants.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../../../src/constants.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,cAAc,oBAAoB,CAAC;AAChD,eAAO,MAAM,eAAe,qBAAqB,CAAC;AAClD,eAAO,MAAM,eAAe,qBAAqB,CAAC;AAClD,eAAO,MAAM,eAAe,qBAAqB,CAAC;AAClD,eAAO,MAAM,iBAAiB,cAAc,CAAC"}
@@ -0,0 +1,37 @@
1
+ import { EventArgsType, EventType, IGenerateTrackingLink } from "./types/types";
2
+ export declare class Fuul {
3
+ private projectId?;
4
+ private BASE_API_URL;
5
+ constructor(projectId?: string);
6
+ /**
7
+ * @param {EventType} name Event name.
8
+ * @param {EventArgsType} args Event additional arguments.
9
+ * ```js
10
+ * import { Fuul } from 'fuul-sdk'
11
+ *
12
+ * // Initialize Fuul in your app root file
13
+ * new Fuul('your-project-id')
14
+ *
15
+ * // Then you can send an event as follows:
16
+ * fuul.sendEvent('connect_wallet', {
17
+ * address,
18
+ * ...args
19
+ * })
20
+ * ```
21
+ */
22
+ sendEvent(name: EventType, args?: EventArgsType): Promise<any>;
23
+ verifyConnection(): void;
24
+ /**
25
+ * Generates a tracking link for a referrer
26
+ * @param {string} address referrer address
27
+ * @param {string} cid campaign id you want to refer the user
28
+ * @param {string} baseUrl base url of your app
29
+ * @returns {string} tracking link
30
+ */
31
+ generateTrackingLink({ address, cid, baseUrl, }: IGenerateTrackingLink): string;
32
+ }
33
+ declare const _default: {
34
+ Fuul: typeof Fuul;
35
+ };
36
+ export default _default;
37
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/index.ts"],"names":[],"mappings":"AAkBA,OAAO,EACL,aAAa,EACb,SAAS,EACT,qBAAqB,EAEtB,MAAM,eAAe,CAAC;AA+EvB,qBAAa,IAAI;IACf,OAAO,CAAC,SAAS,CAAC,CAAS;IAC3B,OAAO,CAAC,YAAY,CAAyC;gBAEjD,SAAS,CAAC,EAAE,MAAM;IAS9B;;;;;;;;;;;;;;;OAeG;IACG,SAAS,CAAC,IAAI,EAAE,SAAS,EAAE,IAAI,CAAC,EAAE,aAAa,GAAG,OAAO,CAAC,GAAG,CAAC;IA4DpE,gBAAgB,IAAI,IAAI;IAMxB;;;;;;OAMG;IACH,oBAAoB,CAAC,EACnB,OAAO,EACP,GAAG,EACH,OAAO,GACR,EAAE,qBAAqB,GAAG,MAAM;CAMlC;;;;AAMD,wBAEE"}
@@ -0,0 +1,20 @@
1
+ export interface SendEventParams {
2
+ name: EventType;
3
+ args?: EventArgsType;
4
+ projectId?: string;
5
+ }
6
+ export type EventArgsType = {
7
+ [key: string]: string;
8
+ };
9
+ export type EventType = "connect_wallet" | "pageview";
10
+ export interface SentEventParams {
11
+ tracking_id: string;
12
+ campaign_id?: string;
13
+ referrer_id?: string;
14
+ }
15
+ export interface IGenerateTrackingLink {
16
+ address: string;
17
+ cid: string;
18
+ baseUrl?: string;
19
+ }
20
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../../src/types/types.ts"],"names":[],"mappings":"AAAA,MAAM,WAAW,eAAe;IAC9B,IAAI,EAAE,SAAS,CAAC;IAChB,IAAI,CAAC,EAAE,aAAa,CAAC;IACrB,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAED,MAAM,MAAM,aAAa,GAAG;IAC1B,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAAC;CACvB,CAAC;AAEF,MAAM,MAAM,SAAS,GAAG,gBAAgB,GAAG,UAAU,CAAC;AAEtD,MAAM,WAAW,eAAe;IAC9B,WAAW,EAAE,MAAM,CAAC;IACpB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED,MAAM,WAAW,qBAAqB;IACpC,OAAO,EAAE,MAAM,CAAC;IAChB,GAAG,EAAE,MAAM,CAAC;IACZ,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB"}
@@ -0,0 +1,2 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -0,0 +1,2 @@
1
+ export declare const datesAreOnSameDay: (first: Date, second: Date) => boolean;
2
+ //# sourceMappingURL=date.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"date.d.ts","sourceRoot":"","sources":["../../../../src/utils/date.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,iBAAiB,UAAW,IAAI,UAAU,IAAI,YAGrB,CAAC"}
@@ -0,0 +1,5 @@
1
+ export declare const getSessionId: () => string | null;
2
+ export declare const getTrackingId: () => string | null;
3
+ export declare const getCampaignId: () => string | null;
4
+ export declare const getReferrerId: () => string | null;
5
+ //# sourceMappingURL=localStorage.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"localStorage.d.ts","sourceRoot":"","sources":["../../../../src/utils/localStorage.ts"],"names":[],"mappings":"AAOA,eAAO,MAAM,YAAY,qBAA6C,CAAC;AACvE,eAAO,MAAM,aAAa,qBAA8C,CAAC;AACzE,eAAO,MAAM,aAAa,qBAA8C,CAAC;AACzE,eAAO,MAAM,aAAa,qBAA8C,CAAC"}
@@ -0,0 +1,7 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.datesAreOnSameDay = void 0;
4
+ const datesAreOnSameDay = (first, second) => first.getFullYear() === second.getFullYear() &&
5
+ first.getMonth() === second.getMonth() &&
6
+ first.getDate() === second.getDate();
7
+ exports.datesAreOnSameDay = datesAreOnSameDay;
@@ -0,0 +1,12 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.getReferrerId = exports.getCampaignId = exports.getTrackingId = exports.getSessionId = void 0;
4
+ const constants_1 = require("../constants");
5
+ const getSessionId = () => localStorage.getItem(constants_1.SESSION_ID_KEY);
6
+ exports.getSessionId = getSessionId;
7
+ const getTrackingId = () => localStorage.getItem(constants_1.TRACKING_ID_KEY);
8
+ exports.getTrackingId = getTrackingId;
9
+ const getCampaignId = () => localStorage.getItem(constants_1.CAMPAIGN_ID_KEY);
10
+ exports.getCampaignId = getCampaignId;
11
+ const getReferrerId = () => localStorage.getItem(constants_1.REFERRER_ID_KEY);
12
+ exports.getReferrerId = getReferrerId;
@@ -0,0 +1,5 @@
1
+ export const SESSION_ID_KEY = "fuul.session_id";
2
+ export const TRACKING_ID_KEY = "fuul.tracking_id";
3
+ export const CAMPAIGN_ID_KEY = "fuul.campaign_id";
4
+ export const REFERRER_ID_KEY = "fuul.referrer_id";
5
+ export const SENT_EVENT_ID_KEY = "fuul.sent";
@@ -0,0 +1,155 @@
1
+ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
2
+ function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
3
+ return new (P || (P = Promise))(function (resolve, reject) {
4
+ function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
5
+ function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
6
+ function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
7
+ step((generator = generator.apply(thisArg, _arguments || [])).next());
8
+ });
9
+ };
10
+ import axios from "axios";
11
+ import { datesAreOnSameDay } from "./utils/date";
12
+ import { getCampaignId, getReferrerId, getSessionId, getTrackingId, } from "./utils/localStorage";
13
+ import { CAMPAIGN_ID_KEY, REFERRER_ID_KEY, SENT_EVENT_ID_KEY, SESSION_ID_KEY, TRACKING_ID_KEY, } from "./constants";
14
+ const saveSentEvent = (eventName, params) => {
15
+ const timestamp = Date.now();
16
+ const SENT_EVENT_KEY = `${SENT_EVENT_ID_KEY}_${eventName}`;
17
+ const eventParams = Object.assign(Object.assign({}, params), { timestamp });
18
+ localStorage.setItem(SENT_EVENT_KEY, JSON.stringify(eventParams));
19
+ };
20
+ const isEventAlreadySentAndInValidTimestamp = (eventName, params) => {
21
+ const SENT_EVENT_KEY = `${SENT_EVENT_ID_KEY}_${eventName}`;
22
+ const storedEvent = localStorage.getItem(SENT_EVENT_KEY);
23
+ if (!storedEvent)
24
+ return false;
25
+ const parsedEvent = JSON.parse(storedEvent);
26
+ const isSameDay = datesAreOnSameDay(new Date(Date.now()), new Date(parsedEvent.timestamp));
27
+ if (eventName === "connect_wallet") {
28
+ return parsedEvent["tracking_id"] === params.tracking_id && isSameDay;
29
+ }
30
+ else {
31
+ return (parsedEvent["tracking_id"] === params.tracking_id &&
32
+ parsedEvent["campaign_id"] === params.campaign_id &&
33
+ parsedEvent["referrer_id"] === params.referrer_id &&
34
+ isSameDay);
35
+ }
36
+ };
37
+ const generateRandomId = () => __awaiter(void 0, void 0, void 0, function* () {
38
+ const nanoid = yield import("nanoid").then((m) => m.nanoid);
39
+ return nanoid();
40
+ });
41
+ const saveSessionId = () => __awaiter(void 0, void 0, void 0, function* () {
42
+ if (typeof window === "undefined")
43
+ return;
44
+ localStorage.setItem(SESSION_ID_KEY, yield generateRandomId());
45
+ });
46
+ const saveTrackingId = () => __awaiter(void 0, void 0, void 0, function* () {
47
+ var _a, _b;
48
+ if (typeof window === "undefined" || typeof document === "undefined")
49
+ return;
50
+ const queryParams = new URLSearchParams(window.location.search);
51
+ if (!queryParams.has("c") ||
52
+ !queryParams.has("origin") ||
53
+ !queryParams.has("r"))
54
+ return;
55
+ const isFuulOrigin = queryParams.get("origin") === "fuul";
56
+ if (!isFuulOrigin)
57
+ return;
58
+ if (!getTrackingId()) {
59
+ localStorage.setItem(TRACKING_ID_KEY, yield generateRandomId());
60
+ }
61
+ localStorage.setItem(CAMPAIGN_ID_KEY, (_a = queryParams.get("c")) !== null && _a !== void 0 ? _a : "");
62
+ localStorage.setItem(REFERRER_ID_KEY, (_b = queryParams.get("r")) !== null && _b !== void 0 ? _b : "");
63
+ });
64
+ const buildTrackingLinkQueryParams = (r, c) => {
65
+ return `c=${c}&origin=fuul&r=${r}`;
66
+ };
67
+ export class Fuul {
68
+ constructor(projectId) {
69
+ this.BASE_API_URL = "https://api.fuul.xyz/api/v1";
70
+ this.projectId = projectId;
71
+ saveSessionId();
72
+ saveTrackingId();
73
+ globalThis.Fuul = this;
74
+ }
75
+ /**
76
+ * @param {EventType} name Event name.
77
+ * @param {EventArgsType} args Event additional arguments.
78
+ * ```js
79
+ * import { Fuul } from 'fuul-sdk'
80
+ *
81
+ * // Initialize Fuul in your app root file
82
+ * new Fuul('your-project-id')
83
+ *
84
+ * // Then you can send an event as follows:
85
+ * fuul.sendEvent('connect_wallet', {
86
+ * address,
87
+ * ...args
88
+ * })
89
+ * ```
90
+ */
91
+ sendEvent(name, args) {
92
+ var _a;
93
+ return __awaiter(this, void 0, void 0, function* () {
94
+ const session_id = getSessionId();
95
+ const tracking_id = getTrackingId();
96
+ const campaign_id = getCampaignId();
97
+ const referrer_id = getReferrerId();
98
+ if (!tracking_id)
99
+ return;
100
+ let params = {
101
+ tracking_id,
102
+ };
103
+ let reqBody = {};
104
+ if (name === "connect_wallet") {
105
+ reqBody = {
106
+ name,
107
+ session_id,
108
+ event_args: Object.assign(Object.assign({}, args), { tracking_id }),
109
+ };
110
+ }
111
+ else {
112
+ if (!campaign_id || !referrer_id)
113
+ return;
114
+ params = Object.assign(Object.assign({}, params), { referrer_id,
115
+ campaign_id });
116
+ reqBody = {
117
+ name,
118
+ session_id,
119
+ project_id: (_a = this.projectId) !== null && _a !== void 0 ? _a : args === null || args === void 0 ? void 0 : args.project_id,
120
+ event_args: Object.assign(Object.assign({}, args), { referrer: referrer_id, campaign_id,
121
+ tracking_id }),
122
+ };
123
+ }
124
+ if (isEventAlreadySentAndInValidTimestamp(name, params))
125
+ return;
126
+ const url = `${this.BASE_API_URL}/events`;
127
+ try {
128
+ const response = yield axios.post(url, reqBody);
129
+ saveSentEvent(name, params);
130
+ return response.data;
131
+ }
132
+ catch (error) {
133
+ return error;
134
+ }
135
+ });
136
+ }
137
+ verifyConnection() {
138
+ if (window !== undefined && globalThis.Fuul) {
139
+ window.alert("You are successfully connected to Fuul SDK! ✅");
140
+ }
141
+ }
142
+ /**
143
+ * Generates a tracking link for a referrer
144
+ * @param {string} address referrer address
145
+ * @param {string} cid campaign id you want to refer the user
146
+ * @param {string} baseUrl base url of your app
147
+ * @returns {string} tracking link
148
+ */
149
+ generateTrackingLink({ address, cid, baseUrl, }) {
150
+ return `${baseUrl !== null && baseUrl !== void 0 ? baseUrl : window.location.href}?${buildTrackingLinkQueryParams(address, cid)}`;
151
+ }
152
+ }
153
+ export default {
154
+ Fuul,
155
+ };
@@ -0,0 +1,6 @@
1
+ export declare const SESSION_ID_KEY = "fuul.session_id";
2
+ export declare const TRACKING_ID_KEY = "fuul.tracking_id";
3
+ export declare const CAMPAIGN_ID_KEY = "fuul.campaign_id";
4
+ export declare const REFERRER_ID_KEY = "fuul.referrer_id";
5
+ export declare const SENT_EVENT_ID_KEY = "fuul.sent";
6
+ //# sourceMappingURL=constants.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"constants.d.ts","sourceRoot":"","sources":["../../../src/constants.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,cAAc,oBAAoB,CAAC;AAChD,eAAO,MAAM,eAAe,qBAAqB,CAAC;AAClD,eAAO,MAAM,eAAe,qBAAqB,CAAC;AAClD,eAAO,MAAM,eAAe,qBAAqB,CAAC;AAClD,eAAO,MAAM,iBAAiB,cAAc,CAAC"}
@@ -0,0 +1,37 @@
1
+ import { EventArgsType, EventType, IGenerateTrackingLink } from "./types/types";
2
+ export declare class Fuul {
3
+ private projectId?;
4
+ private BASE_API_URL;
5
+ constructor(projectId?: string);
6
+ /**
7
+ * @param {EventType} name Event name.
8
+ * @param {EventArgsType} args Event additional arguments.
9
+ * ```js
10
+ * import { Fuul } from 'fuul-sdk'
11
+ *
12
+ * // Initialize Fuul in your app root file
13
+ * new Fuul('your-project-id')
14
+ *
15
+ * // Then you can send an event as follows:
16
+ * fuul.sendEvent('connect_wallet', {
17
+ * address,
18
+ * ...args
19
+ * })
20
+ * ```
21
+ */
22
+ sendEvent(name: EventType, args?: EventArgsType): Promise<any>;
23
+ verifyConnection(): void;
24
+ /**
25
+ * Generates a tracking link for a referrer
26
+ * @param {string} address referrer address
27
+ * @param {string} cid campaign id you want to refer the user
28
+ * @param {string} baseUrl base url of your app
29
+ * @returns {string} tracking link
30
+ */
31
+ generateTrackingLink({ address, cid, baseUrl, }: IGenerateTrackingLink): string;
32
+ }
33
+ declare const _default: {
34
+ Fuul: typeof Fuul;
35
+ };
36
+ export default _default;
37
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../src/index.ts"],"names":[],"mappings":"AAkBA,OAAO,EACL,aAAa,EACb,SAAS,EACT,qBAAqB,EAEtB,MAAM,eAAe,CAAC;AA+EvB,qBAAa,IAAI;IACf,OAAO,CAAC,SAAS,CAAC,CAAS;IAC3B,OAAO,CAAC,YAAY,CAAyC;gBAEjD,SAAS,CAAC,EAAE,MAAM;IAS9B;;;;;;;;;;;;;;;OAeG;IACG,SAAS,CAAC,IAAI,EAAE,SAAS,EAAE,IAAI,CAAC,EAAE,aAAa,GAAG,OAAO,CAAC,GAAG,CAAC;IA4DpE,gBAAgB,IAAI,IAAI;IAMxB;;;;;;OAMG;IACH,oBAAoB,CAAC,EACnB,OAAO,EACP,GAAG,EACH,OAAO,GACR,EAAE,qBAAqB,GAAG,MAAM;CAMlC;;;;AAMD,wBAEE"}
@@ -0,0 +1,20 @@
1
+ export interface SendEventParams {
2
+ name: EventType;
3
+ args?: EventArgsType;
4
+ projectId?: string;
5
+ }
6
+ export type EventArgsType = {
7
+ [key: string]: string;
8
+ };
9
+ export type EventType = "connect_wallet" | "pageview";
10
+ export interface SentEventParams {
11
+ tracking_id: string;
12
+ campaign_id?: string;
13
+ referrer_id?: string;
14
+ }
15
+ export interface IGenerateTrackingLink {
16
+ address: string;
17
+ cid: string;
18
+ baseUrl?: string;
19
+ }
20
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../../../../src/types/types.ts"],"names":[],"mappings":"AAAA,MAAM,WAAW,eAAe;IAC9B,IAAI,EAAE,SAAS,CAAC;IAChB,IAAI,CAAC,EAAE,aAAa,CAAC;IACrB,SAAS,CAAC,EAAE,MAAM,CAAC;CACpB;AAED,MAAM,MAAM,aAAa,GAAG;IAC1B,CAAC,GAAG,EAAE,MAAM,GAAG,MAAM,CAAC;CACvB,CAAC;AAEF,MAAM,MAAM,SAAS,GAAG,gBAAgB,GAAG,UAAU,CAAC;AAEtD,MAAM,WAAW,eAAe;IAC9B,WAAW,EAAE,MAAM,CAAC;IACpB,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,WAAW,CAAC,EAAE,MAAM,CAAC;CACtB;AAED,MAAM,WAAW,qBAAqB;IACpC,OAAO,EAAE,MAAM,CAAC;IAChB,GAAG,EAAE,MAAM,CAAC;IACZ,OAAO,CAAC,EAAE,MAAM,CAAC;CAClB"}
@@ -0,0 +1 @@
1
+ export {};
@@ -0,0 +1,2 @@
1
+ export declare const datesAreOnSameDay: (first: Date, second: Date) => boolean;
2
+ //# sourceMappingURL=date.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"date.d.ts","sourceRoot":"","sources":["../../../../src/utils/date.ts"],"names":[],"mappings":"AAAA,eAAO,MAAM,iBAAiB,UAAW,IAAI,UAAU,IAAI,YAGrB,CAAC"}
@@ -0,0 +1,5 @@
1
+ export declare const getSessionId: () => string | null;
2
+ export declare const getTrackingId: () => string | null;
3
+ export declare const getCampaignId: () => string | null;
4
+ export declare const getReferrerId: () => string | null;
5
+ //# sourceMappingURL=localStorage.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"localStorage.d.ts","sourceRoot":"","sources":["../../../../src/utils/localStorage.ts"],"names":[],"mappings":"AAOA,eAAO,MAAM,YAAY,qBAA6C,CAAC;AACvE,eAAO,MAAM,aAAa,qBAA8C,CAAC;AACzE,eAAO,MAAM,aAAa,qBAA8C,CAAC;AACzE,eAAO,MAAM,aAAa,qBAA8C,CAAC"}
@@ -0,0 +1,3 @@
1
+ export const datesAreOnSameDay = (first, second) => first.getFullYear() === second.getFullYear() &&
2
+ first.getMonth() === second.getMonth() &&
3
+ first.getDate() === second.getDate();
@@ -0,0 +1,5 @@
1
+ import { CAMPAIGN_ID_KEY, REFERRER_ID_KEY, SESSION_ID_KEY, TRACKING_ID_KEY, } from "../constants";
2
+ export const getSessionId = () => localStorage.getItem(SESSION_ID_KEY);
3
+ export const getTrackingId = () => localStorage.getItem(TRACKING_ID_KEY);
4
+ export const getCampaignId = () => localStorage.getItem(CAMPAIGN_ID_KEY);
5
+ export const getReferrerId = () => localStorage.getItem(REFERRER_ID_KEY);
package/package.json ADDED
@@ -0,0 +1,42 @@
1
+ {
2
+ "name": "@fuul/sdk",
3
+ "version": "0.5.0",
4
+ "description": "Fuul SDK",
5
+ "types": "./lib/esm/types/index.d.ts",
6
+ "main": "./lib/esm/index.mjs",
7
+ "files": [
8
+ "lib/**/*"
9
+ ],
10
+ "scripts": {
11
+ "compile": "node compile.js",
12
+ "clean": "rm -rf ./lib",
13
+ "dev": "ts-node ./src/index.ts",
14
+ "build": "npm run clean && npm run build:esm && npm run build:cjs",
15
+ "build:esm": "tsc -p ./configs/tsconfig.esm.json && mv lib/esm/index.js lib/esm/index.mjs",
16
+ "build:cjs": "tsc -p ./configs/tsconfig.cjs.json",
17
+ "semantic-release": "semantic-release"
18
+ },
19
+ "keywords": [],
20
+ "author": "",
21
+ "license": "ISC",
22
+ "dependencies": {
23
+ "axios": "^1.2.2",
24
+ "nanoid": "^4.0.0"
25
+ },
26
+ "devDependencies": {
27
+ "@semantic-release/git": "^10.0.1",
28
+ "@semantic-release/npm": "^9.0.2",
29
+ "@types/node": "^18.11.18",
30
+ "semantic-release": "^20.1.1",
31
+ "ts-node": "^10.9.1",
32
+ "typescript": "^4.7.4"
33
+ },
34
+ "repository": {
35
+ "type": "git",
36
+ "url": "https://github.com/fuul-app/fuul-sdk.git"
37
+ },
38
+ "publishConfig": {
39
+ "tag": "latest",
40
+ "access": "public"
41
+ }
42
+ }