payload-intl 0.2.4 → 1.0.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.
Files changed (131) hide show
  1. package/README.md +8 -12
  2. package/dist/components/MessageController.d.ts +2 -1
  3. package/dist/components/MessageController.d.ts.map +1 -0
  4. package/dist/components/MessageController.js +26 -48
  5. package/dist/components/MessageController.js.map +1 -1
  6. package/dist/components/MessagesForm.d.ts +2 -1
  7. package/dist/components/MessagesForm.d.ts.map +1 -0
  8. package/dist/components/MessagesForm.js +28 -32
  9. package/dist/components/MessagesForm.js.map +1 -1
  10. package/dist/components/actions/JsonImport.d.ts +1 -0
  11. package/dist/components/actions/JsonImport.d.ts.map +1 -0
  12. package/dist/components/actions/JsonImport.js +4 -4
  13. package/dist/components/actions/JsonImport.js.map +1 -1
  14. package/dist/components/actions/Move.d.ts +2 -3
  15. package/dist/components/actions/Move.d.ts.map +1 -0
  16. package/dist/components/inputs/InputWrapper.d.ts +1 -0
  17. package/dist/components/inputs/InputWrapper.d.ts.map +1 -0
  18. package/dist/components/inputs/InputWrapper.js.map +1 -1
  19. package/dist/components/inputs/LexicalInput.d.ts +1 -0
  20. package/dist/components/inputs/LexicalInput.d.ts.map +1 -0
  21. package/dist/components/inputs/MessageInput.d.ts +2 -1
  22. package/dist/components/inputs/MessageInput.d.ts.map +1 -0
  23. package/dist/components/inputs/MessageInput.js +1 -1
  24. package/dist/components/inputs/MessageInput.js.map +1 -1
  25. package/dist/components/inputs/variables/VariableChip.d.ts +1 -0
  26. package/dist/components/inputs/variables/VariableChip.d.ts.map +1 -0
  27. package/dist/components/inputs/variables/VariableChip.js +3 -3
  28. package/dist/components/inputs/variables/VariableChip.js.map +1 -1
  29. package/dist/components/inputs/variables/VariableIcon.d.ts +3 -2
  30. package/dist/components/inputs/variables/VariableIcon.d.ts.map +1 -0
  31. package/dist/components/inputs/variables/VariableSuggestion.d.ts +2 -1
  32. package/dist/components/inputs/variables/VariableSuggestion.d.ts.map +1 -0
  33. package/dist/components/inputs/variables/VariableSuggestion.js +2 -2
  34. package/dist/components/inputs/variables/VariableSuggestion.js.map +1 -1
  35. package/dist/components/inputs/variables/editors/DateVariableEditor.d.ts +2 -1
  36. package/dist/components/inputs/variables/editors/DateVariableEditor.d.ts.map +1 -0
  37. package/dist/components/inputs/variables/editors/PluralVariableEditor.d.ts +2 -1
  38. package/dist/components/inputs/variables/editors/PluralVariableEditor.d.ts.map +1 -0
  39. package/dist/components/inputs/variables/editors/PluralVariableEditor.js +31 -34
  40. package/dist/components/inputs/variables/editors/PluralVariableEditor.js.map +1 -1
  41. package/dist/components/inputs/variables/editors/SelectVariableEditor.d.ts +2 -1
  42. package/dist/components/inputs/variables/editors/SelectVariableEditor.d.ts.map +1 -0
  43. package/dist/components/inputs/variables/editors/SelectVariableEditor.js +17 -10
  44. package/dist/components/inputs/variables/editors/SelectVariableEditor.js.map +1 -1
  45. package/dist/components/inputs/variables/editors/TagVariableEditor.d.ts +2 -1
  46. package/dist/components/inputs/variables/editors/TagVariableEditor.d.ts.map +1 -0
  47. package/dist/components/inputs/variables/editors/TagVariableEditor.js.map +1 -1
  48. package/dist/components/inputs/variables/editors/TimeVariableEditor.d.ts +2 -1
  49. package/dist/components/inputs/variables/editors/TimeVariableEditor.d.ts.map +1 -0
  50. package/dist/components/inputs/variables/extension.d.ts +2 -1
  51. package/dist/components/inputs/variables/extension.d.ts.map +1 -0
  52. package/dist/components/inputs/variables/extension.js.map +1 -1
  53. package/dist/components/inputs/variables/pickers/NumericVariablePicker.d.ts +2 -1
  54. package/dist/components/inputs/variables/pickers/NumericVariablePicker.d.ts.map +1 -0
  55. package/dist/components/inputs/variables/pickers/NumericVariablePicker.js +4 -4
  56. package/dist/components/inputs/variables/pickers/NumericVariablePicker.js.map +1 -1
  57. package/dist/components/inputs/variables/pickers/TemporalElementEditor.d.ts +2 -1
  58. package/dist/components/inputs/variables/pickers/TemporalElementEditor.d.ts.map +1 -0
  59. package/dist/components/layout/MessageField.d.ts +2 -1
  60. package/dist/components/layout/MessageField.d.ts.map +1 -0
  61. package/dist/components/layout/MessageField.js +12 -12
  62. package/dist/components/layout/MessageField.js.map +1 -1
  63. package/dist/components/layout/MessagesTabs.d.ts +2 -1
  64. package/dist/components/layout/MessagesTabs.d.ts.map +1 -0
  65. package/dist/components/layout/MessagesTabs.js +3 -3
  66. package/dist/components/layout/MessagesTabs.js.map +1 -1
  67. package/dist/components/layout/MessagesTree.d.ts +2 -1
  68. package/dist/components/layout/MessagesTree.d.ts.map +1 -0
  69. package/dist/components/layout/MessagesTree.js +2 -2
  70. package/dist/components/layout/MessagesTree.js.map +1 -1
  71. package/dist/context/messages-form.d.ts +2 -1
  72. package/dist/context/messages-form.d.ts.map +1 -0
  73. package/dist/context/messages-form.js.map +1 -1
  74. package/dist/endpoints/get-messages.d.ts +1 -0
  75. package/dist/endpoints/get-messages.d.ts.map +1 -0
  76. package/dist/endpoints/get-messages.js.map +1 -1
  77. package/dist/endpoints/set-messages.d.ts +1 -0
  78. package/dist/endpoints/set-messages.d.ts.map +1 -0
  79. package/dist/endpoints/set-messages.js.map +1 -1
  80. package/dist/exports/link.d.ts +2 -1
  81. package/dist/exports/link.d.ts.map +1 -0
  82. package/dist/exports/link.js.map +1 -1
  83. package/dist/exports/rsc.d.ts +1 -0
  84. package/dist/exports/rsc.d.ts.map +1 -0
  85. package/dist/exports/view.d.ts +2 -1
  86. package/dist/exports/view.d.ts.map +1 -0
  87. package/dist/exports/view.js +26 -30
  88. package/dist/exports/view.js.map +1 -1
  89. package/dist/index.d.ts +2 -1
  90. package/dist/index.d.ts.map +1 -0
  91. package/dist/index.js +19 -34
  92. package/dist/index.js.map +1 -1
  93. package/dist/requests/fetchMessages.d.ts +1 -0
  94. package/dist/requests/fetchMessages.d.ts.map +1 -0
  95. package/dist/requests/fetchMessages.js.map +1 -1
  96. package/dist/styles.css +1 -1
  97. package/dist/types.d.ts +5 -4
  98. package/dist/types.d.ts.map +1 -0
  99. package/dist/utils/cn.d.ts +1 -0
  100. package/dist/utils/cn.d.ts.map +1 -0
  101. package/dist/utils/cn.js.map +1 -1
  102. package/dist/utils/config.d.ts +2 -1
  103. package/dist/utils/config.d.ts.map +1 -0
  104. package/dist/utils/config.js.map +1 -1
  105. package/dist/utils/error-handling.d.ts +1 -0
  106. package/dist/utils/error-handling.d.ts.map +1 -0
  107. package/dist/utils/error-handling.js.map +1 -1
  108. package/dist/utils/format.d.ts +2 -1
  109. package/dist/utils/format.d.ts.map +1 -0
  110. package/dist/utils/format.js.map +1 -1
  111. package/dist/utils/guards.d.ts +2 -0
  112. package/dist/utils/guards.d.ts.map +1 -0
  113. package/dist/utils/guards.js +14 -11
  114. package/dist/utils/guards.js.map +1 -1
  115. package/dist/utils/icu-tranform.d.ts +6 -5
  116. package/dist/utils/icu-tranform.d.ts.map +1 -0
  117. package/dist/utils/icu-tranform.js +32 -27
  118. package/dist/utils/icu-tranform.js.map +1 -1
  119. package/dist/utils/sanitize.d.ts +2 -1
  120. package/dist/utils/sanitize.d.ts.map +1 -0
  121. package/dist/utils/sanitize.js.map +1 -1
  122. package/dist/utils/schema.d.ts +3 -2
  123. package/dist/utils/schema.d.ts.map +1 -0
  124. package/dist/utils/schema.js +10 -9
  125. package/dist/utils/schema.js.map +1 -1
  126. package/dist/utils/validate.d.ts +2 -1
  127. package/dist/utils/validate.d.ts.map +1 -0
  128. package/dist/utils/validate.js.map +1 -1
  129. package/package.json +57 -72
  130. package/dist/components/inputs/LexicalInput.js +0 -80
  131. package/dist/components/inputs/LexicalInput.js.map +0 -1
