@kyro-cms/core 0.9.1 → 0.9.4
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 +0 -6
- package/dist/{WebhookService-Yg2UEOB4.d.cts → WebhookService-BKszZlG0.d.cts} +1 -1
- package/dist/{WebhookService-CUTb9XOy.d.ts → WebhookService-Ccf1j-IN.d.ts} +1 -1
- package/dist/api-handler-graphql.cjs +17 -17
- package/dist/api-handler-graphql.js +13 -13
- package/dist/api-handler-trpc.cjs +15 -15
- package/dist/api-handler-trpc.js +13 -13
- package/dist/api-handler.cjs +16 -16
- package/dist/api-handler.js +13 -13
- package/dist/{base-DaqY2GhA.d.ts → base-CIuXkrH4.d.cts} +3 -5
- package/dist/{base-B71y_EAF.d.cts → base-fFo4lqER.d.ts} +3 -5
- package/dist/bootstrap-3PV3GJ3S.js +7 -0
- package/dist/{bootstrap-T5BK77LD.js.map → bootstrap-3PV3GJ3S.js.map} +1 -1
- package/dist/bootstrap-4CELFLJO.cjs +32 -0
- package/dist/{bootstrap-5NLASFOG.cjs.map → bootstrap-4CELFLJO.cjs.map} +1 -1
- package/dist/{chunk-Z6ZWNWWR.js → chunk-4CV4JOE5.js} +3 -9
- package/dist/{chunk-Z6ZWNWWR.js.map → chunk-4CV4JOE5.js.map} +1 -1
- package/dist/{chunk-5EPFQUQD.js → chunk-53NYVYVX.js} +6 -6
- package/dist/chunk-53NYVYVX.js.map +1 -0
- package/dist/{chunk-22M4O4ZJ.js → chunk-5H3MWQJS.js} +129 -143
- package/dist/chunk-5H3MWQJS.js.map +1 -0
- package/dist/{chunk-RAMGUDJN.cjs → chunk-5PMQQFRE.cjs} +5 -5
- package/dist/{chunk-RAMGUDJN.cjs.map → chunk-5PMQQFRE.cjs.map} +1 -1
- package/dist/{chunk-TXSZFA4G.js → chunk-6UNONDW7.js} +93 -9
- package/dist/chunk-6UNONDW7.js.map +1 -0
- package/dist/{chunk-C36TMDTY.cjs → chunk-7OS7TX2Q.cjs} +49 -48
- package/dist/chunk-7OS7TX2Q.cjs.map +1 -0
- package/dist/{chunk-3TPQ2BU6.js → chunk-BYBMTIMT.js} +2 -6
- package/dist/chunk-BYBMTIMT.js.map +1 -0
- package/dist/{chunk-FOPGUM27.js → chunk-CJX74IYK.js} +5 -4
- package/dist/chunk-CJX74IYK.js.map +1 -0
- package/dist/{chunk-RSF3UU7H.cjs → chunk-CNKT4PME.cjs} +196 -200
- package/dist/chunk-CNKT4PME.cjs.map +1 -0
- package/dist/{chunk-G7VZBCD6.cjs → chunk-CZLDE2OZ.cjs} +2 -9
- package/dist/{chunk-G7VZBCD6.cjs.map → chunk-CZLDE2OZ.cjs.map} +1 -1
- package/dist/{chunk-JOPVMWTM.cjs → chunk-DPA3KWPY.cjs} +3 -3
- package/dist/chunk-DPA3KWPY.cjs.map +1 -0
- package/dist/{chunk-ROJHKAQ4.cjs → chunk-E2763JUP.cjs} +143 -157
- package/dist/chunk-E2763JUP.cjs.map +1 -0
- package/dist/{chunk-FAXU7BMP.js → chunk-E5UJBLQ7.js} +2 -2
- package/dist/chunk-E5UJBLQ7.js.map +1 -0
- package/dist/{chunk-DVD5P72E.cjs → chunk-EEJUFDMF.cjs} +2 -6
- package/dist/chunk-EEJUFDMF.cjs.map +1 -0
- package/dist/{chunk-2HZRBATX.cjs → chunk-FSKONGCX.cjs} +2 -2
- package/dist/chunk-FSKONGCX.cjs.map +1 -0
- package/dist/{chunk-P2HKJ7P5.js → chunk-GAAHG2Z4.js} +3 -3
- package/dist/{chunk-P2HKJ7P5.js.map → chunk-GAAHG2Z4.js.map} +1 -1
- package/dist/{chunk-PI73NNOK.cjs → chunk-GUUB5EAG.cjs} +2 -2
- package/dist/chunk-GUUB5EAG.cjs.map +1 -0
- package/dist/{chunk-PU2Z5VWF.js → chunk-IPTZM3VE.js} +183 -187
- package/dist/chunk-IPTZM3VE.js.map +1 -0
- package/dist/{chunk-4AO3A3JM.js → chunk-NFKRKH3P.js} +10 -2
- package/dist/chunk-NFKRKH3P.js.map +1 -0
- package/dist/{chunk-L46ROHUS.cjs → chunk-NI5D3F7H.cjs} +13 -5
- package/dist/chunk-NI5D3F7H.cjs.map +1 -0
- package/dist/{chunk-UERVXYVK.cjs → chunk-NWUEVLQT.cjs} +13 -13
- package/dist/{chunk-UERVXYVK.cjs.map → chunk-NWUEVLQT.cjs.map} +1 -1
- package/dist/{chunk-KPA4AN4R.js → chunk-OHC6UHFY.js} +86 -12
- package/dist/chunk-OHC6UHFY.js.map +1 -0
- package/dist/{chunk-DEVFAKCQ.cjs → chunk-PHJRNPHY.cjs} +6 -6
- package/dist/chunk-PHJRNPHY.cjs.map +1 -0
- package/dist/{chunk-VO35MNPH.js → chunk-PQ72Z6WC.js} +67 -105
- package/dist/chunk-PQ72Z6WC.js.map +1 -0
- package/dist/{chunk-KNRSROWB.cjs → chunk-PV2I2KMI.cjs} +86 -12
- package/dist/chunk-PV2I2KMI.cjs.map +1 -0
- package/dist/{chunk-V2TVSCV5.cjs → chunk-Q23GAMLE.cjs} +71 -109
- package/dist/chunk-Q23GAMLE.cjs.map +1 -0
- package/dist/{chunk-COIASRDK.cjs → chunk-RFFSZSCL.cjs} +107 -171
- package/dist/chunk-RFFSZSCL.cjs.map +1 -0
- package/dist/{chunk-AL5KX63J.js → chunk-UUDTPZX6.js} +3 -3
- package/dist/chunk-UUDTPZX6.js.map +1 -0
- package/dist/{chunk-EJN2PAOE.js → chunk-V7KZQIZ6.js} +102 -166
- package/dist/chunk-V7KZQIZ6.js.map +1 -0
- package/dist/{chunk-DYTZ6FQ7.js → chunk-WXVB364T.js} +2 -2
- package/dist/chunk-WXVB364T.js.map +1 -0
- package/dist/{chunk-WNCYAKF3.cjs → chunk-Y7AQK4R4.cjs} +93 -9
- package/dist/chunk-Y7AQK4R4.cjs.map +1 -0
- package/dist/{chunk-SPBTLUN6.js → chunk-YFAVQQTU.js} +7 -7
- package/dist/{chunk-SPBTLUN6.js.map → chunk-YFAVQQTU.js.map} +1 -1
- package/dist/cli/index.cjs +5 -5
- package/dist/cli/index.js +5 -5
- package/dist/client.cjs +4 -4
- package/dist/client.d.cts +2 -2
- package/dist/client.d.ts +2 -2
- package/dist/client.js +2 -2
- package/dist/drizzle/index.cjs +14 -14
- package/dist/drizzle/index.d.cts +4 -10
- package/dist/drizzle/index.d.ts +4 -10
- package/dist/drizzle/index.js +5 -5
- package/dist/fields/index.cjs +22 -22
- package/dist/fields/index.d.cts +1 -1
- package/dist/fields/index.d.ts +1 -1
- package/dist/fields/index.js +2 -2
- package/dist/graphql/index.cjs +1 -1
- package/dist/graphql/index.d.cts +3 -3
- package/dist/graphql/index.d.ts +3 -3
- package/dist/graphql/index.js +1 -1
- package/dist/{index-CJXPB_ot.d.ts → index-BKta3cBH.d.cts} +3 -2
- package/dist/{index-CaTNnLGd.d.cts → index-ClOqnkTO.d.ts} +3 -2
- package/dist/index.cjs +119 -119
- package/dist/index.d.cts +10 -15
- package/dist/index.d.ts +10 -15
- package/dist/index.js +19 -19
- package/dist/integration.cjs +3 -3
- package/dist/integration.js +2 -2
- package/dist/media-7WDX4BDJ.js +4 -0
- package/dist/{media-GPPTZ43E.js.map → media-7WDX4BDJ.js.map} +1 -1
- package/dist/{media-XNTUFJZR.cjs → media-TUSLVRQ6.cjs} +3 -3
- package/dist/{media-XNTUFJZR.cjs.map → media-TUSLVRQ6.cjs.map} +1 -1
- package/dist/{mongo-auth-adapter-ISOM7FSS.cjs → mongo-auth-adapter-GT4S7SCU.cjs} +3 -3
- package/dist/{mongo-auth-adapter-ISOM7FSS.cjs.map → mongo-auth-adapter-GT4S7SCU.cjs.map} +1 -1
- package/dist/mongo-auth-adapter-M7VV4LNB.js +4 -0
- package/dist/{mongo-auth-adapter-MO6STCV3.js.map → mongo-auth-adapter-M7VV4LNB.js.map} +1 -1
- package/dist/mongodb/index.cjs +5 -5
- package/dist/mongodb/index.d.cts +4 -9
- package/dist/mongodb/index.d.ts +4 -9
- package/dist/mongodb/index.js +3 -3
- package/dist/postgres-auth-adapter-AFAPISH7.js +5 -0
- package/dist/{postgres-auth-adapter-DWDR7P5G.js.map → postgres-auth-adapter-AFAPISH7.js.map} +1 -1
- package/dist/postgres-auth-adapter-SFDTLONT.cjs +14 -0
- package/dist/{postgres-auth-adapter-WRWSJD4E.cjs.map → postgres-auth-adapter-SFDTLONT.cjs.map} +1 -1
- package/dist/{redis-adapter-KJ3YOOT6.cjs → redis-adapter-UQX4EE3B.cjs} +3 -3
- package/dist/{redis-adapter-KJ3YOOT6.cjs.map → redis-adapter-UQX4EE3B.cjs.map} +1 -1
- package/dist/redis-adapter-XALOGWY3.js +4 -0
- package/dist/{redis-adapter-HGTPWIGV.js.map → redis-adapter-XALOGWY3.js.map} +1 -1
- package/dist/rest/index.cjs +10 -10
- package/dist/rest/index.d.cts +4 -4
- package/dist/rest/index.d.ts +4 -4
- package/dist/rest/index.js +8 -8
- package/dist/{schema-TTFE4467.cjs → schema-6QL3USNB.cjs} +15 -15
- package/dist/{schema-TTFE4467.cjs.map → schema-6QL3USNB.cjs.map} +1 -1
- package/dist/{schema-6I5OFR4Z.js → schema-FNNWEAAW.js} +4 -4
- package/dist/{schema-6I5OFR4Z.js.map → schema-FNNWEAAW.js.map} +1 -1
- package/dist/{sqlite-adapter-CSIZE5SX.cjs → sqlite-adapter-AQB5TCGV.cjs} +3 -3
- package/dist/{sqlite-adapter-CSIZE5SX.cjs.map → sqlite-adapter-AQB5TCGV.cjs.map} +1 -1
- package/dist/sqlite-adapter-N5H6IM2X.js +4 -0
- package/dist/{sqlite-adapter-6GEUSVXQ.js.map → sqlite-adapter-N5H6IM2X.js.map} +1 -1
- package/dist/templates/index.cjs +49 -49
- package/dist/templates/index.d.cts +2 -2
- package/dist/templates/index.d.ts +2 -2
- package/dist/templates/index.js +2 -2
- package/dist/trpc/index.cjs +11 -11
- package/dist/trpc/index.d.cts +3 -3
- package/dist/trpc/index.d.ts +3 -3
- package/dist/trpc/index.js +2 -2
- package/dist/{types-Z6FBiqa2.d.cts → types-DeSApf9T.d.cts} +1 -0
- package/dist/{types-Z6FBiqa2.d.ts → types-DeSApf9T.d.ts} +1 -0
- package/dist/{types-CyCQ6SAI.d.ts → types-Dgzlftb7.d.ts} +6 -28
- package/dist/{types-DJxD9394.d.cts → types-Ds0tCA3L.d.cts} +6 -28
- package/dist/ws/index.cjs +6 -6
- package/dist/ws/index.js +2 -2
- package/package.json +1 -1
- package/dist/bootstrap-5NLASFOG.cjs +0 -32
- package/dist/bootstrap-T5BK77LD.js +0 -7
- package/dist/chunk-22M4O4ZJ.js.map +0 -1
- package/dist/chunk-2HZRBATX.cjs.map +0 -1
- package/dist/chunk-3TPQ2BU6.js.map +0 -1
- package/dist/chunk-4AO3A3JM.js.map +0 -1
- package/dist/chunk-5EPFQUQD.js.map +0 -1
- package/dist/chunk-AL5KX63J.js.map +0 -1
- package/dist/chunk-C36TMDTY.cjs.map +0 -1
- package/dist/chunk-COIASRDK.cjs.map +0 -1
- package/dist/chunk-DEVFAKCQ.cjs.map +0 -1
- package/dist/chunk-DVD5P72E.cjs.map +0 -1
- package/dist/chunk-DYTZ6FQ7.js.map +0 -1
- package/dist/chunk-EJN2PAOE.js.map +0 -1
- package/dist/chunk-FAXU7BMP.js.map +0 -1
- package/dist/chunk-FOPGUM27.js.map +0 -1
- package/dist/chunk-JOPVMWTM.cjs.map +0 -1
- package/dist/chunk-KNRSROWB.cjs.map +0 -1
- package/dist/chunk-KPA4AN4R.js.map +0 -1
- package/dist/chunk-L46ROHUS.cjs.map +0 -1
- package/dist/chunk-PI73NNOK.cjs.map +0 -1
- package/dist/chunk-PU2Z5VWF.js.map +0 -1
- package/dist/chunk-ROJHKAQ4.cjs.map +0 -1
- package/dist/chunk-RSF3UU7H.cjs.map +0 -1
- package/dist/chunk-TXSZFA4G.js.map +0 -1
- package/dist/chunk-V2TVSCV5.cjs.map +0 -1
- package/dist/chunk-VO35MNPH.js.map +0 -1
- package/dist/chunk-WNCYAKF3.cjs.map +0 -1
- package/dist/media-GPPTZ43E.js +0 -4
- package/dist/mongo-auth-adapter-MO6STCV3.js +0 -4
- package/dist/postgres-auth-adapter-DWDR7P5G.js +0 -5
- package/dist/postgres-auth-adapter-WRWSJD4E.cjs +0 -14
- package/dist/redis-adapter-HGTPWIGV.js +0 -4
- package/dist/sqlite-adapter-6GEUSVXQ.js +0 -4
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/fields/types.ts","../src/fields/richtext.ts"],"names":["StarterKit","Link","Image","TextAlign","Underline","Highlight","TaskList","TaskItem","TextStyle","Color","html","generateHTML"],"mappings":";;;;;;;;;;;;;;;;;;;;;;;;;;;AAmVO,SAAS,YAAY,KAAA,EAAkC;AAC5D,EAAA,OAAO,MAAM,IAAA,KAAS,MAAA;AACxB;AAEO,SAAS,cAAc,KAAA,EAAoC;AAChE,EAAA,OAAO,MAAM,IAAA,KAAS,QAAA;AACxB;AAEO,SAAS,oBAAoB,KAAA,EAA0C;AAC5E,EAAA,OAAO,MAAM,IAAA,KAAS,cAAA;AACxB;AAEO,SAAS,aAAa,KAAA,EAAmC;AAC9D,EAAA,OAAO,MAAM,IAAA,KAAS,OAAA;AACxB;AAEO,SAAS,aAAa,KAAA,EAAmC;AAC9D,EAAA,OAAO,MAAM,IAAA,KAAS,OAAA;AACxB;AAEO,SAAS,cAAc,KAAA,EAAoC;AAChE,EAAA,OAAO,MAAM,IAAA,KAAS,QAAA;AACxB;AAEO,SAAS,cAAc,KAAA,EAAoC;AAChE,EAAA,OAAO,MAAM,IAAA,KAAS,QAAA;AACxB;AAEO,SAAS,aAAa,KAAA,EAAmC;AAC9D,EAAA,OAAO,MAAM,IAAA,KAAS,OAAA;AACxB;AAEO,SAAS,gBAAgB,KAAA,EAAsC;AACpE,EAAA,OAAO,MAAM,IAAA,KAAS,UAAA;AACxB;AAEO,SAAS,cAAc,KAAA,EAAoC;AAChE,EAAA,OAAO,MAAM,IAAA,KAAS,QAAA;AACxB;AAEO,SAAS,cACd,KAAA,EACkD;AAClD,EAAA,OACE,MAAM,IAAA,KAAS,KAAA,IACf,MAAM,IAAA,KAAS,aAAA,IACf,MAAM,IAAA,KAAS,MAAA;AAEnB;AAMO,IAAM,qBAAA,GAAwB;AAAA,EACnC,MAAA;AAAA,EACA,QAAA;AAAA,EACA,UAAA;AAAA,EACA,MAAA;AAAA,EACA,OAAA;AAAA,EACA,UAAA;AAAA,EACA,UAAA;AAAA,EACA,QAAA;AAAA,EACA,OAAA;AAAA,EACA;AACF;AAEO,IAAM,mBAAA,GAAsB;AAAA,EACjC,UAAA;AAAA,EACA,MAAA;AAAA,EACA,MAAA;AAAA,EACA,QAAA;AAAA,EACA,OAAA;AAAA,EACA;AACF;AAEO,IAAM,sBAAA,GAAyB;AAAA,EACpC,cAAA;AAAA,EACA,OAAA;AAAA,EACA,OAAA;AAAA,EACA;AACF;AAEO,IAAM,kBAAA,GAAqB,CAAC,KAAA,EAAO,aAAA,EAAe,MAAM;AAExD,IAAM,eAAA,GAAkB;AAAA,EAC7B,GAAG,qBAAA;AAAA,EACH,GAAG,mBAAA;AAAA,EACH,GAAG,sBAAA;AAAA,EACH,GAAG;AACL;AAMO,SAAS,6BAAA,CACd,IAAA,EACA,UAAA,EACA,OAAA,EACmB;AACnB,EAAA,OAAO;AAAA,IACL,IAAA;AAAA,IACA,IAAA,EAAM,cAAA;AAAA,IACN,UAAA;AAAA,IACA,GAAG,OAAA;AAAA,IACH,QAAA,EAAU,SAAS,QAAA,IAAY;AAAA,GACjC;AACF;ACnbO,IAAM,cAAA,GAAiB;AAAA;AAAA;AAAA;AAAA;;AAAA;AAAA;AAAA;;AAAA;AAAA;AAAA;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;;AAAA;AAAA;AAAA;AAAA;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;;AAAA;AAAA;AAAA;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;;AAAA;AAAA;AAAA;AAAA;;AAAA;AAAA;AAAA;AAAA;AAAA;;AAAA;AAAA;AAAA;AAAA;AAAA;;AAAA;AAAA;AAAA;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,CAAA,CAyF5B,IAAA;AAEF,IAAM,UAAA,GAAa;AAAA,EACjBA,2BAAA;AAAA,EACAC,sBAAK,SAAA,CAAU;AAAA,IACb,WAAA,EAAa;AAAA,GACd,CAAA;AAAA,EACDC,sBAAA;AAAA,EACAC,2BAAU,SAAA,CAAU;AAAA,IAClB,KAAA,EAAO,CAAC,SAAA,EAAW,WAAW;AAAA,GAC/B,CAAA;AAAA,EACDC,0BAAA;AAAA,EACAC,2BAAU,SAAA,CAAU;AAAA,IAClB,UAAA,EAAY;AAAA,GACb,CAAA;AAAA,EACDC,yBAAA;AAAA,EACAC,0BAAS,SAAA,CAAU;AAAA,IACjB,MAAA,EAAQ;AAAA,GACT,CAAA;AAAA,EACDC,4BAAA;AAAA,EACAC;AACF,CAAA;AAEO,SAAS,uBAA0B,KAAA,EAAa;AAErD,EAAA,IAAI,OAAO,KAAA,KAAU,QAAA,IAAY,KAAA,KAAU,IAAA,EAAM;AAC/C,IAAA,OAAO,KAAA;AAAA,EACT;AACA,EAAA,OAAO,EAAC;AACV;AAEO,SAAS,eAAe,KAAA,EAAwB;AACrD,EAAA,IAAI,OAAO,KAAA,KAAU,QAAA,IAAY,KAAA,KAAU,IAAA,EAAM;AAC/C,IAAA,OAAO,EAAA;AAAA,EACT;AAEA,EAAA,IAAI;AACF,IAAA,MAAMC,MAAA,GAAOC,iBAAA,CAAa,KAAA,EAA8B,UAAU,CAAA;AAClE,IAAA,OAAO,8BAA8BD,MAAI,CAAA,MAAA,CAAA;AAAA,EAC3C,SAAS,KAAA,EAAO;AACd,IAAA,OAAA,CAAQ,KAAA,CAAM,+BAA+B,KAAK,CAAA;AAClD,IAAA,OAAO,EAAA;AAAA,EACT;AACF","file":"chunk-2HZRBATX.cjs","sourcesContent":["\n\n// ============================================================================\n// Base Field Interface\n// ============================================================================\n\n/**\n * Serializable condition for conditional field visibility.\n * Unlike function conditions, these survive JSON serialization\n * and can be used in admin configs that are built at compile time.\n */\nexport interface DeclarativeCondition {\n /** The field name to evaluate (resolved from root form data) */\n field: string;\n /** Show the field when the target field equals this value */\n equals?: string | number | boolean;\n /** Show the field when the target field does NOT equal this value */\n notEquals?: string | number | boolean;\n /** Show the field when the target field's value is one of these */\n in?: (string | number | boolean)[];\n}\n\nexport interface FieldAdmin {\n description?: string;\n placeholder?: string;\n readOnly?: boolean | ((\n data: Record<string, any>,\n siblingData: Record<string, any>,\n ) => boolean);\n hidden?: boolean | ((\n data: Record<string, any>,\n siblingData: Record<string, any>,\n ) => boolean);\n width?: string;\n position?: \"sidebar\" | \"main\";\n autoGenerate?: string;\n action?: string;\n method?: string;\n inline?: boolean;\n condition?:\n | ((\n data: Record<string, any>,\n siblingData: Record<string, any>,\n ) => boolean)\n | DeclarativeCondition;\n}\n\nexport interface BaseField {\n name: string;\n label?: string;\n required?: boolean;\n unique?: boolean;\n indexed?: boolean;\n defaultValue?: any;\n admin?: FieldAdmin;\n validate?: (\n value: any,\n options: ValidateOptions,\n ) => string | true | Promise<string | true>;\n hooks?: {\n beforeValidate?: Hook[];\n beforeChange?: Hook[];\n afterChange?: Hook[];\n afterRead?: Hook[];\n };\n}\n\nexport interface ValidateOptions {\n data?: Record<string, any>;\n siblingData?: Record<string, any>;\n user?: any;\n operation?: string;\n required?: boolean;\n}\n\nexport type Hook = (args: any) => Promise<any> | any;\n\n// ============================================================================\n// Primitive Fields\n// ============================================================================\n\nexport type TextFieldVariant = \"text\" | \"email\" | \"password\" | \"url\" | \"id\";\n\nexport interface TextField extends BaseField {\n type: \"text\";\n variant?: TextFieldVariant;\n minLength?: number;\n maxLength?: number;\n pattern?: string;\n hasMany?: boolean;\n localized?: boolean;\n}\n\nexport interface NumberField extends BaseField {\n type: \"number\";\n min?: number;\n max?: number;\n step?: number;\n integer?: boolean;\n hasMany?: boolean;\n}\n\nexport interface CheckboxField extends BaseField {\n type: \"checkbox\";\n}\n\nexport interface DateField extends BaseField {\n type: \"date\";\n minDate?: string;\n maxDate?: string;\n time?: boolean;\n}\n\nexport interface EmailField extends BaseField {\n type: \"email\";\n}\n\nexport interface PasswordField extends BaseField {\n type: \"password\";\n}\n\nexport interface TextareaField extends BaseField {\n type: \"textarea\";\n minLength?: number;\n maxLength?: number;\n rows?: number;\n localized?: boolean;\n}\n\nexport interface SelectField extends BaseField {\n type: \"select\";\n options?: Array<{ label: string; value: string }>;\n dynamicOptions?: string;\n hasMany?: boolean;\n defaultValue?: string | string[];\n}\n\nexport interface RadioField extends BaseField {\n type: \"radio\";\n options: Array<{ label: string; value: string }>;\n defaultValue?: string;\n}\n\nexport interface ColorField extends BaseField {\n type: \"color\";\n format?: \"hex\" | \"rgb\" | \"hsl\";\n defaultValue?: string;\n}\n\nexport interface ImageField extends BaseField {\n type: \"image\";\n minCount?: number;\n maxCount?: number;\n allowedTypes?: string[];\n maxSize?: number;\n}\n\n// ============================================================================\n// Complex Fields\n// ============================================================================\n\nexport type RichTextBlock = Record<string, any>; // TipTap JSONContent\n\nexport interface RichTextField extends BaseField {\n type: \"richtext\";\n defaultValue?: Record<string, any>;\n localized?: boolean;\n}\n\nexport interface JSONField extends BaseField {\n type: \"json\";\n defaultValue?: Record<string, any>;\n}\n\nexport interface CodeField extends BaseField {\n type: \"code\";\n language?: string;\n defaultValue?: string;\n}\n\nexport interface UploadField extends BaseField {\n type: \"upload\";\n relationTo: string;\n hasMany?: boolean;\n maxDepth?: number;\n defaultValue?: string;\n}\n\nexport interface MarkdownField extends BaseField {\n type: \"markdown\";\n localized?: boolean;\n defaultValue?: string;\n}\n\n// ============================================================================\n// Relational Fields\n// ============================================================================\n\nexport interface RelationshipField extends BaseField {\n type: \"relationship\";\n relationTo: string | string[];\n hasMany?: boolean;\n maxDepth?: number;\n filterOptions?: (args: { data: any; user: any }) => Record<string, any>;\n defaultValue?: string | string[];\n}\n\nexport interface ArrayField extends BaseField {\n type: \"array\";\n fields: Field[];\n minRows?: number;\n maxRows?: number;\n labels?: { singular?: string; plural?: string };\n defaultValue?: Record<string, any>[];\n}\n\nexport interface ListField extends BaseField {\n type: \"list\";\n defaultValue?: string[];\n}\n\nexport interface GroupField extends BaseField {\n type: \"group\";\n fields: Field[];\n defaultValue?: Record<string, any>;\n}\n\nexport interface BlockImage {\n url: string;\n alt?: string;\n}\n\nexport interface BlockAdmin {\n group?: string;\n description?: string;\n images?: {\n icon?: BlockImage | string;\n thumbnail?: BlockImage | string;\n };\n}\n\nexport interface Block {\n slug: string;\n label: string;\n fields: Field[];\n imageURL?: string;\n admin?: BlockAdmin;\n}\n\nexport interface BlocksField extends BaseField {\n type: \"blocks\";\n blocks?: Block[];\n minRows?: number;\n maxRows?: number;\n defaultValue?: Array<{ blockType: string; [key: string]: any }>;\n}\n\nexport interface RowField extends Omit<BaseField, \"name\"> {\n type: \"row\";\n fields: Field[];\n name?: string;\n}\n\nexport interface CollapsibleField extends Omit<BaseField, \"name\"> {\n type: \"collapsible\";\n fields: Field[];\n label: string;\n name?: string;\n}\n\nexport interface TabsField extends Omit<BaseField, \"name\"> {\n type: \"tabs\";\n tabs: Array<{\n label: string;\n fields: Field[];\n name?: string;\n }>;\n name?: string;\n}\n\nexport interface ButtonField extends BaseField {\n type: \"button\";\n label: string;\n action?: string;\n method?: string;\n inline?: boolean;\n}\n\nexport interface ActionField extends BaseField {\n type: \"action\";\n label: string;\n action?: string;\n method?: string;\n inline?: boolean;\n}\n\nexport interface SecretField extends BaseField {\n type: \"secret\";\n}\n\n// ============================================================================\n// Union Type\n// ============================================================================\n\nexport type Field =\n | TextField\n | NumberField\n | CheckboxField\n | DateField\n | EmailField\n | PasswordField\n | TextareaField\n | SelectField\n | RadioField\n | ColorField\n | ImageField\n | RichTextField\n | JSONField\n | CodeField\n | UploadField\n | MarkdownField\n | RelationshipField\n | ArrayField\n | ListField\n | GroupField\n | BlocksField\n | RowField\n | CollapsibleField\n | TabsField\n | ButtonField\n | ActionField\n | SecretField;\n\nexport type FieldType = Field[\"type\"];\n\n// ============================================================================\n// Field Type Guards\n// ============================================================================\n\nexport function isTextField(field: Field): field is TextField {\n return field.type === \"text\";\n}\n\nexport function isNumberField(field: Field): field is NumberField {\n return field.type === \"number\";\n}\n\nexport function isRelationshipField(field: Field): field is RelationshipField {\n return field.type === \"relationship\";\n}\n\nexport function isArrayField(field: Field): field is ArrayField {\n return field.type === \"array\";\n}\n\nexport function isGroupField(field: Field): field is GroupField {\n return field.type === \"group\";\n}\n\nexport function isBlocksField(field: Field): field is BlocksField {\n return field.type === \"blocks\";\n}\n\nexport function isUploadField(field: Field): field is UploadField {\n return field.type === \"upload\";\n}\n\nexport function isImageField(field: Field): field is ImageField {\n return field.type === \"image\";\n}\n\nexport function isRichTextField(field: Field): field is RichTextField {\n return field.type === \"richtext\";\n}\n\nexport function isSelectField(field: Field): field is SelectField {\n return field.type === \"select\";\n}\n\nexport function isLayoutField(\n field: Field,\n): field is RowField | CollapsibleField | TabsField {\n return (\n field.type === \"row\" ||\n field.type === \"collapsible\" ||\n field.type === \"tabs\"\n );\n}\n\n// ============================================================================\n// Field Type List\n// ============================================================================\n\nexport const PRIMITIVE_FIELD_TYPES = [\n \"text\",\n \"number\",\n \"checkbox\",\n \"date\",\n \"email\",\n \"password\",\n \"textarea\",\n \"select\",\n \"radio\",\n \"color\",\n] as const;\n\nexport const COMPLEX_FIELD_TYPES = [\n \"richtext\",\n \"json\",\n \"code\",\n \"upload\",\n \"image\",\n \"markdown\",\n] as const;\n\nexport const RELATIONAL_FIELD_TYPES = [\n \"relationship\",\n \"array\",\n \"group\",\n \"blocks\",\n] as const;\n\nexport const LAYOUT_FIELD_TYPES = [\"row\", \"collapsible\", \"tabs\"] as const;\n\nexport const ALL_FIELD_TYPES = [\n ...PRIMITIVE_FIELD_TYPES,\n ...COMPLEX_FIELD_TYPES,\n ...RELATIONAL_FIELD_TYPES,\n ...LAYOUT_FIELD_TYPES,\n] as const;\n\n// ============================================================================\n// Field Factory Functions\n// ============================================================================\n\nexport function createRelationshipFieldConfig(\n name: string,\n relationTo: string | string[],\n options?: Partial<Omit<RelationshipField, \"type\" | \"name\" | \"relationTo\">>,\n): RelationshipField {\n return {\n name,\n type: \"relationship\",\n relationTo,\n ...options,\n required: options?.required ?? false,\n };\n}\n","import { generateHTML } from \"@tiptap/html\";\nimport StarterKit from \"@tiptap/starter-kit\";\nimport Link from \"@tiptap/extension-link\";\nimport Image from \"@tiptap/extension-image\";\nimport TextAlign from \"@tiptap/extension-text-align\";\nimport Underline from \"@tiptap/extension-underline\";\nimport Highlight from \"@tiptap/extension-highlight\";\nimport TaskList from \"@tiptap/extension-task-list\";\nimport TaskItem from \"@tiptap/extension-task-item\";\nimport { TextStyle } from \"@tiptap/extension-text-style\";\nimport Color from \"@tiptap/extension-color\";\n\nexport const richTextStyles = `\n.kyro-richtext {\n color: inherit;\n line-height: 1.7;\n}\n\n.kyro-richtext > *:first-child {\n margin-top: 0;\n}\n\n.kyro-richtext > *:last-child {\n margin-bottom: 0;\n}\n\n.kyro-richtext p,\n.kyro-richtext ul,\n.kyro-richtext ol,\n.kyro-richtext blockquote,\n.kyro-richtext pre {\n margin: 0 0 1rem;\n}\n\n.kyro-richtext h1,\n.kyro-richtext h2,\n.kyro-richtext h3,\n.kyro-richtext h4,\n.kyro-richtext h5,\n.kyro-richtext h6 {\n margin: 0 0 0.75rem;\n line-height: 1.2;\n}\n\n.kyro-richtext ul,\n.kyro-richtext ol {\n padding-left: 1.5rem;\n}\n\n.kyro-richtext blockquote {\n border-left: 4px solid rgba(148, 163, 184, 0.5);\n margin-left: 0;\n padding-left: 1rem;\n font-style: italic;\n}\n\n.kyro-richtext pre {\n overflow-x: auto;\n border-radius: 0.75rem;\n background: rgba(15, 23, 42, 0.92);\n color: #f8fafc;\n padding: 1rem;\n}\n\n.kyro-richtext code {\n font-family: ui-monospace, SFMono-Regular, Menlo, monospace;\n}\n\n.kyro-richtext img {\n display: block;\n max-width: 100%;\n height: auto;\n border-radius: 0.75rem;\n}\n\n.kyro-richtext ul[data-type=\"taskList\"] {\n list-style: none;\n padding: 0;\n}\n\n.kyro-richtext li[data-type=\"taskItem\"] {\n display: flex;\n align-items: flex-start;\n gap: 0.5rem;\n}\n\n.kyro-richtext li[data-type=\"taskItem\"] > label {\n user-select: none;\n pointer-events: none;\n margin-top: 0.2rem;\n}\n\n.kyro-richtext li[data-type=\"taskItem\"] > div {\n flex: 1;\n}\n\n.kyro-richtext mark {\n background-color: #fef08a;\n border-radius: 0.25rem;\n padding: 0.125rem 0.25rem;\n}\n`.trim();\n\nconst extensions = [\n StarterKit,\n Link.configure({\n openOnClick: false,\n }),\n Image,\n TextAlign.configure({\n types: [\"heading\", \"paragraph\"],\n }),\n Underline,\n Highlight.configure({\n multicolor: true,\n }),\n TaskList,\n TaskItem.configure({\n nested: true,\n }),\n TextStyle,\n Color,\n];\n\nexport function normalizeRichTextValue<T>(value: T): T {\n // TipTap JSON is already standard JSON, so we just ensure it's an object.\n if (typeof value === \"object\" && value !== null) {\n return value;\n }\n return {} as T;\n}\n\nexport function renderRichText(value: unknown): string {\n if (typeof value !== \"object\" || value === null) {\n return \"\";\n }\n \n try {\n const html = generateHTML(value as Record<string, any>, extensions);\n return `<div class=\"kyro-richtext\">${html}</div>`;\n } catch (error) {\n console.error(\"Failed to render rich text:\", error);\n return \"\";\n }\n}\n"]}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/api/ws/pubsub.ts","../src/api/ws/server.ts"],"names":[],"mappings":";;;AAMO,IAAM,SAAN,MAAa;AAAA,EACV,QAAA,uBAA+C,GAAA,EAAI;AAAA,EACnD,YAAA;AAAA,EAER,WAAA,CAAY,eAAe,GAAA,EAAK;AAC9B,IAAA,IAAA,CAAK,YAAA,GAAe,YAAA;AAAA,EACtB;AAAA,EAEA,SAAA,CAAU,SAAiB,OAAA,EAAmC;AAC5D,IAAA,IAAI,CAAC,IAAA,CAAK,QAAA,CAAS,GAAA,CAAI,OAAO,CAAA,EAAG;AAC/B,MAAA,IAAA,CAAK,QAAA,CAAS,GAAA,CAAI,OAAA,kBAAS,IAAI,KAAK,CAAA;AAAA,IACtC;AAEA,IAAA,MAAM,QAAA,GAAW,IAAA,CAAK,QAAA,CAAS,GAAA,CAAI,OAAO,CAAA;AAC1C,IAAA,IAAI,QAAA,CAAS,IAAA,IAAQ,IAAA,CAAK,YAAA,EAAc;AACtC,MAAA,MAAM,IAAI,KAAA,CAAM,CAAA,eAAA,EAAkB,KAAK,YAAY,CAAA,uBAAA,EAA0B,OAAO,CAAA,CAAA,CAAG,CAAA;AAAA,IACzF;AAEA,IAAA,QAAA,CAAS,IAAI,OAAO,CAAA;AAGpB,IAAA,OAAO,MAAM;AACX,MAAA,QAAA,CAAS,OAAO,OAAO,CAAA;AACvB,MAAA,IAAI,QAAA,CAAS,SAAS,CAAA,EAAG;AACvB,QAAA,IAAA,CAAK,QAAA,CAAS,OAAO,OAAO,CAAA;AAAA,MAC9B;AAAA,IACF,CAAA;AAAA,EACF;AAAA,EAEA,OAAA,CAAQ,SAAiB,IAAA,EAAiB;AACxC,IAAA,MAAM,QAAA,GAAW,IAAA,CAAK,QAAA,CAAS,GAAA,CAAI,OAAO,CAAA;AAC1C,IAAA,IAAI,QAAA,EAAU;AACZ,MAAA,KAAA,MAAW,WAAW,QAAA,EAAU;AAC9B,QAAA,IAAI;AACF,UAAA,MAAM,MAAA,GAAS,QAAQ,IAAI,CAAA;AAC3B,UAAA,IAAI,kBAAkB,OAAA,EAAS;AAC7B,YAAA,MAAA,CAAO,KAAA,CAAM,CAAC,GAAA,KAAQ;AACpB,cAAA,OAAA,CAAQ,KAAA,CAAM,CAAA,uCAAA,EAA0C,OAAO,CAAA,EAAA,CAAA,EAAM,GAAG,CAAA;AAAA,YAC1E,CAAC,CAAA;AAAA,UACH;AAAA,QACF,SAAS,GAAA,EAAK;AACZ,UAAA,OAAA,CAAQ,KAAA,CAAM,CAAA,uCAAA,EAA0C,OAAO,CAAA,EAAA,CAAA,EAAM,GAAG,CAAA;AAAA,QAC1E;AAAA,MACF;AAAA,IACF;AAAA,EACF;AAAA,EAEA,eAAe,OAAA,EAA0B;AACvC,IAAA,OAAO,IAAA,CAAK,QAAA,CAAS,GAAA,CAAI,OAAO,CAAA,IAAK,KAAK,QAAA,CAAS,GAAA,CAAI,OAAO,CAAA,CAAG,IAAA,GAAO,CAAA;AAAA,EAC1E;AAAA,EAEA,mBAAmB,OAAA,EAAyB;AAC1C,IAAA,OAAO,IAAA,CAAK,QAAA,CAAS,GAAA,CAAI,OAAO,GAAG,IAAA,IAAQ,CAAA;AAAA,EAC7C;AAAA,EAEA,WAAA,GAAwB;AACtB,IAAA,OAAO,KAAA,CAAM,IAAA,CAAK,IAAA,CAAK,QAAA,CAAS,MAAM,CAAA;AAAA,EACxC;AAAA,EAEA,KAAA,GAAc;AACZ,IAAA,IAAA,CAAK,SAAS,KAAA,EAAM;AAAA,EACtB;AACF;AAqBO,IAAM,UAAA,GAAN,cAAyB,MAAA,CAAO;AAAA,EAC7B,QAAA;AAAA,EAER,WAAA,CAAY,QAAA,EAAe,YAAA,GAAe,GAAA,EAAK;AAC7C,IAAA,KAAA,CAAM,YAAY,CAAA;AAClB,IAAA,IAAA,CAAK,QAAA,GAAW,QAAA;AAAA,EAClB;AAAA;AAAA,EAGA,sBAAA,CAAuB,YAAoB,KAAA,EAAwB;AAEjE,IAAA,IAAA,CAAK,OAAA,CAAQ,CAAA,WAAA,EAAc,UAAU,CAAA,CAAA,EAAI,KAAK,CAAA;AAG9C,IAAA,IAAA,CAAK,OAAA,CAAQ,qBAAqB,KAAK,CAAA;AAGvC,IAAA,IAAI,MAAM,QAAA,EAAU;AAClB,MAAA,IAAA,CAAK,QAAQ,CAAA,OAAA,EAAU,KAAA,CAAM,QAAQ,CAAA,YAAA,EAAe,UAAU,IAAI,KAAK,CAAA;AACvE,MAAA,IAAA,CAAK,OAAA,CAAQ,CAAA,OAAA,EAAU,KAAA,CAAM,QAAQ,WAAW,KAAK,CAAA;AAAA,IACvD;AAGA,IAAA,IAAA,CAAK,QAAQ,CAAA,WAAA,EAAc,UAAU,IAAI,KAAA,CAAM,IAAI,IAAI,KAAK,CAAA;AAAA,EAC9D;AAAA;AAAA,EAGA,qBAAA,CAAsB,YAAoB,OAAA,EAAmC;AAC3E,IAAA,OAAO,IAAA,CAAK,SAAA,CAAU,CAAA,WAAA,EAAc,UAAU,IAAI,OAAO,CAAA;AAAA,EAC3D;AAAA;AAAA,EAGA,0BAAA,CACE,UAAA,EACA,SAAA,EACA,OAAA,EACY;AACZ,IAAA,OAAO,KAAK,SAAA,CAAU,CAAA,WAAA,EAAc,UAAU,CAAA,CAAA,EAAI,SAAS,IAAI,OAAO,CAAA;AAAA,EACxE;AAAA;AAAA,EAGA,iBAAA,CAAkB,UAAkB,OAAA,EAAmC;AACrE,IAAA,OAAO,IAAA,CAAK,SAAA,CAAU,CAAA,OAAA,EAAU,QAAQ,WAAW,OAAO,CAAA;AAAA,EAC5D;AAAA;AAAA,EAGA,2BAAA,CACE,QAAA,EACA,UAAA,EACA,OAAA,EACY;AACZ,IAAA,OAAO,KAAK,SAAA,CAAU,CAAA,OAAA,EAAU,QAAQ,CAAA,YAAA,EAAe,UAAU,IAAI,OAAO,CAAA;AAAA,EAC9E;AAAA;AAAA,EAGA,0BAA0B,OAAA,EAAmC;AAC3D,IAAA,OAAO,IAAA,CAAK,SAAA,CAAU,mBAAA,EAAqB,OAAO,CAAA;AAAA,EACpD;AAAA;AAAA,EAGA,sBAAsB,UAAA,EAAoB;AACxC,IAAA,OAAO,OAAO,IAAA,KAAc;AAC1B,MAAA,IAAA,CAAK,uBAAuB,UAAA,EAAY;AAAA,QACtC,IAAA,EAAM,IAAA,CAAK,SAAA,KAAc,QAAA,GAAW,QAAA,GAAW,QAAA;AAAA,QAC/C,UAAA;AAAA,QACA,KAAK,IAAA,CAAK,GAAA;AAAA,QACV,aAAa,IAAA,CAAK,WAAA;AAAA,QAClB,EAAA,EAAI,IAAA,CAAK,EAAA,IAAM,IAAA,CAAK,GAAA,EAAK,EAAA;AAAA,QACzB,UAAU,IAAA,CAAK,QAAA;AAAA,QACf,SAAA,EAAA,iBAAW,IAAI,IAAA,EAAK,EAAE,WAAA,EAAY;AAAA,QAClC,MAAM,IAAA,CAAK;AAAA,OACZ,CAAA;AAAA,IACH,CAAA;AAAA,EACF;AAAA,EAEA,sBAAsB,UAAA,EAAoB;AACxC,IAAA,OAAO,OAAO,IAAA,KAAc;AAC1B,MAAA,IAAA,CAAK,uBAAuB,UAAA,EAAY;AAAA,QACtC,IAAA,EAAM,QAAA;AAAA,QACN,UAAA;AAAA,QACA,KAAK,IAAA,CAAK,GAAA;AAAA,QACV,aAAa,IAAA,CAAK,WAAA;AAAA,QAClB,EAAA,EAAI,IAAA,CAAK,EAAA,IAAM,IAAA,CAAK,GAAA,EAAK,EAAA;AAAA,QACzB,UAAU,IAAA,CAAK,QAAA;AAAA,QACf,SAAA,EAAA,iBAAW,IAAI,IAAA,EAAK,EAAE,WAAA,EAAY;AAAA,QAClC,MAAM,IAAA,CAAK;AAAA,OACZ,CAAA;AAAA,IACH,CAAA;AAAA,EACF;AAAA;AAAA,EAGA,iBAAA,GAA0B;AACxB,IAAA,MAAM,WAAA,GAAc,IAAA,CAAK,QAAA,CAAS,cAAA,EAAe;AACjD,IAAA,KAAA,MAAW,cAAc,WAAA,EAAa;AACpC,MAAA,MAAM,MAAA,GAAS,IAAA,CAAK,QAAA,CAAS,aAAA,CAAc,WAAW,IAAI,CAAA;AAC1D,MAAA,IAAI,MAAA,EAAQ;AACV,QAAA,IAAI,CAAC,MAAA,CAAO,KAAA,EAAO,MAAA,CAAO,QAAQ,EAAC;AACnC,QAAA,IAAI,CAAC,MAAA,CAAO,KAAA,CAAM,aAAa,MAAA,CAAO,KAAA,CAAM,cAAc,EAAC;AAC3D,QAAA,IAAI,CAAC,MAAA,CAAO,KAAA,CAAM,aAAa,MAAA,CAAO,KAAA,CAAM,cAAc,EAAC;AAE3D,QAAA,MAAA,CAAO,MAAM,WAAA,CAAY,IAAA,CAAK,KAAK,qBAAA,CAAsB,UAAA,CAAW,IAAI,CAAC,CAAA;AACzE,QAAA,MAAA,CAAO,MAAM,WAAA,CAAY,IAAA,CAAK,KAAK,qBAAA,CAAsB,UAAA,CAAW,IAAI,CAAC,CAAA;AAAA,MAC3E;AAAA,IACF;AAAA,EACF;AACF;AClKO,IAAM,eAAN,MAAmB;AAAA,EAChB,GAAA;AAAA,EACA,OAAA,uBAAqC,GAAA,EAAI;AAAA,EACzC,MAAA;AAAA,EACA,OAAA;AAAA,EACA,SAAA;AAAA,EAER,YAAY,OAAA,EAA0B;AACpC,IAAA,IAAA,CAAK,OAAA,GAAU,OAAA;AACf,IAAA,IAAA,CAAK,SAAS,OAAA,CAAQ,MAAA;AAEtB,IAAA,IAAA,CAAK,GAAA,GAAM,IAAI,eAAA,CAAgB;AAAA,MAC7B,IAAA,EAAM,QAAQ,IAAA,IAAQ;AAAA,KACvB,CAAA;AAED,IAAA,IAAA,CAAK,WAAA,EAAY;AACjB,IAAA,IAAA,CAAK,iBAAA,EAAkB;AAAA,EACzB;AAAA,EAEQ,WAAA,GAAoB;AAC1B,IAAA,IAAA,CAAK,GAAA,CAAI,EAAA,CAAG,YAAA,EAAc,CAAC,IAAe,GAAA,KAAa;AACrD,MAAA,MAAM,QAAA,GAAW,KAAK,gBAAA,EAAiB;AAEvC,MAAA,IAAI,IAAA,CAAK,QAAQ,cAAA,IAAkB,IAAA,CAAK,QAAQ,IAAA,IAAQ,IAAA,CAAK,QAAQ,cAAA,EAAgB;AACnF,QAAA,EAAA,CAAG,KAAA,CAAM,MAAM,oBAAoB,CAAA;AACnC,QAAA;AAAA,MACF;AAEA,MAAA,MAAM,MAAA,GAAmB;AAAA,QACvB,EAAA,EAAI,QAAA;AAAA,QACJ,EAAA;AAAA,QACA,aAAA,sBAAmB,GAAA,EAAI;AAAA,QACvB,aAAA,EAAe,KAAA;AAAA,QACf,WAAA,sBAAiB,IAAA,EAAK;AAAA,QACtB,YAAA,sBAAkB,IAAA;AAAK,OACzB;AAEA,MAAA,IAAA,CAAK,OAAA,CAAQ,GAAA,CAAI,QAAA,EAAU,MAAM,CAAA;AACjC,MAAA,OAAA,CAAQ,IAAI,CAAA,uBAAA,EAA0B,QAAQ,YAAY,IAAA,CAAK,OAAA,CAAQ,IAAI,CAAA,CAAA,CAAG,CAAA;AAG9E,MAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,QACxB,IAAA,EAAM,WAAA;AAAA,QACN,QAAA;AAAA,QACA,SAAA,EAAA,iBAAW,IAAI,IAAA,EAAK,EAAE,WAAA;AAAY,OACnC,CAAA;AAGD,MAAA,EAAA,CAAG,EAAA,CAAG,SAAA,EAAW,CAAC,IAAA,KAAiB;AACjC,QAAA,IAAA,CAAK,aAAA,CAAc,QAAQ,IAAI,CAAA;AAAA,MACjC,CAAC,CAAA;AAGD,MAAA,EAAA,CAAG,EAAA,CAAG,OAAA,EAAS,CAAC,KAAA,KAAiB;AAC/B,QAAA,OAAA,CAAQ,KAAA,CAAM,CAAA,kBAAA,EAAqB,QAAQ,CAAA,CAAA,CAAA,EAAK,KAAK,CAAA;AAAA,MACvD,CAAC,CAAA;AAGD,MAAA,EAAA,CAAG,EAAA,CAAG,SAAS,MAAM;AACnB,QAAA,IAAA,CAAK,iBAAiB,MAAM,CAAA;AAAA,MAC9B,CAAC,CAAA;AAGD,MAAA,EAAA,CAAG,EAAA,CAAG,QAAQ,MAAM;AAClB,QAAA,MAAA,CAAO,YAAA,uBAAmB,IAAA,EAAK;AAAA,MACjC,CAAC,CAAA;AAAA,IACH,CAAC,CAAA;AAED,IAAA,IAAA,CAAK,GAAA,CAAI,EAAA,CAAG,OAAA,EAAS,CAAC,KAAA,KAAiB;AACrC,MAAA,OAAA,CAAQ,KAAA,CAAM,sBAAsB,KAAK,CAAA;AAAA,IAC3C,CAAC,CAAA;AAAA,EACH;AAAA,EAEQ,aAAA,CAAc,QAAkB,IAAA,EAAoB;AAC1D,IAAA,MAAA,CAAO,YAAA,uBAAmB,IAAA,EAAK;AAE/B,IAAA,IAAI,OAAA;AACJ,IAAA,IAAI;AACF,MAAA,OAAA,GAAU,IAAA,CAAK,KAAA,CAAM,IAAA,CAAK,QAAA,EAAU,CAAA;AAAA,IACtC,CAAA,CAAA,MAAQ;AACN,MAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,QACxB,IAAA,EAAM,OAAA;AAAA,QACN,KAAA,EAAO;AAAA,OACR,CAAA;AACD,MAAA;AAAA,IACF;AAEA,IAAA,QAAQ,QAAQ,IAAA;AAAM,MACpB,KAAK,cAAA;AACH,QAAA,IAAA,CAAK,kBAAA,CAAmB,QAAQ,OAAO,CAAA;AACvC,QAAA;AAAA,MACF,KAAK,WAAA;AACH,QAAA,IAAA,CAAK,eAAA,CAAgB,QAAQ,OAAO,CAAA;AACpC,QAAA;AAAA,MACF,KAAK,aAAA;AACH,QAAA,IAAA,CAAK,iBAAA,CAAkB,QAAQ,OAAO,CAAA;AACtC,QAAA;AAAA,MACF,KAAK,gBAAA;AACH,QAAA,IAAA,CAAK,qBAAqB,MAAM,CAAA;AAChC,QAAA;AAAA,MACF,KAAK,MAAA;AACH,QAAA,IAAA,CAAK,WAAW,MAAM,CAAA;AACtB,QAAA;AAAA,MACF,KAAK,MAAA;AACH,QAAA,IAAA,CAAK,YAAA,CAAa,MAAA,EAAQ,EAAE,IAAA,EAAM,MAAA,EAAQ,SAAA,EAAA,iBAAW,IAAI,IAAA,EAAK,EAAE,WAAA,EAAY,EAAG,CAAA;AAC/E,QAAA;AAAA,MACF;AACE,QAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,UACxB,IAAA,EAAM,OAAA;AAAA,UACN,KAAA,EAAO,CAAA,sBAAA,EAAyB,OAAA,CAAQ,IAAI,CAAA;AAAA,SAC7C,CAAA;AAAA;AACL,EACF;AAAA,EAEA,MAAc,kBAAA,CAAmB,MAAA,EAAkB,OAAA,EAA6B;AAC9E,IAAA,IAAI,CAAC,IAAA,CAAK,OAAA,CAAQ,WAAA,EAAa;AAC7B,MAAA,MAAA,CAAO,aAAA,GAAgB,IAAA;AACvB,MAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,QACxB,IAAA,EAAM,eAAA;AAAA,QACN,OAAA,EAAS;AAAA,OACV,CAAA;AACD,MAAA;AAAA,IACF;AAEA,IAAA,IAAI,CAAC,IAAA,CAAK,OAAA,CAAQ,WAAA,EAAa;AAC7B,MAAA,MAAA,CAAO,aAAA,GAAgB,IAAA;AACvB,MAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,QACxB,IAAA,EAAM,eAAA;AAAA,QACN,OAAA,EAAS;AAAA,OACV,CAAA;AACD,MAAA;AAAA,IACF;AAEA,IAAA,IAAI;AACF,MAAA,MAAM,OAAO,MAAM,IAAA,CAAK,OAAA,CAAQ,WAAA,CAAY,QAAQ,KAAK,CAAA;AACzD,MAAA,MAAA,CAAO,aAAA,GAAgB,IAAA;AACvB,MAAA,MAAA,CAAO,IAAA,GAAO,IAAA;AACd,MAAA,MAAA,CAAO,WAAW,IAAA,CAAK,QAAA;AACvB,MAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,QACxB,IAAA,EAAM,eAAA;AAAA,QACN,OAAA,EAAS,IAAA;AAAA,QACT,MAAM,EAAE,EAAA,EAAI,KAAK,EAAA,EAAI,KAAA,EAAO,KAAK,KAAA;AAAM,OACxC,CAAA;AAAA,IACH,SAAS,KAAA,EAAY;AACnB,MAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,QACxB,IAAA,EAAM,eAAA;AAAA,QACN,OAAA,EAAS,KAAA;AAAA,QACT,OAAO,KAAA,CAAM;AAAA,OACd,CAAA;AAAA,IACH;AAAA,EACF;AAAA,EAEQ,eAAA,CAAgB,QAAkB,OAAA,EAAoB;AAC5D,IAAA,IAAI,IAAA,CAAK,OAAA,CAAQ,WAAA,IAAe,CAAC,OAAO,aAAA,EAAe;AACrD,MAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,QACxB,IAAA,EAAM,OAAA;AAAA,QACN,KAAA,EAAO;AAAA,OACR,CAAA;AACD,MAAA;AAAA,IACF;AAEA,IAAA,MAAM,UAAU,OAAA,CAAQ,OAAA;AACxB,IAAA,IAAI,CAAC,OAAA,EAAS;AACZ,MAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,QACxB,IAAA,EAAM,OAAA;AAAA,QACN,KAAA,EAAO;AAAA,OACR,CAAA;AACD,MAAA;AAAA,IACF;AAGA,IAAA,IAAI,MAAA,CAAO,aAAA,CAAc,GAAA,CAAI,OAAO,CAAA,EAAG;AACrC,MAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,QACxB,IAAA,EAAM,YAAA;AAAA,QACN,OAAA;AAAA,QACA,OAAA,EAAS,IAAA;AAAA,QACT,OAAA,EAAS;AAAA,OACV,CAAA;AACD,MAAA;AAAA,IACF;AAGA,IAAA,MAAM,cAAc,IAAA,CAAK,MAAA,CAAO,SAAA,CAAU,OAAA,EAAS,CAAC,IAAA,KAAc;AAChE,MAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,QACxB,IAAA,EAAM,OAAA;AAAA,QACN,OAAA;AAAA,QACA,IAAA;AAAA,QACA,SAAA,EAAA,iBAAW,IAAI,IAAA,EAAK,EAAE,WAAA;AAAY,OACnC,CAAA;AAAA,IACH,CAAC,CAAA;AAED,IAAA,MAAA,CAAO,cAAc,GAAA,CAAI,OAAA,EAAS,EAAE,OAAA,EAAS,aAAa,CAAA;AAE1D,IAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,MACxB,IAAA,EAAM,YAAA;AAAA,MACN,OAAA;AAAA,MACA,OAAA,EAAS;AAAA,KACV,CAAA;AAAA,EACH;AAAA,EAEQ,iBAAA,CAAkB,QAAkB,OAAA,EAAoB;AAC9D,IAAA,MAAM,UAAU,OAAA,CAAQ,OAAA;AACxB,IAAA,IAAI,CAAC,OAAA,EAAS;AACZ,MAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,QACxB,IAAA,EAAM,OAAA;AAAA,QACN,KAAA,EAAO;AAAA,OACR,CAAA;AACD,MAAA;AAAA,IACF;AAEA,IAAA,MAAM,YAAA,GAAe,MAAA,CAAO,aAAA,CAAc,GAAA,CAAI,OAAO,CAAA;AACrD,IAAA,IAAI,YAAA,EAAc;AAChB,MAAA,YAAA,CAAa,WAAA,EAAY;AACzB,MAAA,MAAA,CAAO,aAAA,CAAc,OAAO,OAAO,CAAA;AACnC,MAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,QACxB,IAAA,EAAM,cAAA;AAAA,QACN,OAAA;AAAA,QACA,OAAA,EAAS;AAAA,OACV,CAAA;AAAA,IACH,CAAA,MAAO;AACL,MAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,QACxB,IAAA,EAAM,cAAA;AAAA,QACN,OAAA;AAAA,QACA,OAAA,EAAS,KAAA;AAAA,QACT,OAAA,EAAS;AAAA,OACV,CAAA;AAAA,IACH;AAAA,EACF;AAAA,EAEQ,qBAAqB,MAAA,EAAwB;AACnD,IAAA,KAAA,MAAW,GAAG,YAAY,CAAA,IAAK,OAAO,aAAA,EAAe;AACnD,MAAA,YAAA,CAAa,WAAA,EAAY;AAAA,IAC3B;AACA,IAAA,MAAA,CAAO,cAAc,KAAA,EAAM;AAE3B,IAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,MACxB,IAAA,EAAM,iBAAA;AAAA,MACN,OAAA,EAAS;AAAA,KACV,CAAA;AAAA,EACH;AAAA,EAEQ,WAAW,MAAA,EAAwB;AACzC,IAAA,MAAM,QAAA,GAAW,IAAA,CAAK,MAAA,CAAO,WAAA,EAAY;AACzC,IAAA,IAAA,CAAK,aAAa,MAAA,EAAQ;AAAA,MACxB,IAAA,EAAM,UAAA;AAAA,MACN,QAAA;AAAA,MACA,OAAO,QAAA,CAAS;AAAA,KACjB,CAAA;AAAA,EACH;AAAA,EAEQ,iBAAiB,MAAA,EAAwB;AAE/C,IAAA,KAAA,MAAW,GAAG,YAAY,CAAA,IAAK,OAAO,aAAA,EAAe;AACnD,MAAA,YAAA,CAAa,WAAA,EAAY;AAAA,IAC3B;AAEA,IAAA,IAAA,CAAK,OAAA,CAAQ,MAAA,CAAO,MAAA,CAAO,EAAE,CAAA;AAC7B,IAAA,OAAA,CAAQ,GAAA,CAAI,6BAA6B,MAAA,CAAO,EAAE,YAAY,IAAA,CAAK,OAAA,CAAQ,IAAI,CAAA,CAAA,CAAG,CAAA;AAAA,EACpF;AAAA,EAEQ,YAAA,CAAa,QAAkB,IAAA,EAAiB;AACtD,IAAA,IAAI,MAAA,CAAO,EAAA,CAAG,UAAA,KAAe,SAAA,CAAU,IAAA,EAAM;AAC3C,MAAA,MAAA,CAAO,EAAA,CAAG,IAAA,CAAK,IAAA,CAAK,SAAA,CAAU,IAAI,CAAC,CAAA;AAAA,IACrC;AAAA,EACF;AAAA,EAEQ,gBAAA,GAA2B;AACjC,IAAA,OAAO,CAAA,GAAA,EAAM,IAAA,CAAK,GAAA,EAAK,IAAI,IAAA,CAAK,MAAA,EAAO,CAAE,QAAA,CAAS,EAAE,CAAA,CAAE,KAAA,CAAM,CAAA,EAAG,CAAC,CAAC,CAAA,CAAA;AAAA,EACnE;AAAA,EAEQ,iBAAA,GAA0B;AAChC,IAAA,IAAI,CAAC,IAAA,CAAK,OAAA,CAAQ,YAAA,EAAc;AAEhC,IAAA,IAAA,CAAK,SAAA,GAAY,YAAY,MAAM;AACjC,MAAA,KAAA,MAAW,CAAC,EAAA,EAAI,MAAM,CAAA,IAAK,KAAK,OAAA,EAAS;AACvC,QAAA,IAAI,MAAA,CAAO,EAAA,CAAG,UAAA,KAAe,SAAA,CAAU,IAAA,EAAM;AAE3C,UAAA,MAAM,wBAAwB,IAAA,CAAK,GAAA,EAAI,GAAI,MAAA,CAAO,aAAa,OAAA,EAAQ;AACvE,UAAA,IAAI,qBAAA,GAAyB,IAAA,CAAK,OAAA,CAAQ,YAAA,GAAgB,CAAA,EAAI;AAC5D,YAAA,OAAA,CAAQ,GAAA,CAAI,CAAA,YAAA,EAAe,EAAE,CAAA,UAAA,CAAY,CAAA;AACzC,YAAA,MAAA,CAAO,GAAG,SAAA,EAAU;AACpB,YAAA,IAAA,CAAK,iBAAiB,MAAM,CAAA;AAC5B,YAAA;AAAA,UACF;AACA,UAAA,MAAA,CAAO,GAAG,IAAA,EAAK;AAAA,QACjB;AAAA,MACF;AAAA,IACF,CAAA,EAAG,IAAA,CAAK,OAAA,CAAQ,YAAY,CAAA;AAAA,EAC9B;AAAA;AAAA;AAAA;AAAA,EAMA,SAAA,CAAU,SAAiB,IAAA,EAAiB;AAC1C,IAAA,IAAA,CAAK,MAAA,CAAO,OAAA,CAAQ,OAAA,EAAS,IAAI,CAAA;AAAA,EACnC;AAAA,EAEA,mBAAA,GAAkC;AAChC,IAAA,OAAO,KAAA,CAAM,IAAA,CAAK,IAAA,CAAK,OAAA,CAAQ,QAAQ,CAAA;AAAA,EACzC;AAAA,EAEA,cAAA,GAAyB;AACvB,IAAA,OAAO,KAAK,OAAA,CAAQ,IAAA;AAAA,EACtB;AAAA,EAEA,oBAAA,GAA+B;AAC7B,IAAA,IAAI,KAAA,GAAQ,CAAA;AACZ,IAAA,KAAA,MAAW,MAAA,IAAU,IAAA,CAAK,OAAA,CAAQ,MAAA,EAAO,EAAG;AAC1C,MAAA,KAAA,IAAS,OAAO,aAAA,CAAc,IAAA;AAAA,IAChC;AACA,IAAA,OAAO,KAAA;AAAA,EACT;AAAA,EAEA,MAAM,KAAA,GAAuB;AAC3B,IAAA,IAAI,KAAK,SAAA,EAAW;AAClB,MAAA,aAAA,CAAc,KAAK,SAAgB,CAAA;AAAA,IACrC;AAGA,IAAA,KAAA,MAAW,MAAA,IAAU,IAAA,CAAK,OAAA,CAAQ,MAAA,EAAO,EAAG;AAC1C,MAAA,MAAA,CAAO,EAAA,CAAG,KAAA,CAAM,IAAA,EAAM,sBAAsB,CAAA;AAAA,IAC9C;AAGA,IAAA,OAAO,IAAI,OAAA,CAAQ,CAAC,OAAA,KAAY;AAC9B,MAAA,IAAA,CAAK,GAAA,CAAI,MAAM,MAAM;AACnB,QAAA,OAAA,CAAQ,IAAI,oBAAoB,CAAA;AAChC,QAAA,OAAA,EAAQ;AAAA,MACV,CAAC,CAAA;AAAA,IACH,CAAC,CAAA;AAAA,EACH;AAAA,EAEA,SAAA,GAA6B;AAC3B,IAAA,OAAO,IAAA,CAAK,GAAA;AAAA,EACd;AACF;AAMO,SAAS,eAAe,OAAA,EAAwC;AACrE,EAAA,OAAO,IAAI,aAAa,OAAO,CAAA;AACjC","file":"chunk-3TPQ2BU6.js","sourcesContent":["// ============================================================================\n// Pub/Sub Event Emitter\n// ============================================================================\n\nexport type EventHandler = (data: any) => void | Promise<void>;\n\nexport class PubSub {\n private channels: Map<string, Set<EventHandler>> = new Map();\n private maxListeners: number;\n\n constructor(maxListeners = 100) {\n this.maxListeners = maxListeners;\n }\n\n subscribe(channel: string, handler: EventHandler): () => void {\n if (!this.channels.has(channel)) {\n this.channels.set(channel, new Set());\n }\n\n const handlers = this.channels.get(channel)!;\n if (handlers.size >= this.maxListeners) {\n throw new Error(`Max listeners (${this.maxListeners}) reached for channel \"${channel}\"`);\n }\n\n handlers.add(handler);\n\n // Return unsubscribe function\n return () => {\n handlers.delete(handler);\n if (handlers.size === 0) {\n this.channels.delete(channel);\n }\n };\n }\n\n publish(channel: string, data: any): void {\n const handlers = this.channels.get(channel);\n if (handlers) {\n for (const handler of handlers) {\n try {\n const result = handler(data);\n if (result instanceof Promise) {\n result.catch((err) => {\n console.error(`[PubSub] Error in handler for channel \"${channel}\":`, err);\n });\n }\n } catch (err) {\n console.error(`[PubSub] Error in handler for channel \"${channel}\":`, err);\n }\n }\n }\n }\n\n hasSubscribers(channel: string): boolean {\n return this.channels.has(channel) && this.channels.get(channel)!.size > 0;\n }\n\n getSubscriberCount(channel: string): number {\n return this.channels.get(channel)?.size || 0;\n }\n\n getChannels(): string[] {\n return Array.from(this.channels.keys());\n }\n\n clear(): void {\n this.channels.clear();\n }\n}\n\n// ============================================================================\n// Kyro-specific Event Types\n// ============================================================================\n\nexport interface KyroEvent {\n type: 'create' | 'update' | 'delete';\n collection: string;\n doc?: any;\n originalDoc?: any;\n id?: string;\n tenantID?: string;\n timestamp: string;\n user?: any;\n}\n\n// ============================================================================\n// Kyro Pub/Sub with Hook Integration\n// ============================================================================\n\nexport class KyroPubSub extends PubSub {\n private registry: any;\n\n constructor(registry: any, maxListeners = 100) {\n super(maxListeners);\n this.registry = registry;\n }\n\n // Publish collection-level events\n publishCollectionEvent(collection: string, event: KyroEvent): void {\n // Publish to collection channel\n this.publish(`collection:${collection}`, event);\n\n // Publish to global events channel\n this.publish('events:collection', event);\n\n // Publish to tenant-specific channel if scoped\n if (event.tenantID) {\n this.publish(`tenant:${event.tenantID}:collection:${collection}`, event);\n this.publish(`tenant:${event.tenantID}:events`, event);\n }\n\n // Publish to type-specific channel\n this.publish(`collection:${collection}:${event.type}`, event);\n }\n\n // Subscribe to a collection\n subscribeToCollection(collection: string, handler: EventHandler): () => void {\n return this.subscribe(`collection:${collection}`, handler);\n }\n\n // Subscribe to a specific event type on a collection\n subscribeToCollectionEvent(\n collection: string,\n eventType: 'create' | 'update' | 'delete',\n handler: EventHandler\n ): () => void {\n return this.subscribe(`collection:${collection}:${eventType}`, handler);\n }\n\n // Subscribe to tenant-scoped events\n subscribeToTenant(tenantID: string, handler: EventHandler): () => void {\n return this.subscribe(`tenant:${tenantID}:events`, handler);\n }\n\n // Subscribe to tenant + collection events\n subscribeToTenantCollection(\n tenantID: string,\n collection: string,\n handler: EventHandler\n ): () => void {\n return this.subscribe(`tenant:${tenantID}:collection:${collection}`, handler);\n }\n\n // Subscribe to all collection events\n subscribeToAllCollections(handler: EventHandler): () => void {\n return this.subscribe('events:collection', handler);\n }\n\n // Create hooks for afterChange/afterDelete\n createAfterChangeHook(collection: string) {\n return async (args: any) => {\n this.publishCollectionEvent(collection, {\n type: args.operation === 'create' ? 'create' : 'update',\n collection,\n doc: args.doc,\n originalDoc: args.originalDoc,\n id: args.id || args.doc?.id,\n tenantID: args.tenantID,\n timestamp: new Date().toISOString(),\n user: args.user,\n });\n };\n }\n\n createAfterDeleteHook(collection: string) {\n return async (args: any) => {\n this.publishCollectionEvent(collection, {\n type: 'delete',\n collection,\n doc: args.doc,\n originalDoc: args.originalDoc,\n id: args.id || args.doc?.id,\n tenantID: args.tenantID,\n timestamp: new Date().toISOString(),\n user: args.user,\n });\n };\n }\n\n // Auto-register hooks for all collections\n autoRegisterHooks(): void {\n const collections = this.registry.getCollections();\n for (const collection of collections) {\n const config = this.registry.getCollection(collection.slug);\n if (config) {\n if (!config.hooks) config.hooks = {};\n if (!config.hooks.afterChange) config.hooks.afterChange = [];\n if (!config.hooks.afterDelete) config.hooks.afterDelete = [];\n\n config.hooks.afterChange.push(this.createAfterChangeHook(collection.slug));\n config.hooks.afterDelete.push(this.createAfterDeleteHook(collection.slug));\n }\n }\n }\n}\n","import { WebSocketServer, WebSocket } from 'ws';\nimport type { KyroPubSub, KyroEvent } from './pubsub.js';\n\n// ============================================================================\n// WebSocket Server\n// ============================================================================\n\nexport interface WSServerOptions {\n port?: number;\n pubsub: KyroPubSub;\n maxConnections?: number;\n pingInterval?: number;\n requireAuth?: boolean;\n verifyToken?: (token: string) => Promise<any>;\n}\n\nexport interface WSSubscription {\n channel: string;\n unsubscribe: () => void;\n}\n\nexport interface WSClient {\n id: string;\n ws: WebSocket;\n subscriptions: Map<string, WSSubscription>;\n authenticated: boolean;\n user?: any;\n tenantID?: string;\n connectedAt: Date;\n lastActivity: Date;\n}\n\nexport class KyroWSServer {\n private wss: WebSocketServer;\n private clients: Map<string, WSClient> = new Map();\n private pubsub: KyroPubSub;\n private options: WSServerOptions;\n private pingTimer?: NodeJS.Timer;\n\n constructor(options: WSServerOptions) {\n this.options = options;\n this.pubsub = options.pubsub;\n\n this.wss = new WebSocketServer({\n port: options.port || 8080,\n });\n\n this.setupServer();\n this.startPingInterval();\n }\n\n private setupServer(): void {\n this.wss.on('connection', (ws: WebSocket, req: any) => {\n const clientId = this.generateClientId();\n\n if (this.options.maxConnections && this.clients.size >= this.options.maxConnections) {\n ws.close(1013, 'Server at capacity');\n return;\n }\n\n const client: WSClient = {\n id: clientId,\n ws,\n subscriptions: new Map(),\n authenticated: false,\n connectedAt: new Date(),\n lastActivity: new Date(),\n };\n\n this.clients.set(clientId, client);\n console.log(`[WS] Client connected: ${clientId} (total: ${this.clients.size})`);\n\n // Send welcome message\n this.sendToClient(client, {\n type: 'connected',\n clientId,\n timestamp: new Date().toISOString(),\n });\n\n // Handle messages\n ws.on('message', (data: Buffer) => {\n this.handleMessage(client, data);\n });\n\n // Handle errors\n ws.on('error', (error: Error) => {\n console.error(`[WS] Client error ${clientId}:`, error);\n });\n\n // Handle close\n ws.on('close', () => {\n this.handleDisconnect(client);\n });\n\n // Handle pong\n ws.on('pong', () => {\n client.lastActivity = new Date();\n });\n });\n\n this.wss.on('error', (error: Error) => {\n console.error('[WS] Server error:', error);\n });\n }\n\n private handleMessage(client: WSClient, data: Buffer): void {\n client.lastActivity = new Date();\n\n let message: any;\n try {\n message = JSON.parse(data.toString());\n } catch {\n this.sendToClient(client, {\n type: 'error',\n error: 'Invalid JSON',\n });\n return;\n }\n\n switch (message.type) {\n case 'authenticate':\n this.handleAuthenticate(client, message);\n break;\n case 'subscribe':\n this.handleSubscribe(client, message);\n break;\n case 'unsubscribe':\n this.handleUnsubscribe(client, message);\n break;\n case 'unsubscribeAll':\n this.handleUnsubscribeAll(client);\n break;\n case 'list':\n this.handleList(client);\n break;\n case 'ping':\n this.sendToClient(client, { type: 'pong', timestamp: new Date().toISOString() });\n break;\n default:\n this.sendToClient(client, {\n type: 'error',\n error: `Unknown message type: ${message.type}`,\n });\n }\n }\n\n private async handleAuthenticate(client: WSClient, message: any): Promise<void> {\n if (!this.options.requireAuth) {\n client.authenticated = true;\n this.sendToClient(client, {\n type: 'authenticated',\n success: true,\n });\n return;\n }\n\n if (!this.options.verifyToken) {\n client.authenticated = true;\n this.sendToClient(client, {\n type: 'authenticated',\n success: true,\n });\n return;\n }\n\n try {\n const user = await this.options.verifyToken(message.token);\n client.authenticated = true;\n client.user = user;\n client.tenantID = user.tenantID;\n this.sendToClient(client, {\n type: 'authenticated',\n success: true,\n user: { id: user.id, email: user.email },\n });\n } catch (error: any) {\n this.sendToClient(client, {\n type: 'authenticated',\n success: false,\n error: error.message,\n });\n }\n }\n\n private handleSubscribe(client: WSClient, message: any): void {\n if (this.options.requireAuth && !client.authenticated) {\n this.sendToClient(client, {\n type: 'error',\n error: 'Not authenticated',\n });\n return;\n }\n\n const channel = message.channel;\n if (!channel) {\n this.sendToClient(client, {\n type: 'error',\n error: 'Channel is required',\n });\n return;\n }\n\n // Check if already subscribed\n if (client.subscriptions.has(channel)) {\n this.sendToClient(client, {\n type: 'subscribed',\n channel,\n success: true,\n message: 'Already subscribed',\n });\n return;\n }\n\n // Subscribe to channel\n const unsubscribe = this.pubsub.subscribe(channel, (data: any) => {\n this.sendToClient(client, {\n type: 'event',\n channel,\n data,\n timestamp: new Date().toISOString(),\n });\n });\n\n client.subscriptions.set(channel, { channel, unsubscribe });\n\n this.sendToClient(client, {\n type: 'subscribed',\n channel,\n success: true,\n });\n }\n\n private handleUnsubscribe(client: WSClient, message: any): void {\n const channel = message.channel;\n if (!channel) {\n this.sendToClient(client, {\n type: 'error',\n error: 'Channel is required',\n });\n return;\n }\n\n const subscription = client.subscriptions.get(channel);\n if (subscription) {\n subscription.unsubscribe();\n client.subscriptions.delete(channel);\n this.sendToClient(client, {\n type: 'unsubscribed',\n channel,\n success: true,\n });\n } else {\n this.sendToClient(client, {\n type: 'unsubscribed',\n channel,\n success: false,\n message: 'Not subscribed',\n });\n }\n }\n\n private handleUnsubscribeAll(client: WSClient): void {\n for (const [, subscription] of client.subscriptions) {\n subscription.unsubscribe();\n }\n client.subscriptions.clear();\n\n this.sendToClient(client, {\n type: 'unsubscribedAll',\n success: true,\n });\n }\n\n private handleList(client: WSClient): void {\n const channels = this.pubsub.getChannels();\n this.sendToClient(client, {\n type: 'channels',\n channels,\n count: channels.length,\n });\n }\n\n private handleDisconnect(client: WSClient): void {\n // Unsubscribe from all channels\n for (const [, subscription] of client.subscriptions) {\n subscription.unsubscribe();\n }\n\n this.clients.delete(client.id);\n console.log(`[WS] Client disconnected: ${client.id} (total: ${this.clients.size})`);\n }\n\n private sendToClient(client: WSClient, data: any): void {\n if (client.ws.readyState === WebSocket.OPEN) {\n client.ws.send(JSON.stringify(data));\n }\n }\n\n private generateClientId(): string {\n return `ws_${Date.now()}_${Math.random().toString(36).slice(2, 9)}`;\n }\n\n private startPingInterval(): void {\n if (!this.options.pingInterval) return;\n\n this.pingTimer = setInterval(() => {\n for (const [id, client] of this.clients) {\n if (client.ws.readyState === WebSocket.OPEN) {\n // Check if client responded to last ping\n const timeSinceLastActivity = Date.now() - client.lastActivity.getTime();\n if (timeSinceLastActivity > (this.options.pingInterval! * 3)) {\n console.log(`[WS] Client ${id} timed out`);\n client.ws.terminate();\n this.handleDisconnect(client);\n continue;\n }\n client.ws.ping();\n }\n }\n }, this.options.pingInterval);\n }\n\n // ============================================================================\n // Public API\n // ============================================================================\n\n broadcast(channel: string, data: any): void {\n this.pubsub.publish(channel, data);\n }\n\n getConnectedClients(): WSClient[] {\n return Array.from(this.clients.values());\n }\n\n getClientCount(): number {\n return this.clients.size;\n }\n\n getSubscriptionCount(): number {\n let count = 0;\n for (const client of this.clients.values()) {\n count += client.subscriptions.size;\n }\n return count;\n }\n\n async close(): Promise<void> {\n if (this.pingTimer) {\n clearInterval(this.pingTimer as any);\n }\n\n // Close all client connections\n for (const client of this.clients.values()) {\n client.ws.close(1001, 'Server shutting down');\n }\n\n // Close server\n return new Promise((resolve) => {\n this.wss.close(() => {\n console.log('[WS] Server closed');\n resolve();\n });\n });\n }\n\n getServer(): WebSocketServer {\n return this.wss;\n }\n}\n\n// ============================================================================\n// Factory\n// ============================================================================\n\nexport function createWSServer(options: WSServerOptions): KyroWSServer {\n return new KyroWSServer(options);\n}\n"]}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/integration.ts"],"names":[],"mappings":";;;;AAIA,IAAM,yBAAyB,IAAA,CAAK,OAAA;AAAA,EAClC,IAAI,GAAA,CAAI,GAAA,EAAK,MAAA,CAAA,IAAA,CAAY,GAAG,CAAA,CAAE,QAAA;AAAA,EAC9B;AACF,CAAA;AACA,IAAM,6BAA6B,IAAA,CAAK,OAAA;AAAA,EACtC,IAAI,GAAA,CAAI,GAAA,EAAK,MAAA,CAAA,IAAA,CAAY,GAAG,CAAA,CAAE,QAAA;AAAA,EAC9B;AACF,CAAA;AACA,IAAM,0BAA0B,IAAA,CAAK,OAAA;AAAA,EACnC,IAAI,GAAA,CAAI,GAAA,EAAK,MAAA,CAAA,IAAA,CAAY,GAAG,CAAA,CAAE,QAAA;AAAA,EAC9B;AACF,CAAA;AAYe,SAAR,IAAA,CAAsB,OAAA,GAAkC,EAAC,EAAqB;AACnF,EAAA,MAAM;AAAA,IACJ,UAAA,GAAa,kBAAA;AAAA,IACb,OAAA,GAAU,MAAA;AAAA,IACV,SAAA,GAAY,QAAA;AAAA,IACZ,KAAA,GAAQ,IAAA;AAAA,IACR,aAAA,GAAgB,KAAA;AAAA,IAChB,UAAA,GAAa,KAAA;AAAA,IACb,eAAA,GAAkB;AAAA,GACpB,GAAI,OAAA;AAEJ,EAAA,OAAO;AAAA,IACL,IAAA,EAAM,gBAAA;AAAA,IACN,KAAA,EAAO;AAAA,MACL,sBAAsB,OAAO,EAAE,QAAQ,YAAA,EAAc,WAAA,EAAa,QAAO,KAAM;AAC7E,QAAA,MAAA,CAAO,IAAA,CAAK,CAAA,0BAAA,EAA6B,OAAO,CAAA,SAAA,EAAY,SAAS,CAAA,CAAA,CAAG,CAAA;AAExE,QAAA,IAAI,YAAY,SAAA,EAAW;AACzB,UAAA,MAAM,IAAI,KAAA,CAAM,CAAA,qDAAA,EAAwD,OAAO,CAAA,EAAA,CAAI,CAAA;AAAA,QACrF;AAEA,QAAA,MAAM,qBAAqB,IAAA,CAAK,OAAA,CAAQ,MAAA,CAAO,IAAA,CAAK,UAAU,UAAU,CAAA;AAExE,QAAA,IAAI,eAAA,GAAkB,kBAAA;AACtB,QAAA,IAAI,CAAC,EAAA,CAAG,UAAA,CAAW,kBAAkB,CAAA,EAAG;AACtC,UAAA,MAAA,CAAO,IAAA,CAAK,CAAA,8BAAA,EAAiC,UAAU,CAAA,sDAAA,CAAwD,CAAA;AAAA,QACjH;AAEA,QAAA,YAAA,CAAa;AAAA,UACX,IAAA,EAAM;AAAA,YACJ,OAAA,EAAS;AAAA,cACP;AAAA,gBACE,IAAA,EAAM,kCAAA;AAAA,gBACN,OAAA,EAAS,KAAA;AAAA,gBACT,UAAU,EAAA,EAAY;AACpB,kBAAA,IACE,EAAA,KAAO,8BAAA,IACP,EAAA,KAAO,uCAAA,EACP;AACA,oBAAA,OAAO,wCAAA;AAAA,kBACT;AACA,kBAAA,IACE,EAAA,KAAO,4CAAA,IACP,EAAA,KAAO,+CAAA,EACP;AACA,oBAAA,OAAO,sDAAA;AAAA,kBACT;AAAA,gBACF,CAAA;AAAA,gBACA,KAAK,EAAA,EAAY;AACf,kBAAA,IAAI,OAAO,wCAAA,EAA0C;AACnD,oBAAA,OAAO,CAAA,6CAAA,CAAA;AAAA,kBACT;AACA,kBAAA,IAAI,OAAO,sDAAA,EAAwD;AACjE,oBAAA,OAAO;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA,CAAA;AAAA,kBAoBT;AAAA,gBACF;AAAA;AACF,aACF;AAAA,YACA,OAAA,EAAS;AAAA,cACP,KAAA,EAAO;AAAA,gBACL,aAAA,EAAe;AAAA;AACjB,aACF;AAAA,YACA,MAAA,EAAQ;AAAA,cACN,iBAAA,EAAmB,IAAA,CAAK,SAAA,CAAU,OAAO,CAAA;AAAA,cACzC,mBAAA,EAAqB,IAAA,CAAK,SAAA,CAAU,SAAS,CAAA;AAAA,cAC7C,uBAAA,EAAyB,IAAA,CAAK,SAAA,CAAU,aAAa,CAAA;AAAA,cACrD,oBAAA,EAAsB,IAAA,CAAK,SAAA,CAAU,UAAU,CAAA;AAAA,cAC/C,kBAAA,EAAoB,IAAA,CAAK,SAAA,CAAU,eAAe;AAAA;AACpD;AACF,SACD,CAAA;AAED,QAAA,WAAA,CAAY;AAAA,UACV,OAAA,EAAS,GAAG,OAAO,CAAA,UAAA,CAAA;AAAA,UACnB,UAAA,EAAY;AAAA,SACb,CAAA;AAED,QAAA,IAAI,aAAA,EAAe;AACjB,UAAA,WAAA,CAAY;AAAA,YACV,OAAA,EAAS,GAAG,OAAO,CAAA,QAAA,CAAA;AAAA,YACnB,UAAA,EAAY;AAAA,WACb,CAAA;AACD,UAAA,MAAA,CAAO,IAAA,CAAK,CAAA,4BAAA,EAA+B,OAAO,CAAA,QAAA,CAAU,CAAA;AAAA,QAC9D;AAEA,QAAA,IAAI,UAAA,EAAY;AACd,UAAA,WAAA,CAAY;AAAA,YACV,OAAA,EAAS,GAAG,OAAO,CAAA,eAAA,CAAA;AAAA,YACnB,UAAA,EAAY;AAAA,WACb,CAAA;AACD,UAAA,MAAA,CAAO,IAAA,CAAK,CAAA,yBAAA,EAA4B,OAAO,CAAA,KAAA,CAAO,CAAA;AAAA,QACxD;AAEA,QAAA,IAAI,eAAA,EAAiB;AACnB,UAAA,MAAA,CAAO,KAAK,CAAA,wDAAA,CAA0D,CAAA;AAAA,QACxE;AAAA,MACF;AAAA;AACF,GACF;AACF","file":"chunk-4AO3A3JM.js","sourcesContent":["import type { AstroIntegration } from \"astro\";\nimport path from \"path\";\nimport fs from \"fs\";\n\nconst API_HANDLER_ENTRYPOINT = path.resolve(\n new URL(\".\", import.meta.url).pathname,\n \"api-handler.js\",\n);\nconst GRAPHQL_HANDLER_ENTRYPOINT = path.resolve(\n new URL(\".\", import.meta.url).pathname,\n \"api-handler-graphql.js\",\n);\nconst TRPC_HANDLER_ENTRYPOINT = path.resolve(\n new URL(\".\", import.meta.url).pathname,\n \"api-handler-trpc.js\",\n);\n\nexport interface KyroIntegrationOptions {\n configPath?: string;\n apiPath?: string;\n adminPath?: string;\n admin?: boolean;\n enableGraphQL?: boolean;\n enableTRPC?: boolean;\n enableWebSocket?: boolean;\n}\n\nexport default function kyro(options: KyroIntegrationOptions = {}): AstroIntegration {\n const {\n configPath = \"./kyro.config.ts\",\n apiPath = \"/api\",\n adminPath = \"/admin\",\n admin = true,\n enableGraphQL = false,\n enableTRPC = false,\n enableWebSocket = false,\n } = options;\n\n return {\n name: \"@kyro-cms/core\",\n hooks: {\n \"astro:config:setup\": async ({ config, updateConfig, injectRoute, logger }) => {\n logger.info(`Setting up Kyro CMS (API: ${apiPath}, Admin: ${adminPath})`);\n \n if (apiPath === adminPath) {\n throw new Error(`Kyro CMS: apiPath and adminPath cannot be the same (\"${apiPath}\")`);\n }\n\n const resolvedConfigPath = path.resolve(config.root.pathname, configPath);\n \n let finalConfigPath = resolvedConfigPath;\n if (!fs.existsSync(resolvedConfigPath)) {\n logger.warn(`Kyro config file not found at ${configPath}. The API will fail to boot if collections are needed.`);\n }\n \n updateConfig({\n vite: {\n plugins: [\n {\n name: \"use-sync-external-store-shim-fix\",\n enforce: \"pre\" as const,\n resolveId(id: string) {\n if (\n id === \"use-sync-external-store/shim\" ||\n id === \"use-sync-external-store/shim/index.js\"\n ) {\n return \"\\0virtual:use-sync-external-store-shim\";\n }\n if (\n id === \"use-sync-external-store/shim/with-selector\" ||\n id === \"use-sync-external-store/shim/with-selector.js\"\n ) {\n return \"\\0virtual:use-sync-external-store-shim-with-selector\";\n }\n },\n load(id: string) {\n if (id === \"\\0virtual:use-sync-external-store-shim\") {\n return `export { useSyncExternalStore } from \"react\";`;\n }\n if (id === \"\\0virtual:use-sync-external-store-shim-with-selector\") {\n return `\nimport { useSyncExternalStore, useMemo } from \"react\";\nexport function useSyncExternalStoreWithSelector(subscribe, getSnapshot, getServerSnapshot, selector, isEqual) {\n const memoizedSelector = useMemo(() => {\n let last, lastSnap, hasMemo = false;\n return (snap) => {\n if (!hasMemo || !Object.is(lastSnap, snap)) {\n const next = selector(snap);\n if (!hasMemo || !(isEqual ? isEqual(last, next) : Object.is(last, next))) {\n last = next; lastSnap = snap; hasMemo = true;\n }\n }\n return last;\n };\n }, [selector, isEqual]);\n const getSelection = () => memoizedSelector(getSnapshot());\n const getServerSelection = getServerSnapshot != null ? () => memoizedSelector(getServerSnapshot()) : undefined;\n return useSyncExternalStore(subscribe, getSelection, getServerSelection);\n}\n`;\n }\n },\n },\n ],\n resolve: {\n alias: {\n \"kyro:config\": finalConfigPath,\n },\n },\n define: {\n __KYRO_API_PATH__: JSON.stringify(apiPath),\n __KYRO_ADMIN_PATH__: JSON.stringify(adminPath),\n __KYRO_ENABLE_GRAPHQL__: JSON.stringify(enableGraphQL),\n __KYRO_ENABLE_TRPC__: JSON.stringify(enableTRPC),\n __KYRO_ENABLE_WS__: JSON.stringify(enableWebSocket),\n },\n },\n });\n \n injectRoute({\n pattern: `${apiPath}/[...path]`,\n entrypoint: API_HANDLER_ENTRYPOINT,\n });\n\n if (enableGraphQL) {\n injectRoute({\n pattern: `${apiPath}/graphql`,\n entrypoint: GRAPHQL_HANDLER_ENTRYPOINT,\n });\n logger.info(`GraphQL endpoint enabled at ${apiPath}/graphql`);\n }\n\n if (enableTRPC) {\n injectRoute({\n pattern: `${apiPath}/trpc/[...path]`,\n entrypoint: TRPC_HANDLER_ENTRYPOINT,\n });\n logger.info(`tRPC endpoint enabled at ${apiPath}/trpc`);\n }\n\n if (enableWebSocket) {\n logger.info(`WebSocket support enabled (auto-starts at first request)`);\n }\n },\n },\n };\n}\n"]}
|