@deway-ai/web-sdk 0.44.0 → 0.45.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/dist/loader.es.js +28 -22
- package/dist/loader.umd.js +1 -1
- package/package.json +1 -1
package/dist/loader.es.js
CHANGED
|
@@ -45,6 +45,12 @@ class S {
|
|
|
45
45
|
getPromptSuggestions() {
|
|
46
46
|
return this.loadConfig()?.promptSuggestions;
|
|
47
47
|
}
|
|
48
|
+
getWelcomeTitle() {
|
|
49
|
+
return this.loadConfig()?.welcomeTitle ?? "How can I help you today?";
|
|
50
|
+
}
|
|
51
|
+
getWelcomeSubtitle() {
|
|
52
|
+
return this.loadConfig()?.welcomeSubtitle ?? "I'm ready to help you navigate, learn, and get things done.";
|
|
53
|
+
}
|
|
48
54
|
getBookmarkAppearanceMode() {
|
|
49
55
|
return this.loadConfig()?.bookmarkAppearanceMode ?? "bookmark";
|
|
50
56
|
}
|
|
@@ -82,23 +88,23 @@ class s {
|
|
|
82
88
|
});
|
|
83
89
|
} catch {
|
|
84
90
|
try {
|
|
85
|
-
const
|
|
91
|
+
const a = JSON.stringify({
|
|
86
92
|
code: e,
|
|
87
93
|
version: t,
|
|
88
94
|
checksum: i,
|
|
89
95
|
signature: n,
|
|
90
96
|
timestamp: Date.now()
|
|
91
97
|
});
|
|
92
|
-
localStorage.setItem(s.CACHE_KEY,
|
|
98
|
+
localStorage.setItem(s.CACHE_KEY, a);
|
|
93
99
|
} catch {
|
|
94
100
|
}
|
|
95
101
|
}
|
|
96
102
|
}
|
|
97
103
|
async getCachedSDK() {
|
|
98
104
|
try {
|
|
99
|
-
const i = (await this.openIndexedDB()).transaction([s.STORE_NAME], "readonly").objectStore(s.STORE_NAME), n = await new Promise((
|
|
105
|
+
const i = (await this.openIndexedDB()).transaction([s.STORE_NAME], "readonly").objectStore(s.STORE_NAME), n = await new Promise((o, a) => {
|
|
100
106
|
const d = i.get("latest");
|
|
101
|
-
d.onsuccess = () =>
|
|
107
|
+
d.onsuccess = () => o(d.result || null), d.onerror = () => a(d.error);
|
|
102
108
|
});
|
|
103
109
|
if (n)
|
|
104
110
|
return n;
|
|
@@ -116,15 +122,15 @@ class s {
|
|
|
116
122
|
return new Promise((e, t) => {
|
|
117
123
|
const i = indexedDB.open(s.DB_NAME, s.DB_VERSION);
|
|
118
124
|
i.onerror = () => t(i.error), i.onsuccess = () => e(i.result), i.onupgradeneeded = (n) => {
|
|
119
|
-
const
|
|
120
|
-
|
|
125
|
+
const o = n.target.result;
|
|
126
|
+
o.objectStoreNames.contains(s.STORE_NAME) || o.createObjectStore(s.STORE_NAME, { keyPath: "id" });
|
|
121
127
|
};
|
|
122
128
|
});
|
|
123
129
|
}
|
|
124
130
|
}
|
|
125
131
|
async function C(r) {
|
|
126
132
|
const t = new TextEncoder().encode(r), i = await crypto.subtle.digest("SHA-256", t);
|
|
127
|
-
return Array.from(new Uint8Array(i)).map((
|
|
133
|
+
return Array.from(new Uint8Array(i)).map((o) => o.toString(16).padStart(2, "0")).join("");
|
|
128
134
|
}
|
|
129
135
|
function w(r) {
|
|
130
136
|
const e = atob(r), t = new Uint8Array(e.length);
|
|
@@ -140,8 +146,8 @@ function E(r) {
|
|
|
140
146
|
}
|
|
141
147
|
async function D(r, e, t) {
|
|
142
148
|
try {
|
|
143
|
-
const i = w(r), n = E(e),
|
|
144
|
-
return await crypto.subtle.verify("Ed25519",
|
|
149
|
+
const i = w(r), n = E(e), o = w(t), a = await crypto.subtle.importKey("raw", i, { name: "Ed25519" }, !1, ["verify"]);
|
|
150
|
+
return await crypto.subtle.verify("Ed25519", a, o, n);
|
|
145
151
|
} catch {
|
|
146
152
|
return !1;
|
|
147
153
|
}
|
|
@@ -160,7 +166,7 @@ class b {
|
|
|
160
166
|
}
|
|
161
167
|
async fetchSDK(e, t, i) {
|
|
162
168
|
try {
|
|
163
|
-
const n = this.cleanApiEndpoint(t),
|
|
169
|
+
const n = this.cleanApiEndpoint(t), o = await fetch(`${n}/sdk-serve/sdk/v0`, {
|
|
164
170
|
method: "GET",
|
|
165
171
|
headers: {
|
|
166
172
|
Accept: "application/javascript",
|
|
@@ -168,16 +174,16 @@ class b {
|
|
|
168
174
|
Origin: window?.location?.origin || ""
|
|
169
175
|
}
|
|
170
176
|
});
|
|
171
|
-
return
|
|
177
|
+
return o.ok ? this.handleSuccessfulFetch(o, i) : null;
|
|
172
178
|
} catch {
|
|
173
179
|
return null;
|
|
174
180
|
}
|
|
175
181
|
}
|
|
176
182
|
async handleSuccessfulFetch(e, t) {
|
|
177
|
-
const i = e.headers.get("x-sdk-checksum"), n = e.headers.get("x-sdk-version"),
|
|
178
|
-
if (!n || !
|
|
183
|
+
const i = e.headers.get("x-sdk-checksum"), n = e.headers.get("x-sdk-version"), o = e.headers.get("x-sdk-signature"), a = await e.text();
|
|
184
|
+
if (!n || !a || !i)
|
|
179
185
|
throw Object.fromEntries(e.headers.entries()), new Error("Invalid SDK response: missing version, code, or checksum");
|
|
180
|
-
return await A(
|
|
186
|
+
return await A(a, i, o, t), { code: a, version: n, checksum: i, signature: o || "" };
|
|
181
187
|
}
|
|
182
188
|
}
|
|
183
189
|
class g {
|
|
@@ -294,13 +300,13 @@ class K {
|
|
|
294
300
|
const i = document.createElement("script");
|
|
295
301
|
i.textContent = e, i.type = "text/javascript";
|
|
296
302
|
let n = !1;
|
|
297
|
-
const
|
|
298
|
-
n || (n = !0, this.cleanupScript(i), t(
|
|
303
|
+
const o = (a) => {
|
|
304
|
+
n || (n = !0, this.cleanupScript(i), t(a));
|
|
299
305
|
};
|
|
300
306
|
i.onerror = () => {
|
|
301
|
-
|
|
302
|
-
}, i.onload = () =>
|
|
303
|
-
!n && this.verifySDKLoaded() ?
|
|
307
|
+
o(!1);
|
|
308
|
+
}, i.onload = () => o(!0), document.head.appendChild(i), setTimeout(() => {
|
|
309
|
+
!n && this.verifySDKLoaded() ? o(!0) : n || o(!1);
|
|
304
310
|
}, 100);
|
|
305
311
|
} catch {
|
|
306
312
|
t(!1);
|
|
@@ -362,11 +368,11 @@ class I {
|
|
|
362
368
|
if (!this.configValidator.validateConfig(i))
|
|
363
369
|
return;
|
|
364
370
|
this.isLoading = !0;
|
|
365
|
-
const n = i.apiEndpoint || f.apiEndpoint,
|
|
366
|
-
if (!
|
|
371
|
+
const n = i.apiEndpoint || f.apiEndpoint, o = i.publicKey || f.publicKey, [a, d] = await Promise.all([this.fetchOrLoadSDK(i.appKey, n, o), this.fetchRemoteConfigWithCache(i, n)]);
|
|
372
|
+
if (!a)
|
|
367
373
|
return;
|
|
368
374
|
const h = t ? e : this.createInitializationPayload(d, i);
|
|
369
|
-
if (!await this.scriptExecutor.executeSDK(
|
|
375
|
+
if (!await this.scriptExecutor.executeSDK(a.code) || !this.initializeSDK(h))
|
|
370
376
|
return;
|
|
371
377
|
this.commandQueue.replayQueuedCommands(), this.isLoaded = !0;
|
|
372
378
|
} finally {
|
package/dist/loader.umd.js
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
(function(l,u){typeof exports=="object"&&typeof module<"u"?module.exports=u():typeof define=="function"&&define.amd?define(u):(l=typeof globalThis<"u"?globalThis:l||self,l.Deway=u())})(this,(function(){"use strict";const l="deway-sdk-config",u=["Understanding intent","Reading web page","Browsing the docs","Enriching context","Validating understanding","Crafting response"];class C{saveConfig(e){if(window?.localStorage)try{const t=JSON.stringify(e);window.localStorage.setItem(l,t)}catch{}}loadConfig(){if(window?.localStorage)try{const e=window.localStorage.getItem(l);return e?JSON.parse(e):null}catch{return null}return null}getExcludedVendors(){return this.loadConfig()?.excludedVendors??[]}getAssistantName(){return this.loadConfig()?.assistantName??"Assistant"}getAiDisclaimer(){return this.loadConfig()?.aiDisclaimer}getThinkingMessages(){return this.loadConfig()?.thinkingMessages??u}getTalkToHumanBtnTxt(){return this.loadConfig()?.talkToHumanBtnTxt??"talk to Support"}getHumanHandoffUrl(){return this.loadConfig()?.humanHandoffUrl}getFeatureFlags(){return this.loadConfig()?.featureFlags??{}}getFeatureFlag(e){return this.getFeatureFlags()[e]??!1}getPromptSuggestions(){return this.loadConfig()?.promptSuggestions}getBookmarkAppearanceMode(){return this.loadConfig()?.bookmarkAppearanceMode??"bookmark"}getTenantTheme(){return this.loadConfig()?.tenantTheme??null}getTenantThemeForMode(e){const t=this.getTenantTheme();return t?e==="dark"?t.dark:t.light:null}}class s{static CACHE_KEY="deway-sdk-cache";static DB_NAME="DewaySdk";static DB_VERSION=1;static STORE_NAME="sdk";async cacheSDK(e,t,i,n){try{const d=(await this.openIndexedDB()).transaction([s.STORE_NAME],"readwrite").objectStore(s.STORE_NAME);await new Promise((y,S)=>{const f=d.put({id:"latest",code:e,version:t,checksum:i,signature:n,timestamp:Date.now()});f.onsuccess=()=>y(f.result),f.onerror=()=>S(f.error)})}catch{try{const a=JSON.stringify({code:e,version:t,checksum:i,signature:n,timestamp:Date.now()});localStorage.setItem(s.CACHE_KEY,a)}catch{}}}async getCachedSDK(){try{const i=(await this.openIndexedDB()).transaction([s.STORE_NAME],"readonly").objectStore(s.STORE_NAME),n=await new Promise((o,a)=>{const d=i.get("latest");d.onsuccess=()=>o(d.result||null),d.onerror=()=>a(d.error)});if(n)return n}catch{}try{const e=localStorage.getItem(s.CACHE_KEY);if(e)return JSON.parse(e)}catch{}return null}openIndexedDB(){return new Promise((e,t)=>{const i=indexedDB.open(s.DB_NAME,s.DB_VERSION);i.onerror=()=>t(i.error),i.onsuccess=()=>e(i.result),i.onupgradeneeded=n=>{const o=n.target.result;o.objectStoreNames.contains(s.STORE_NAME)||o.createObjectStore(s.STORE_NAME,{keyPath:"id"})}})}}async function E(r){const t=new TextEncoder().encode(r),i=await crypto.subtle.digest("SHA-256",t);return Array.from(new Uint8Array(i)).map(o=>o.toString(16).padStart(2,"0")).join("")}function w(r){const e=atob(r),t=new Uint8Array(e.length);for(let i=0;i<e.length;i++)t[i]=e.charCodeAt(i);return t}function D(r){const e=new Uint8Array(r.length/2);for(let t=0;t<r.length;t+=2)e[t/2]=Number.parseInt(r.substr(t,2),16);return e}async function A(r,e,t){try{const i=w(r),n=D(e),o=w(t),a=await crypto.subtle.importKey("raw",i,{name:"Ed25519"},!1,["verify"]);return await crypto.subtle.verify("Ed25519",a,o,n)}catch{return!1}}async function b(r,e,t,i){if(!e||!t)throw new Error("SDK verification failed: Missing security headers");if(await E(r)!==e)throw new Error("SDK verification failed: Checksum mismatch - content tampered");if(!await A(i,e,t))throw new Error("SDK verification failed: Invalid signature - content tampered")}class v{cleanApiEndpoint(e){return e.trim().replace(/\/+$/,"")}async fetchSDK(e,t,i){try{const n=this.cleanApiEndpoint(t),o=await fetch(`${n}/sdk-serve/sdk/v0`,{method:"GET",headers:{Accept:"application/javascript","deway-app-key":e,Origin:window?.location?.origin||""}});return o.ok?this.handleSuccessfulFetch(o,i):null}catch{return null}}async handleSuccessfulFetch(e,t){const i=e.headers.get("x-sdk-checksum"),n=e.headers.get("x-sdk-version"),o=e.headers.get("x-sdk-signature"),a=await e.text();if(!n||!a||!i)throw Object.fromEntries(e.headers.entries()),new Error("Invalid SDK response: missing version, code, or checksum");return await b(a,i,o,t),{code:a,version:n,checksum:i,signature:o||""}}}class m{static MAX_QUEUE_SIZE=50;commandQueue=[];queueCommand(e,...t){this.commandQueue.length>=m.MAX_QUEUE_SIZE&&this.commandQueue.shift(),this.commandQueue.push({method:e,args:t})}replayQueuedCommands(){if(this.commandQueue.length===0)return;const e=[...this.commandQueue];if(this.commandQueue=[],!!this.isSDKAvailable())for(const t of e)this.replayCommand(t)}clearQueue(){this.commandQueue=[]}isSDKAvailable(){return typeof window<"u"&&"Deway"in window&&!!window.Deway}replayCommand(e){try{const t=window.Deway,i=t?.[e.method];typeof i=="function"&&i.apply(t,e.args)}catch{}}}class h{static CACHE_KEY="deway-remote-config-cache";async cacheRemoteConfig(e,t){try{const i={config:e,ttl_seconds:t,timestamp:Date.now()};localStorage.setItem(h.CACHE_KEY,JSON.stringify(i))}catch{}}async getCachedRemoteConfig(){try{const e=localStorage.getItem(h.CACHE_KEY);return e?JSON.parse(e):null}catch{return null}}isCacheValid(e,t){const i=Date.now(),n=e+t*1e3;return i<n}}class K{cleanApiEndpoint(e){return e.trim().replace(/\/+$/,"")}async fetchRemoteConfig(e,t){try{const i=this.cleanApiEndpoint(t),n=await fetch(`${i}/sdk-remote-config-serve/`,{method:"GET",headers:{Accept:"application/json","deway-app-key":e,Origin:window?.location?.origin||""}});return n.ok?await n.json():null}catch{return null}}}class k{async executeSDK(e){return new Promise(t=>{try{if(!this.isDocumentReady()){t(!1);return}const i=document.createElement("script");i.textContent=e,i.type="text/javascript";let n=!1;const o=a=>{n||(n=!0,this.cleanupScript(i),t(a))};i.onerror=()=>{o(!1)},i.onload=()=>o(!0),document.head.appendChild(i),setTimeout(()=>{!n&&this.verifySDKLoaded()?o(!0):n||o(!1)},100)}catch{t(!1)}})}isDocumentReady(){return typeof document<"u"&&document.head!=null}verifySDKLoaded(){return typeof window<"u"&&"Deway"in window&&!!window.Deway}cleanupScript(e){try{e.parentNode&&e.parentNode.removeChild(e)}catch{}}}class T{validateConfig(e){return!(!e||!e.appKey||e.appKey.trim().length===0||e.apiEndpoint!==void 0&&!this.isValidUrl(e.apiEndpoint)||e.publicKey!==void 0&&e.publicKey.trim().length===0)}isValidUrl(e){try{return new URL(e),!0}catch{return!1}}}const g={apiEndpoint:"https://service.deway.app",publicKey:"9d3dBUvqyUQ7egd5j5uORdHSqZ7VFWOu+ud/SWt9WUY="};class I{isLoaded=!1;isLoading=!1;cacheManager;scriptExecutor;commandQueue;sdkFetcher;configValidator;remoteConfigFetcher;remoteConfigCache;sdkConfigStore;constructor(){this.cacheManager=new s,this.scriptExecutor=new k,this.commandQueue=new m,this.sdkFetcher=new v,this.configValidator=new T,this.sdkConfigStore=new C,this.remoteConfigFetcher=new K,this.remoteConfigCache=new h}init(e){this.performInit(e).catch(t=>{})}async performInit(e){try{if(!this.canInitialize())return;const t=this.isInitializationPayload(e),i=t?e.localConfig:e;if(!this.configValidator.validateConfig(i))return;this.isLoading=!0;const n=i.apiEndpoint||g.apiEndpoint,o=i.publicKey||g.publicKey,[a,d]=await Promise.all([this.fetchOrLoadSDK(i.appKey,n,o),this.fetchRemoteConfigWithCache(i,n)]);if(!a)return;const y=t?e:this.createInitializationPayload(d,i);if(!await this.scriptExecutor.executeSDK(a.code)||!this.initializeSDK(y))return;this.commandQueue.replayQueuedCommands(),this.isLoaded=!0}finally{this.isLoading=!1}}isInitializationPayload(e){return"localConfig"in e&&"remoteConfig"in e&&"defaults"in e}canInitialize(){return!(this.isLoaded||this.isLoading)}async fetchRemoteConfigWithCache(e,t){this.sdkConfigStore.saveConfig(e);const i=await this.remoteConfigFetcher.fetchRemoteConfig(e.appKey,t);if(i)return await this.remoteConfigCache.cacheRemoteConfig(i.config,i.ttl_seconds),i;const n=await this.remoteConfigCache.getCachedRemoteConfig();return n?{config:n.config,ttl_seconds:n.ttl_seconds}:null}createInitializationPayload(e,t){return{localConfig:t,remoteConfig:e?.config??null,defaults:g}}async fetchOrLoadSDK(e,t,i){const n=await this.sdkFetcher.fetchSDK(e,t,i);return n?(await this.cacheManager.cacheSDK(n.code,n.version,n.checksum,n.signature),n):this.loadFromCache()}async loadFromCache(){const e=await this.cacheManager.getCachedSDK();return e?{code:e.code,version:e.version}:null}initializeSDK(e){if(!this.isSDKAvailable())return!1;try{return window.Deway?.init(e),!0}catch{return!1}}identify(e){try{this.isLoaded&&this.isSDKAvailable()?window.Deway?.identify(e):this.commandQueue.queueCommand("identify",e)}catch{}}reportEvent(e,t){try{this.isLoaded&&this.isSDKAvailable()?window.Deway?.reportEvent(e,t):this.commandQueue.queueCommand("reportEvent",e,t)}catch{}}setUserProfile(e){try{this.isLoaded&&this.isSDKAvailable()?window.Deway?.setUserProfile(e):this.commandQueue.queueCommand("setUserProfile",e)}catch{}}show(e){try{this.isLoaded&&this.isSDKAvailable()?window.Deway?.show(e):this.commandQueue.queueCommand("show",e)}catch{}}hide(){try{this.isLoaded&&this.isSDKAvailable()?window.Deway?.hide():this.commandQueue.queueCommand("hide")}catch{}}isVisible(){try{return this.isLoaded&&this.isSDKAvailable()?window.Deway?.isVisible()??!1:!1}catch{return!1}}isInitialized(){try{return this.isLoaded&&this.isSDKAvailable()?window.Deway?.isInitialized()??!1:!1}catch{return!1}}destroy(){try{this.isLoaded&&this.isSDKAvailable()?window.Deway?.destroy():this.commandQueue.queueCommand("destroy"),this.commandQueue.clearQueue()}catch{}}isSDKAvailable(){return typeof window<"u"&&"Deway"in window&&!!window.Deway}}const c=new I,p={init:r=>c.init(r),identify:r=>c.identify(r),reportEvent:(r,e)=>c.reportEvent(r,e),setUserProfile:r=>c.setUserProfile(r),show:r=>c.show(r),hide:()=>c.hide(),isVisible:()=>c.isVisible(),isInitialized:()=>c.isInitialized(),destroy:()=>c.destroy()};return typeof window<"u"&&(window.Deway=p),p}));
|
|
1
|
+
(function(l,u){typeof exports=="object"&&typeof module<"u"?module.exports=u():typeof define=="function"&&define.amd?define(u):(l=typeof globalThis<"u"?globalThis:l||self,l.Deway=u())})(this,(function(){"use strict";const l="deway-sdk-config",u=["Understanding intent","Reading web page","Browsing the docs","Enriching context","Validating understanding","Crafting response"];class C{saveConfig(e){if(window?.localStorage)try{const t=JSON.stringify(e);window.localStorage.setItem(l,t)}catch{}}loadConfig(){if(window?.localStorage)try{const e=window.localStorage.getItem(l);return e?JSON.parse(e):null}catch{return null}return null}getExcludedVendors(){return this.loadConfig()?.excludedVendors??[]}getAssistantName(){return this.loadConfig()?.assistantName??"Assistant"}getAiDisclaimer(){return this.loadConfig()?.aiDisclaimer}getThinkingMessages(){return this.loadConfig()?.thinkingMessages??u}getTalkToHumanBtnTxt(){return this.loadConfig()?.talkToHumanBtnTxt??"talk to Support"}getHumanHandoffUrl(){return this.loadConfig()?.humanHandoffUrl}getFeatureFlags(){return this.loadConfig()?.featureFlags??{}}getFeatureFlag(e){return this.getFeatureFlags()[e]??!1}getPromptSuggestions(){return this.loadConfig()?.promptSuggestions}getWelcomeTitle(){return this.loadConfig()?.welcomeTitle??"How can I help you today?"}getWelcomeSubtitle(){return this.loadConfig()?.welcomeSubtitle??"I'm ready to help you navigate, learn, and get things done."}getBookmarkAppearanceMode(){return this.loadConfig()?.bookmarkAppearanceMode??"bookmark"}getTenantTheme(){return this.loadConfig()?.tenantTheme??null}getTenantThemeForMode(e){const t=this.getTenantTheme();return t?e==="dark"?t.dark:t.light:null}}class s{static CACHE_KEY="deway-sdk-cache";static DB_NAME="DewaySdk";static DB_VERSION=1;static STORE_NAME="sdk";async cacheSDK(e,t,i,n){try{const d=(await this.openIndexedDB()).transaction([s.STORE_NAME],"readwrite").objectStore(s.STORE_NAME);await new Promise((y,S)=>{const f=d.put({id:"latest",code:e,version:t,checksum:i,signature:n,timestamp:Date.now()});f.onsuccess=()=>y(f.result),f.onerror=()=>S(f.error)})}catch{try{const a=JSON.stringify({code:e,version:t,checksum:i,signature:n,timestamp:Date.now()});localStorage.setItem(s.CACHE_KEY,a)}catch{}}}async getCachedSDK(){try{const i=(await this.openIndexedDB()).transaction([s.STORE_NAME],"readonly").objectStore(s.STORE_NAME),n=await new Promise((o,a)=>{const d=i.get("latest");d.onsuccess=()=>o(d.result||null),d.onerror=()=>a(d.error)});if(n)return n}catch{}try{const e=localStorage.getItem(s.CACHE_KEY);if(e)return JSON.parse(e)}catch{}return null}openIndexedDB(){return new Promise((e,t)=>{const i=indexedDB.open(s.DB_NAME,s.DB_VERSION);i.onerror=()=>t(i.error),i.onsuccess=()=>e(i.result),i.onupgradeneeded=n=>{const o=n.target.result;o.objectStoreNames.contains(s.STORE_NAME)||o.createObjectStore(s.STORE_NAME,{keyPath:"id"})}})}}async function E(r){const t=new TextEncoder().encode(r),i=await crypto.subtle.digest("SHA-256",t);return Array.from(new Uint8Array(i)).map(o=>o.toString(16).padStart(2,"0")).join("")}function w(r){const e=atob(r),t=new Uint8Array(e.length);for(let i=0;i<e.length;i++)t[i]=e.charCodeAt(i);return t}function D(r){const e=new Uint8Array(r.length/2);for(let t=0;t<r.length;t+=2)e[t/2]=Number.parseInt(r.substr(t,2),16);return e}async function A(r,e,t){try{const i=w(r),n=D(e),o=w(t),a=await crypto.subtle.importKey("raw",i,{name:"Ed25519"},!1,["verify"]);return await crypto.subtle.verify("Ed25519",a,o,n)}catch{return!1}}async function b(r,e,t,i){if(!e||!t)throw new Error("SDK verification failed: Missing security headers");if(await E(r)!==e)throw new Error("SDK verification failed: Checksum mismatch - content tampered");if(!await A(i,e,t))throw new Error("SDK verification failed: Invalid signature - content tampered")}class v{cleanApiEndpoint(e){return e.trim().replace(/\/+$/,"")}async fetchSDK(e,t,i){try{const n=this.cleanApiEndpoint(t),o=await fetch(`${n}/sdk-serve/sdk/v0`,{method:"GET",headers:{Accept:"application/javascript","deway-app-key":e,Origin:window?.location?.origin||""}});return o.ok?this.handleSuccessfulFetch(o,i):null}catch{return null}}async handleSuccessfulFetch(e,t){const i=e.headers.get("x-sdk-checksum"),n=e.headers.get("x-sdk-version"),o=e.headers.get("x-sdk-signature"),a=await e.text();if(!n||!a||!i)throw Object.fromEntries(e.headers.entries()),new Error("Invalid SDK response: missing version, code, or checksum");return await b(a,i,o,t),{code:a,version:n,checksum:i,signature:o||""}}}class g{static MAX_QUEUE_SIZE=50;commandQueue=[];queueCommand(e,...t){this.commandQueue.length>=g.MAX_QUEUE_SIZE&&this.commandQueue.shift(),this.commandQueue.push({method:e,args:t})}replayQueuedCommands(){if(this.commandQueue.length===0)return;const e=[...this.commandQueue];if(this.commandQueue=[],!!this.isSDKAvailable())for(const t of e)this.replayCommand(t)}clearQueue(){this.commandQueue=[]}isSDKAvailable(){return typeof window<"u"&&"Deway"in window&&!!window.Deway}replayCommand(e){try{const t=window.Deway,i=t?.[e.method];typeof i=="function"&&i.apply(t,e.args)}catch{}}}class h{static CACHE_KEY="deway-remote-config-cache";async cacheRemoteConfig(e,t){try{const i={config:e,ttl_seconds:t,timestamp:Date.now()};localStorage.setItem(h.CACHE_KEY,JSON.stringify(i))}catch{}}async getCachedRemoteConfig(){try{const e=localStorage.getItem(h.CACHE_KEY);return e?JSON.parse(e):null}catch{return null}}isCacheValid(e,t){const i=Date.now(),n=e+t*1e3;return i<n}}class K{cleanApiEndpoint(e){return e.trim().replace(/\/+$/,"")}async fetchRemoteConfig(e,t){try{const i=this.cleanApiEndpoint(t),n=await fetch(`${i}/sdk-remote-config-serve/`,{method:"GET",headers:{Accept:"application/json","deway-app-key":e,Origin:window?.location?.origin||""}});return n.ok?await n.json():null}catch{return null}}}class k{async executeSDK(e){return new Promise(t=>{try{if(!this.isDocumentReady()){t(!1);return}const i=document.createElement("script");i.textContent=e,i.type="text/javascript";let n=!1;const o=a=>{n||(n=!0,this.cleanupScript(i),t(a))};i.onerror=()=>{o(!1)},i.onload=()=>o(!0),document.head.appendChild(i),setTimeout(()=>{!n&&this.verifySDKLoaded()?o(!0):n||o(!1)},100)}catch{t(!1)}})}isDocumentReady(){return typeof document<"u"&&document.head!=null}verifySDKLoaded(){return typeof window<"u"&&"Deway"in window&&!!window.Deway}cleanupScript(e){try{e.parentNode&&e.parentNode.removeChild(e)}catch{}}}class T{validateConfig(e){return!(!e||!e.appKey||e.appKey.trim().length===0||e.apiEndpoint!==void 0&&!this.isValidUrl(e.apiEndpoint)||e.publicKey!==void 0&&e.publicKey.trim().length===0)}isValidUrl(e){try{return new URL(e),!0}catch{return!1}}}const m={apiEndpoint:"https://service.deway.app",publicKey:"9d3dBUvqyUQ7egd5j5uORdHSqZ7VFWOu+ud/SWt9WUY="};class I{isLoaded=!1;isLoading=!1;cacheManager;scriptExecutor;commandQueue;sdkFetcher;configValidator;remoteConfigFetcher;remoteConfigCache;sdkConfigStore;constructor(){this.cacheManager=new s,this.scriptExecutor=new k,this.commandQueue=new g,this.sdkFetcher=new v,this.configValidator=new T,this.sdkConfigStore=new C,this.remoteConfigFetcher=new K,this.remoteConfigCache=new h}init(e){this.performInit(e).catch(t=>{})}async performInit(e){try{if(!this.canInitialize())return;const t=this.isInitializationPayload(e),i=t?e.localConfig:e;if(!this.configValidator.validateConfig(i))return;this.isLoading=!0;const n=i.apiEndpoint||m.apiEndpoint,o=i.publicKey||m.publicKey,[a,d]=await Promise.all([this.fetchOrLoadSDK(i.appKey,n,o),this.fetchRemoteConfigWithCache(i,n)]);if(!a)return;const y=t?e:this.createInitializationPayload(d,i);if(!await this.scriptExecutor.executeSDK(a.code)||!this.initializeSDK(y))return;this.commandQueue.replayQueuedCommands(),this.isLoaded=!0}finally{this.isLoading=!1}}isInitializationPayload(e){return"localConfig"in e&&"remoteConfig"in e&&"defaults"in e}canInitialize(){return!(this.isLoaded||this.isLoading)}async fetchRemoteConfigWithCache(e,t){this.sdkConfigStore.saveConfig(e);const i=await this.remoteConfigFetcher.fetchRemoteConfig(e.appKey,t);if(i)return await this.remoteConfigCache.cacheRemoteConfig(i.config,i.ttl_seconds),i;const n=await this.remoteConfigCache.getCachedRemoteConfig();return n?{config:n.config,ttl_seconds:n.ttl_seconds}:null}createInitializationPayload(e,t){return{localConfig:t,remoteConfig:e?.config??null,defaults:m}}async fetchOrLoadSDK(e,t,i){const n=await this.sdkFetcher.fetchSDK(e,t,i);return n?(await this.cacheManager.cacheSDK(n.code,n.version,n.checksum,n.signature),n):this.loadFromCache()}async loadFromCache(){const e=await this.cacheManager.getCachedSDK();return e?{code:e.code,version:e.version}:null}initializeSDK(e){if(!this.isSDKAvailable())return!1;try{return window.Deway?.init(e),!0}catch{return!1}}identify(e){try{this.isLoaded&&this.isSDKAvailable()?window.Deway?.identify(e):this.commandQueue.queueCommand("identify",e)}catch{}}reportEvent(e,t){try{this.isLoaded&&this.isSDKAvailable()?window.Deway?.reportEvent(e,t):this.commandQueue.queueCommand("reportEvent",e,t)}catch{}}setUserProfile(e){try{this.isLoaded&&this.isSDKAvailable()?window.Deway?.setUserProfile(e):this.commandQueue.queueCommand("setUserProfile",e)}catch{}}show(e){try{this.isLoaded&&this.isSDKAvailable()?window.Deway?.show(e):this.commandQueue.queueCommand("show",e)}catch{}}hide(){try{this.isLoaded&&this.isSDKAvailable()?window.Deway?.hide():this.commandQueue.queueCommand("hide")}catch{}}isVisible(){try{return this.isLoaded&&this.isSDKAvailable()?window.Deway?.isVisible()??!1:!1}catch{return!1}}isInitialized(){try{return this.isLoaded&&this.isSDKAvailable()?window.Deway?.isInitialized()??!1:!1}catch{return!1}}destroy(){try{this.isLoaded&&this.isSDKAvailable()?window.Deway?.destroy():this.commandQueue.queueCommand("destroy"),this.commandQueue.clearQueue()}catch{}}isSDKAvailable(){return typeof window<"u"&&"Deway"in window&&!!window.Deway}}const c=new I,p={init:r=>c.init(r),identify:r=>c.identify(r),reportEvent:(r,e)=>c.reportEvent(r,e),setUserProfile:r=>c.setUserProfile(r),show:r=>c.show(r),hide:()=>c.hide(),isVisible:()=>c.isVisible(),isInitialized:()=>c.isInitialized(),destroy:()=>c.destroy()};return typeof window<"u"&&(window.Deway=p),p}));
|