@@ -1,9 +1,10 @@
1
1
  import { parse as r, TYPE as e } from "@formatjs/icu-messageformat-parser";
2
- const n = (a) => ({
2
+ const i = (a) => ({
3
3
  description: a.match(/^\[.+\]/)?.[0]?.slice(1, -1),
4
- type: a === "$RICH$" ? "rich" : "icu",
5
- variables: i(a)
6
- }), i = (a) => c(r(a)), c = (a) => a.flatMap((t) => {
4
+ // type: schema === "$RICH$" ? "rich" : "icu",
5
+ type: "icu",
6
+ variables: l(a)
7
+ }), l = (a) => s(r(a)), s = (a) => a.flatMap((t) => {
7
8
  switch (t.type) {
8
9
  case e.literal:
9
10
  case e.pound:
@@ -17,18 +18,18 @@ const n = (a) => ({
17
18
  case e.select:
18
19
  return [
19
20
  t,
20
- ...c(
21
- Object.values(t.options).flatMap(({ value: s }) => s)
21
+ ...s(
22
+ Object.values(t.options).flatMap(({ value: c }) => c)
22
23
  )
23
24
  ];
24
25
  case e.tag:
25
- return [t, ...c(t.children)];
26
+ return [t, ...s(t.children)];
26
27
  default:
27
28
  return [t];
28
29
  }
29
30
  });
30
31
  export {
31
- i as extractTemplateVariables,
32
- n as parseMessageSchema
32
+ l as extractTemplateVariables,
33
+ i as parseMessageSchema
33
34
  };
34
35
  //# sourceMappingURL=schema.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"schema.js","sources":["../../src/utils/schema.ts"],"sourcesContent":["import type { MessageSchema, TemplateVariable } from \"@/types\";\nimport type { MessageFormatElement } from \"@formatjs/icu-messageformat-parser\";\nimport { parse, TYPE } from \"@formatjs/icu-messageformat-parser\";\n\nexport const parseMessageSchema = (schema: MessageSchema): MessageConfig => {\n const description = schema.match(/^\\[.+\\]/)?.[0];\n // TODO add support for variables description\n // const withoutDescription = schema.replace(description || \"\", \"\").trim();\n // const withoutOptional = withoutDescription.split(\" | \")[0]?.trim();\n\n return {\n description: description?.slice(1, -1),\n type: schema === \"$RICH$\" ? \"rich\" : \"icu\",\n variables: extractTemplateVariables(schema),\n };\n};\n\nexport const extractTemplateVariables = (\n schema: MessageSchema,\n): TemplateVariable[] => collectTemplateVariables(parse(schema));\n\nconst collectTemplateVariables = (\n parts: MessageFormatElement[],\n): TemplateVariable[] =>\n parts.flatMap<TemplateVariable>((part) => {\n switch (part.type) {\n case TYPE.literal:\n case TYPE.pound:\n return [];\n case TYPE.argument:\n case TYPE.number:\n case TYPE.date:\n case TYPE.time:\n return [part];\n case TYPE.plural:\n case TYPE.select:\n return [\n part,\n ...collectTemplateVariables(\n Object.values(part.options).flatMap(({ value }) => value),\n ),\n ];\n case TYPE.tag:\n return [part, ...collectTemplateVariables(part.children)];\n default:\n return [part];\n }\n });\n\n// MARK: Types\n\nexport type MessageType = \"rich\" | \"icu\";\nexport type MessageConfig = {\n description: string | undefined;\n type: MessageType;\n variables: TemplateVariable[];\n};\n"],"names":["parseMessageSchema","schema","extractTemplateVariables","collectTemplateVariables","parse","parts","part","TYPE","value"],"mappings":";AAIO,MAAMA,IAAqB,CAACC,OAM1B;AAAA,EACL,aANkBA,EAAO,MAAM,SAAS,IAAI,CAAC,GAMnB,MAAM,GAAG,EAAE;AAAA,EACrC,MAAMA,MAAW,WAAW,SAAS;AAAA,EACrC,WAAWC,EAAyBD,CAAM;AAAA,IAIjCC,IAA2B,CACtCD,MACuBE,EAAyBC,EAAMH,CAAM,CAAC,GAEzDE,IAA2B,CAC/BE,MAEAA,EAAM,QAA0B,CAACC,MAAS;AACxC,UAAQA,EAAK,MAAA;AAAA,IACX,KAAKC,EAAK;AAAA,IACV,KAAKA,EAAK;AACR,aAAO,CAAA;AAAA,IACT,KAAKA,EAAK;AAAA,IACV,KAAKA,EAAK;AAAA,IACV,KAAKA,EAAK;AAAA,IACV,KAAKA,EAAK;AACR,aAAO,CAACD,CAAI;AAAA,IACd,KAAKC,EAAK;AAAA,IACV,KAAKA,EAAK;AACR,aAAO;AAAA,QACLD;AAAA,QACA,GAAGH;AAAA,UACD,OAAO,OAAOG,EAAK,OAAO,EAAE,QAAQ,CAAC,EAAE,OAAAE,EAAA,MAAYA,CAAK;AAAA,QAAA;AAAA,MAC1D;AAAA,IAEJ,KAAKD,EAAK;AACR,aAAO,CAACD,GAAM,GAAGH,EAAyBG,EAAK,QAAQ,CAAC;AAAA,IAC1D;AACE,aAAO,CAACA,CAAI;AAAA,EAAA;AAElB,CAAC;"}
1
+ {"version":3,"file":"schema.js","sources":["../../src/utils/schema.ts"],"sourcesContent":["import type { MessageFormatElement } from '@formatjs/icu-messageformat-parser';\nimport { parse, TYPE } from '@formatjs/icu-messageformat-parser';\nimport type { MessageSchema, TemplateVariable } from '@/types';\n\nexport const parseMessageSchema = (schema: MessageSchema): MessageConfig => {\n const description = schema.match(/^\\[.+\\]/)?.[0];\n // TODO add support for variables description\n // const withoutDescription = schema.replace(description || \"\", \"\").trim();\n // const withoutOptional = withoutDescription.split(\" | \")[0]?.trim();\n\n return {\n description: description?.slice(1, -1),\n // type: schema === \"$RICH$\" ? \"rich\" : \"icu\",\n type: 'icu',\n variables: extractTemplateVariables(schema),\n };\n};\n\nexport const extractTemplateVariables = (\n schema: MessageSchema,\n): TemplateVariable[] => collectTemplateVariables(parse(schema));\n\nconst collectTemplateVariables = (\n parts: MessageFormatElement[],\n): TemplateVariable[] =>\n parts.flatMap<TemplateVariable>((part) => {\n switch (part.type) {\n case TYPE.literal:\n case TYPE.pound:\n return [];\n case TYPE.argument:\n case TYPE.number:\n case TYPE.date:\n case TYPE.time:\n return [part];\n case TYPE.plural:\n case TYPE.select:\n return [\n part,\n ...collectTemplateVariables(\n Object.values(part.options).flatMap(({ value }) => value),\n ),\n ];\n case TYPE.tag:\n return [part, ...collectTemplateVariables(part.children)];\n default:\n return [part];\n }\n });\n\n// MARK: Types\n\nexport type MessageType = 'icu'; // \"rich\";\nexport type MessageConfig = {\n description: string | undefined;\n type: MessageType;\n variables: TemplateVariable[];\n};\n"],"names":["parseMessageSchema","schema","extractTemplateVariables","collectTemplateVariables","parse","parts","part","TYPE","value"],"mappings":";AAIO,MAAMA,IAAqB,CAACC,OAM1B;AAAA,EACL,aANkBA,EAAO,MAAM,SAAS,IAAI,CAAC,GAMnB,MAAM,GAAG,EAAE;AAAA;AAAA,EAErC,MAAM;AAAA,EACN,WAAWC,EAAyBD,CAAM;AAAA,IAIjCC,IAA2B,CACtCD,MACuBE,EAAyBC,EAAMH,CAAM,CAAC,GAEzDE,IAA2B,CAC/BE,MAEAA,EAAM,QAA0B,CAACC,MAAS;AACxC,UAAQA,EAAK,MAAA;AAAA,IACX,KAAKC,EAAK;AAAA,IACV,KAAKA,EAAK;AACR,aAAO,CAAA;AAAA,IACT,KAAKA,EAAK;AAAA,IACV,KAAKA,EAAK;AAAA,IACV,KAAKA,EAAK;AAAA,IACV,KAAKA,EAAK;AACR,aAAO,CAACD,CAAI;AAAA,IACd,KAAKC,EAAK;AAAA,IACV,KAAKA,EAAK;AACR,aAAO;AAAA,QACLD;AAAA,QACA,GAAGH;AAAA,UACD,OAAO,OAAOG,EAAK,OAAO,EAAE,QAAQ,CAAC,EAAE,OAAAE,EAAA,MAAYA,CAAK;AAAA,QAAA;AAAA,MAC1D;AAAA,IAEJ,KAAKD,EAAK;AACR,aAAO,CAACD,GAAM,GAAGH,EAAyBG,EAAK,QAAQ,CAAC;AAAA,IAC1D;AACE,aAAO,CAACA,CAAI;AAAA,EAAA;AAElB,CAAC;"}
@@ -1,5 +1,6 @@
1
- import { TemplateVariable } from '../types.ts';
2
1
  import { ValidateResult } from 'react-hook-form';
2
+ import { TemplateVariable } from '../types';
3
3
  export declare const validateMessage: (value: unknown, variables: TemplateVariable[]) => ValidateResult;
4
4
  export declare const createValidator: (variables: TemplateVariable[]) => MessageValidator;
5
5
  export type MessageValidator = (value: unknown) => ValidateResult;
6
+ //# sourceMappingURL=validate.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"validate.d.ts","sourceRoot":"","sources":["../../src/utils/validate.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,iBAAiB,CAAC;AACtD,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,SAAS,CAAC;AAKhD,eAAO,MAAM,eAAe,UACnB,OAAO,aACH,gBAAgB,EAAE,KAC5B,cA6DF,CAAC;AAEF,eAAO,MAAM,eAAe,cACd,gBAAgB,EAAE,KAAG,gBAEE,CAAC;AAEtC,MAAM,MAAM,gBAAgB,GAAG,CAAC,KAAK,EAAE,OAAO,KAAK,cAAc,CAAC"}
@@ -1 +1 @@
1
- {"version":3,"file":"validate.js","sources":["../../src/utils/validate.ts"],"sourcesContent":["import type { TemplateVariable } from \"@/types\";\nimport type { ValidateResult } from \"react-hook-form\";\nimport { TYPE } from \"@formatjs/icu-messageformat-parser\";\n\nimport { isNumericElement, isTemporalElement } from \"./guards\";\nimport { extractTemplateVariables } from \"./schema\";\n\nexport const validateMessage = (\n value: unknown,\n variables: TemplateVariable[],\n): ValidateResult => {\n if (typeof value !== \"string\") return \"Invalid value\";\n\n try {\n const variableUsages = extractTemplateVariables(value);\n\n for (const allowedVariable of variables) {\n const variableUsage = variableUsages.find(\n (placeholder) => placeholder.value === allowedVariable.value,\n );\n\n if (!variableUsage) continue;\n\n if (isNumericElement(allowedVariable)) {\n if (isNumericElement(variableUsage)) continue;\n return `{${allowedVariable.value}} has invalid type`;\n }\n\n if (isTemporalElement(allowedVariable)) {\n if (isTemporalElement(variableUsage)) continue;\n return `{${allowedVariable.value}} has invalid type`;\n }\n\n switch (allowedVariable.type) {\n case TYPE.argument:\n if (variableUsage.type === TYPE.argument) continue;\n return `{${allowedVariable.value}} has invalid type`;\n case TYPE.select: {\n if (variableUsage.type !== TYPE.select)\n return `{${allowedVariable.value}} has invalid type`;\n\n const allowedOptions = Object.keys(allowedVariable.options);\n for (const option of allowedOptions) {\n if (variableUsage.options[option]) continue;\n return `{${allowedVariable.value}} has missing option: ${option}`;\n }\n const usedOptions = Object.keys(variableUsage.options);\n for (const option of usedOptions) {\n if (allowedOptions.includes(option)) continue;\n return `{${allowedVariable.value}} has unsupported option: ${option}`;\n }\n continue;\n }\n case TYPE.tag:\n if (variableUsage.type === TYPE.tag) continue;\n return `{${allowedVariable.value}} has invalid type`;\n }\n }\n\n const supportedVariables = new Set(variables.map(({ value }) => value));\n\n for (const variableUsage of variableUsages) {\n if (supportedVariables.has(variableUsage.value)) continue;\n return `{${variableUsage.value}} is not supported`;\n }\n\n return true;\n } catch (error) {\n if (!(error instanceof Error)) return false;\n return `Invalid syntax: ${error.message}`;\n }\n};\n\nexport const createValidator =\n (variables: TemplateVariable[]): MessageValidator =>\n (value: unknown) =>\n validateMessage(value, variables);\n\nexport type MessageValidator = (value: unknown) => ValidateResult;\n"],"names":["validateMessage","value","variables","variableUsages","extractTemplateVariables","allowedVariable","variableUsage","placeholder","isNumericElement","isTemporalElement","TYPE","allowedOptions","option","usedOptions","supportedVariables","error","createValidator"],"mappings":";;;AAOO,MAAMA,IAAkB,CAC7BC,GACAC,MACmB;AACnB,MAAI,OAAOD,KAAU,SAAU,QAAO;AAEtC,MAAI;AACF,UAAME,IAAiBC,EAAyBH,CAAK;AAErD,eAAWI,KAAmBH,GAAW;AACvC,YAAMI,IAAgBH,EAAe;AAAA,QACnC,CAACI,MAAgBA,EAAY,UAAUF,EAAgB;AAAA,MAAA;AAGzD,UAAKC,GAEL;AAAA,YAAIE,EAAiBH,CAAe,GAAG;AACrC,cAAIG,EAAiBF,CAAa,EAAG;AACrC,iBAAO,IAAID,EAAgB,KAAK;AAAA,QAClC;AAEA,YAAII,EAAkBJ,CAAe,GAAG;AACtC,cAAII,EAAkBH,CAAa,EAAG;AACtC,iBAAO,IAAID,EAAgB,KAAK;AAAA,QAClC;AAEA,gBAAQA,EAAgB,MAAA;AAAA,UACtB,KAAKK,EAAK;AACR,gBAAIJ,EAAc,SAASI,EAAK,SAAU;AAC1C,mBAAO,IAAIL,EAAgB,KAAK;AAAA,UAClC,KAAKK,EAAK,QAAQ;AAChB,gBAAIJ,EAAc,SAASI,EAAK;AAC9B,qBAAO,IAAIL,EAAgB,KAAK;AAElC,kBAAMM,IAAiB,OAAO,KAAKN,EAAgB,OAAO;AAC1D,uBAAWO,KAAUD;AACnB,kBAAI,CAAAL,EAAc,QAAQM,CAAM;AAChC,uBAAO,IAAIP,EAAgB,KAAK,yBAAyBO,CAAM;AAEjE,kBAAMC,IAAc,OAAO,KAAKP,EAAc,OAAO;AACrD,uBAAWM,KAAUC;AACnB,kBAAI,CAAAF,EAAe,SAASC,CAAM;AAClC,uBAAO,IAAIP,EAAgB,KAAK,6BAA6BO,CAAM;AAErE;AAAA,UACF;AAAA,UACA,KAAKF,EAAK;AACR,gBAAIJ,EAAc,SAASI,EAAK,IAAK;AACrC,mBAAO,IAAIL,EAAgB,KAAK;AAAA,QAAA;AAAA;AAAA,IAEtC;AAEA,UAAMS,IAAqB,IAAI,IAAIZ,EAAU,IAAI,CAAC,EAAE,OAAAD,QAAYA,CAAK,CAAC;AAEtE,eAAWK,KAAiBH;AAC1B,UAAI,CAAAW,EAAmB,IAAIR,EAAc,KAAK;AAC9C,eAAO,IAAIA,EAAc,KAAK;AAGhC,WAAO;AAAA,EACT,SAASS,GAAO;AACd,WAAMA,aAAiB,QAChB,mBAAmBA,EAAM,OAAO,KADD;AAAA,EAExC;AACF,GAEaC,IACX,CAACd,MACD,CAACD,MACCD,EAAgBC,GAAOC,CAAS;"}
1
+ {"version":3,"file":"validate.js","sources":["../../src/utils/validate.ts"],"sourcesContent":["import { TYPE } from '@formatjs/icu-messageformat-parser';\nimport type { ValidateResult } from 'react-hook-form';\nimport type { TemplateVariable } from '@/types';\n\nimport { isNumericElement, isTemporalElement } from './guards';\nimport { extractTemplateVariables } from './schema';\n\nexport const validateMessage = (\n value: unknown,\n variables: TemplateVariable[],\n): ValidateResult => {\n if (typeof value !== 'string') return 'Invalid value';\n\n try {\n const variableUsages = extractTemplateVariables(value);\n\n for (const allowedVariable of variables) {\n const variableUsage = variableUsages.find(\n (placeholder) => placeholder.value === allowedVariable.value,\n );\n\n if (!variableUsage) continue;\n\n if (isNumericElement(allowedVariable)) {\n if (isNumericElement(variableUsage)) continue;\n return `{${allowedVariable.value}} has invalid type`;\n }\n\n if (isTemporalElement(allowedVariable)) {\n if (isTemporalElement(variableUsage)) continue;\n return `{${allowedVariable.value}} has invalid type`;\n }\n\n switch (allowedVariable.type) {\n case TYPE.argument:\n if (variableUsage.type === TYPE.argument) continue;\n return `{${allowedVariable.value}} has invalid type`;\n case TYPE.select: {\n if (variableUsage.type !== TYPE.select)\n return `{${allowedVariable.value}} has invalid type`;\n\n const allowedOptions = Object.keys(allowedVariable.options);\n for (const option of allowedOptions) {\n if (variableUsage.options[option]) continue;\n return `{${allowedVariable.value}} has missing option: ${option}`;\n }\n const usedOptions = Object.keys(variableUsage.options);\n for (const option of usedOptions) {\n if (allowedOptions.includes(option)) continue;\n return `{${allowedVariable.value}} has unsupported option: ${option}`;\n }\n continue;\n }\n case TYPE.tag:\n if (variableUsage.type === TYPE.tag) continue;\n return `{${allowedVariable.value}} has invalid type`;\n }\n }\n\n const supportedVariables = new Set(variables.map(({ value }) => value));\n\n for (const variableUsage of variableUsages) {\n if (supportedVariables.has(variableUsage.value)) continue;\n return `{${variableUsage.value}} is not supported`;\n }\n\n return true;\n } catch (error) {\n if (!(error instanceof Error)) return false;\n return `Invalid syntax: ${error.message}`;\n }\n};\n\nexport const createValidator =\n (variables: TemplateVariable[]): MessageValidator =>\n (value: unknown) =>\n validateMessage(value, variables);\n\nexport type MessageValidator = (value: unknown) => ValidateResult;\n"],"names":["validateMessage","value","variables","variableUsages","extractTemplateVariables","allowedVariable","variableUsage","placeholder","isNumericElement","isTemporalElement","TYPE","allowedOptions","option","usedOptions","supportedVariables","error","createValidator"],"mappings":";;;AAOO,MAAMA,IAAkB,CAC7BC,GACAC,MACmB;AACnB,MAAI,OAAOD,KAAU,SAAU,QAAO;AAEtC,MAAI;AACF,UAAME,IAAiBC,EAAyBH,CAAK;AAErD,eAAWI,KAAmBH,GAAW;AACvC,YAAMI,IAAgBH,EAAe;AAAA,QACnC,CAACI,MAAgBA,EAAY,UAAUF,EAAgB;AAAA,MAAA;AAGzD,UAAKC,GAEL;AAAA,YAAIE,EAAiBH,CAAe,GAAG;AACrC,cAAIG,EAAiBF,CAAa,EAAG;AACrC,iBAAO,IAAID,EAAgB,KAAK;AAAA,QAClC;AAEA,YAAII,EAAkBJ,CAAe,GAAG;AACtC,cAAII,EAAkBH,CAAa,EAAG;AACtC,iBAAO,IAAID,EAAgB,KAAK;AAAA,QAClC;AAEA,gBAAQA,EAAgB,MAAA;AAAA,UACtB,KAAKK,EAAK;AACR,gBAAIJ,EAAc,SAASI,EAAK,SAAU;AAC1C,mBAAO,IAAIL,EAAgB,KAAK;AAAA,UAClC,KAAKK,EAAK,QAAQ;AAChB,gBAAIJ,EAAc,SAASI,EAAK;AAC9B,qBAAO,IAAIL,EAAgB,KAAK;AAElC,kBAAMM,IAAiB,OAAO,KAAKN,EAAgB,OAAO;AAC1D,uBAAWO,KAAUD;AACnB,kBAAI,CAAAL,EAAc,QAAQM,CAAM;AAChC,uBAAO,IAAIP,EAAgB,KAAK,yBAAyBO,CAAM;AAEjE,kBAAMC,IAAc,OAAO,KAAKP,EAAc,OAAO;AACrD,uBAAWM,KAAUC;AACnB,kBAAI,CAAAF,EAAe,SAASC,CAAM;AAClC,uBAAO,IAAIP,EAAgB,KAAK,6BAA6BO,CAAM;AAErE;AAAA,UACF;AAAA,UACA,KAAKF,EAAK;AACR,gBAAIJ,EAAc,SAASI,EAAK,IAAK;AACrC,mBAAO,IAAIL,EAAgB,KAAK;AAAA,QAAA;AAAA;AAAA,IAEtC;AAEA,UAAMS,IAAqB,IAAI,IAAIZ,EAAU,IAAI,CAAC,EAAE,OAAAD,QAAYA,CAAK,CAAC;AAEtE,eAAWK,KAAiBH;AAC1B,UAAI,CAAAW,EAAmB,IAAIR,EAAc,KAAK;AAC9C,eAAO,IAAIA,EAAc,KAAK;AAGhC,WAAO;AAAA,EACT,SAASS,GAAO;AACd,WAAMA,aAAiB,QAChB,mBAAmBA,EAAM,OAAO,KADD;AAAA,EAExC;AACF,GAEaC,IACX,CAACd,MACD,CAACD,MACCD,EAAgBC,GAAOC,CAAS;"}
package/package.json CHANGED
@@ -1,9 +1,7 @@
1
1
  {
2
2
  "name": "payload-intl",
3
- "version": "0.2.4",
3
+ "version": "1.0.0",
4
4
  "description": "Payload Plugin for I18N using ICU Messages",
5
- "license": "MIT",
6
- "author": "Michael Zeltner",
7
5
  "keywords": [
8
6
  "payload",
9
7
  "intl",
@@ -16,16 +14,23 @@
16
14
  "translations",
17
15
  "icu"
18
16
  ],
17
+ "repository": {
18
+ "type": "git",
19
+ "url": "https://github.com/davincicoding-org/payload-plugins.git",
20
+ "directory": "packages/intl"
21
+ },
22
+ "license": "MIT",
23
+ "author": "Michael Zeltner",
19
24
  "type": "module",
20
25
  "exports": {
21
26
  ".": {
22
- "import": "./dist/index.js",
23
27
  "types": "./dist/index.d.ts",
28
+ "import": "./dist/index.js",
24
29
  "default": "./dist/index.js"
25
30
  },
26
31
  "./rsc": {
27
- "import": "./dist/exports/rsc.js",
28
32
  "types": "./dist/exports/rsc.d.ts",
33
+ "import": "./dist/exports/rsc.js",
29
34
  "default": "./dist/exports/rsc.js"
30
35
  },
31
36
  "./styles.css": "./dist/styles.css"
@@ -35,62 +40,9 @@
35
40
  "files": [
36
41
  "dist"
37
42
  ],
38
- "devDependencies": {
39
- "@eslint/eslintrc": "^3.2.0",
40
- "@ianvs/prettier-plugin-sort-imports": "^4.5.1",
41
- "@payloadcms/db-postgres": "3.72.0",
42
- "@payloadcms/eslint-config": "3.28.0",
43
- "@payloadcms/next": "3.72.0",
44
- "@payloadcms/richtext-lexical": "3.72.0",
45
- "@payloadcms/storage-uploadthing": "3.72.0",
46
- "@payloadcms/ui": "3.72.0",
47
- "@playwright/test": "^1.52.0",
48
- "@tailwindcss/typography": "^0.5.16",
49
- "@tailwindcss/vite": "^4.1.11",
50
- "@tiptap/suggestion": "^3.16.0",
51
- "@types/lodash-es": "^4.17.12",
52
- "@types/node": "^22.5.4",
53
- "@types/react": "19.1.0",
54
- "@types/react-dom": "19.1.2",
55
- "concurrently": "^9.2.0",
56
- "cross-env": "^7.0.3",
57
- "eslint": "^9.23.0",
58
- "eslint-config-next": "15.3.0",
59
- "graphql": "^16.8.1",
60
- "next": "15.5.9",
61
- "next-intl": "^4.3.4",
62
- "open": "^10.1.0",
63
- "payload": "3.72.0",
64
- "prettier": "^3.4.2",
65
- "prettier-plugin-tailwindcss": "^0.6.14",
66
- "react": "19.1.0",
67
- "react-dom": "19.1.0",
68
- "rollup-preserve-directives": "^1.1.3",
69
- "sharp": "0.32.6",
70
- "sort-package-json": "^2.10.0",
71
- "tailwindcss": "^4.1.11",
72
- "tw-animate-css": "^1.3.6",
73
- "typescript": "5.7.3",
74
- "vite": "^7.0.6",
75
- "vite-plugin-dts": "^4.5.4",
76
- "vite-tsconfig-paths": "^5.1.4",
77
- "vitest": "^3.1.2"
78
- },
79
- "peerDependencies": {
80
- "@payloadcms/next": ">=3.72.0",
81
- "@payloadcms/ui": ">=3.72.0",
82
- "next": ">=15.2.3",
83
- "payload": ">=3.72.0"
84
- },
85
- "engines": {
86
- "node": "^18.20.2 || >=20.9.0",
87
- "pnpm": "^9 || ^10"
88
- },
89
- "registry": "https://registry.npmjs.org/",
90
43
  "dependencies": {
91
44
  "@floating-ui/dom": "^1.7.3",
92
45
  "@formatjs/icu-messageformat-parser": "^2.11.2",
93
- "@payloadcms/storage-vercel-blob": "^3.72.0",
94
46
  "@radix-ui/react-dropdown-menu": "^2.1.15",
95
47
  "@radix-ui/react-hover-card": "^1.1.14",
96
48
  "@radix-ui/react-popover": "^1.1.14",
@@ -105,28 +57,61 @@
105
57
  "@tiptap/extension-text": "^3.16.0",
106
58
  "@tiptap/pm": "^3.16.0",
107
59
  "@tiptap/react": "^3.16.0",
60
+ "@tiptap/suggestion": "^3.16.0",
108
61
  "clsx": "^2.1.1",
109
62
  "lodash-es": "^4.17.21",
110
63
  "radix-ui": "^1.4.2",
111
64
  "react-hook-form": "^7.58.1",
112
- "sonner": "^2.0.6",
113
65
  "tailwind-merge": "^3.3.1",
114
66
  "zod": "^4.0.14"
115
67
  },
68
+ "devDependencies": {
69
+ "@payloadcms/richtext-lexical": "3.72.0",
70
+ "@payloadcms/ui": "3.72.0",
71
+ "@tailwindcss/typography": "^0.5.16",
72
+ "@tailwindcss/vite": "^4.1.11",
73
+ "@types/lodash-es": "^4.17.12",
74
+ "@types/node": "^22.5.4",
75
+ "@types/react": "19.2.1",
76
+ "@types/react-dom": "19.2.1",
77
+ "next": "15.5.9",
78
+ "payload": "3.72.0",
79
+ "react": "19.2.1",
80
+ "react-dom": "19.2.1",
81
+ "rollup-preserve-directives": "1.1.3",
82
+ "tailwindcss": "^4.1.11",
83
+ "tw-animate-css": "^1.3.6",
84
+ "typescript": "5.7.3",
85
+ "vite": "7.0.6",
86
+ "vite-plugin-dts": "4.5.4",
87
+ "vite-tsconfig-paths": "5.1.4",
88
+ "vitest": "^3.1.2",
89
+ "@repo/configs": "0.0.1"
90
+ },
91
+ "peerDependencies": {
92
+ "@payloadcms/next": ">=3.72.0",
93
+ "@payloadcms/ui": ">=3.72.0",
94
+ "next": ">=15.2.3",
95
+ "payload": ">=3.72.0"
96
+ },
97
+ "engines": {
98
+ "node": "^18.20.2 || >=20.9.0",
99
+ "pnpm": "^9 || ^10"
100
+ },
101
+ "publishConfig": {
102
+ "access": "public",
103
+ "provenance": true
104
+ },
105
+ "registry": "https://registry.npmjs.org/",
116
106
  "scripts": {
107
+ "prebuild": "pnpm typecheck",
117
108
  "build": "vite build",
118
- "dev": "pnpm build && cd dev && next dev --turbo",
119
- "dev:watch": "pnpm build --watch & cd dev && next dev --turbo",
120
- "dev:generate-importmap": "pnpm dev:payload generate:importmap",
121
- "dev:generate-types": "pnpm dev:payload generate:types",
122
- "dev:payload": "cross-env PAYLOAD_CONFIG_PATH=./dev/payload.config.ts payload",
123
- "typecheck": "tsc --noEmit",
124
- "format": "prettier --write \"**/*.{ts,tsx,js,jsx,mdx}\" --cache",
125
- "lint": "eslint",
126
- "lint:fix": "eslint ./src --fix",
127
- "release": "pnpm publish --access public",
128
- "test": "pnpm test:int && pnpm test:e2e",
129
- "test:e2e": "playwright test",
130
- "test:int": "vitest"
109
+ "clean": "rm -rf dist && rm -rf node_modules",
110
+ "dev": "vite build --watch",
111
+ "lint": "biome check .",
112
+ "lint:fix": "biome check --write .",
113
+ "test": "vitest run",
114
+ "test:watch": "vitest",
115
+ "typecheck": "tsc --noEmit"
131
116
  }
132
117
  }
@@ -1,80 +0,0 @@
1
- import { jsx as l } from "react/jsx-runtime";
2
- import { defaultEditorFeatures as p, defaultEditorConfig as f } from "@payloadcms/richtext-lexical";
3
- import { buildDefaultEditorState as E, RenderLexical as g, getEnabledNodes as S, sanitizeClientEditorConfig as x } from "@payloadcms/richtext-lexical/client";
4
- import { $getRoot as b } from "@payloadcms/richtext-lexical/lexical";
5
- import { createHeadlessEditor as h } from "@payloadcms/richtext-lexical/lexical/headless";
6
- import { $generateNodesFromDOM as C, $generateHtmlFromNodes as T } from "@payloadcms/richtext-lexical/lexical/html";
7
- import { useRef as F, useCallback as u, useMemo as H } from "react";
8
- import { InputWrapper as M } from "./InputWrapper.js";
9
- function y({
10
- error: r,
11
- label: o,
12
- value: i,
13
- onChange: a,
14
- className: s
15
- }) {
16
- const n = v({
17
- html: i,
18
- onChange: a
19
- });
20
- return /* @__PURE__ */ l(M, { label: o, error: r, className: s, children: /* @__PURE__ */ l(
21
- g,
22
- {
23
- field: {
24
- name: "myCustomEditor",
25
- label: !1,
26
- type: "richText"
27
- },
28
- value: n.value,
29
- setValue: (e) => n.setValue(e),
30
- schemaPath: "global.intl-plugin.editorTemplate"
31
- }
32
- ) });
33
- }
34
- const N = E({});
35
- function v({
36
- html: r,
37
- onChange: o
38
- }) {
39
- const i = F(
40
- h({
41
- nodes: S({
42
- editorConfig: x(
43
- // @ts-expect-error - FIXME
44
- p,
45
- f
46
- )
47
- })
48
- })
49
- ), a = u(
50
- (e) => {
51
- const t = i.current;
52
- return t.update(
53
- () => {
54
- const c = new DOMParser().parseFromString(e, "text/html"), m = C(t, c);
55
- b().clear().append(...m);
56
- },
57
- { discrete: !0 }
58
- ), t.getEditorState().toJSON();
59
- },
60
- []
61
- ), s = H(() => {
62
- const e = a(r);
63
- return e.root.children.length === 0 ? N : e;
64
- }, [r, a]), n = u(
65
- (e) => {
66
- const t = i.current;
67
- t.setEditorState(t.parseEditorState(e)), t.read(() => {
68
- const d = T(t);
69
- d !== r && o(d);
70
- });
71
- },
72
- [r, o]
73
- );
74
- return { value: s, setValue: n };
75
- }
76
- export {
77
- y as LexicalInput,
78
- v as useHtmlLexicalAdapter
79
- };
80
- //# sourceMappingURL=LexicalInput.js.map
@@ -1 +0,0 @@
1
- {"version":3,"file":"LexicalInput.js","sources":["../../../src/components/inputs/LexicalInput.tsx"],"sourcesContent":["import type {\n DefaultNodeTypes,\n TypedEditorState,\n} from \"@payloadcms/richtext-lexical\";\nimport type { SerializedEditorState } from \"@payloadcms/richtext-lexical/lexical\";\nimport {\n defaultEditorConfig,\n defaultEditorFeatures,\n} from \"@payloadcms/richtext-lexical\";\nimport {\n buildDefaultEditorState,\n getEnabledNodes,\n RenderLexical,\n sanitizeClientEditorConfig,\n} from \"@payloadcms/richtext-lexical/client\";\nimport { $getRoot } from \"@payloadcms/richtext-lexical/lexical\";\nimport { createHeadlessEditor } from \"@payloadcms/richtext-lexical/lexical/headless\";\nimport {\n $generateHtmlFromNodes,\n $generateNodesFromDOM,\n} from \"@payloadcms/richtext-lexical/lexical/html\";\nimport { useCallback, useMemo, useRef } from \"react\";\n\nimport type { InputWrapperProps } from \"./InputWrapper\";\nimport { InputWrapper } from \"./InputWrapper\";\n\nexport interface LexicalInputProps extends InputWrapperProps {\n lang: string;\n value: string;\n onChange: (value: string) => void;\n onBlur: () => void;\n}\n\nexport function LexicalInput({\n error,\n label,\n value,\n onChange,\n className,\n}: LexicalInputProps): React.ReactNode {\n const editor = useHtmlLexicalAdapter({\n html: value,\n onChange,\n });\n\n return (\n <InputWrapper label={label} error={error} className={className}>\n <RenderLexical\n field={{\n name: \"myCustomEditor\",\n label: false,\n type: \"richText\",\n }}\n value={editor.value}\n setValue={(val) => editor.setValue(val as SerializedEditorState)}\n schemaPath=\"global.intl-plugin.editorTemplate\"\n />\n </InputWrapper>\n );\n}\n\nconst EMPTY_STATE = buildDefaultEditorState({});\n\ninterface UseHtmlLexicalAdapterProps {\n html: string;\n onChange: (html: string) => void;\n}\n\nexport function useHtmlLexicalAdapter({\n html,\n onChange,\n}: UseHtmlLexicalAdapterProps) {\n // 1. Maintain a persistent headless editor for conversion\n const headlessEditor = useRef(\n createHeadlessEditor({\n nodes: getEnabledNodes({\n editorConfig: sanitizeClientEditorConfig(\n // @ts-expect-error - FIXME\n defaultEditorFeatures,\n defaultEditorConfig,\n ),\n }),\n }),\n );\n\n // 2. HTML -> SerializedState\n const getSerializedState = useCallback(\n (htmlString: string): SerializedEditorState => {\n const editor = headlessEditor.current;\n editor.update(\n () => {\n const parser = new DOMParser();\n const dom = parser.parseFromString(htmlString, \"text/html\");\n const nodes = $generateNodesFromDOM(editor, dom);\n\n const root = $getRoot();\n root.clear().append(...nodes);\n },\n { discrete: true },\n );\n\n return editor.getEditorState().toJSON();\n },\n [],\n );\n\n // 3. Memoize the initial value to prevent unnecessary re-renders\n const value = useMemo(() => {\n const serializedState = getSerializedState(html);\n\n if (serializedState.root.children.length === 0) {\n return EMPTY_STATE;\n }\n\n return serializedState;\n }, [html, getSerializedState]);\n\n // 4. SerializedState -> HTML\n const setValue = useCallback(\n (serializedState: SerializedEditorState) => {\n const editor = headlessEditor.current;\n\n // Update headless editor to match the incoming state\n editor.setEditorState(editor.parseEditorState(serializedState));\n\n // Generate HTML and broadcast if it has changed\n editor.read(() => {\n const newHtml = $generateHtmlFromNodes(editor);\n if (newHtml !== html) {\n onChange(newHtml);\n }\n });\n },\n [html, onChange],\n );\n\n return { value: value as TypedEditorState<DefaultNodeTypes>, setValue };\n}\n"],"names":["LexicalInput","error","label","value","onChange","className","editor","useHtmlLexicalAdapter","jsx","InputWrapper","RenderLexical","val","EMPTY_STATE","buildDefaultEditorState","html","headlessEditor","useRef","createHeadlessEditor","getEnabledNodes","sanitizeClientEditorConfig","defaultEditorFeatures","defaultEditorConfig","getSerializedState","useCallback","htmlString","dom","nodes","$generateNodesFromDOM","$getRoot","useMemo","serializedState","setValue","newHtml","$generateHtmlFromNodes"],"mappings":";;;;;;;;AAiCO,SAASA,EAAa;AAAA,EAC3B,OAAAC;AAAA,EACA,OAAAC;AAAA,EACA,OAAAC;AAAA,EACA,UAAAC;AAAA,EACA,WAAAC;AACF,GAAuC;AACrC,QAAMC,IAASC,EAAsB;AAAA,IACnC,MAAMJ;AAAA,IACN,UAAAC;AAAA,EAAA,CACD;AAED,SACE,gBAAAI,EAACC,GAAA,EAAa,OAAAP,GAAc,OAAAD,GAAc,WAAAI,GACxC,UAAA,gBAAAG;AAAA,IAACE;AAAA,IAAA;AAAA,MACC,OAAO;AAAA,QACL,MAAM;AAAA,QACN,OAAO;AAAA,QACP,MAAM;AAAA,MAAA;AAAA,MAER,OAAOJ,EAAO;AAAA,MACd,UAAU,CAACK,MAAQL,EAAO,SAASK,CAA4B;AAAA,MAC/D,YAAW;AAAA,IAAA;AAAA,EAAA,GAEf;AAEJ;AAEA,MAAMC,IAAcC,EAAwB,EAAE;AAOvC,SAASN,EAAsB;AAAA,EACpC,MAAAO;AAAA,EACA,UAAAV;AACF,GAA+B;AAE7B,QAAMW,IAAiBC;AAAA,IACrBC,EAAqB;AAAA,MACnB,OAAOC,EAAgB;AAAA,QACrB,cAAcC;AAAA;AAAA,UAEZC;AAAA,UACAC;AAAA,QAAA;AAAA,MACF,CACD;AAAA,IAAA,CACF;AAAA,EAAA,GAIGC,IAAqBC;AAAA,IACzB,CAACC,MAA8C;AAC7C,YAAMlB,IAASS,EAAe;AAC9B,aAAAT,EAAO;AAAA,QACL,MAAM;AAEJ,gBAAMmB,IADS,IAAI,UAAA,EACA,gBAAgBD,GAAY,WAAW,GACpDE,IAAQC,EAAsBrB,GAAQmB,CAAG;AAG/C,UADaG,EAAA,EACR,MAAA,EAAQ,OAAO,GAAGF,CAAK;AAAA,QAC9B;AAAA,QACA,EAAE,UAAU,GAAA;AAAA,MAAK,GAGZpB,EAAO,eAAA,EAAiB,OAAA;AAAA,IACjC;AAAA,IACA,CAAA;AAAA,EAAC,GAIGH,IAAQ0B,EAAQ,MAAM;AAC1B,UAAMC,IAAkBR,EAAmBR,CAAI;AAE/C,WAAIgB,EAAgB,KAAK,SAAS,WAAW,IACpClB,IAGFkB;AAAA,EACT,GAAG,CAAChB,GAAMQ,CAAkB,CAAC,GAGvBS,IAAWR;AAAA,IACf,CAACO,MAA2C;AAC1C,YAAMxB,IAASS,EAAe;AAG9B,MAAAT,EAAO,eAAeA,EAAO,iBAAiBwB,CAAe,CAAC,GAG9DxB,EAAO,KAAK,MAAM;AAChB,cAAM0B,IAAUC,EAAuB3B,CAAM;AAC7C,QAAI0B,MAAYlB,KACdV,EAAS4B,CAAO;AAAA,MAEpB,CAAC;AAAA,IACH;AAAA,IACA,CAAClB,GAAMV,CAAQ;AAAA,EAAA;AAGjB,SAAO,EAAE,OAAAD,GAAoD,UAAA4B,EAAA;AAC/D;"}