@sonordev/site-kit 4.0.2 → 4.2.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/agent-manifest.json +6 -1
- package/dist/AnalyticsProvider-JTAJ27EC.js +31 -0
- package/dist/{AnalyticsProvider-5SX4ZRGN.js.map → AnalyticsProvider-JTAJ27EC.js.map} +1 -1
- package/dist/AnalyticsProvider-QD7H2FER.mjs +10 -0
- package/dist/{AnalyticsProvider-6DIRTRRA.mjs.map → AnalyticsProvider-QD7H2FER.mjs.map} +1 -1
- package/dist/ChatWidget-7UV4LXJR.js +20 -0
- package/dist/{ChatWidget-3SUC7HZA.js.map → ChatWidget-7UV4LXJR.js.map} +1 -1
- package/dist/ChatWidget-BS6STWYV.mjs +11 -0
- package/dist/{ChatWidget-JTTERPI5.mjs.map → ChatWidget-BS6STWYV.mjs.map} +1 -1
- package/dist/EngageWidget-AQOTCO46.js +18 -0
- package/dist/{EngageWidget-YVAIP2NW.js.map → EngageWidget-AQOTCO46.js.map} +1 -1
- package/dist/EngageWidget-M7MZXPC4.mjs +9 -0
- package/dist/{EngageWidget-3MDY2W5G.mjs.map → EngageWidget-M7MZXPC4.mjs.map} +1 -1
- package/dist/{FileField-PD52URLX.js → FileField-JIWKVY73.js} +6 -6
- package/dist/{FileField-PD52URLX.js.map → FileField-JIWKVY73.js.map} +1 -1
- package/dist/{FileField-XMBF3XCG.mjs → FileField-VIYBV4GM.mjs} +5 -5
- package/dist/{FileField-XMBF3XCG.mjs.map → FileField-VIYBV4GM.mjs.map} +1 -1
- package/dist/{FormSpotlight-72TYHDPV.mjs → FormSpotlight-7P3JV3XK.mjs} +3 -3
- package/dist/{FormSpotlight-72TYHDPV.mjs.map → FormSpotlight-7P3JV3XK.mjs.map} +1 -1
- package/dist/{FormSpotlight-AL6KGMGG.js → FormSpotlight-MSBWEM3F.js} +15 -15
- package/dist/{FormSpotlight-AL6KGMGG.js.map → FormSpotlight-MSBWEM3F.js.map} +1 -1
- package/dist/{FormStage-GNBPJ7WX.mjs → FormStage-327WGVBM.mjs} +3 -3
- package/dist/{FormStage-GNBPJ7WX.mjs.map → FormStage-327WGVBM.mjs.map} +1 -1
- package/dist/{FormStage-NLO52ER2.js → FormStage-FME3O3N2.js} +13 -13
- package/dist/{FormStage-NLO52ER2.js.map → FormStage-FME3O3N2.js.map} +1 -1
- package/dist/ManagedForm-5BXS3XKX.js +23 -0
- package/dist/{ManagedForm-XWN3TVQQ.js.map → ManagedForm-5BXS3XKX.js.map} +1 -1
- package/dist/ManagedForm-BFZWPWGY.mjs +14 -0
- package/dist/{ManagedForm-2SYVMJY6.mjs.map → ManagedForm-BFZWPWGY.mjs.map} +1 -1
- package/dist/{SignalCore-4NOVH33M.mjs → SignalCore-EE2RAGZ2.mjs} +5 -5
- package/dist/{SignalCore-4NOVH33M.mjs.map → SignalCore-EE2RAGZ2.mjs.map} +1 -1
- package/dist/{SignalCore-PD75O7GB.js → SignalCore-IPLGFFC3.js} +11 -11
- package/dist/{SignalCore-PD75O7GB.js.map → SignalCore-IPLGFFC3.js.map} +1 -1
- package/dist/SitemapSync-2X6NM3TX.mjs +8 -0
- package/dist/{SitemapSync-UH6VZ55T.mjs.map → SitemapSync-2X6NM3TX.mjs.map} +1 -1
- package/dist/SitemapSync-XBYRZ7WH.js +17 -0
- package/dist/{SitemapSync-KKUF43DS.js.map → SitemapSync-XBYRZ7WH.js.map} +1 -1
- package/dist/analytics/index.js +9 -9
- package/dist/analytics/index.mjs +4 -4
- package/dist/{chunk-6PNWJXAE.mjs → chunk-4HNFMOYE.mjs} +3 -3
- package/dist/{chunk-6PNWJXAE.mjs.map → chunk-4HNFMOYE.mjs.map} +1 -1
- package/dist/{chunk-T2YAEBEY.js → chunk-4PP4D3TF.js} +4 -4
- package/dist/{chunk-T2YAEBEY.js.map → chunk-4PP4D3TF.js.map} +1 -1
- package/dist/{chunk-WHVUSVHA.js → chunk-4YWGUQPU.js} +3 -3
- package/dist/{chunk-WHVUSVHA.js.map → chunk-4YWGUQPU.js.map} +1 -1
- package/dist/{chunk-AQA4PFMJ.mjs → chunk-57IFVXCB.mjs} +4 -4
- package/dist/{chunk-AQA4PFMJ.mjs.map → chunk-57IFVXCB.mjs.map} +1 -1
- package/dist/{chunk-QO5NS62X.js → chunk-7UCKV4WA.js} +8 -8
- package/dist/{chunk-QO5NS62X.js.map → chunk-7UCKV4WA.js.map} +1 -1
- package/dist/{chunk-NWJX6NHR.mjs → chunk-A5FJZWGY.mjs} +4 -4
- package/dist/{chunk-NWJX6NHR.mjs.map → chunk-A5FJZWGY.mjs.map} +1 -1
- package/dist/chunk-AAZNH3MA.mjs +23 -0
- package/dist/chunk-AAZNH3MA.mjs.map +1 -0
- package/dist/{chunk-5QVXHD6V.js → chunk-AVWIKVVE.js} +14 -14
- package/dist/{chunk-5QVXHD6V.js.map → chunk-AVWIKVVE.js.map} +1 -1
- package/dist/chunk-CBN73TLK.js +8 -0
- package/dist/{chunk-LYAU5PRS.js.map → chunk-CBN73TLK.js.map} +1 -1
- package/dist/chunk-CIM5W3UO.js +26 -0
- package/dist/chunk-CIM5W3UO.js.map +1 -0
- package/dist/{chunk-6ZFXASW6.mjs → chunk-CMIFYDKA.mjs} +5 -5
- package/dist/{chunk-6ZFXASW6.mjs.map → chunk-CMIFYDKA.mjs.map} +1 -1
- package/dist/{chunk-T5DXYGWK.mjs → chunk-DNEUGYTE.mjs} +3 -3
- package/dist/{chunk-T5DXYGWK.mjs.map → chunk-DNEUGYTE.mjs.map} +1 -1
- package/dist/{chunk-UBNVD567.mjs → chunk-DSECSIWJ.mjs} +3 -3
- package/dist/{chunk-UBNVD567.mjs.map → chunk-DSECSIWJ.mjs.map} +1 -1
- package/dist/{chunk-FZ643CZK.mjs → chunk-DYDAV4Y4.mjs} +4 -4
- package/dist/{chunk-FZ643CZK.mjs.map → chunk-DYDAV4Y4.mjs.map} +1 -1
- package/dist/{chunk-WXKEYKE6.js → chunk-FFQAKIV5.js} +15 -15
- package/dist/{chunk-WXKEYKE6.js.map → chunk-FFQAKIV5.js.map} +1 -1
- package/dist/{chunk-OP5FYTWJ.js → chunk-FMAEUQEZ.js} +12 -12
- package/dist/{chunk-OP5FYTWJ.js.map → chunk-FMAEUQEZ.js.map} +1 -1
- package/dist/{chunk-LVCUT2OX.js → chunk-GXABJJ4F.js} +3 -3
- package/dist/{chunk-LVCUT2OX.js.map → chunk-GXABJJ4F.js.map} +1 -1
- package/dist/{chunk-HOB2A6JM.mjs → chunk-HI6DVYVN.mjs} +3 -3
- package/dist/{chunk-HOB2A6JM.mjs.map → chunk-HI6DVYVN.mjs.map} +1 -1
- package/dist/{chunk-NJN467OM.js → chunk-HLCCE7BD.js} +14 -14
- package/dist/{chunk-NJN467OM.js.map → chunk-HLCCE7BD.js.map} +1 -1
- package/dist/{chunk-2MIOQYF5.js → chunk-INW43FWV.js} +6 -6
- package/dist/{chunk-2MIOQYF5.js.map → chunk-INW43FWV.js.map} +1 -1
- package/dist/{chunk-ARBOKZAU.mjs → chunk-IUZ2RH4V.mjs} +3 -4
- package/dist/chunk-IUZ2RH4V.mjs.map +1 -0
- package/dist/{chunk-VLY3SFNH.js → chunk-IV7LOJZO.js} +4 -4
- package/dist/{chunk-VLY3SFNH.js.map → chunk-IV7LOJZO.js.map} +1 -1
- package/dist/{chunk-RAX3HS4T.js → chunk-IWFP2FQ5.js} +16 -16
- package/dist/{chunk-RAX3HS4T.js.map → chunk-IWFP2FQ5.js.map} +1 -1
- package/dist/chunk-JA77WXRE.js +30 -0
- package/dist/chunk-JA77WXRE.js.map +1 -0
- package/dist/{chunk-62Z4D3QR.js → chunk-JWIJZQYI.js} +5 -5
- package/dist/{chunk-62Z4D3QR.js.map → chunk-JWIJZQYI.js.map} +1 -1
- package/dist/{chunk-PGND73EV.js → chunk-KFDFXRBE.js} +4 -4
- package/dist/{chunk-PGND73EV.js.map → chunk-KFDFXRBE.js.map} +1 -1
- package/dist/chunk-LS64Y25E.mjs +6 -0
- package/dist/{chunk-QTN3F7D7.mjs.map → chunk-LS64Y25E.mjs.map} +1 -1
- package/dist/{chunk-NCWVR4BU.mjs → chunk-MTXQG3TX.mjs} +7 -7
- package/dist/{chunk-NCWVR4BU.mjs.map → chunk-MTXQG3TX.mjs.map} +1 -1
- package/dist/{chunk-GCS4XZHC.mjs → chunk-MZZQHGXY.mjs} +3 -3
- package/dist/{chunk-GCS4XZHC.mjs.map → chunk-MZZQHGXY.mjs.map} +1 -1
- package/dist/{chunk-Y26LKDE4.js → chunk-NDASB3X3.js} +9 -9
- package/dist/{chunk-Y26LKDE4.js.map → chunk-NDASB3X3.js.map} +1 -1
- package/dist/{chunk-7QDTXT4N.js → chunk-NF3QVKWU.js} +6 -7
- package/dist/chunk-NF3QVKWU.js.map +1 -0
- package/dist/{chunk-R4PCXP3F.mjs → chunk-OO4T5X4Z.mjs} +3 -3
- package/dist/{chunk-R4PCXP3F.mjs.map → chunk-OO4T5X4Z.mjs.map} +1 -1
- package/dist/{chunk-ZK5VSIRO.js → chunk-PKQVV6LW.js} +12 -12
- package/dist/{chunk-ZK5VSIRO.js.map → chunk-PKQVV6LW.js.map} +1 -1
- package/dist/{chunk-ZPG4GTU7.js → chunk-QNEBWBZ4.js} +5 -5
- package/dist/{chunk-ZPG4GTU7.js.map → chunk-QNEBWBZ4.js.map} +1 -1
- package/dist/chunk-QZF5NTXQ.mjs +28 -0
- package/dist/chunk-QZF5NTXQ.mjs.map +1 -0
- package/dist/{chunk-FGN27J35.mjs → chunk-R6LQRHPQ.mjs} +4 -4
- package/dist/{chunk-FGN27J35.mjs.map → chunk-R6LQRHPQ.mjs.map} +1 -1
- package/dist/{chunk-NWPNFCNY.js → chunk-S2C3QU4E.js} +18 -18
- package/dist/{chunk-NWPNFCNY.js.map → chunk-S2C3QU4E.js.map} +1 -1
- package/dist/{chunk-XNPITFJ5.mjs → chunk-SDBUPTF4.mjs} +3 -3
- package/dist/{chunk-XNPITFJ5.mjs.map → chunk-SDBUPTF4.mjs.map} +1 -1
- package/dist/{chunk-B7J7SU5A.mjs → chunk-TGGSXT3F.mjs} +8 -8
- package/dist/{chunk-B7J7SU5A.mjs.map → chunk-TGGSXT3F.mjs.map} +1 -1
- package/dist/{chunk-MZY3MEUO.mjs → chunk-UDPUBSSS.mjs} +3 -3
- package/dist/{chunk-MZY3MEUO.mjs.map → chunk-UDPUBSSS.mjs.map} +1 -1
- package/dist/{chunk-VUIQLKJB.mjs → chunk-UKFBG6FV.mjs} +3 -3
- package/dist/{chunk-VUIQLKJB.mjs.map → chunk-UKFBG6FV.mjs.map} +1 -1
- package/dist/{chunk-UQPUFRXF.mjs → chunk-VGPZ4PCZ.mjs} +3 -3
- package/dist/{chunk-UQPUFRXF.mjs.map → chunk-VGPZ4PCZ.mjs.map} +1 -1
- package/dist/{chunk-MRRTAJWQ.js → chunk-VOMAEC5G.js} +3 -3
- package/dist/{chunk-MRRTAJWQ.js.map → chunk-VOMAEC5G.js.map} +1 -1
- package/dist/{chunk-MPACJDDG.js → chunk-VTFDE7H2.js} +7 -7
- package/dist/{chunk-MPACJDDG.js.map → chunk-VTFDE7H2.js.map} +1 -1
- package/dist/{chunk-KNYK2VLX.mjs → chunk-WCIQKO7W.mjs} +3 -3
- package/dist/{chunk-KNYK2VLX.mjs.map → chunk-WCIQKO7W.mjs.map} +1 -1
- package/dist/{chunk-JFVEKSZT.mjs → chunk-WCRBZZRI.mjs} +4 -4
- package/dist/{chunk-JFVEKSZT.mjs.map → chunk-WCRBZZRI.mjs.map} +1 -1
- package/dist/{chunk-53RHVKTD.mjs → chunk-WFCRXUNA.mjs} +4 -4
- package/dist/{chunk-53RHVKTD.mjs.map → chunk-WFCRXUNA.mjs.map} +1 -1
- package/dist/{chunk-ZRGCKWIT.js → chunk-WLVS4QBK.js} +4 -4
- package/dist/{chunk-ZRGCKWIT.js.map → chunk-WLVS4QBK.js.map} +1 -1
- package/dist/{chunk-WNNY2BCV.js → chunk-XOSAVYAI.js} +8 -8
- package/dist/{chunk-WNNY2BCV.js.map → chunk-XOSAVYAI.js.map} +1 -1
- package/dist/{chunk-AJNT5GCU.mjs → chunk-XXBVF7WN.mjs} +3 -3
- package/dist/{chunk-AJNT5GCU.mjs.map → chunk-XXBVF7WN.mjs.map} +1 -1
- package/dist/{chunk-XRC3JZAK.mjs → chunk-XZCZCND2.mjs} +3 -3
- package/dist/{chunk-XRC3JZAK.mjs.map → chunk-XZCZCND2.mjs.map} +1 -1
- package/dist/{chunk-LP6MC2RH.js → chunk-Z7HAQTWP.js} +14 -14
- package/dist/{chunk-LP6MC2RH.js.map → chunk-Z7HAQTWP.js.map} +1 -1
- package/dist/cli/index.js +3 -3
- package/dist/cli/index.mjs +1 -1
- package/dist/client/index.js +4 -4
- package/dist/client/index.mjs +3 -3
- package/dist/cms/index.d.ts +23 -0
- package/dist/cms/index.d.ts.map +1 -1
- package/dist/cms/index.js +2 -2
- package/dist/cms/index.mjs +1 -1
- package/dist/cms/server-api.d.ts.map +1 -1
- package/dist/cms/server.js +4 -4
- package/dist/cms/server.mjs +1 -1
- package/dist/commerce/index.js +56 -56
- package/dist/commerce/index.mjs +5 -5
- package/dist/engage/EngageWidget.d.ts.map +1 -1
- package/dist/engage/dependency-contract.test.d.ts +2 -0
- package/dist/engage/dependency-contract.test.d.ts.map +1 -0
- package/dist/engage/index.js +10 -10
- package/dist/engage/index.mjs +7 -7
- package/dist/engage/socket-loader.d.ts +13 -0
- package/dist/engage/socket-loader.d.ts.map +1 -1
- package/dist/fleet/index.js +8 -8
- package/dist/fleet/index.mjs +4 -4
- package/dist/forms/index.js +16 -16
- package/dist/forms/index.mjs +9 -9
- package/dist/forms/server.js +10 -10
- package/dist/forms/server.mjs +8 -8
- package/dist/forms/static.js +7 -7
- package/dist/forms/static.mjs +6 -6
- package/dist/images/index.js +11 -11
- package/dist/images/index.mjs +4 -4
- package/dist/index.js +67 -66
- package/dist/index.js.map +1 -1
- package/dist/index.mjs +11 -10
- package/dist/index.mjs.map +1 -1
- package/dist/landing/index.d.ts +12 -0
- package/dist/landing/index.d.ts.map +1 -1
- package/dist/landing/index.js +5 -4
- package/dist/landing/index.mjs +2 -1
- package/dist/landing/server-entry.test.d.ts +2 -0
- package/dist/landing/server-entry.test.d.ts.map +1 -0
- package/dist/landing/server.d.ts +32 -0
- package/dist/landing/server.d.ts.map +1 -0
- package/dist/landing/server.js +17 -0
- package/dist/landing/server.js.map +1 -0
- package/dist/landing/server.mjs +4 -0
- package/dist/landing/server.mjs.map +1 -0
- package/dist/layout/client.js +8 -8
- package/dist/layout/client.mjs +7 -7
- package/dist/layout/index.js +10 -10
- package/dist/layout/index.mjs +8 -8
- package/dist/maps/index.js +5 -5
- package/dist/maps/index.mjs +3 -3
- package/dist/search/index.js +4 -4
- package/dist/search/index.mjs +3 -3
- package/dist/seo/client.js +5 -5
- package/dist/seo/client.mjs +4 -4
- package/dist/seo/index.js +5 -5
- package/dist/seo/index.mjs +4 -4
- package/dist/server/index.js +3 -3
- package/dist/server/index.mjs +2 -2
- package/dist/shared/build-entries.d.ts +7 -0
- package/dist/shared/build-entries.d.ts.map +1 -1
- package/dist/shared/no-cjs-require.test.d.ts +2 -0
- package/dist/shared/no-cjs-require.test.d.ts.map +1 -0
- package/dist/shared/version.d.ts +1 -1
- package/dist/signal/index.js +11 -11
- package/dist/signal/index.mjs +2 -2
- package/dist/{socket-loader-YEAQZ3XC.js → socket-loader-2NYBMBFQ.js} +2 -2
- package/dist/socket-loader-2NYBMBFQ.js.map +1 -0
- package/dist/{socket-loader-JHNN2QK4.mjs → socket-loader-JA2DI2RT.mjs} +2 -2
- package/dist/socket-loader-JA2DI2RT.mjs.map +1 -0
- package/dist/sync/index.js +16 -16
- package/dist/sync/index.mjs +4 -4
- package/package.json +26 -9
- package/dist/AnalyticsProvider-5SX4ZRGN.js +0 -31
- package/dist/AnalyticsProvider-6DIRTRRA.mjs +0 -10
- package/dist/ChatWidget-3SUC7HZA.js +0 -20
- package/dist/ChatWidget-JTTERPI5.mjs +0 -11
- package/dist/EngageWidget-3MDY2W5G.mjs +0 -9
- package/dist/EngageWidget-YVAIP2NW.js +0 -18
- package/dist/ManagedForm-2SYVMJY6.mjs +0 -14
- package/dist/ManagedForm-XWN3TVQQ.js +0 -23
- package/dist/SitemapSync-KKUF43DS.js +0 -17
- package/dist/SitemapSync-UH6VZ55T.mjs +0 -8
- package/dist/chunk-7QDTXT4N.js.map +0 -1
- package/dist/chunk-ARBOKZAU.mjs.map +0 -1
- package/dist/chunk-EU2UGO25.js +0 -52
- package/dist/chunk-EU2UGO25.js.map +0 -1
- package/dist/chunk-IBMOX3YE.mjs +0 -48
- package/dist/chunk-IBMOX3YE.mjs.map +0 -1
- package/dist/chunk-LYAU5PRS.js +0 -8
- package/dist/chunk-QTN3F7D7.mjs +0 -6
- package/dist/socket-loader-JHNN2QK4.mjs.map +0 -1
- package/dist/socket-loader-YEAQZ3XC.js.map +0 -1
package/dist/forms/static.js
CHANGED
|
@@ -1,20 +1,20 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
-
var
|
|
4
|
-
require('../chunk-
|
|
3
|
+
var chunk7UCKV4WA_js = require('../chunk-7UCKV4WA.js');
|
|
4
|
+
require('../chunk-IV7LOJZO.js');
|
|
5
5
|
require('../chunk-2ACKOMAL.js');
|
|
6
|
-
require('../chunk-
|
|
6
|
+
require('../chunk-WLVS4QBK.js');
|
|
7
7
|
require('../chunk-KHPJ3CEL.js');
|
|
8
|
-
require('../chunk-
|
|
9
|
-
require('../chunk-
|
|
10
|
-
require('../chunk-
|
|
8
|
+
require('../chunk-FFQAKIV5.js');
|
|
9
|
+
require('../chunk-KFDFXRBE.js');
|
|
10
|
+
require('../chunk-CBN73TLK.js');
|
|
11
11
|
require('../chunk-SNAQBZPT.js');
|
|
12
12
|
|
|
13
13
|
|
|
14
14
|
|
|
15
15
|
Object.defineProperty(exports, "StaticForm", {
|
|
16
16
|
enumerable: true,
|
|
17
|
-
get: function () { return
|
|
17
|
+
get: function () { return chunk7UCKV4WA_js.StaticForm; }
|
|
18
18
|
});
|
|
19
19
|
//# sourceMappingURL=static.js.map
|
|
20
20
|
//# sourceMappingURL=static.js.map
|
package/dist/forms/static.mjs
CHANGED
|
@@ -1,11 +1,11 @@
|
|
|
1
|
-
export { StaticForm } from '../chunk-
|
|
2
|
-
import '../chunk-
|
|
1
|
+
export { StaticForm } from '../chunk-57IFVXCB.mjs';
|
|
2
|
+
import '../chunk-OO4T5X4Z.mjs';
|
|
3
3
|
import '../chunk-LB7LHVWI.mjs';
|
|
4
|
-
import '../chunk-
|
|
4
|
+
import '../chunk-XXBVF7WN.mjs';
|
|
5
5
|
import '../chunk-TMVKRQGJ.mjs';
|
|
6
|
-
import '../chunk-
|
|
7
|
-
import '../chunk-
|
|
8
|
-
import '../chunk-
|
|
6
|
+
import '../chunk-R6LQRHPQ.mjs';
|
|
7
|
+
import '../chunk-WCIQKO7W.mjs';
|
|
8
|
+
import '../chunk-LS64Y25E.mjs';
|
|
9
9
|
import '../chunk-BEXTDHO4.mjs';
|
|
10
10
|
//# sourceMappingURL=static.mjs.map
|
|
11
11
|
//# sourceMappingURL=static.mjs.map
|
package/dist/images/index.js
CHANGED
|
@@ -1,41 +1,41 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
-
var
|
|
3
|
+
var chunkZ7HAQTWP_js = require('../chunk-Z7HAQTWP.js');
|
|
4
4
|
var chunkGCPPXUAI_js = require('../chunk-GCPPXUAI.js');
|
|
5
|
-
require('../chunk-
|
|
6
|
-
require('../chunk-
|
|
7
|
-
require('../chunk-
|
|
5
|
+
require('../chunk-FFQAKIV5.js');
|
|
6
|
+
require('../chunk-KFDFXRBE.js');
|
|
7
|
+
require('../chunk-CBN73TLK.js');
|
|
8
8
|
require('../chunk-SNAQBZPT.js');
|
|
9
9
|
|
|
10
10
|
|
|
11
11
|
|
|
12
12
|
Object.defineProperty(exports, "ManagedImage", {
|
|
13
13
|
enumerable: true,
|
|
14
|
-
get: function () { return
|
|
14
|
+
get: function () { return chunkZ7HAQTWP_js.ManagedImage; }
|
|
15
15
|
});
|
|
16
16
|
Object.defineProperty(exports, "assignImageToSlot", {
|
|
17
17
|
enumerable: true,
|
|
18
|
-
get: function () { return
|
|
18
|
+
get: function () { return chunkZ7HAQTWP_js.assignImageToSlot; }
|
|
19
19
|
});
|
|
20
20
|
Object.defineProperty(exports, "clearImageSlot", {
|
|
21
21
|
enumerable: true,
|
|
22
|
-
get: function () { return
|
|
22
|
+
get: function () { return chunkZ7HAQTWP_js.clearImageSlot; }
|
|
23
23
|
});
|
|
24
24
|
Object.defineProperty(exports, "fetchManagedImage", {
|
|
25
25
|
enumerable: true,
|
|
26
|
-
get: function () { return
|
|
26
|
+
get: function () { return chunkZ7HAQTWP_js.fetchManagedImage; }
|
|
27
27
|
});
|
|
28
28
|
Object.defineProperty(exports, "fetchManagedImages", {
|
|
29
29
|
enumerable: true,
|
|
30
|
-
get: function () { return
|
|
30
|
+
get: function () { return chunkZ7HAQTWP_js.fetchManagedImages; }
|
|
31
31
|
});
|
|
32
32
|
Object.defineProperty(exports, "listImageFiles", {
|
|
33
33
|
enumerable: true,
|
|
34
|
-
get: function () { return
|
|
34
|
+
get: function () { return chunkZ7HAQTWP_js.listImageFiles; }
|
|
35
35
|
});
|
|
36
36
|
Object.defineProperty(exports, "uploadImage", {
|
|
37
37
|
enumerable: true,
|
|
38
|
-
get: function () { return
|
|
38
|
+
get: function () { return chunkZ7HAQTWP_js.uploadImage; }
|
|
39
39
|
});
|
|
40
40
|
Object.defineProperty(exports, "ManagedFavicon", {
|
|
41
41
|
enumerable: true,
|
package/dist/images/index.mjs
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
|
-
export { ManagedImage, assignImageToSlot, clearImageSlot, fetchManagedImage, fetchManagedImages, listImageFiles, uploadImage } from '../chunk-
|
|
1
|
+
export { ManagedImage, assignImageToSlot, clearImageSlot, fetchManagedImage, fetchManagedImages, listImageFiles, uploadImage } from '../chunk-DSECSIWJ.mjs';
|
|
2
2
|
export { ManagedFavicon, getManagedFaviconUrl } from '../chunk-CU6OGBKK.mjs';
|
|
3
|
-
import '../chunk-
|
|
4
|
-
import '../chunk-
|
|
5
|
-
import '../chunk-
|
|
3
|
+
import '../chunk-R6LQRHPQ.mjs';
|
|
4
|
+
import '../chunk-WCIQKO7W.mjs';
|
|
5
|
+
import '../chunk-LS64Y25E.mjs';
|
|
6
6
|
import '../chunk-BEXTDHO4.mjs';
|
|
7
7
|
//# sourceMappingURL=index.mjs.map
|
|
8
8
|
//# sourceMappingURL=index.mjs.map
|
package/dist/index.js
CHANGED
|
@@ -1,24 +1,25 @@
|
|
|
1
1
|
'use strict';
|
|
2
2
|
|
|
3
|
-
var
|
|
3
|
+
var chunkJA77WXRE_js = require('./chunk-JA77WXRE.js');
|
|
4
|
+
var chunkCIM5W3UO_js = require('./chunk-CIM5W3UO.js');
|
|
4
5
|
var chunkGC3BC6HQ_js = require('./chunk-GC3BC6HQ.js');
|
|
5
|
-
var
|
|
6
|
+
var chunkZ7HAQTWP_js = require('./chunk-Z7HAQTWP.js');
|
|
6
7
|
require('./chunk-GCPPXUAI.js');
|
|
7
8
|
var chunkEHJANA5C_js = require('./chunk-EHJANA5C.js');
|
|
8
9
|
var chunkGSRT66PA_js = require('./chunk-GSRT66PA.js');
|
|
9
|
-
var
|
|
10
|
-
var
|
|
10
|
+
var chunkHLCCE7BD_js = require('./chunk-HLCCE7BD.js');
|
|
11
|
+
var chunkNDASB3X3_js = require('./chunk-NDASB3X3.js');
|
|
11
12
|
require('./chunk-JP5WGL75.js');
|
|
12
|
-
var
|
|
13
|
-
var
|
|
13
|
+
var chunkXOSAVYAI_js = require('./chunk-XOSAVYAI.js');
|
|
14
|
+
var chunkVOMAEC5G_js = require('./chunk-VOMAEC5G.js');
|
|
14
15
|
require('./chunk-EDZWNCSE.js');
|
|
15
|
-
require('./chunk-
|
|
16
|
+
require('./chunk-AVWIKVVE.js');
|
|
16
17
|
require('./chunk-HMFFAUCD.js');
|
|
17
18
|
require('./chunk-RC4WWQXR.js');
|
|
18
19
|
require('./chunk-VJMPIRSD.js');
|
|
19
|
-
var
|
|
20
|
-
require('./chunk-
|
|
21
|
-
require('./chunk-
|
|
20
|
+
var chunkFFQAKIV5_js = require('./chunk-FFQAKIV5.js');
|
|
21
|
+
require('./chunk-KFDFXRBE.js');
|
|
22
|
+
require('./chunk-CBN73TLK.js');
|
|
22
23
|
require('./chunk-SNAQBZPT.js');
|
|
23
24
|
var react = require('react');
|
|
24
25
|
var jsxRuntime = require('react/jsx-runtime');
|
|
@@ -36,7 +37,7 @@ async function apiGet(endpoint) {
|
|
|
36
37
|
return null;
|
|
37
38
|
}
|
|
38
39
|
try {
|
|
39
|
-
const response = await
|
|
40
|
+
const response = await chunkFFQAKIV5_js.sonorFetch(
|
|
40
41
|
`${apiUrl}${endpoint}`,
|
|
41
42
|
{ method: "GET" },
|
|
42
43
|
{ apiKey, retries: 0 }
|
|
@@ -165,11 +166,11 @@ function AffiliatesWidget({
|
|
|
165
166
|
|
|
166
167
|
Object.defineProperty(exports, "LandingPage", {
|
|
167
168
|
enumerable: true,
|
|
168
|
-
get: function () { return
|
|
169
|
+
get: function () { return chunkJA77WXRE_js.LandingPage; }
|
|
169
170
|
});
|
|
170
171
|
Object.defineProperty(exports, "landingPageMetadata", {
|
|
171
172
|
enumerable: true,
|
|
172
|
-
get: function () { return
|
|
173
|
+
get: function () { return chunkCIM5W3UO_js.landingPageMetadata; }
|
|
173
174
|
});
|
|
174
175
|
Object.defineProperty(exports, "clearRedirectCache", {
|
|
175
176
|
enumerable: true,
|
|
@@ -189,31 +190,31 @@ Object.defineProperty(exports, "handleManagedRedirects", {
|
|
|
189
190
|
});
|
|
190
191
|
Object.defineProperty(exports, "ManagedImage", {
|
|
191
192
|
enumerable: true,
|
|
192
|
-
get: function () { return
|
|
193
|
+
get: function () { return chunkZ7HAQTWP_js.ManagedImage; }
|
|
193
194
|
});
|
|
194
195
|
Object.defineProperty(exports, "assignImageToSlot", {
|
|
195
196
|
enumerable: true,
|
|
196
|
-
get: function () { return
|
|
197
|
+
get: function () { return chunkZ7HAQTWP_js.assignImageToSlot; }
|
|
197
198
|
});
|
|
198
199
|
Object.defineProperty(exports, "clearImageSlot", {
|
|
199
200
|
enumerable: true,
|
|
200
|
-
get: function () { return
|
|
201
|
+
get: function () { return chunkZ7HAQTWP_js.clearImageSlot; }
|
|
201
202
|
});
|
|
202
203
|
Object.defineProperty(exports, "fetchManagedImage", {
|
|
203
204
|
enumerable: true,
|
|
204
|
-
get: function () { return
|
|
205
|
+
get: function () { return chunkZ7HAQTWP_js.fetchManagedImage; }
|
|
205
206
|
});
|
|
206
207
|
Object.defineProperty(exports, "fetchManagedImages", {
|
|
207
208
|
enumerable: true,
|
|
208
|
-
get: function () { return
|
|
209
|
+
get: function () { return chunkZ7HAQTWP_js.fetchManagedImages; }
|
|
209
210
|
});
|
|
210
211
|
Object.defineProperty(exports, "listImageFiles", {
|
|
211
212
|
enumerable: true,
|
|
212
|
-
get: function () { return
|
|
213
|
+
get: function () { return chunkZ7HAQTWP_js.listImageFiles; }
|
|
213
214
|
});
|
|
214
215
|
Object.defineProperty(exports, "uploadImage", {
|
|
215
216
|
enumerable: true,
|
|
216
|
-
get: function () { return
|
|
217
|
+
get: function () { return chunkZ7HAQTWP_js.uploadImage; }
|
|
217
218
|
});
|
|
218
219
|
Object.defineProperty(exports, "TestimonialSection", {
|
|
219
220
|
enumerable: true,
|
|
@@ -229,187 +230,187 @@ Object.defineProperty(exports, "fetchReviews", {
|
|
|
229
230
|
});
|
|
230
231
|
Object.defineProperty(exports, "CalendarView", {
|
|
231
232
|
enumerable: true,
|
|
232
|
-
get: function () { return
|
|
233
|
+
get: function () { return chunkHLCCE7BD_js.CalendarView; }
|
|
233
234
|
});
|
|
234
235
|
Object.defineProperty(exports, "CheckoutForm", {
|
|
235
236
|
enumerable: true,
|
|
236
|
-
get: function () { return
|
|
237
|
+
get: function () { return chunkHLCCE7BD_js.CheckoutForm; }
|
|
237
238
|
});
|
|
238
239
|
Object.defineProperty(exports, "EventCalendar", {
|
|
239
240
|
enumerable: true,
|
|
240
|
-
get: function () { return
|
|
241
|
+
get: function () { return chunkHLCCE7BD_js.EventCalendar; }
|
|
241
242
|
});
|
|
242
243
|
Object.defineProperty(exports, "EventCheckout", {
|
|
243
244
|
enumerable: true,
|
|
244
|
-
get: function () { return
|
|
245
|
+
get: function () { return chunkHLCCE7BD_js.EventCheckout; }
|
|
245
246
|
});
|
|
246
247
|
Object.defineProperty(exports, "EventEmbed", {
|
|
247
248
|
enumerable: true,
|
|
248
|
-
get: function () { return
|
|
249
|
+
get: function () { return chunkHLCCE7BD_js.EventEmbed; }
|
|
249
250
|
});
|
|
250
251
|
Object.defineProperty(exports, "EventModal", {
|
|
251
252
|
enumerable: true,
|
|
252
|
-
get: function () { return
|
|
253
|
+
get: function () { return chunkHLCCE7BD_js.EventModal; }
|
|
253
254
|
});
|
|
254
255
|
Object.defineProperty(exports, "EventTile", {
|
|
255
256
|
enumerable: true,
|
|
256
|
-
get: function () { return
|
|
257
|
+
get: function () { return chunkHLCCE7BD_js.EventTile; }
|
|
257
258
|
});
|
|
258
259
|
Object.defineProperty(exports, "OfferingCard", {
|
|
259
260
|
enumerable: true,
|
|
260
|
-
get: function () { return
|
|
261
|
+
get: function () { return chunkHLCCE7BD_js.OfferingCard; }
|
|
261
262
|
});
|
|
262
263
|
Object.defineProperty(exports, "OfferingList", {
|
|
263
264
|
enumerable: true,
|
|
264
|
-
get: function () { return
|
|
265
|
+
get: function () { return chunkHLCCE7BD_js.OfferingList; }
|
|
265
266
|
});
|
|
266
267
|
Object.defineProperty(exports, "ProductEmbed", {
|
|
267
268
|
enumerable: true,
|
|
268
|
-
get: function () { return
|
|
269
|
+
get: function () { return chunkHLCCE7BD_js.ProductEmbed; }
|
|
269
270
|
});
|
|
270
271
|
Object.defineProperty(exports, "RegistrationForm", {
|
|
271
272
|
enumerable: true,
|
|
272
|
-
get: function () { return
|
|
273
|
+
get: function () { return chunkHLCCE7BD_js.RegistrationForm; }
|
|
273
274
|
});
|
|
274
275
|
Object.defineProperty(exports, "UpcomingEvents", {
|
|
275
276
|
enumerable: true,
|
|
276
|
-
get: function () { return
|
|
277
|
+
get: function () { return chunkHLCCE7BD_js.UpcomingEvents; }
|
|
277
278
|
});
|
|
278
279
|
Object.defineProperty(exports, "createCheckoutSession", {
|
|
279
280
|
enumerable: true,
|
|
280
|
-
get: function () { return
|
|
281
|
+
get: function () { return chunkHLCCE7BD_js.createCheckoutSession; }
|
|
281
282
|
});
|
|
282
283
|
Object.defineProperty(exports, "fetchNextEvent", {
|
|
283
284
|
enumerable: true,
|
|
284
|
-
get: function () { return
|
|
285
|
+
get: function () { return chunkHLCCE7BD_js.fetchNextEvent; }
|
|
285
286
|
});
|
|
286
287
|
Object.defineProperty(exports, "fetchOffering", {
|
|
287
288
|
enumerable: true,
|
|
288
|
-
get: function () { return
|
|
289
|
+
get: function () { return chunkHLCCE7BD_js.fetchOffering; }
|
|
289
290
|
});
|
|
290
291
|
Object.defineProperty(exports, "fetchOfferings", {
|
|
291
292
|
enumerable: true,
|
|
292
|
-
get: function () { return
|
|
293
|
+
get: function () { return chunkHLCCE7BD_js.fetchOfferings; }
|
|
293
294
|
});
|
|
294
295
|
Object.defineProperty(exports, "fetchProducts", {
|
|
295
296
|
enumerable: true,
|
|
296
|
-
get: function () { return
|
|
297
|
+
get: function () { return chunkHLCCE7BD_js.fetchProducts; }
|
|
297
298
|
});
|
|
298
299
|
Object.defineProperty(exports, "fetchServices", {
|
|
299
300
|
enumerable: true,
|
|
300
|
-
get: function () { return
|
|
301
|
+
get: function () { return chunkHLCCE7BD_js.fetchServices; }
|
|
301
302
|
});
|
|
302
303
|
Object.defineProperty(exports, "fetchUpcomingEvents", {
|
|
303
304
|
enumerable: true,
|
|
304
|
-
get: function () { return
|
|
305
|
+
get: function () { return chunkHLCCE7BD_js.fetchUpcomingEvents; }
|
|
305
306
|
});
|
|
306
307
|
Object.defineProperty(exports, "formatDate", {
|
|
307
308
|
enumerable: true,
|
|
308
|
-
get: function () { return
|
|
309
|
+
get: function () { return chunkHLCCE7BD_js.formatDate; }
|
|
309
310
|
});
|
|
310
311
|
Object.defineProperty(exports, "formatDateTime", {
|
|
311
312
|
enumerable: true,
|
|
312
|
-
get: function () { return
|
|
313
|
+
get: function () { return chunkHLCCE7BD_js.formatDateTime; }
|
|
313
314
|
});
|
|
314
315
|
Object.defineProperty(exports, "formatPrice", {
|
|
315
316
|
enumerable: true,
|
|
316
|
-
get: function () { return
|
|
317
|
+
get: function () { return chunkHLCCE7BD_js.formatPrice; }
|
|
317
318
|
});
|
|
318
319
|
Object.defineProperty(exports, "getOfferingUrl", {
|
|
319
320
|
enumerable: true,
|
|
320
|
-
get: function () { return
|
|
321
|
+
get: function () { return chunkHLCCE7BD_js.getOfferingUrl; }
|
|
321
322
|
});
|
|
322
323
|
Object.defineProperty(exports, "registerForEvent", {
|
|
323
324
|
enumerable: true,
|
|
324
|
-
get: function () { return
|
|
325
|
+
get: function () { return chunkHLCCE7BD_js.registerForEvent; }
|
|
325
326
|
});
|
|
326
327
|
Object.defineProperty(exports, "useEventModal", {
|
|
327
328
|
enumerable: true,
|
|
328
|
-
get: function () { return
|
|
329
|
+
get: function () { return chunkHLCCE7BD_js.useEventModal; }
|
|
329
330
|
});
|
|
330
331
|
Object.defineProperty(exports, "BookingWidget", {
|
|
331
332
|
enumerable: true,
|
|
332
|
-
get: function () { return
|
|
333
|
+
get: function () { return chunkNDASB3X3_js.BookingWidget; }
|
|
333
334
|
});
|
|
334
335
|
Object.defineProperty(exports, "createBooking", {
|
|
335
336
|
enumerable: true,
|
|
336
|
-
get: function () { return
|
|
337
|
+
get: function () { return chunkNDASB3X3_js.createBooking; }
|
|
337
338
|
});
|
|
338
339
|
Object.defineProperty(exports, "createSlotHold", {
|
|
339
340
|
enumerable: true,
|
|
340
|
-
get: function () { return
|
|
341
|
+
get: function () { return chunkNDASB3X3_js.createSlotHold; }
|
|
341
342
|
});
|
|
342
343
|
Object.defineProperty(exports, "detectTimezone", {
|
|
343
344
|
enumerable: true,
|
|
344
|
-
get: function () { return
|
|
345
|
+
get: function () { return chunkNDASB3X3_js.detectTimezone; }
|
|
345
346
|
});
|
|
346
347
|
Object.defineProperty(exports, "fetchAvailability", {
|
|
347
348
|
enumerable: true,
|
|
348
|
-
get: function () { return
|
|
349
|
+
get: function () { return chunkNDASB3X3_js.fetchAvailability; }
|
|
349
350
|
});
|
|
350
351
|
Object.defineProperty(exports, "fetchAvailableDates", {
|
|
351
352
|
enumerable: true,
|
|
352
|
-
get: function () { return
|
|
353
|
+
get: function () { return chunkNDASB3X3_js.fetchAvailableDates; }
|
|
353
354
|
});
|
|
354
355
|
Object.defineProperty(exports, "fetchBookingTypeDetails", {
|
|
355
356
|
enumerable: true,
|
|
356
|
-
get: function () { return
|
|
357
|
+
get: function () { return chunkNDASB3X3_js.fetchBookingTypeDetails; }
|
|
357
358
|
});
|
|
358
359
|
Object.defineProperty(exports, "fetchBookingTypes", {
|
|
359
360
|
enumerable: true,
|
|
360
|
-
get: function () { return
|
|
361
|
+
get: function () { return chunkNDASB3X3_js.fetchBookingTypes; }
|
|
361
362
|
});
|
|
362
363
|
Object.defineProperty(exports, "formatBookingDate", {
|
|
363
364
|
enumerable: true,
|
|
364
|
-
get: function () { return
|
|
365
|
+
get: function () { return chunkNDASB3X3_js.formatDate; }
|
|
365
366
|
});
|
|
366
367
|
Object.defineProperty(exports, "formatBookingTime", {
|
|
367
368
|
enumerable: true,
|
|
368
|
-
get: function () { return
|
|
369
|
+
get: function () { return chunkNDASB3X3_js.formatTime; }
|
|
369
370
|
});
|
|
370
371
|
Object.defineProperty(exports, "formatDuration", {
|
|
371
372
|
enumerable: true,
|
|
372
|
-
get: function () { return
|
|
373
|
+
get: function () { return chunkNDASB3X3_js.formatDuration; }
|
|
373
374
|
});
|
|
374
375
|
Object.defineProperty(exports, "releaseSlotHold", {
|
|
375
376
|
enumerable: true,
|
|
376
|
-
get: function () { return
|
|
377
|
+
get: function () { return chunkNDASB3X3_js.releaseSlotHold; }
|
|
377
378
|
});
|
|
378
379
|
Object.defineProperty(exports, "ExperimentConversion", {
|
|
379
380
|
enumerable: true,
|
|
380
|
-
get: function () { return
|
|
381
|
+
get: function () { return chunkXOSAVYAI_js.ExperimentConversion; }
|
|
381
382
|
});
|
|
382
383
|
Object.defineProperty(exports, "SignalExperiment", {
|
|
383
384
|
enumerable: true,
|
|
384
|
-
get: function () { return
|
|
385
|
+
get: function () { return chunkXOSAVYAI_js.SignalExperiment; }
|
|
385
386
|
});
|
|
386
387
|
Object.defineProperty(exports, "useExperimentVariant", {
|
|
387
388
|
enumerable: true,
|
|
388
|
-
get: function () { return
|
|
389
|
+
get: function () { return chunkXOSAVYAI_js.useExperimentVariant; }
|
|
389
390
|
});
|
|
390
391
|
Object.defineProperty(exports, "SignalBridge", {
|
|
391
392
|
enumerable: true,
|
|
392
|
-
get: function () { return
|
|
393
|
+
get: function () { return chunkVOMAEC5G_js.SignalBridge; }
|
|
393
394
|
});
|
|
394
395
|
Object.defineProperty(exports, "useSignal", {
|
|
395
396
|
enumerable: true,
|
|
396
|
-
get: function () { return
|
|
397
|
+
get: function () { return chunkVOMAEC5G_js.useSignal; }
|
|
397
398
|
});
|
|
398
399
|
Object.defineProperty(exports, "useSignalConfig", {
|
|
399
400
|
enumerable: true,
|
|
400
|
-
get: function () { return
|
|
401
|
+
get: function () { return chunkVOMAEC5G_js.useSignalConfig; }
|
|
401
402
|
});
|
|
402
403
|
Object.defineProperty(exports, "useSignalEvent", {
|
|
403
404
|
enumerable: true,
|
|
404
|
-
get: function () { return
|
|
405
|
+
get: function () { return chunkVOMAEC5G_js.useSignalEvent; }
|
|
405
406
|
});
|
|
406
407
|
Object.defineProperty(exports, "useSignalExperiment", {
|
|
407
408
|
enumerable: true,
|
|
408
|
-
get: function () { return
|
|
409
|
+
get: function () { return chunkVOMAEC5G_js.useSignalExperiment; }
|
|
409
410
|
});
|
|
410
411
|
Object.defineProperty(exports, "useSignalOutcome", {
|
|
411
412
|
enumerable: true,
|
|
412
|
-
get: function () { return
|
|
413
|
+
get: function () { return chunkVOMAEC5G_js.useSignalOutcome; }
|
|
413
414
|
});
|
|
414
415
|
exports.AffiliateCard = AffiliateCard;
|
|
415
416
|
exports.AffiliatesWidget = AffiliatesWidget;
|
package/dist/index.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/affiliates/api.ts","../src/affiliates/useAffiliates.ts","../src/affiliates/AffiliatesWidget.tsx"],"names":["sonorFetch","useState","useEffect","getTrackingUrl","jsx"],"mappings":"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","file":"index.js","sourcesContent":["/**\n * @sonordev/site-kit/affiliates - Affiliates API\n * \n * API functions for fetching affiliate data for client sites.\n * All data goes through Portal API with API key auth - never Supabase directly.\n */\n\nimport { sonorFetch } from '../shared/sonorFetch'\nimport type { Affiliate, AffiliateWithOffers, FetchAffiliatesOptions } from './types'\n\n// ============================================\n// API Config Helpers\n// ============================================\n\nfunction getApiConfig() {\n const apiUrl = typeof window !== 'undefined' \n ? (window as any).__SITE_KIT_API_URL__ || 'https://api.sonor.io'\n : 'https://api.sonor.io'\n const apiKey = typeof window !== 'undefined' \n ? (window as any).__SITE_KIT_API_KEY__ || ''\n : ''\n return { apiUrl, apiKey }\n}\n\nasync function apiGet<T>(endpoint: string): Promise<T | null> {\n const { apiUrl, apiKey } = getApiConfig()\n \n if (!apiKey) {\n console.error('[Affiliates] No API key configured')\n return null\n }\n \n try {\n // Route through sonorFetch (the canonical transport) — NOT bare fetch — so a\n // stale build-time seed token is transparently refreshed and a 401 triggers\n // one refresh+retry. The credential goes via options.apiKey, never a header:\n // sonorFetch injects the freshest token as x-api-key; a hand-set header would\n // pin the stale seed and 401.\n const response = await sonorFetch(\n `${apiUrl}${endpoint}`,\n { method: 'GET' },\n { apiKey, retries: 0 },\n )\n\n if (!response.ok) {\n console.error(`[Affiliates] API error: ${response.statusText}`)\n return null\n }\n \n return await response.json()\n } catch (error) {\n console.error('[Affiliates] Network error:', error)\n return null\n }\n}\n\n// ============================================\n// Fetch Affiliates\n// ============================================\n\n/**\n * Fetch all active affiliates for the project\n * \n * @example\n * ```ts\n * const affiliates = await fetchAffiliates()\n * ```\n */\nexport async function fetchAffiliates(\n options: FetchAffiliatesOptions = {}\n): Promise<AffiliateWithOffers[]> {\n const result = await apiGet<{ affiliates: AffiliateWithOffers[] }>(\n '/api/public/affiliates'\n )\n \n return result?.affiliates || []\n}\n\n/**\n * Build a tracking URL for an affiliate offer\n * When clicked, this redirects through our tracking endpoint and then to the destination\n * \n * @example\n * ```ts\n * const trackingUrl = getTrackingUrl(affiliate.id, offer.id)\n * // Returns: https://api.sonor.io/a/{affiliateId}/{offerId}\n * ```\n */\nexport function getTrackingUrl(affiliateId: string, offerId: string): string {\n const { apiUrl } = getApiConfig()\n return `${apiUrl}/a/${affiliateId}/${offerId}`\n}\n","/**\n * @sonordev/site-kit/affiliates - useAffiliates Hook\n * \n * React hook for fetching and displaying affiliates on client sites.\n */\n\n'use client'\n\nimport { useState, useEffect } from 'react'\nimport type { AffiliateWithOffers } from './types'\nimport { fetchAffiliates, getTrackingUrl } from './api'\n\nexport interface UseAffiliatesResult {\n affiliates: AffiliateWithOffers[]\n isLoading: boolean\n error: string | null\n getTrackingUrl: (affiliateId: string, offerId: string) => string\n}\n\n/**\n * Hook to fetch affiliates for display on client sites\n * \n * @example\n * ```tsx\n * function AffiliatesSection() {\n * const { affiliates, isLoading } = useAffiliates()\n * \n * if (isLoading) return <div>Loading...</div>\n * \n * return (\n * <div className=\"grid grid-cols-3 gap-4\">\n * {affiliates.map(affiliate => (\n * <AffiliateCard key={affiliate.id} affiliate={affiliate} />\n * ))}\n * </div>\n * )\n * }\n * ```\n */\nexport function useAffiliates(): UseAffiliatesResult {\n const [affiliates, setAffiliates] = useState<AffiliateWithOffers[]>([])\n const [isLoading, setIsLoading] = useState(true)\n const [error, setError] = useState<string | null>(null)\n\n useEffect(() => {\n async function load() {\n try {\n setIsLoading(true)\n setError(null)\n const data = await fetchAffiliates()\n setAffiliates(data)\n } catch (err) {\n setError(err instanceof Error ? err.message : 'Failed to load affiliates')\n } finally {\n setIsLoading(false)\n }\n }\n \n load()\n }, [])\n\n return {\n affiliates,\n isLoading,\n error,\n getTrackingUrl,\n }\n}\n","/**\n * @sonordev/site-kit/affiliates - AffiliatesWidget Component\n * \n * Unstyled, headless component for displaying affiliates.\n * Client sites can wrap this or use it directly with their own styling.\n */\n\n'use client'\n\nimport React from 'react'\nimport { useAffiliates } from './useAffiliates'\nimport type { AffiliateWithOffers, AffiliateOffer } from './types'\n\n// ============================================\n// Affiliate Card (Unstyled)\n// ============================================\n\nexport interface AffiliateCardProps {\n affiliate: AffiliateWithOffers\n className?: string\n /** Optional custom render for the logo */\n renderLogo?: (affiliate: AffiliateWithOffers) => React.ReactNode\n /** Show offers as links below the card */\n showOffers?: boolean\n}\n\n/**\n * Single affiliate card - unstyled, bring your own CSS\n * \n * @example\n * ```tsx\n * <AffiliateCard \n * affiliate={affiliate}\n * className=\"p-4 bg-white rounded-lg shadow\"\n * showOffers\n * />\n * ```\n */\nexport function AffiliateCard({\n affiliate,\n className = '',\n renderLogo,\n showOffers = false,\n}: AffiliateCardProps) {\n const { getTrackingUrl } = useAffiliates()\n \n const defaultLogo = (\n <div data-affiliate-logo className=\"affiliate-logo\">\n {affiliate.logo_url ? (\n <img \n src={affiliate.logo_url} \n alt={affiliate.name}\n loading=\"lazy\"\n />\n ) : (\n <span>{affiliate.name.charAt(0)}</span>\n )}\n </div>\n )\n\n return (\n <div className={className} data-affiliate-card data-affiliate-id={affiliate.id}>\n {/* Logo */}\n {renderLogo ? renderLogo(affiliate) : defaultLogo}\n \n {/* Name */}\n <div data-affiliate-name className=\"affiliate-name\">\n {affiliate.name}\n </div>\n \n {/* Website link */}\n {affiliate.website_url && (\n <a \n href={affiliate.website_url}\n target=\"_blank\"\n rel=\"noopener noreferrer sponsored\"\n data-affiliate-website\n className=\"affiliate-website\"\n >\n Visit Website\n </a>\n )}\n \n {/* Offers */}\n {showOffers && affiliate.offers && affiliate.offers.length > 0 && (\n <div data-affiliate-offers className=\"affiliate-offers\">\n {affiliate.offers.map(offer => (\n <a\n key={offer.id}\n href={getTrackingUrl(affiliate.id, offer.id)}\n target=\"_blank\"\n rel=\"noopener noreferrer sponsored\"\n data-affiliate-offer\n data-offer-id={offer.id}\n className=\"affiliate-offer\"\n >\n {offer.name}\n </a>\n ))}\n </div>\n )}\n </div>\n )\n}\n\n// ============================================\n// Affiliates Grid (Unstyled)\n// ============================================\n\nexport interface AffiliatesWidgetProps {\n className?: string\n /** Custom loading component */\n loadingComponent?: React.ReactNode\n /** Custom empty state component */\n emptyComponent?: React.ReactNode\n /** Custom error component */\n errorComponent?: React.ReactNode\n /** Show offers on each card */\n showOffers?: boolean\n /** Custom render function for each affiliate */\n renderAffiliate?: (affiliate: AffiliateWithOffers) => React.ReactNode\n /** Maximum number to display */\n limit?: number\n}\n\n/**\n * Display a grid of affiliates - unstyled, bring your own CSS\n * \n * @example\n * ```tsx\n * // Basic usage\n * <AffiliatesWidget className=\"grid grid-cols-3 gap-4\" />\n * \n * // With custom rendering\n * <AffiliatesWidget\n * renderAffiliate={(affiliate) => (\n * <MyCustomCard key={affiliate.id} data={affiliate} />\n * )}\n * />\n * ```\n */\nexport function AffiliatesWidget({\n className = '',\n loadingComponent,\n emptyComponent,\n errorComponent,\n showOffers = false,\n renderAffiliate,\n limit,\n}: AffiliatesWidgetProps) {\n const { affiliates, isLoading, error, getTrackingUrl } = useAffiliates()\n \n if (isLoading) {\n return loadingComponent || <div data-affiliates-loading>Loading affiliates...</div>\n }\n \n if (error) {\n return errorComponent || <div data-affiliates-error>{error}</div>\n }\n \n const displayAffiliates = limit ? affiliates.slice(0, limit) : affiliates\n \n if (displayAffiliates.length === 0) {\n return emptyComponent || null\n }\n \n return (\n <div className={className} data-affiliates-widget>\n {displayAffiliates.map(affiliate => \n renderAffiliate \n ? renderAffiliate(affiliate)\n : <AffiliateCard \n key={affiliate.id} \n affiliate={affiliate} \n showOffers={showOffers}\n />\n )}\n </div>\n )\n}\n"]}
|
|
1
|
+
{"version":3,"sources":["../src/affiliates/api.ts","../src/affiliates/useAffiliates.ts","../src/affiliates/AffiliatesWidget.tsx"],"names":["sonorFetch","useState","useEffect","getTrackingUrl","jsx"],"mappings":"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","file":"index.js","sourcesContent":["/**\n * @sonordev/site-kit/affiliates - Affiliates API\n * \n * API functions for fetching affiliate data for client sites.\n * All data goes through Portal API with API key auth - never Supabase directly.\n */\n\nimport { sonorFetch } from '../shared/sonorFetch'\nimport type { Affiliate, AffiliateWithOffers, FetchAffiliatesOptions } from './types'\n\n// ============================================\n// API Config Helpers\n// ============================================\n\nfunction getApiConfig() {\n const apiUrl = typeof window !== 'undefined' \n ? (window as any).__SITE_KIT_API_URL__ || 'https://api.sonor.io'\n : 'https://api.sonor.io'\n const apiKey = typeof window !== 'undefined' \n ? (window as any).__SITE_KIT_API_KEY__ || ''\n : ''\n return { apiUrl, apiKey }\n}\n\nasync function apiGet<T>(endpoint: string): Promise<T | null> {\n const { apiUrl, apiKey } = getApiConfig()\n \n if (!apiKey) {\n console.error('[Affiliates] No API key configured')\n return null\n }\n \n try {\n // Route through sonorFetch (the canonical transport) — NOT bare fetch — so a\n // stale build-time seed token is transparently refreshed and a 401 triggers\n // one refresh+retry. The credential goes via options.apiKey, never a header:\n // sonorFetch injects the freshest token as x-api-key; a hand-set header would\n // pin the stale seed and 401.\n const response = await sonorFetch(\n `${apiUrl}${endpoint}`,\n { method: 'GET' },\n { apiKey, retries: 0 },\n )\n\n if (!response.ok) {\n console.error(`[Affiliates] API error: ${response.statusText}`)\n return null\n }\n \n return await response.json()\n } catch (error) {\n console.error('[Affiliates] Network error:', error)\n return null\n }\n}\n\n// ============================================\n// Fetch Affiliates\n// ============================================\n\n/**\n * Fetch all active affiliates for the project\n * \n * @example\n * ```ts\n * const affiliates = await fetchAffiliates()\n * ```\n */\nexport async function fetchAffiliates(\n options: FetchAffiliatesOptions = {}\n): Promise<AffiliateWithOffers[]> {\n const result = await apiGet<{ affiliates: AffiliateWithOffers[] }>(\n '/api/public/affiliates'\n )\n \n return result?.affiliates || []\n}\n\n/**\n * Build a tracking URL for an affiliate offer\n * When clicked, this redirects through our tracking endpoint and then to the destination\n * \n * @example\n * ```ts\n * const trackingUrl = getTrackingUrl(affiliate.id, offer.id)\n * // Returns: https://api.sonor.io/a/{affiliateId}/{offerId}\n * ```\n */\nexport function getTrackingUrl(affiliateId: string, offerId: string): string {\n const { apiUrl } = getApiConfig()\n return `${apiUrl}/a/${affiliateId}/${offerId}`\n}\n","/**\n * @sonordev/site-kit/affiliates - useAffiliates Hook\n * \n * React hook for fetching and displaying affiliates on client sites.\n */\n\n'use client'\n\nimport { useState, useEffect } from 'react'\nimport type { AffiliateWithOffers } from './types'\nimport { fetchAffiliates, getTrackingUrl } from './api'\n\nexport interface UseAffiliatesResult {\n affiliates: AffiliateWithOffers[]\n isLoading: boolean\n error: string | null\n getTrackingUrl: (affiliateId: string, offerId: string) => string\n}\n\n/**\n * Hook to fetch affiliates for display on client sites\n * \n * @example\n * ```tsx\n * function AffiliatesSection() {\n * const { affiliates, isLoading } = useAffiliates()\n * \n * if (isLoading) return <div>Loading...</div>\n * \n * return (\n * <div className=\"grid grid-cols-3 gap-4\">\n * {affiliates.map(affiliate => (\n * <AffiliateCard key={affiliate.id} affiliate={affiliate} />\n * ))}\n * </div>\n * )\n * }\n * ```\n */\nexport function useAffiliates(): UseAffiliatesResult {\n const [affiliates, setAffiliates] = useState<AffiliateWithOffers[]>([])\n const [isLoading, setIsLoading] = useState(true)\n const [error, setError] = useState<string | null>(null)\n\n useEffect(() => {\n async function load() {\n try {\n setIsLoading(true)\n setError(null)\n const data = await fetchAffiliates()\n setAffiliates(data)\n } catch (err) {\n setError(err instanceof Error ? err.message : 'Failed to load affiliates')\n } finally {\n setIsLoading(false)\n }\n }\n \n load()\n }, [])\n\n return {\n affiliates,\n isLoading,\n error,\n getTrackingUrl,\n }\n}\n","/**\n * @sonordev/site-kit/affiliates - AffiliatesWidget Component\n * \n * Unstyled, headless component for displaying affiliates.\n * Client sites can wrap this or use it directly with their own styling.\n */\n\n'use client'\n\nimport React from 'react'\nimport { useAffiliates } from './useAffiliates'\nimport type { AffiliateWithOffers, AffiliateOffer } from './types'\n\n// ============================================\n// Affiliate Card (Unstyled)\n// ============================================\n\nexport interface AffiliateCardProps {\n affiliate: AffiliateWithOffers\n className?: string\n /** Optional custom render for the logo */\n renderLogo?: (affiliate: AffiliateWithOffers) => React.ReactNode\n /** Show offers as links below the card */\n showOffers?: boolean\n}\n\n/**\n * Single affiliate card - unstyled, bring your own CSS\n * \n * @example\n * ```tsx\n * <AffiliateCard \n * affiliate={affiliate}\n * className=\"p-4 bg-white rounded-lg shadow\"\n * showOffers\n * />\n * ```\n */\nexport function AffiliateCard({\n affiliate,\n className = '',\n renderLogo,\n showOffers = false,\n}: AffiliateCardProps) {\n const { getTrackingUrl } = useAffiliates()\n \n const defaultLogo = (\n <div data-affiliate-logo className=\"affiliate-logo\">\n {affiliate.logo_url ? (\n <img \n src={affiliate.logo_url} \n alt={affiliate.name}\n loading=\"lazy\"\n />\n ) : (\n <span>{affiliate.name.charAt(0)}</span>\n )}\n </div>\n )\n\n return (\n <div className={className} data-affiliate-card data-affiliate-id={affiliate.id}>\n {/* Logo */}\n {renderLogo ? renderLogo(affiliate) : defaultLogo}\n \n {/* Name */}\n <div data-affiliate-name className=\"affiliate-name\">\n {affiliate.name}\n </div>\n \n {/* Website link */}\n {affiliate.website_url && (\n <a \n href={affiliate.website_url}\n target=\"_blank\"\n rel=\"noopener noreferrer sponsored\"\n data-affiliate-website\n className=\"affiliate-website\"\n >\n Visit Website\n </a>\n )}\n \n {/* Offers */}\n {showOffers && affiliate.offers && affiliate.offers.length > 0 && (\n <div data-affiliate-offers className=\"affiliate-offers\">\n {affiliate.offers.map(offer => (\n <a\n key={offer.id}\n href={getTrackingUrl(affiliate.id, offer.id)}\n target=\"_blank\"\n rel=\"noopener noreferrer sponsored\"\n data-affiliate-offer\n data-offer-id={offer.id}\n className=\"affiliate-offer\"\n >\n {offer.name}\n </a>\n ))}\n </div>\n )}\n </div>\n )\n}\n\n// ============================================\n// Affiliates Grid (Unstyled)\n// ============================================\n\nexport interface AffiliatesWidgetProps {\n className?: string\n /** Custom loading component */\n loadingComponent?: React.ReactNode\n /** Custom empty state component */\n emptyComponent?: React.ReactNode\n /** Custom error component */\n errorComponent?: React.ReactNode\n /** Show offers on each card */\n showOffers?: boolean\n /** Custom render function for each affiliate */\n renderAffiliate?: (affiliate: AffiliateWithOffers) => React.ReactNode\n /** Maximum number to display */\n limit?: number\n}\n\n/**\n * Display a grid of affiliates - unstyled, bring your own CSS\n * \n * @example\n * ```tsx\n * // Basic usage\n * <AffiliatesWidget className=\"grid grid-cols-3 gap-4\" />\n * \n * // With custom rendering\n * <AffiliatesWidget\n * renderAffiliate={(affiliate) => (\n * <MyCustomCard key={affiliate.id} data={affiliate} />\n * )}\n * />\n * ```\n */\nexport function AffiliatesWidget({\n className = '',\n loadingComponent,\n emptyComponent,\n errorComponent,\n showOffers = false,\n renderAffiliate,\n limit,\n}: AffiliatesWidgetProps) {\n const { affiliates, isLoading, error, getTrackingUrl } = useAffiliates()\n \n if (isLoading) {\n return loadingComponent || <div data-affiliates-loading>Loading affiliates...</div>\n }\n \n if (error) {\n return errorComponent || <div data-affiliates-error>{error}</div>\n }\n \n const displayAffiliates = limit ? affiliates.slice(0, limit) : affiliates\n \n if (displayAffiliates.length === 0) {\n return emptyComponent || null\n }\n \n return (\n <div className={className} data-affiliates-widget>\n {displayAffiliates.map(affiliate => \n renderAffiliate \n ? renderAffiliate(affiliate)\n : <AffiliateCard \n key={affiliate.id} \n affiliate={affiliate} \n showOffers={showOffers}\n />\n )}\n </div>\n )\n}\n"]}
|
package/dist/index.mjs
CHANGED
|
@@ -1,22 +1,23 @@
|
|
|
1
|
-
export { LandingPage
|
|
1
|
+
export { LandingPage } from './chunk-QZF5NTXQ.mjs';
|
|
2
|
+
export { landingPageMetadata } from './chunk-AAZNH3MA.mjs';
|
|
2
3
|
export { clearRedirectCache, fetchRedirectRules, generateNextRedirects, handleManagedRedirects } from './chunk-KRARQ2ZF.mjs';
|
|
3
|
-
export { ManagedImage, assignImageToSlot, clearImageSlot, fetchManagedImage, fetchManagedImages, listImageFiles, uploadImage } from './chunk-
|
|
4
|
+
export { ManagedImage, assignImageToSlot, clearImageSlot, fetchManagedImage, fetchManagedImages, listImageFiles, uploadImage } from './chunk-DSECSIWJ.mjs';
|
|
4
5
|
import './chunk-CU6OGBKK.mjs';
|
|
5
6
|
export { TestimonialSection } from './chunk-VIGRGMWR.mjs';
|
|
6
7
|
export { fetchReviewStats, fetchReviews } from './chunk-MU7DTEUF.mjs';
|
|
7
|
-
export { CalendarView, CheckoutForm, EventCalendar, EventCheckout, EventEmbed, EventModal, EventTile, OfferingCard, OfferingList, ProductEmbed, RegistrationForm, UpcomingEvents, createCheckoutSession, fetchNextEvent, fetchOffering, fetchOfferings, fetchProducts, fetchServices, fetchUpcomingEvents, formatDate, formatDateTime, formatPrice, getOfferingUrl, registerForEvent, useEventModal } from './chunk-
|
|
8
|
-
export { BookingWidget, createBooking, createSlotHold, detectTimezone, fetchAvailability, fetchAvailableDates, fetchBookingTypeDetails, fetchBookingTypes, formatDate as formatBookingDate, formatTime as formatBookingTime, formatDuration, releaseSlotHold } from './chunk-
|
|
8
|
+
export { CalendarView, CheckoutForm, EventCalendar, EventCheckout, EventEmbed, EventModal, EventTile, OfferingCard, OfferingList, ProductEmbed, RegistrationForm, UpcomingEvents, createCheckoutSession, fetchNextEvent, fetchOffering, fetchOfferings, fetchProducts, fetchServices, fetchUpcomingEvents, formatDate, formatDateTime, formatPrice, getOfferingUrl, registerForEvent, useEventModal } from './chunk-DYDAV4Y4.mjs';
|
|
9
|
+
export { BookingWidget, createBooking, createSlotHold, detectTimezone, fetchAvailability, fetchAvailableDates, fetchBookingTypeDetails, fetchBookingTypes, formatDate as formatBookingDate, formatTime as formatBookingTime, formatDuration, releaseSlotHold } from './chunk-SDBUPTF4.mjs';
|
|
9
10
|
import './chunk-B22WSN4L.mjs';
|
|
10
|
-
export { ExperimentConversion, SignalExperiment, useExperimentVariant } from './chunk-
|
|
11
|
-
export { SignalBridge, useSignal, useSignalConfig, useSignalEvent, useSignalExperiment, useSignalOutcome } from './chunk-
|
|
11
|
+
export { ExperimentConversion, SignalExperiment, useExperimentVariant } from './chunk-DNEUGYTE.mjs';
|
|
12
|
+
export { SignalBridge, useSignal, useSignalConfig, useSignalEvent, useSignalExperiment, useSignalOutcome } from './chunk-XZCZCND2.mjs';
|
|
12
13
|
import './chunk-26JXNW7B.mjs';
|
|
13
|
-
import './chunk-
|
|
14
|
+
import './chunk-4HNFMOYE.mjs';
|
|
14
15
|
import './chunk-3DPXOZAU.mjs';
|
|
15
16
|
import './chunk-ZZQAGCSI.mjs';
|
|
16
17
|
import './chunk-6EDVCUAG.mjs';
|
|
17
|
-
import { sonorFetch } from './chunk-
|
|
18
|
-
import './chunk-
|
|
19
|
-
import './chunk-
|
|
18
|
+
import { sonorFetch } from './chunk-R6LQRHPQ.mjs';
|
|
19
|
+
import './chunk-WCIQKO7W.mjs';
|
|
20
|
+
import './chunk-LS64Y25E.mjs';
|
|
20
21
|
import './chunk-BEXTDHO4.mjs';
|
|
21
22
|
import { useState, useEffect } from 'react';
|
|
22
23
|
import { jsx, jsxs } from 'react/jsx-runtime';
|
package/dist/index.mjs.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/affiliates/api.ts","../src/affiliates/useAffiliates.ts","../src/affiliates/AffiliatesWidget.tsx"],"names":["getTrackingUrl"],"mappings":"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","file":"index.mjs","sourcesContent":["/**\n * @sonordev/site-kit/affiliates - Affiliates API\n * \n * API functions for fetching affiliate data for client sites.\n * All data goes through Portal API with API key auth - never Supabase directly.\n */\n\nimport { sonorFetch } from '../shared/sonorFetch'\nimport type { Affiliate, AffiliateWithOffers, FetchAffiliatesOptions } from './types'\n\n// ============================================\n// API Config Helpers\n// ============================================\n\nfunction getApiConfig() {\n const apiUrl = typeof window !== 'undefined' \n ? (window as any).__SITE_KIT_API_URL__ || 'https://api.sonor.io'\n : 'https://api.sonor.io'\n const apiKey = typeof window !== 'undefined' \n ? (window as any).__SITE_KIT_API_KEY__ || ''\n : ''\n return { apiUrl, apiKey }\n}\n\nasync function apiGet<T>(endpoint: string): Promise<T | null> {\n const { apiUrl, apiKey } = getApiConfig()\n \n if (!apiKey) {\n console.error('[Affiliates] No API key configured')\n return null\n }\n \n try {\n // Route through sonorFetch (the canonical transport) — NOT bare fetch — so a\n // stale build-time seed token is transparently refreshed and a 401 triggers\n // one refresh+retry. The credential goes via options.apiKey, never a header:\n // sonorFetch injects the freshest token as x-api-key; a hand-set header would\n // pin the stale seed and 401.\n const response = await sonorFetch(\n `${apiUrl}${endpoint}`,\n { method: 'GET' },\n { apiKey, retries: 0 },\n )\n\n if (!response.ok) {\n console.error(`[Affiliates] API error: ${response.statusText}`)\n return null\n }\n \n return await response.json()\n } catch (error) {\n console.error('[Affiliates] Network error:', error)\n return null\n }\n}\n\n// ============================================\n// Fetch Affiliates\n// ============================================\n\n/**\n * Fetch all active affiliates for the project\n * \n * @example\n * ```ts\n * const affiliates = await fetchAffiliates()\n * ```\n */\nexport async function fetchAffiliates(\n options: FetchAffiliatesOptions = {}\n): Promise<AffiliateWithOffers[]> {\n const result = await apiGet<{ affiliates: AffiliateWithOffers[] }>(\n '/api/public/affiliates'\n )\n \n return result?.affiliates || []\n}\n\n/**\n * Build a tracking URL for an affiliate offer\n * When clicked, this redirects through our tracking endpoint and then to the destination\n * \n * @example\n * ```ts\n * const trackingUrl = getTrackingUrl(affiliate.id, offer.id)\n * // Returns: https://api.sonor.io/a/{affiliateId}/{offerId}\n * ```\n */\nexport function getTrackingUrl(affiliateId: string, offerId: string): string {\n const { apiUrl } = getApiConfig()\n return `${apiUrl}/a/${affiliateId}/${offerId}`\n}\n","/**\n * @sonordev/site-kit/affiliates - useAffiliates Hook\n * \n * React hook for fetching and displaying affiliates on client sites.\n */\n\n'use client'\n\nimport { useState, useEffect } from 'react'\nimport type { AffiliateWithOffers } from './types'\nimport { fetchAffiliates, getTrackingUrl } from './api'\n\nexport interface UseAffiliatesResult {\n affiliates: AffiliateWithOffers[]\n isLoading: boolean\n error: string | null\n getTrackingUrl: (affiliateId: string, offerId: string) => string\n}\n\n/**\n * Hook to fetch affiliates for display on client sites\n * \n * @example\n * ```tsx\n * function AffiliatesSection() {\n * const { affiliates, isLoading } = useAffiliates()\n * \n * if (isLoading) return <div>Loading...</div>\n * \n * return (\n * <div className=\"grid grid-cols-3 gap-4\">\n * {affiliates.map(affiliate => (\n * <AffiliateCard key={affiliate.id} affiliate={affiliate} />\n * ))}\n * </div>\n * )\n * }\n * ```\n */\nexport function useAffiliates(): UseAffiliatesResult {\n const [affiliates, setAffiliates] = useState<AffiliateWithOffers[]>([])\n const [isLoading, setIsLoading] = useState(true)\n const [error, setError] = useState<string | null>(null)\n\n useEffect(() => {\n async function load() {\n try {\n setIsLoading(true)\n setError(null)\n const data = await fetchAffiliates()\n setAffiliates(data)\n } catch (err) {\n setError(err instanceof Error ? err.message : 'Failed to load affiliates')\n } finally {\n setIsLoading(false)\n }\n }\n \n load()\n }, [])\n\n return {\n affiliates,\n isLoading,\n error,\n getTrackingUrl,\n }\n}\n","/**\n * @sonordev/site-kit/affiliates - AffiliatesWidget Component\n * \n * Unstyled, headless component for displaying affiliates.\n * Client sites can wrap this or use it directly with their own styling.\n */\n\n'use client'\n\nimport React from 'react'\nimport { useAffiliates } from './useAffiliates'\nimport type { AffiliateWithOffers, AffiliateOffer } from './types'\n\n// ============================================\n// Affiliate Card (Unstyled)\n// ============================================\n\nexport interface AffiliateCardProps {\n affiliate: AffiliateWithOffers\n className?: string\n /** Optional custom render for the logo */\n renderLogo?: (affiliate: AffiliateWithOffers) => React.ReactNode\n /** Show offers as links below the card */\n showOffers?: boolean\n}\n\n/**\n * Single affiliate card - unstyled, bring your own CSS\n * \n * @example\n * ```tsx\n * <AffiliateCard \n * affiliate={affiliate}\n * className=\"p-4 bg-white rounded-lg shadow\"\n * showOffers\n * />\n * ```\n */\nexport function AffiliateCard({\n affiliate,\n className = '',\n renderLogo,\n showOffers = false,\n}: AffiliateCardProps) {\n const { getTrackingUrl } = useAffiliates()\n \n const defaultLogo = (\n <div data-affiliate-logo className=\"affiliate-logo\">\n {affiliate.logo_url ? (\n <img \n src={affiliate.logo_url} \n alt={affiliate.name}\n loading=\"lazy\"\n />\n ) : (\n <span>{affiliate.name.charAt(0)}</span>\n )}\n </div>\n )\n\n return (\n <div className={className} data-affiliate-card data-affiliate-id={affiliate.id}>\n {/* Logo */}\n {renderLogo ? renderLogo(affiliate) : defaultLogo}\n \n {/* Name */}\n <div data-affiliate-name className=\"affiliate-name\">\n {affiliate.name}\n </div>\n \n {/* Website link */}\n {affiliate.website_url && (\n <a \n href={affiliate.website_url}\n target=\"_blank\"\n rel=\"noopener noreferrer sponsored\"\n data-affiliate-website\n className=\"affiliate-website\"\n >\n Visit Website\n </a>\n )}\n \n {/* Offers */}\n {showOffers && affiliate.offers && affiliate.offers.length > 0 && (\n <div data-affiliate-offers className=\"affiliate-offers\">\n {affiliate.offers.map(offer => (\n <a\n key={offer.id}\n href={getTrackingUrl(affiliate.id, offer.id)}\n target=\"_blank\"\n rel=\"noopener noreferrer sponsored\"\n data-affiliate-offer\n data-offer-id={offer.id}\n className=\"affiliate-offer\"\n >\n {offer.name}\n </a>\n ))}\n </div>\n )}\n </div>\n )\n}\n\n// ============================================\n// Affiliates Grid (Unstyled)\n// ============================================\n\nexport interface AffiliatesWidgetProps {\n className?: string\n /** Custom loading component */\n loadingComponent?: React.ReactNode\n /** Custom empty state component */\n emptyComponent?: React.ReactNode\n /** Custom error component */\n errorComponent?: React.ReactNode\n /** Show offers on each card */\n showOffers?: boolean\n /** Custom render function for each affiliate */\n renderAffiliate?: (affiliate: AffiliateWithOffers) => React.ReactNode\n /** Maximum number to display */\n limit?: number\n}\n\n/**\n * Display a grid of affiliates - unstyled, bring your own CSS\n * \n * @example\n * ```tsx\n * // Basic usage\n * <AffiliatesWidget className=\"grid grid-cols-3 gap-4\" />\n * \n * // With custom rendering\n * <AffiliatesWidget\n * renderAffiliate={(affiliate) => (\n * <MyCustomCard key={affiliate.id} data={affiliate} />\n * )}\n * />\n * ```\n */\nexport function AffiliatesWidget({\n className = '',\n loadingComponent,\n emptyComponent,\n errorComponent,\n showOffers = false,\n renderAffiliate,\n limit,\n}: AffiliatesWidgetProps) {\n const { affiliates, isLoading, error, getTrackingUrl } = useAffiliates()\n \n if (isLoading) {\n return loadingComponent || <div data-affiliates-loading>Loading affiliates...</div>\n }\n \n if (error) {\n return errorComponent || <div data-affiliates-error>{error}</div>\n }\n \n const displayAffiliates = limit ? affiliates.slice(0, limit) : affiliates\n \n if (displayAffiliates.length === 0) {\n return emptyComponent || null\n }\n \n return (\n <div className={className} data-affiliates-widget>\n {displayAffiliates.map(affiliate => \n renderAffiliate \n ? renderAffiliate(affiliate)\n : <AffiliateCard \n key={affiliate.id} \n affiliate={affiliate} \n showOffers={showOffers}\n />\n )}\n </div>\n )\n}\n"]}
|
|
1
|
+
{"version":3,"sources":["../src/affiliates/api.ts","../src/affiliates/useAffiliates.ts","../src/affiliates/AffiliatesWidget.tsx"],"names":["getTrackingUrl"],"mappings":"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","file":"index.mjs","sourcesContent":["/**\n * @sonordev/site-kit/affiliates - Affiliates API\n * \n * API functions for fetching affiliate data for client sites.\n * All data goes through Portal API with API key auth - never Supabase directly.\n */\n\nimport { sonorFetch } from '../shared/sonorFetch'\nimport type { Affiliate, AffiliateWithOffers, FetchAffiliatesOptions } from './types'\n\n// ============================================\n// API Config Helpers\n// ============================================\n\nfunction getApiConfig() {\n const apiUrl = typeof window !== 'undefined' \n ? (window as any).__SITE_KIT_API_URL__ || 'https://api.sonor.io'\n : 'https://api.sonor.io'\n const apiKey = typeof window !== 'undefined' \n ? (window as any).__SITE_KIT_API_KEY__ || ''\n : ''\n return { apiUrl, apiKey }\n}\n\nasync function apiGet<T>(endpoint: string): Promise<T | null> {\n const { apiUrl, apiKey } = getApiConfig()\n \n if (!apiKey) {\n console.error('[Affiliates] No API key configured')\n return null\n }\n \n try {\n // Route through sonorFetch (the canonical transport) — NOT bare fetch — so a\n // stale build-time seed token is transparently refreshed and a 401 triggers\n // one refresh+retry. The credential goes via options.apiKey, never a header:\n // sonorFetch injects the freshest token as x-api-key; a hand-set header would\n // pin the stale seed and 401.\n const response = await sonorFetch(\n `${apiUrl}${endpoint}`,\n { method: 'GET' },\n { apiKey, retries: 0 },\n )\n\n if (!response.ok) {\n console.error(`[Affiliates] API error: ${response.statusText}`)\n return null\n }\n \n return await response.json()\n } catch (error) {\n console.error('[Affiliates] Network error:', error)\n return null\n }\n}\n\n// ============================================\n// Fetch Affiliates\n// ============================================\n\n/**\n * Fetch all active affiliates for the project\n * \n * @example\n * ```ts\n * const affiliates = await fetchAffiliates()\n * ```\n */\nexport async function fetchAffiliates(\n options: FetchAffiliatesOptions = {}\n): Promise<AffiliateWithOffers[]> {\n const result = await apiGet<{ affiliates: AffiliateWithOffers[] }>(\n '/api/public/affiliates'\n )\n \n return result?.affiliates || []\n}\n\n/**\n * Build a tracking URL for an affiliate offer\n * When clicked, this redirects through our tracking endpoint and then to the destination\n * \n * @example\n * ```ts\n * const trackingUrl = getTrackingUrl(affiliate.id, offer.id)\n * // Returns: https://api.sonor.io/a/{affiliateId}/{offerId}\n * ```\n */\nexport function getTrackingUrl(affiliateId: string, offerId: string): string {\n const { apiUrl } = getApiConfig()\n return `${apiUrl}/a/${affiliateId}/${offerId}`\n}\n","/**\n * @sonordev/site-kit/affiliates - useAffiliates Hook\n * \n * React hook for fetching and displaying affiliates on client sites.\n */\n\n'use client'\n\nimport { useState, useEffect } from 'react'\nimport type { AffiliateWithOffers } from './types'\nimport { fetchAffiliates, getTrackingUrl } from './api'\n\nexport interface UseAffiliatesResult {\n affiliates: AffiliateWithOffers[]\n isLoading: boolean\n error: string | null\n getTrackingUrl: (affiliateId: string, offerId: string) => string\n}\n\n/**\n * Hook to fetch affiliates for display on client sites\n * \n * @example\n * ```tsx\n * function AffiliatesSection() {\n * const { affiliates, isLoading } = useAffiliates()\n * \n * if (isLoading) return <div>Loading...</div>\n * \n * return (\n * <div className=\"grid grid-cols-3 gap-4\">\n * {affiliates.map(affiliate => (\n * <AffiliateCard key={affiliate.id} affiliate={affiliate} />\n * ))}\n * </div>\n * )\n * }\n * ```\n */\nexport function useAffiliates(): UseAffiliatesResult {\n const [affiliates, setAffiliates] = useState<AffiliateWithOffers[]>([])\n const [isLoading, setIsLoading] = useState(true)\n const [error, setError] = useState<string | null>(null)\n\n useEffect(() => {\n async function load() {\n try {\n setIsLoading(true)\n setError(null)\n const data = await fetchAffiliates()\n setAffiliates(data)\n } catch (err) {\n setError(err instanceof Error ? err.message : 'Failed to load affiliates')\n } finally {\n setIsLoading(false)\n }\n }\n \n load()\n }, [])\n\n return {\n affiliates,\n isLoading,\n error,\n getTrackingUrl,\n }\n}\n","/**\n * @sonordev/site-kit/affiliates - AffiliatesWidget Component\n * \n * Unstyled, headless component for displaying affiliates.\n * Client sites can wrap this or use it directly with their own styling.\n */\n\n'use client'\n\nimport React from 'react'\nimport { useAffiliates } from './useAffiliates'\nimport type { AffiliateWithOffers, AffiliateOffer } from './types'\n\n// ============================================\n// Affiliate Card (Unstyled)\n// ============================================\n\nexport interface AffiliateCardProps {\n affiliate: AffiliateWithOffers\n className?: string\n /** Optional custom render for the logo */\n renderLogo?: (affiliate: AffiliateWithOffers) => React.ReactNode\n /** Show offers as links below the card */\n showOffers?: boolean\n}\n\n/**\n * Single affiliate card - unstyled, bring your own CSS\n * \n * @example\n * ```tsx\n * <AffiliateCard \n * affiliate={affiliate}\n * className=\"p-4 bg-white rounded-lg shadow\"\n * showOffers\n * />\n * ```\n */\nexport function AffiliateCard({\n affiliate,\n className = '',\n renderLogo,\n showOffers = false,\n}: AffiliateCardProps) {\n const { getTrackingUrl } = useAffiliates()\n \n const defaultLogo = (\n <div data-affiliate-logo className=\"affiliate-logo\">\n {affiliate.logo_url ? (\n <img \n src={affiliate.logo_url} \n alt={affiliate.name}\n loading=\"lazy\"\n />\n ) : (\n <span>{affiliate.name.charAt(0)}</span>\n )}\n </div>\n )\n\n return (\n <div className={className} data-affiliate-card data-affiliate-id={affiliate.id}>\n {/* Logo */}\n {renderLogo ? renderLogo(affiliate) : defaultLogo}\n \n {/* Name */}\n <div data-affiliate-name className=\"affiliate-name\">\n {affiliate.name}\n </div>\n \n {/* Website link */}\n {affiliate.website_url && (\n <a \n href={affiliate.website_url}\n target=\"_blank\"\n rel=\"noopener noreferrer sponsored\"\n data-affiliate-website\n className=\"affiliate-website\"\n >\n Visit Website\n </a>\n )}\n \n {/* Offers */}\n {showOffers && affiliate.offers && affiliate.offers.length > 0 && (\n <div data-affiliate-offers className=\"affiliate-offers\">\n {affiliate.offers.map(offer => (\n <a\n key={offer.id}\n href={getTrackingUrl(affiliate.id, offer.id)}\n target=\"_blank\"\n rel=\"noopener noreferrer sponsored\"\n data-affiliate-offer\n data-offer-id={offer.id}\n className=\"affiliate-offer\"\n >\n {offer.name}\n </a>\n ))}\n </div>\n )}\n </div>\n )\n}\n\n// ============================================\n// Affiliates Grid (Unstyled)\n// ============================================\n\nexport interface AffiliatesWidgetProps {\n className?: string\n /** Custom loading component */\n loadingComponent?: React.ReactNode\n /** Custom empty state component */\n emptyComponent?: React.ReactNode\n /** Custom error component */\n errorComponent?: React.ReactNode\n /** Show offers on each card */\n showOffers?: boolean\n /** Custom render function for each affiliate */\n renderAffiliate?: (affiliate: AffiliateWithOffers) => React.ReactNode\n /** Maximum number to display */\n limit?: number\n}\n\n/**\n * Display a grid of affiliates - unstyled, bring your own CSS\n * \n * @example\n * ```tsx\n * // Basic usage\n * <AffiliatesWidget className=\"grid grid-cols-3 gap-4\" />\n * \n * // With custom rendering\n * <AffiliatesWidget\n * renderAffiliate={(affiliate) => (\n * <MyCustomCard key={affiliate.id} data={affiliate} />\n * )}\n * />\n * ```\n */\nexport function AffiliatesWidget({\n className = '',\n loadingComponent,\n emptyComponent,\n errorComponent,\n showOffers = false,\n renderAffiliate,\n limit,\n}: AffiliatesWidgetProps) {\n const { affiliates, isLoading, error, getTrackingUrl } = useAffiliates()\n \n if (isLoading) {\n return loadingComponent || <div data-affiliates-loading>Loading affiliates...</div>\n }\n \n if (error) {\n return errorComponent || <div data-affiliates-error>{error}</div>\n }\n \n const displayAffiliates = limit ? affiliates.slice(0, limit) : affiliates\n \n if (displayAffiliates.length === 0) {\n return emptyComponent || null\n }\n \n return (\n <div className={className} data-affiliates-widget>\n {displayAffiliates.map(affiliate => \n renderAffiliate \n ? renderAffiliate(affiliate)\n : <AffiliateCard \n key={affiliate.id} \n affiliate={affiliate} \n showOffers={showOffers}\n />\n )}\n </div>\n )\n}\n"]}
|