@homekynd/hk-embed-sdk 0.0.7 → 0.1.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 +23 -16
- package/dist/index.cjs +1 -1
- package/dist/index.d.ts +22 -4
- package/dist/index.js +93 -51
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -50,16 +50,23 @@ function MyComponent() {
|
|
|
50
50
|
}
|
|
51
51
|
```
|
|
52
52
|
|
|
53
|
+
### Available Handlers
|
|
54
|
+
|
|
55
|
+
| Function | Type |
|
|
56
|
+
| --------------------------- | --------------------------------------------------------- |
|
|
57
|
+
| `addModel(modelId: string)` | Adds a model in the iframe canvas by passing the model ID |
|
|
58
|
+
| `getDeviceId()` | Provides the device unique identification (uuid format) |
|
|
59
|
+
|
|
53
60
|
### Configuration Options React
|
|
54
61
|
|
|
55
|
-
| Option | Type
|
|
56
|
-
| ---------- |
|
|
57
|
-
| `clientId` | `string`
|
|
58
|
-
| `apiKey` | `string`
|
|
59
|
-
| `width` | `string \| number`
|
|
60
|
-
| `height` | `string \| number`
|
|
61
|
-
| `path` | `
|
|
62
|
-
| `style` | `React.CSSProperties`
|
|
62
|
+
| Option | Type | Required | Default | Description |
|
|
63
|
+
| ---------- | -------------------------------- | -------- | -------------- | ----------------------------------------- |
|
|
64
|
+
| `clientId` | `string` | ✅ Yes | - | Your Homekynd client ID |
|
|
65
|
+
| `apiKey` | `string` | ✅ Yes | - | Your Homekynd API key |
|
|
66
|
+
| `width` | `string \| number` | No | `"100%"` | Embed width (e.g., "500px", "100%", 500) |
|
|
67
|
+
| `height` | `string \| number` | No | `"100%"` | Embed height (e.g., "400px", "50vh", 400) |
|
|
68
|
+
| `path` | `"designTool" \| "configurator"` | No | `"designTool"` | Initial page to load |
|
|
69
|
+
| `style` | `React.CSSProperties` | No | - | Custom styles |
|
|
63
70
|
|
|
64
71
|
### For Vanilla JavaScript (NPM)
|
|
65
72
|
|
|
@@ -113,14 +120,14 @@ function MyComponent() {
|
|
|
113
120
|
|
|
114
121
|
### Configuration Options Vanilla
|
|
115
122
|
|
|
116
|
-
| Option | Type
|
|
117
|
-
| ----------- |
|
|
118
|
-
| `clientId` | `string`
|
|
119
|
-
| `apiKey` | `string`
|
|
120
|
-
| `container` | `HTMLElement`
|
|
121
|
-
| `width` | `string \| number`
|
|
122
|
-
| `height` | `string \| number`
|
|
123
|
-
| `path` | `
|
|
123
|
+
| Option | Type | Required | Default | Description |
|
|
124
|
+
| ----------- | -------------------------------- | -------- | -------------- | ----------------------------------------- |
|
|
125
|
+
| `clientId` | `string` | ✅ Yes | - | Your Homekynd client ID |
|
|
126
|
+
| `apiKey` | `string` | ✅ Yes | - | Your Homekynd API key |
|
|
127
|
+
| `container` | `HTMLElement` | ✅ Yes | - | Container element |
|
|
128
|
+
| `width` | `string \| number` | No | `"100%"` | Embed width (e.g., "500px", "100%", 500) |
|
|
129
|
+
| `height` | `string \| number` | No | `"100%"` | Embed height (e.g., "400px", "50vh", 400) |
|
|
130
|
+
| `path` | `"designTool" \| "configurator"` | No | `"designTool"` | Initial page to load |
|
|
124
131
|
|
|
125
132
|
## Common Examples
|
|
126
133
|
|
package/dist/index.cjs
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
"use strict";var
|
|
1
|
+
"use strict";var v=Object.defineProperty,D=Object.defineProperties;var L=Object.getOwnPropertyDescriptors;var M=Object.getOwnPropertySymbols;var P=Object.prototype.hasOwnProperty,T=Object.prototype.propertyIsEnumerable;var w=(n,e,t)=>e in n?v(n,e,{enumerable:!0,configurable:!0,writable:!0,value:t}):n[e]=t,b=(n,e)=>{for(var t in e||(e={}))P.call(e,t)&&w(n,t,e[t]);if(M)for(var t of M(e))T.call(e,t)&&w(n,t,e[t]);return n},I=(n,e)=>D(n,L(e));var h=(n,e,t)=>w(n,typeof e!="symbol"?e+"":e,t);var y=(n,e,t)=>new Promise((r,o)=>{var s=a=>{try{c(t.next(a))}catch(l){o(l)}},f=a=>{try{c(t.throw(a))}catch(l){o(l)}},c=a=>a.done?r(a.value):Promise.resolve(a.value).then(s,f);c((t=t.apply(n,e)).next())});Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const i=require("react"),U="https://app.homekynd.com";function O(n,e){return y(this,null,function*(){try{const t=yield fetch(`${U}/api/v1/company/generate-token`,{method:"POST",headers:{"Content-Type":"application/json"},body:JSON.stringify({api_secret:n,id:e})}),r=yield t.json();if(t.ok)return r.token;console.error("Error fetching token: please confirm your API Secret and Client ID",r)}catch(t){console.error("Fetch error:",t)}})}const N={designTool:"/company",configurator:"/configurator"};class m{static setDeviceId(e){this.deviceId=e}static getDeviceId(){return this.deviceId}}h(m,"deviceId");const u="https://app.homekynd.com",_="https://hk-socket-987653813850.us-central1.run.app";class R{constructor(e){h(this,"container");h(this,"iframe");h(this,"currentToken");h(this,"created",!1);h(this,"screenMode","design-tool");const{container:t}=e;if(!t)throw new Error("Container element is required");this.container=t,this.create(e)}create(e){return y(this,null,function*(){if(this.created)return;const{clientId:t,apiKey:r,path:o="designTool",width:s="100%",height:f="100%",enablePathSync:c=!0}=e;o==="configurator"?this.screenMode="configurator":this.screenMode="design-tool";const a=new URL(window.location.href),g=a.searchParams.get("ifpath")||N[o],k=u.endsWith("/")?u:u+"/",S=g.startsWith("/")?g.substring(1):g,E=new URL(S,k),p=yield O(r,t);this.currentToken=p,p&&E.searchParams.set("token",p);const d=document.createElement("iframe");return d.src=E.toString(),d.style.border="0",d.style.width=isNaN(Number(s))?s:`${s}px`,d.style.height=isNaN(Number(f))?f:`${f}px`,this.iframe=d,d.onload=()=>{this.currentToken&&this.sendMessage({type:"SET_TOKEN",token:this.currentToken})},this.container.innerHTML="",this.container.appendChild(d),c&&(a.searchParams.set("ifpath",g),window.history.replaceState({},"",a.toString())),this.setupMessageHandling(),this.created=!0,{sendMessage:this.sendMessage.bind(this),onMessage:this.onMessage.bind(this)}})}setupMessageHandling(){window.addEventListener("message",e=>{var t;switch((t=e.data)==null?void 0:t.type){case"ROUTE_CHANGE":this.onRouteChange(e.data.path);break;case"SET_DEVICE_ID":m.setDeviceId(e.data.deviceId);break;case"ADD_MODEL":this.addModel(e.data.modelId);break}})}onRouteChange(e){this.inputParentRoute(e),this.inputIframeRoute(e)}inputParentRoute(e){const t=new URL(window.location.href);t.searchParams.set("ifpath",e),window.history.replaceState({},"",t.toString())}inputIframeRoute(e){if(!this.iframe)return;const t=new URL(this.iframe.src),r=u.endsWith("/")?u:u+"/",o=e.startsWith("/")?e.substring(1):e,s=new URL(o,r);t.pathname!==s.pathname&&(this.iframe.src=s.toString())}sendMessage(e){var t;if((t=this.iframe)!=null&&t.contentWindow){const r=new URL(u).origin;this.iframe.contentWindow.postMessage(e,r)}}onMessage(e){window.addEventListener("message",t=>{e(t.data)})}addModel(e){fetch(`${_}/api/${this.screenMode}/addmodel`,{method:"POST",body:JSON.stringify({modelData:{modelId:e},deviceId:m.getDeviceId()})})}}const C=n=>{const e=i.useRef(null),t=i.useRef(null),[r,o]=i.useState(!1),s=i.useMemo(()=>n,[n.clientId,n.apiKey,n.path,n.width,n.height,n.enablePathSync]);return i.useEffect(()=>{o(!0)},[]),(typeof window!="undefined"?i.useLayoutEffect:i.useEffect)(()=>{if(!(!r||typeof window=="undefined")){if(e.current&&!t.current)try{t.current=new R(I(b({},s),{container:e.current}))}catch(c){console.error("Error creating HKEmbed:",c)}return()=>{t.current&&(t.current=null)}}},[s,r]),i.createElement("div",{ref:e,style:n.style})},H=n=>{try{return window.postMessage({type:"ADD_MODEL",modelId:n}),{success:!0,message:"Model added"}}catch(e){return console.error(e),{success:!1,message:e instanceof Error?e.message:"An unknown error occurred"}}},K=()=>m.getDeviceId();exports.HKEmbed=R;exports.HKReactEmbed=C;exports.addModel=H;exports.getDeviceId=K;
|
package/dist/index.d.ts
CHANGED
|
@@ -1,12 +1,29 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { JSX as JSX_2 } from 'react/jsx-runtime';
|
|
2
|
+
|
|
3
|
+
/**
|
|
4
|
+
*
|
|
5
|
+
* @description Adds a model to the iframe
|
|
6
|
+
*/
|
|
7
|
+
export declare const addModel: (modelId: string) => {
|
|
8
|
+
success: boolean;
|
|
9
|
+
message: string;
|
|
10
|
+
};
|
|
11
|
+
|
|
12
|
+
export declare type DisplayMode = "configurator" | "web-embedded";
|
|
2
13
|
|
|
3
14
|
export declare type GenericMessageObject = any;
|
|
4
15
|
|
|
16
|
+
/**
|
|
17
|
+
* @description Returns the device ID
|
|
18
|
+
*/
|
|
19
|
+
export declare const getDeviceId: () => string;
|
|
20
|
+
|
|
5
21
|
export declare class HKEmbed {
|
|
6
22
|
private container;
|
|
7
23
|
private iframe?;
|
|
8
24
|
private currentToken?;
|
|
9
25
|
private created;
|
|
26
|
+
private screenMode;
|
|
10
27
|
constructor(options: HKEmbedConfigVanilla);
|
|
11
28
|
private create;
|
|
12
29
|
private setupMessageHandling;
|
|
@@ -15,6 +32,7 @@ export declare class HKEmbed {
|
|
|
15
32
|
private inputIframeRoute;
|
|
16
33
|
private sendMessage;
|
|
17
34
|
private onMessage;
|
|
35
|
+
private addModel;
|
|
18
36
|
}
|
|
19
37
|
|
|
20
38
|
export declare interface HKEmbedConfigContainer {
|
|
@@ -23,7 +41,7 @@ export declare interface HKEmbedConfigContainer {
|
|
|
23
41
|
|
|
24
42
|
export declare interface HKEmbedConfigOptions {
|
|
25
43
|
clientId: string;
|
|
26
|
-
apiKey: string
|
|
44
|
+
apiKey: `hk-${string}`;
|
|
27
45
|
path?: HKPathKey;
|
|
28
46
|
width?: string | number;
|
|
29
47
|
height?: string | number;
|
|
@@ -42,8 +60,8 @@ export declare interface HKEmbedConfigVanilla extends HKEmbedConfigContainer, HK
|
|
|
42
60
|
|
|
43
61
|
export declare type HKPath = Record<HKPathKey, string>;
|
|
44
62
|
|
|
45
|
-
export declare type HKPathKey = "
|
|
63
|
+
export declare type HKPathKey = "designTool" | "configurator";
|
|
46
64
|
|
|
47
|
-
export declare const HKReactEmbed:
|
|
65
|
+
export declare const HKReactEmbed: (options: HKEmbedConfigReact) => JSX_2.Element;
|
|
48
66
|
|
|
49
67
|
export { }
|
package/dist/index.js
CHANGED
|
@@ -1,38 +1,38 @@
|
|
|
1
|
-
var
|
|
1
|
+
var D = Object.defineProperty, P = Object.defineProperties;
|
|
2
2
|
var T = Object.getOwnPropertyDescriptors;
|
|
3
3
|
var E = Object.getOwnPropertySymbols;
|
|
4
|
-
var
|
|
5
|
-
var p = (n, e, t) => e in n ?
|
|
4
|
+
var U = Object.prototype.hasOwnProperty, v = Object.prototype.propertyIsEnumerable;
|
|
5
|
+
var p = (n, e, t) => e in n ? D(n, e, { enumerable: !0, configurable: !0, writable: !0, value: t }) : n[e] = t, M = (n, e) => {
|
|
6
6
|
for (var t in e || (e = {}))
|
|
7
|
-
|
|
7
|
+
U.call(e, t) && p(n, t, e[t]);
|
|
8
8
|
if (E)
|
|
9
9
|
for (var t of E(e))
|
|
10
|
-
|
|
10
|
+
v.call(e, t) && p(n, t, e[t]);
|
|
11
11
|
return n;
|
|
12
|
-
},
|
|
13
|
-
var
|
|
14
|
-
var
|
|
12
|
+
}, I = (n, e) => P(n, T(e));
|
|
13
|
+
var d = (n, e, t) => p(n, typeof e != "symbol" ? e + "" : e, t);
|
|
14
|
+
var w = (n, e, t) => new Promise((r, o) => {
|
|
15
15
|
var s = (a) => {
|
|
16
16
|
try {
|
|
17
|
-
|
|
17
|
+
i(t.next(a));
|
|
18
18
|
} catch (f) {
|
|
19
|
-
|
|
19
|
+
o(f);
|
|
20
20
|
}
|
|
21
|
-
},
|
|
21
|
+
}, u = (a) => {
|
|
22
22
|
try {
|
|
23
|
-
|
|
23
|
+
i(t.throw(a));
|
|
24
24
|
} catch (f) {
|
|
25
|
-
|
|
25
|
+
o(f);
|
|
26
26
|
}
|
|
27
|
-
},
|
|
28
|
-
|
|
27
|
+
}, i = (a) => a.done ? r(a.value) : Promise.resolve(a.value).then(s, u);
|
|
28
|
+
i((t = t.apply(n, e)).next());
|
|
29
29
|
});
|
|
30
|
-
import
|
|
31
|
-
const
|
|
32
|
-
function
|
|
33
|
-
return
|
|
30
|
+
import R, { useRef as k, useMemo as O, useEffect as b, useLayoutEffect as N } from "react";
|
|
31
|
+
const _ = "https://app.homekynd.com";
|
|
32
|
+
function C(n, e) {
|
|
33
|
+
return w(this, null, function* () {
|
|
34
34
|
try {
|
|
35
|
-
const t = yield fetch(`${
|
|
35
|
+
const t = yield fetch(`${_}/api/v1/company/generate-token`, {
|
|
36
36
|
method: "POST",
|
|
37
37
|
headers: {
|
|
38
38
|
"Content-Type": "application/json"
|
|
@@ -50,40 +50,52 @@ function K(n, e) {
|
|
|
50
50
|
}
|
|
51
51
|
});
|
|
52
52
|
}
|
|
53
|
-
const
|
|
54
|
-
|
|
55
|
-
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
53
|
+
const A = {
|
|
54
|
+
designTool: "/company",
|
|
55
|
+
configurator: "/configurator"
|
|
56
|
+
};
|
|
57
|
+
class g {
|
|
58
|
+
static setDeviceId(e) {
|
|
59
|
+
this.deviceId = e;
|
|
60
|
+
}
|
|
61
|
+
static getDeviceId() {
|
|
62
|
+
return this.deviceId;
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
d(g, "deviceId");
|
|
66
|
+
const h = "https://app.homekynd.com", H = "https://hk-socket-987653813850.us-central1.run.app";
|
|
67
|
+
class K {
|
|
59
68
|
constructor(e) {
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
69
|
+
d(this, "container");
|
|
70
|
+
d(this, "iframe");
|
|
71
|
+
d(this, "currentToken");
|
|
72
|
+
d(this, "created", !1);
|
|
73
|
+
d(this, "screenMode", "design-tool");
|
|
64
74
|
const { container: t } = e;
|
|
65
75
|
if (!t) throw new Error("Container element is required");
|
|
66
76
|
this.container = t, this.create(e);
|
|
67
77
|
}
|
|
68
78
|
create(e) {
|
|
69
|
-
return
|
|
79
|
+
return w(this, null, function* () {
|
|
70
80
|
if (this.created) return;
|
|
71
81
|
const {
|
|
72
82
|
clientId: t,
|
|
73
83
|
apiKey: r,
|
|
74
|
-
path:
|
|
84
|
+
path: o = "designTool",
|
|
75
85
|
width: s = "100%",
|
|
76
|
-
height:
|
|
77
|
-
enablePathSync:
|
|
78
|
-
} = e
|
|
86
|
+
height: u = "100%",
|
|
87
|
+
enablePathSync: i = !0
|
|
88
|
+
} = e;
|
|
89
|
+
o === "configurator" ? this.screenMode = "configurator" : this.screenMode = "design-tool";
|
|
90
|
+
const a = new URL(window.location.href), l = a.searchParams.get("ifpath") || A[o], S = h.endsWith("/") ? h : h + "/", L = l.startsWith("/") ? l.substring(1) : l, y = new URL(L, S), m = yield C(r, t);
|
|
79
91
|
this.currentToken = m, m && y.searchParams.set("token", m);
|
|
80
92
|
const c = document.createElement("iframe");
|
|
81
|
-
return c.src = y.toString(), c.style.border = "0", c.style.width = isNaN(Number(s)) ? s : `${s}px`, c.style.height = isNaN(Number(
|
|
93
|
+
return c.src = y.toString(), c.style.border = "0", c.style.width = isNaN(Number(s)) ? s : `${s}px`, c.style.height = isNaN(Number(u)) ? u : `${u}px`, this.iframe = c, c.onload = () => {
|
|
82
94
|
this.currentToken && this.sendMessage({
|
|
83
95
|
type: "SET_TOKEN",
|
|
84
96
|
token: this.currentToken
|
|
85
97
|
});
|
|
86
|
-
}, this.container.innerHTML = "", this.container.appendChild(c),
|
|
98
|
+
}, this.container.innerHTML = "", this.container.appendChild(c), i && (a.searchParams.set("ifpath", l), window.history.replaceState({}, "", a.toString())), this.setupMessageHandling(), this.created = !0, {
|
|
87
99
|
sendMessage: this.sendMessage.bind(this),
|
|
88
100
|
onMessage: this.onMessage.bind(this)
|
|
89
101
|
};
|
|
@@ -92,7 +104,17 @@ class W {
|
|
|
92
104
|
setupMessageHandling() {
|
|
93
105
|
window.addEventListener("message", (e) => {
|
|
94
106
|
var t;
|
|
95
|
-
((t = e.data) == null ? void 0 : t.type)
|
|
107
|
+
switch ((t = e.data) == null ? void 0 : t.type) {
|
|
108
|
+
case "ROUTE_CHANGE":
|
|
109
|
+
this.onRouteChange(e.data.path);
|
|
110
|
+
break;
|
|
111
|
+
case "SET_DEVICE_ID":
|
|
112
|
+
g.setDeviceId(e.data.deviceId);
|
|
113
|
+
break;
|
|
114
|
+
case "ADD_MODEL":
|
|
115
|
+
this.addModel(e.data.modelId);
|
|
116
|
+
break;
|
|
117
|
+
}
|
|
96
118
|
});
|
|
97
119
|
}
|
|
98
120
|
onRouteChange(e) {
|
|
@@ -104,7 +126,7 @@ class W {
|
|
|
104
126
|
}
|
|
105
127
|
inputIframeRoute(e) {
|
|
106
128
|
if (!this.iframe) return;
|
|
107
|
-
const t = new URL(this.iframe.src), r = h.endsWith("/") ? h : h + "/",
|
|
129
|
+
const t = new URL(this.iframe.src), r = h.endsWith("/") ? h : h + "/", o = e.startsWith("/") ? e.substring(1) : e, s = new URL(o, r);
|
|
108
130
|
t.pathname !== s.pathname && (this.iframe.src = s.toString());
|
|
109
131
|
}
|
|
110
132
|
sendMessage(e) {
|
|
@@ -119,9 +141,18 @@ class W {
|
|
|
119
141
|
e(t.data);
|
|
120
142
|
});
|
|
121
143
|
}
|
|
144
|
+
addModel(e) {
|
|
145
|
+
fetch(`${H}/api/${this.screenMode}/addmodel`, {
|
|
146
|
+
method: "POST",
|
|
147
|
+
body: JSON.stringify({
|
|
148
|
+
modelData: { modelId: e },
|
|
149
|
+
deviceId: g.getDeviceId()
|
|
150
|
+
})
|
|
151
|
+
});
|
|
152
|
+
}
|
|
122
153
|
}
|
|
123
|
-
const
|
|
124
|
-
const e = k(null), t = k(null), [r,
|
|
154
|
+
const x = (n) => {
|
|
155
|
+
const e = k(null), t = k(null), [r, o] = R.useState(!1), s = O(
|
|
125
156
|
() => n,
|
|
126
157
|
[
|
|
127
158
|
n.clientId,
|
|
@@ -132,25 +163,36 @@ const $ = (n) => {
|
|
|
132
163
|
n.enablePathSync
|
|
133
164
|
]
|
|
134
165
|
);
|
|
135
|
-
return
|
|
136
|
-
|
|
137
|
-
}, []), (typeof window != "undefined" ?
|
|
166
|
+
return b(() => {
|
|
167
|
+
o(!0);
|
|
168
|
+
}, []), (typeof window != "undefined" ? N : b)(() => {
|
|
138
169
|
if (!(!r || typeof window == "undefined")) {
|
|
139
170
|
if (e.current && !t.current)
|
|
140
171
|
try {
|
|
141
|
-
t.current = new
|
|
172
|
+
t.current = new K(I(M({}, s), {
|
|
142
173
|
container: e.current
|
|
143
174
|
}));
|
|
144
|
-
} catch (
|
|
145
|
-
console.error("Error creating HKEmbed:",
|
|
175
|
+
} catch (i) {
|
|
176
|
+
console.error("Error creating HKEmbed:", i);
|
|
146
177
|
}
|
|
147
178
|
return () => {
|
|
148
179
|
t.current && (t.current = null);
|
|
149
180
|
};
|
|
150
181
|
}
|
|
151
|
-
}, [s, r]),
|
|
152
|
-
}
|
|
182
|
+
}, [s, r]), /* @__PURE__ */ R.createElement("div", { ref: e, style: n.style });
|
|
183
|
+
}, j = (n) => {
|
|
184
|
+
try {
|
|
185
|
+
return window.postMessage({
|
|
186
|
+
type: "ADD_MODEL",
|
|
187
|
+
modelId: n
|
|
188
|
+
}), { success: !0, message: "Model added" };
|
|
189
|
+
} catch (e) {
|
|
190
|
+
return console.error(e), { success: !1, message: e instanceof Error ? e.message : "An unknown error occurred" };
|
|
191
|
+
}
|
|
192
|
+
}, B = () => g.getDeviceId();
|
|
153
193
|
export {
|
|
154
|
-
|
|
155
|
-
|
|
194
|
+
K as HKEmbed,
|
|
195
|
+
x as HKReactEmbed,
|
|
196
|
+
j as addModel,
|
|
197
|
+
B as getDeviceId
|
|
156
198
|
};
|