email-builder-online 4.1.4 → 4.1.5

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 CHANGED
@@ -775,6 +775,122 @@ interface AIFeatureRequest {
775
775
  }
776
776
  ```
777
777
 
778
+ ## Block Schemas & Validation (`@eb/document-core`)
779
+
780
+ All block schemas, the document-level schema, and the validation logic are exported from the `@eb/document-core` package. This package has **zero browser dependencies** (only `zod`) and is safe to use in Node.js processes — designed for MCP servers, backend scripts, and CLI tools.
781
+
782
+ ### Installation
783
+
784
+ ```bash
785
+ # Within the monorepo (workspace protocol)
786
+ pnpm add @eb/document-core
787
+ ```
788
+
789
+ ### Schemas
790
+
791
+ ```ts
792
+ import {
793
+ // Composite schemas
794
+ EditorBlockSchema, // z.discriminatedUnion of all 9 block types
795
+ EditorConfigurationSchema, // z.record(string, EditorBlockSchema) — full document
796
+ BLOCK_TYPES, // ['EmailLayout', 'Container', ...] as const
797
+
798
+ // Individual block schemas
799
+ ButtonPropsSchema,
800
+ ColumnsContainerPropsSchema,
801
+ ContainerPropsSchema,
802
+ DividerPropsSchema,
803
+ EmailLayoutPropsSchema,
804
+ ImagePropsSchema,
805
+ NotionTextPropsSchema,
806
+ SocialMediaPropsSchema,
807
+ SpacerPropsSchema,
808
+
809
+ // Primitives (shared across blocks)
810
+ COLOR_SCHEMA,
811
+ PADDING_SCHEMA,
812
+ FONT_FAMILY_SCHEMA,
813
+ FONT_FAMILY_NAMES,
814
+ SHAPE_SCHEMA,
815
+
816
+ // Types
817
+ type TEditorBlock,
818
+ type TEditorConfiguration,
819
+ type BlockType,
820
+ } from '@eb/document-core';
821
+ ```
822
+
823
+ ### Validation
824
+
825
+ ```ts
826
+ import { validateDocument, type ValidationResult } from '@eb/document-core';
827
+
828
+ const result: ValidationResult = validateDocument(jsonDocument);
829
+
830
+ if (result.ok) {
831
+ // result.data is a valid TEditorConfiguration
832
+ console.log('Valid document with', Object.keys(result.data).length, 'blocks');
833
+ } else {
834
+ // result.issues is string[] of human-readable errors
835
+ console.error('Validation failed:', result.issues);
836
+ }
837
+ ```
838
+
839
+ `validateDocument()` runs **3 layers** that mirror the editor's own validation:
840
+
841
+ 1. **Zod schema parse** — every block conforms to its type-specific schema (props, enums, ranges).
842
+ 2. **Root invariant** — a `root` key must exist with `type: "EmailLayout"`.
843
+ 3. **Structural integrity** — every `childrenIds` reference points to an existing block.
844
+
845
+ A document that passes `validateDocument()` is guaranteed to load in the editor via `resetDocument()`.
846
+
847
+ ### Document Format
848
+
849
+ The document is a flat `Record<blockId, TEditorBlock>`:
850
+
851
+ ```json
852
+ {
853
+ "root": {
854
+ "type": "EmailLayout",
855
+ "data": {
856
+ "backdropColor": "#F5F5F5",
857
+ "canvasColor": "#FFFFFF",
858
+ "textColor": "#262626",
859
+ "fontFamily": "MODERN_SANS",
860
+ "childrenIds": ["block-1"]
861
+ }
862
+ },
863
+ "block-1": {
864
+ "type": "Container",
865
+ "data": {
866
+ "style": { "backgroundColor": "#FFFFFF", "padding": { "top": 16, "bottom": 16, "left": 24, "right": 24 } },
867
+ "props": { "childrenIds": ["block-2"] }
868
+ }
869
+ },
870
+ "block-2": {
871
+ "type": "NotionText",
872
+ "data": {
873
+ "style": { "fontSize": 16, "padding": { "top": 16, "bottom": 16, "left": 24, "right": 24 } },
874
+ "props": { "html": "<p>Hello world</p>" }
875
+ }
876
+ }
877
+ }
878
+ ```
879
+
880
+ ### Valid Block Types
881
+
882
+ | Type | Description |
883
+ |------|-------------|
884
+ | `EmailLayout` | Root block (exactly one, keyed as `root`) |
885
+ | `Container` | Section wrapper with `childrenIds` |
886
+ | `ColumnsContainer` | 2–3 column layout with `columns[].childrenIds` |
887
+ | `NotionText` | Rich text (HTML string in `props.html`) |
888
+ | `Button` | CTA button with text, URL, colors |
889
+ | `Image` | Image with URL, alt, alignment |
890
+ | `Divider` | Horizontal rule |
891
+ | `Spacer` | Vertical spacing |
892
+ | `SocialMedia` | Social media icon links |
893
+
778
894
  ## License
779
895
 
780
896
  Free to use. © Laravel42. All rights reserved.