@cmssy/react 7.0.1 → 8.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.
- package/dist/client.cjs +17 -15
- package/dist/client.d.cts +1 -1
- package/dist/client.d.ts +1 -1
- package/dist/client.js +17 -15
- package/dist/index.cjs +1 -1
- package/dist/index.d.cts +3 -3
- package/dist/index.d.ts +3 -3
- package/dist/index.js +1 -1
- package/dist/registry-Bfq4Pq18.d.cts +107 -0
- package/dist/registry-Bfq4Pq18.d.ts +107 -0
- package/package.json +3 -3
- package/dist/registry-DnhIHuzF.d.cts +0 -72
- package/dist/registry-DnhIHuzF.d.ts +0 -72
package/dist/client.cjs
CHANGED
|
@@ -967,6 +967,14 @@ function useCart() {
|
|
|
967
967
|
}
|
|
968
968
|
return ctx;
|
|
969
969
|
}
|
|
970
|
+
var productProps = {
|
|
971
|
+
modelSlug: core.fields.text({ label: "Model slug" }),
|
|
972
|
+
slugField: core.fields.text({ label: "Slug field" }),
|
|
973
|
+
slug: core.fields.text({ label: "Product slug" }),
|
|
974
|
+
nameField: core.fields.text({ label: "Name field" }),
|
|
975
|
+
priceField: core.fields.text({ label: "Price field" }),
|
|
976
|
+
imageField: core.fields.text({ label: "Image field" })
|
|
977
|
+
};
|
|
970
978
|
function deriveAxes(variants) {
|
|
971
979
|
const axes = /* @__PURE__ */ new Map();
|
|
972
980
|
for (const variant of variants) {
|
|
@@ -987,8 +995,7 @@ function matchVariant(variants, selections) {
|
|
|
987
995
|
)
|
|
988
996
|
) ?? null;
|
|
989
997
|
}
|
|
990
|
-
function ProductComponent({ content }) {
|
|
991
|
-
const c = content;
|
|
998
|
+
function ProductComponent({ content: c }) {
|
|
992
999
|
const { fetchProduct, addToCart } = useCart();
|
|
993
1000
|
const injected = c.product ?? null;
|
|
994
1001
|
const [product, setProduct] = react.useState(injected);
|
|
@@ -1096,14 +1103,7 @@ var productBlock = defineBlock({
|
|
|
1096
1103
|
type: "product",
|
|
1097
1104
|
label: "Product",
|
|
1098
1105
|
category: "Commerce",
|
|
1099
|
-
props:
|
|
1100
|
-
modelSlug: core.fields.text({ label: "Model slug" }),
|
|
1101
|
-
slugField: core.fields.text({ label: "Slug field" }),
|
|
1102
|
-
slug: core.fields.text({ label: "Product slug" }),
|
|
1103
|
-
nameField: core.fields.text({ label: "Name field" }),
|
|
1104
|
-
priceField: core.fields.text({ label: "Price field" }),
|
|
1105
|
-
imageField: core.fields.text({ label: "Image field" })
|
|
1106
|
-
},
|
|
1106
|
+
props: productProps,
|
|
1107
1107
|
component: ProductComponent
|
|
1108
1108
|
});
|
|
1109
1109
|
function CartComponent() {
|
|
@@ -1221,9 +1221,13 @@ var cartBlock = defineBlock({
|
|
|
1221
1221
|
props: {},
|
|
1222
1222
|
component: CartComponent
|
|
1223
1223
|
});
|
|
1224
|
+
var checkoutProps = {
|
|
1225
|
+
successMessage: core.fields.text({ label: "Success message" })
|
|
1226
|
+
};
|
|
1224
1227
|
var EMAIL_RE = /^[^@\s]+@[^@\s]+\.[^@\s]+$/;
|
|
1225
|
-
function CheckoutComponent({
|
|
1226
|
-
|
|
1228
|
+
function CheckoutComponent({
|
|
1229
|
+
content: c
|
|
1230
|
+
}) {
|
|
1227
1231
|
const { cart, loading, checkout } = useCart();
|
|
1228
1232
|
const [email, setEmail] = react.useState("");
|
|
1229
1233
|
const [busy, setBusy] = react.useState(false);
|
|
@@ -1295,9 +1299,7 @@ var checkoutBlock = defineBlock({
|
|
|
1295
1299
|
type: "checkout",
|
|
1296
1300
|
label: "Checkout",
|
|
1297
1301
|
category: "Commerce",
|
|
1298
|
-
props:
|
|
1299
|
-
successMessage: core.fields.text({ label: "Success message" })
|
|
1300
|
-
},
|
|
1302
|
+
props: checkoutProps,
|
|
1301
1303
|
component: CheckoutComponent
|
|
1302
1304
|
});
|
|
1303
1305
|
function useCmssyOrders(options = {}) {
|
package/dist/client.d.cts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import * as react_jsx_runtime from 'react/jsx-runtime';
|
|
2
2
|
import { BlockSchema, BlockMeta, CmssyPageData, CmssyFormDefinition, CmssyLayoutGroup, CmssyLocaleContext } from '@cmssy/core';
|
|
3
3
|
export { CmssyCart, CmssyCartDiscount, CmssyCartItem, CmssyCartItemSnapshot, CmssyOrder, CmssyOrderItem, CmssyProduct, CmssyProductVariant, formatPrice, fractionDigits, fromMinorUnits, toMinorUnits } from '@cmssy/core';
|
|
4
|
-
import { B as BlockDefinition } from './registry-
|
|
4
|
+
import { B as BlockDefinition } from './registry-Bfq4Pq18.cjs';
|
|
5
5
|
import { ReactNode } from 'react';
|
|
6
6
|
import { CmssyAuthUser, CmssyAuthActionResult, CmssyCart, CmssyAddToCartOptions, CmssyCheckoutInput, CmssyOrder, CmssyProduct, UseCmssyOrderOptions, UseCmssyOrdersOptions } from '@cmssy/types';
|
|
7
7
|
export { CmssyAddToCartOptions, CmssyAuthActionResult, CmssyAuthUser, CmssyCheckoutInput, UseCmssyOrderOptions, UseCmssyOrdersOptions } from '@cmssy/types';
|
package/dist/client.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import * as react_jsx_runtime from 'react/jsx-runtime';
|
|
2
2
|
import { BlockSchema, BlockMeta, CmssyPageData, CmssyFormDefinition, CmssyLayoutGroup, CmssyLocaleContext } from '@cmssy/core';
|
|
3
3
|
export { CmssyCart, CmssyCartDiscount, CmssyCartItem, CmssyCartItemSnapshot, CmssyOrder, CmssyOrderItem, CmssyProduct, CmssyProductVariant, formatPrice, fractionDigits, fromMinorUnits, toMinorUnits } from '@cmssy/core';
|
|
4
|
-
import { B as BlockDefinition } from './registry-
|
|
4
|
+
import { B as BlockDefinition } from './registry-Bfq4Pq18.js';
|
|
5
5
|
import { ReactNode } from 'react';
|
|
6
6
|
import { CmssyAuthUser, CmssyAuthActionResult, CmssyCart, CmssyAddToCartOptions, CmssyCheckoutInput, CmssyOrder, CmssyProduct, UseCmssyOrderOptions, UseCmssyOrdersOptions } from '@cmssy/types';
|
|
7
7
|
export { CmssyAddToCartOptions, CmssyAuthActionResult, CmssyAuthUser, CmssyCheckoutInput, UseCmssyOrderOptions, UseCmssyOrdersOptions } from '@cmssy/types';
|
package/dist/client.js
CHANGED
|
@@ -966,6 +966,14 @@ function useCart() {
|
|
|
966
966
|
}
|
|
967
967
|
return ctx;
|
|
968
968
|
}
|
|
969
|
+
var productProps = {
|
|
970
|
+
modelSlug: fields.text({ label: "Model slug" }),
|
|
971
|
+
slugField: fields.text({ label: "Slug field" }),
|
|
972
|
+
slug: fields.text({ label: "Product slug" }),
|
|
973
|
+
nameField: fields.text({ label: "Name field" }),
|
|
974
|
+
priceField: fields.text({ label: "Price field" }),
|
|
975
|
+
imageField: fields.text({ label: "Image field" })
|
|
976
|
+
};
|
|
969
977
|
function deriveAxes(variants) {
|
|
970
978
|
const axes = /* @__PURE__ */ new Map();
|
|
971
979
|
for (const variant of variants) {
|
|
@@ -986,8 +994,7 @@ function matchVariant(variants, selections) {
|
|
|
986
994
|
)
|
|
987
995
|
) ?? null;
|
|
988
996
|
}
|
|
989
|
-
function ProductComponent({ content }) {
|
|
990
|
-
const c = content;
|
|
997
|
+
function ProductComponent({ content: c }) {
|
|
991
998
|
const { fetchProduct, addToCart } = useCart();
|
|
992
999
|
const injected = c.product ?? null;
|
|
993
1000
|
const [product, setProduct] = useState(injected);
|
|
@@ -1095,14 +1102,7 @@ var productBlock = defineBlock({
|
|
|
1095
1102
|
type: "product",
|
|
1096
1103
|
label: "Product",
|
|
1097
1104
|
category: "Commerce",
|
|
1098
|
-
props:
|
|
1099
|
-
modelSlug: fields.text({ label: "Model slug" }),
|
|
1100
|
-
slugField: fields.text({ label: "Slug field" }),
|
|
1101
|
-
slug: fields.text({ label: "Product slug" }),
|
|
1102
|
-
nameField: fields.text({ label: "Name field" }),
|
|
1103
|
-
priceField: fields.text({ label: "Price field" }),
|
|
1104
|
-
imageField: fields.text({ label: "Image field" })
|
|
1105
|
-
},
|
|
1105
|
+
props: productProps,
|
|
1106
1106
|
component: ProductComponent
|
|
1107
1107
|
});
|
|
1108
1108
|
function CartComponent() {
|
|
@@ -1220,9 +1220,13 @@ var cartBlock = defineBlock({
|
|
|
1220
1220
|
props: {},
|
|
1221
1221
|
component: CartComponent
|
|
1222
1222
|
});
|
|
1223
|
+
var checkoutProps = {
|
|
1224
|
+
successMessage: fields.text({ label: "Success message" })
|
|
1225
|
+
};
|
|
1223
1226
|
var EMAIL_RE = /^[^@\s]+@[^@\s]+\.[^@\s]+$/;
|
|
1224
|
-
function CheckoutComponent({
|
|
1225
|
-
|
|
1227
|
+
function CheckoutComponent({
|
|
1228
|
+
content: c
|
|
1229
|
+
}) {
|
|
1226
1230
|
const { cart, loading, checkout } = useCart();
|
|
1227
1231
|
const [email, setEmail] = useState("");
|
|
1228
1232
|
const [busy, setBusy] = useState(false);
|
|
@@ -1294,9 +1298,7 @@ var checkoutBlock = defineBlock({
|
|
|
1294
1298
|
type: "checkout",
|
|
1295
1299
|
label: "Checkout",
|
|
1296
1300
|
category: "Commerce",
|
|
1297
|
-
props:
|
|
1298
|
-
successMessage: fields.text({ label: "Success message" })
|
|
1299
|
-
},
|
|
1301
|
+
props: checkoutProps,
|
|
1300
1302
|
component: CheckoutComponent
|
|
1301
1303
|
});
|
|
1302
1304
|
function useCmssyOrders(options = {}) {
|
package/dist/index.cjs
CHANGED
|
@@ -130,7 +130,7 @@ async function resolveRenderLocale({
|
|
|
130
130
|
if (process.env.NODE_ENV !== "production" && !warned2) {
|
|
131
131
|
warned2 = true;
|
|
132
132
|
console.warn(
|
|
133
|
-
'[cmssy] Rendering in "en": no locale was passed and no config was given to look the workspace\'s default language up. Pass `locale` (from the route) or `config`, or a workspace whose default language is not English will render its
|
|
133
|
+
'[cmssy] Rendering in "en": no locale was passed and no config was given to look the workspace\'s default language up. Pass `locale` (from the route) or `config`, or a workspace whose default language is not English will render its header and footer in the wrong one.'
|
|
134
134
|
);
|
|
135
135
|
}
|
|
136
136
|
return {
|
package/dist/index.d.cts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { CmssyPageData, CmssyClientConfig, CmssyFormDefinition, CmssyBlockAuthContext, CmssyBlockWorkspace, CmssyLayoutGroup, RawBlock, CmssyBlockContext } from '@cmssy/core';
|
|
2
|
-
export { AppToEditorMessage, BlockMeta, BlockRect, BlockSchema, BoundsMessage, BuildBlockContextExtra, ClickMessage, CmssyAddress, CmssyBlockAuthContext, CmssyBlockContext, CmssyBlockMember, CmssyBlockWorkspace, CmssyBranding, CmssyCart, CmssyCartDiscount, CmssyCartItem, CmssyCartItemSnapshot, CmssyClient, CmssyClientConfig, CmssyFormDefinition, CmssyFormField, CmssyFormSettings, CmssyFormSubmitResponse, CmssyLayoutGroup, CmssyLayoutSettings, CmssyLocaleContext, CmssyLocalizedValue, CmssyModelDefinition, CmssyModelRecord, CmssyOrder, CmssyOrderDiscount, CmssyOrderItem, CmssyOrderTaxSummaryLine, CmssyPageData, CmssyPageMeta, CmssyPageSummary, CmssyPriceTier, CmssyProduct, CmssyProductVariant, CmssyRecordList, CmssyRequestError, CmssyShippingMethod, CmssySiteConfig, CmssySiteLocales, CmssyTaxSummaryLine, DEFAULT_CMSSY_API_URL, EditorToAppMessage, FORM_QUERY, FetchLike, FetchLikeResponse, FetchPageOptions, FieldControl, FieldDefinition, FieldType, GraphqlRequestOptions, MODEL_DEFINITIONS_QUERY, MODEL_RECORDS_QUERY, PROTOCOL_VERSION, ParentReadyMessage, PatchMessage, PostTarget, QueryScopedOptions, RawBlock, RawLayoutBlock, ReadyMessage, RetryPolicy, SITE_CONFIG_QUERY, SUBMIT_FORM_MUTATION, SelectMessage, SubmitFormInput, buildBlockContext, buildLocaleSwitchHref, collectFormIds, createCmssyClient, fetchLayouts, fetchPage, fetchPageById, fetchPageMeta, fetchPages, fetchSiteConfig, fields, getBlockContentForLanguage, graphqlRequest, isProtocolCompatible, localizeHref, localizeHtmlLinks, normalizeOrigin, normalizeSlug, parseEditorMessage, postToEditor, resolveApiUrl, resolveForms, resolvePublicUrl, resolveSiteLocales, resolveWorkspaceId, splitLocaleFromPath } from '@cmssy/core';
|
|
3
|
-
import { B as BlockDefinition, a as BlockMap } from './registry-
|
|
4
|
-
export { b as
|
|
2
|
+
export { AppToEditorMessage, BlockMeta, BlockPropsSchema, BlockRect, BlockSchema, BoundsMessage, BuildBlockContextExtra, ClickMessage, CmssyAddress, CmssyBlockAuthContext, CmssyBlockContext, CmssyBlockMember, CmssyBlockWorkspace, CmssyBranding, CmssyCart, CmssyCartDiscount, CmssyCartItem, CmssyCartItemSnapshot, CmssyClient, CmssyClientConfig, CmssyFormDefinition, CmssyFormField, CmssyFormSettings, CmssyFormSubmitResponse, CmssyLayoutGroup, CmssyLayoutSettings, CmssyLocaleContext, CmssyLocalizedValue, CmssyModelDefinition, CmssyModelRecord, CmssyOrder, CmssyOrderDiscount, CmssyOrderItem, CmssyOrderTaxSummaryLine, CmssyPageData, CmssyPageMeta, CmssyPageSummary, CmssyPriceTier, CmssyProduct, CmssyProductVariant, CmssyRecordList, CmssyRequestError, CmssyShippingMethod, CmssySiteConfig, CmssySiteLocales, CmssyTaxSummaryLine, DEFAULT_CMSSY_API_URL, EditorToAppMessage, FORM_QUERY, FetchLike, FetchLikeResponse, FetchPageOptions, FieldControl, FieldDefinition, FieldType, GraphqlRequestOptions, InferBlockContent, MODEL_DEFINITIONS_QUERY, MODEL_RECORDS_QUERY, PROTOCOL_VERSION, ParentReadyMessage, PatchMessage, PostTarget, QueryScopedOptions, RawBlock, RawLayoutBlock, ReadyMessage, RetryPolicy, SITE_CONFIG_QUERY, SUBMIT_FORM_MUTATION, SelectMessage, SubmitFormInput, TypedField, buildBlockContext, buildLocaleSwitchHref, collectFormIds, createCmssyClient, fetchLayouts, fetchPage, fetchPageById, fetchPageMeta, fetchPages, fetchSiteConfig, fields, getBlockContentForLanguage, graphqlRequest, isProtocolCompatible, localizeHref, localizeHtmlLinks, normalizeOrigin, normalizeSlug, parseEditorMessage, postToEditor, resolveApiUrl, resolveForms, resolvePublicUrl, resolveSiteLocales, resolveWorkspaceId, splitLocaleFromPath } from '@cmssy/core';
|
|
3
|
+
import { B as BlockDefinition, a as BlockMap } from './registry-Bfq4Pq18.cjs';
|
|
4
|
+
export { b as BlockProps, c as blocksToMeta, d as blocksToSchemas, e as buildBlockMap, f as defineBlock } from './registry-Bfq4Pq18.cjs';
|
|
5
5
|
import * as react_jsx_runtime from 'react/jsx-runtime';
|
|
6
6
|
export { FieldCondition, FieldConditionGroup, FieldConditionLogic, evaluateFieldConditionGroup } from '@cmssy/types';
|
|
7
7
|
import 'react';
|
package/dist/index.d.ts
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { CmssyPageData, CmssyClientConfig, CmssyFormDefinition, CmssyBlockAuthContext, CmssyBlockWorkspace, CmssyLayoutGroup, RawBlock, CmssyBlockContext } from '@cmssy/core';
|
|
2
|
-
export { AppToEditorMessage, BlockMeta, BlockRect, BlockSchema, BoundsMessage, BuildBlockContextExtra, ClickMessage, CmssyAddress, CmssyBlockAuthContext, CmssyBlockContext, CmssyBlockMember, CmssyBlockWorkspace, CmssyBranding, CmssyCart, CmssyCartDiscount, CmssyCartItem, CmssyCartItemSnapshot, CmssyClient, CmssyClientConfig, CmssyFormDefinition, CmssyFormField, CmssyFormSettings, CmssyFormSubmitResponse, CmssyLayoutGroup, CmssyLayoutSettings, CmssyLocaleContext, CmssyLocalizedValue, CmssyModelDefinition, CmssyModelRecord, CmssyOrder, CmssyOrderDiscount, CmssyOrderItem, CmssyOrderTaxSummaryLine, CmssyPageData, CmssyPageMeta, CmssyPageSummary, CmssyPriceTier, CmssyProduct, CmssyProductVariant, CmssyRecordList, CmssyRequestError, CmssyShippingMethod, CmssySiteConfig, CmssySiteLocales, CmssyTaxSummaryLine, DEFAULT_CMSSY_API_URL, EditorToAppMessage, FORM_QUERY, FetchLike, FetchLikeResponse, FetchPageOptions, FieldControl, FieldDefinition, FieldType, GraphqlRequestOptions, MODEL_DEFINITIONS_QUERY, MODEL_RECORDS_QUERY, PROTOCOL_VERSION, ParentReadyMessage, PatchMessage, PostTarget, QueryScopedOptions, RawBlock, RawLayoutBlock, ReadyMessage, RetryPolicy, SITE_CONFIG_QUERY, SUBMIT_FORM_MUTATION, SelectMessage, SubmitFormInput, buildBlockContext, buildLocaleSwitchHref, collectFormIds, createCmssyClient, fetchLayouts, fetchPage, fetchPageById, fetchPageMeta, fetchPages, fetchSiteConfig, fields, getBlockContentForLanguage, graphqlRequest, isProtocolCompatible, localizeHref, localizeHtmlLinks, normalizeOrigin, normalizeSlug, parseEditorMessage, postToEditor, resolveApiUrl, resolveForms, resolvePublicUrl, resolveSiteLocales, resolveWorkspaceId, splitLocaleFromPath } from '@cmssy/core';
|
|
3
|
-
import { B as BlockDefinition, a as BlockMap } from './registry-
|
|
4
|
-
export { b as
|
|
2
|
+
export { AppToEditorMessage, BlockMeta, BlockPropsSchema, BlockRect, BlockSchema, BoundsMessage, BuildBlockContextExtra, ClickMessage, CmssyAddress, CmssyBlockAuthContext, CmssyBlockContext, CmssyBlockMember, CmssyBlockWorkspace, CmssyBranding, CmssyCart, CmssyCartDiscount, CmssyCartItem, CmssyCartItemSnapshot, CmssyClient, CmssyClientConfig, CmssyFormDefinition, CmssyFormField, CmssyFormSettings, CmssyFormSubmitResponse, CmssyLayoutGroup, CmssyLayoutSettings, CmssyLocaleContext, CmssyLocalizedValue, CmssyModelDefinition, CmssyModelRecord, CmssyOrder, CmssyOrderDiscount, CmssyOrderItem, CmssyOrderTaxSummaryLine, CmssyPageData, CmssyPageMeta, CmssyPageSummary, CmssyPriceTier, CmssyProduct, CmssyProductVariant, CmssyRecordList, CmssyRequestError, CmssyShippingMethod, CmssySiteConfig, CmssySiteLocales, CmssyTaxSummaryLine, DEFAULT_CMSSY_API_URL, EditorToAppMessage, FORM_QUERY, FetchLike, FetchLikeResponse, FetchPageOptions, FieldControl, FieldDefinition, FieldType, GraphqlRequestOptions, InferBlockContent, MODEL_DEFINITIONS_QUERY, MODEL_RECORDS_QUERY, PROTOCOL_VERSION, ParentReadyMessage, PatchMessage, PostTarget, QueryScopedOptions, RawBlock, RawLayoutBlock, ReadyMessage, RetryPolicy, SITE_CONFIG_QUERY, SUBMIT_FORM_MUTATION, SelectMessage, SubmitFormInput, TypedField, buildBlockContext, buildLocaleSwitchHref, collectFormIds, createCmssyClient, fetchLayouts, fetchPage, fetchPageById, fetchPageMeta, fetchPages, fetchSiteConfig, fields, getBlockContentForLanguage, graphqlRequest, isProtocolCompatible, localizeHref, localizeHtmlLinks, normalizeOrigin, normalizeSlug, parseEditorMessage, postToEditor, resolveApiUrl, resolveForms, resolvePublicUrl, resolveSiteLocales, resolveWorkspaceId, splitLocaleFromPath } from '@cmssy/core';
|
|
3
|
+
import { B as BlockDefinition, a as BlockMap } from './registry-Bfq4Pq18.js';
|
|
4
|
+
export { b as BlockProps, c as blocksToMeta, d as blocksToSchemas, e as buildBlockMap, f as defineBlock } from './registry-Bfq4Pq18.js';
|
|
5
5
|
import * as react_jsx_runtime from 'react/jsx-runtime';
|
|
6
6
|
export { FieldCondition, FieldConditionGroup, FieldConditionLogic, evaluateFieldConditionGroup } from '@cmssy/types';
|
|
7
7
|
import 'react';
|
package/dist/index.js
CHANGED
|
@@ -129,7 +129,7 @@ async function resolveRenderLocale({
|
|
|
129
129
|
if (process.env.NODE_ENV !== "production" && !warned2) {
|
|
130
130
|
warned2 = true;
|
|
131
131
|
console.warn(
|
|
132
|
-
'[cmssy] Rendering in "en": no locale was passed and no config was given to look the workspace\'s default language up. Pass `locale` (from the route) or `config`, or a workspace whose default language is not English will render its
|
|
132
|
+
'[cmssy] Rendering in "en": no locale was passed and no config was given to look the workspace\'s default language up. Pass `locale` (from the route) or `config`, or a workspace whose default language is not English will render its header and footer in the wrong one.'
|
|
133
133
|
);
|
|
134
134
|
}
|
|
135
135
|
return {
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
import { ComponentType } from 'react';
|
|
2
|
+
import { FieldDefinition, CmssyBlockContext, BlockPropsSchema, InferBlockContent, BlockMeta, BlockSchema } from '@cmssy/core';
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* The props a block component receives, derived from the fields it declares:
|
|
6
|
+
*
|
|
7
|
+
* const props = { headline: fields.text({ required: true }) };
|
|
8
|
+
* export function Hero({ content }: BlockProps<typeof props>) { … }
|
|
9
|
+
*
|
|
10
|
+
* Type the component this way and the schema is the only place a field is
|
|
11
|
+
* named. Rename `headline` and the component stops compiling, instead of
|
|
12
|
+
* quietly rendering nothing.
|
|
13
|
+
*/
|
|
14
|
+
interface BlockProps<P extends BlockPropsSchema, D = unknown> {
|
|
15
|
+
content: InferBlockContent<P>;
|
|
16
|
+
style?: Record<string, unknown>;
|
|
17
|
+
advanced?: Record<string, unknown>;
|
|
18
|
+
context?: CmssyBlockContext;
|
|
19
|
+
data?: D;
|
|
20
|
+
}
|
|
21
|
+
type Identical<X, Y> = (<T>() => T extends X ? 1 : 2) extends <T>() => T extends Y ? 1 : 2 ? true : false;
|
|
22
|
+
/** What the component says about the fields the schema declares - nothing else. */
|
|
23
|
+
type SchemaSlice<C, Content> = {
|
|
24
|
+
[K in keyof Content]: K extends keyof C ? C[K] : never;
|
|
25
|
+
};
|
|
26
|
+
/**
|
|
27
|
+
* Rejects a component whose `content` disagrees with the schema about a field
|
|
28
|
+
* the schema declares. Extra keys are fine - a loader may inject content the
|
|
29
|
+
* editor knows nothing about (see `productBlock`) - but a declared field must
|
|
30
|
+
* have the name and the type the schema gives it.
|
|
31
|
+
*
|
|
32
|
+
* Without this, a hand-written content type only had to be *compatible* with the
|
|
33
|
+
* schema, and since every optional field is optional on both sides, a field the
|
|
34
|
+
* component invented was compatible with the one it forgot.
|
|
35
|
+
*/
|
|
36
|
+
type ContentGuard<C, P extends BlockPropsSchema> = Identical<SchemaSlice<C, InferBlockContent<P>>, InferBlockContent<P>> extends true ? unknown : {
|
|
37
|
+
CONTENT_MUST_BE_TYPED_AS_BlockProps_OF_THIS_PROPS: InferBlockContent<P>;
|
|
38
|
+
};
|
|
39
|
+
interface BlockLoaderArgs {
|
|
40
|
+
content: Record<string, unknown>;
|
|
41
|
+
context?: CmssyBlockContext;
|
|
42
|
+
}
|
|
43
|
+
type BlockLoader = (args: BlockLoaderArgs) => Promise<unknown> | unknown;
|
|
44
|
+
interface BlockDefinition {
|
|
45
|
+
type: string;
|
|
46
|
+
label?: string;
|
|
47
|
+
category?: string;
|
|
48
|
+
icon?: string;
|
|
49
|
+
layoutPositions?: string[];
|
|
50
|
+
/**
|
|
51
|
+
* One-line semantic description of what the block is and when it belongs on a
|
|
52
|
+
* page. Surfaced to the AI page composer to guide block selection and order.
|
|
53
|
+
*/
|
|
54
|
+
description?: string;
|
|
55
|
+
props: Record<string, FieldDefinition>;
|
|
56
|
+
/**
|
|
57
|
+
* Optional server-side data loader. Run by CmssyServerPage during SSR; its
|
|
58
|
+
* result is passed to the component as the `data` prop. Not run in the
|
|
59
|
+
* editor (the component receives `data: undefined` there).
|
|
60
|
+
*
|
|
61
|
+
* The result crosses the server→client boundary when the block component is a
|
|
62
|
+
* Client Component, so it must be RSC-serializable (plain objects, arrays and
|
|
63
|
+
* primitives - no functions, class instances, etc.).
|
|
64
|
+
*/
|
|
65
|
+
loader?: BlockLoader;
|
|
66
|
+
component: ComponentType<{
|
|
67
|
+
content: Record<string, unknown>;
|
|
68
|
+
style?: Record<string, unknown>;
|
|
69
|
+
advanced?: Record<string, unknown>;
|
|
70
|
+
context?: CmssyBlockContext;
|
|
71
|
+
data?: unknown;
|
|
72
|
+
}>;
|
|
73
|
+
}
|
|
74
|
+
declare function defineBlock<P extends BlockPropsSchema, C = InferBlockContent<P>, D = unknown, S extends Record<string, unknown> = Record<string, unknown>, A extends Record<string, unknown> = Record<string, unknown>>(def: {
|
|
75
|
+
type: string;
|
|
76
|
+
label?: string;
|
|
77
|
+
category?: string;
|
|
78
|
+
icon?: string;
|
|
79
|
+
layoutPositions?: string[];
|
|
80
|
+
description?: string;
|
|
81
|
+
props: P;
|
|
82
|
+
loader?: (args: {
|
|
83
|
+
content: InferBlockContent<P>;
|
|
84
|
+
context?: CmssyBlockContext;
|
|
85
|
+
}) => Promise<D> | D;
|
|
86
|
+
component: ComponentType<{
|
|
87
|
+
content: C;
|
|
88
|
+
style?: S;
|
|
89
|
+
advanced?: A;
|
|
90
|
+
context?: CmssyBlockContext;
|
|
91
|
+
data?: D;
|
|
92
|
+
}>;
|
|
93
|
+
} & ContentGuard<C, P>): BlockDefinition;
|
|
94
|
+
type BlockMap = Record<string, ComponentType<{
|
|
95
|
+
content: Record<string, unknown>;
|
|
96
|
+
style?: Record<string, unknown>;
|
|
97
|
+
advanced?: Record<string, unknown>;
|
|
98
|
+
context?: CmssyBlockContext;
|
|
99
|
+
data?: unknown;
|
|
100
|
+
}>>;
|
|
101
|
+
declare function buildBlockMap(blocks: BlockDefinition[]): BlockMap;
|
|
102
|
+
declare function blocksToSchemas(blocks: BlockDefinition[]): Record<string, BlockSchema>;
|
|
103
|
+
declare function blocksToMeta(blocks: BlockDefinition[], defaults?: {
|
|
104
|
+
category?: string;
|
|
105
|
+
}): Record<string, BlockMeta>;
|
|
106
|
+
|
|
107
|
+
export { type BlockDefinition as B, type BlockMap as a, type BlockProps as b, blocksToMeta as c, blocksToSchemas as d, buildBlockMap as e, defineBlock as f };
|
|
@@ -0,0 +1,107 @@
|
|
|
1
|
+
import { ComponentType } from 'react';
|
|
2
|
+
import { FieldDefinition, CmssyBlockContext, BlockPropsSchema, InferBlockContent, BlockMeta, BlockSchema } from '@cmssy/core';
|
|
3
|
+
|
|
4
|
+
/**
|
|
5
|
+
* The props a block component receives, derived from the fields it declares:
|
|
6
|
+
*
|
|
7
|
+
* const props = { headline: fields.text({ required: true }) };
|
|
8
|
+
* export function Hero({ content }: BlockProps<typeof props>) { … }
|
|
9
|
+
*
|
|
10
|
+
* Type the component this way and the schema is the only place a field is
|
|
11
|
+
* named. Rename `headline` and the component stops compiling, instead of
|
|
12
|
+
* quietly rendering nothing.
|
|
13
|
+
*/
|
|
14
|
+
interface BlockProps<P extends BlockPropsSchema, D = unknown> {
|
|
15
|
+
content: InferBlockContent<P>;
|
|
16
|
+
style?: Record<string, unknown>;
|
|
17
|
+
advanced?: Record<string, unknown>;
|
|
18
|
+
context?: CmssyBlockContext;
|
|
19
|
+
data?: D;
|
|
20
|
+
}
|
|
21
|
+
type Identical<X, Y> = (<T>() => T extends X ? 1 : 2) extends <T>() => T extends Y ? 1 : 2 ? true : false;
|
|
22
|
+
/** What the component says about the fields the schema declares - nothing else. */
|
|
23
|
+
type SchemaSlice<C, Content> = {
|
|
24
|
+
[K in keyof Content]: K extends keyof C ? C[K] : never;
|
|
25
|
+
};
|
|
26
|
+
/**
|
|
27
|
+
* Rejects a component whose `content` disagrees with the schema about a field
|
|
28
|
+
* the schema declares. Extra keys are fine - a loader may inject content the
|
|
29
|
+
* editor knows nothing about (see `productBlock`) - but a declared field must
|
|
30
|
+
* have the name and the type the schema gives it.
|
|
31
|
+
*
|
|
32
|
+
* Without this, a hand-written content type only had to be *compatible* with the
|
|
33
|
+
* schema, and since every optional field is optional on both sides, a field the
|
|
34
|
+
* component invented was compatible with the one it forgot.
|
|
35
|
+
*/
|
|
36
|
+
type ContentGuard<C, P extends BlockPropsSchema> = Identical<SchemaSlice<C, InferBlockContent<P>>, InferBlockContent<P>> extends true ? unknown : {
|
|
37
|
+
CONTENT_MUST_BE_TYPED_AS_BlockProps_OF_THIS_PROPS: InferBlockContent<P>;
|
|
38
|
+
};
|
|
39
|
+
interface BlockLoaderArgs {
|
|
40
|
+
content: Record<string, unknown>;
|
|
41
|
+
context?: CmssyBlockContext;
|
|
42
|
+
}
|
|
43
|
+
type BlockLoader = (args: BlockLoaderArgs) => Promise<unknown> | unknown;
|
|
44
|
+
interface BlockDefinition {
|
|
45
|
+
type: string;
|
|
46
|
+
label?: string;
|
|
47
|
+
category?: string;
|
|
48
|
+
icon?: string;
|
|
49
|
+
layoutPositions?: string[];
|
|
50
|
+
/**
|
|
51
|
+
* One-line semantic description of what the block is and when it belongs on a
|
|
52
|
+
* page. Surfaced to the AI page composer to guide block selection and order.
|
|
53
|
+
*/
|
|
54
|
+
description?: string;
|
|
55
|
+
props: Record<string, FieldDefinition>;
|
|
56
|
+
/**
|
|
57
|
+
* Optional server-side data loader. Run by CmssyServerPage during SSR; its
|
|
58
|
+
* result is passed to the component as the `data` prop. Not run in the
|
|
59
|
+
* editor (the component receives `data: undefined` there).
|
|
60
|
+
*
|
|
61
|
+
* The result crosses the server→client boundary when the block component is a
|
|
62
|
+
* Client Component, so it must be RSC-serializable (plain objects, arrays and
|
|
63
|
+
* primitives - no functions, class instances, etc.).
|
|
64
|
+
*/
|
|
65
|
+
loader?: BlockLoader;
|
|
66
|
+
component: ComponentType<{
|
|
67
|
+
content: Record<string, unknown>;
|
|
68
|
+
style?: Record<string, unknown>;
|
|
69
|
+
advanced?: Record<string, unknown>;
|
|
70
|
+
context?: CmssyBlockContext;
|
|
71
|
+
data?: unknown;
|
|
72
|
+
}>;
|
|
73
|
+
}
|
|
74
|
+
declare function defineBlock<P extends BlockPropsSchema, C = InferBlockContent<P>, D = unknown, S extends Record<string, unknown> = Record<string, unknown>, A extends Record<string, unknown> = Record<string, unknown>>(def: {
|
|
75
|
+
type: string;
|
|
76
|
+
label?: string;
|
|
77
|
+
category?: string;
|
|
78
|
+
icon?: string;
|
|
79
|
+
layoutPositions?: string[];
|
|
80
|
+
description?: string;
|
|
81
|
+
props: P;
|
|
82
|
+
loader?: (args: {
|
|
83
|
+
content: InferBlockContent<P>;
|
|
84
|
+
context?: CmssyBlockContext;
|
|
85
|
+
}) => Promise<D> | D;
|
|
86
|
+
component: ComponentType<{
|
|
87
|
+
content: C;
|
|
88
|
+
style?: S;
|
|
89
|
+
advanced?: A;
|
|
90
|
+
context?: CmssyBlockContext;
|
|
91
|
+
data?: D;
|
|
92
|
+
}>;
|
|
93
|
+
} & ContentGuard<C, P>): BlockDefinition;
|
|
94
|
+
type BlockMap = Record<string, ComponentType<{
|
|
95
|
+
content: Record<string, unknown>;
|
|
96
|
+
style?: Record<string, unknown>;
|
|
97
|
+
advanced?: Record<string, unknown>;
|
|
98
|
+
context?: CmssyBlockContext;
|
|
99
|
+
data?: unknown;
|
|
100
|
+
}>>;
|
|
101
|
+
declare function buildBlockMap(blocks: BlockDefinition[]): BlockMap;
|
|
102
|
+
declare function blocksToSchemas(blocks: BlockDefinition[]): Record<string, BlockSchema>;
|
|
103
|
+
declare function blocksToMeta(blocks: BlockDefinition[], defaults?: {
|
|
104
|
+
category?: string;
|
|
105
|
+
}): Record<string, BlockMeta>;
|
|
106
|
+
|
|
107
|
+
export { type BlockDefinition as B, type BlockMap as a, type BlockProps as b, blocksToMeta as c, blocksToSchemas as d, buildBlockMap as e, defineBlock as f };
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@cmssy/react",
|
|
3
|
-
"version": "
|
|
3
|
+
"version": "8.0.0",
|
|
4
4
|
"description": "React blocks, renderers, data client and editor bridge for cmssy headless sites",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"cmssy",
|
|
@@ -56,8 +56,8 @@
|
|
|
56
56
|
"vitest": "^2.1.0"
|
|
57
57
|
},
|
|
58
58
|
"dependencies": {
|
|
59
|
-
"@cmssy/types": "0.
|
|
60
|
-
"@cmssy/core": "
|
|
59
|
+
"@cmssy/types": "0.28.0",
|
|
60
|
+
"@cmssy/core": "8.0.0"
|
|
61
61
|
},
|
|
62
62
|
"scripts": {
|
|
63
63
|
"build": "tsup",
|
|
@@ -1,72 +0,0 @@
|
|
|
1
|
-
import { ComponentType } from 'react';
|
|
2
|
-
import { FieldDefinition, CmssyBlockContext, BlockMeta, BlockSchema } from '@cmssy/core';
|
|
3
|
-
|
|
4
|
-
interface BlockLoaderArgs {
|
|
5
|
-
content: Record<string, unknown>;
|
|
6
|
-
context?: CmssyBlockContext;
|
|
7
|
-
}
|
|
8
|
-
type BlockLoader = (args: BlockLoaderArgs) => Promise<unknown> | unknown;
|
|
9
|
-
interface BlockDefinition {
|
|
10
|
-
type: string;
|
|
11
|
-
label?: string;
|
|
12
|
-
category?: string;
|
|
13
|
-
icon?: string;
|
|
14
|
-
layoutPositions?: string[];
|
|
15
|
-
/**
|
|
16
|
-
* One-line semantic description of what the block is and when it belongs on a
|
|
17
|
-
* page. Surfaced to the AI page composer to guide block selection and order.
|
|
18
|
-
*/
|
|
19
|
-
description?: string;
|
|
20
|
-
props: Record<string, FieldDefinition>;
|
|
21
|
-
/**
|
|
22
|
-
* Optional server-side data loader. Run by CmssyServerPage during SSR; its
|
|
23
|
-
* result is passed to the component as the `data` prop. Not run in the
|
|
24
|
-
* editor (the component receives `data: undefined` there).
|
|
25
|
-
*
|
|
26
|
-
* The result crosses the server→client boundary when the block component is a
|
|
27
|
-
* Client Component, so it must be RSC-serializable (plain objects, arrays and
|
|
28
|
-
* primitives - no functions, class instances, etc.).
|
|
29
|
-
*/
|
|
30
|
-
loader?: BlockLoader;
|
|
31
|
-
component: ComponentType<{
|
|
32
|
-
content: Record<string, unknown>;
|
|
33
|
-
style?: Record<string, unknown>;
|
|
34
|
-
advanced?: Record<string, unknown>;
|
|
35
|
-
context?: CmssyBlockContext;
|
|
36
|
-
data?: unknown;
|
|
37
|
-
}>;
|
|
38
|
-
}
|
|
39
|
-
declare function defineBlock<C extends Record<string, unknown>, D = unknown, S extends Record<string, unknown> = Record<string, unknown>, A extends Record<string, unknown> = Record<string, unknown>>(def: {
|
|
40
|
-
type: string;
|
|
41
|
-
label?: string;
|
|
42
|
-
category?: string;
|
|
43
|
-
icon?: string;
|
|
44
|
-
layoutPositions?: string[];
|
|
45
|
-
description?: string;
|
|
46
|
-
props: Record<string, FieldDefinition>;
|
|
47
|
-
loader?: (args: {
|
|
48
|
-
content: C;
|
|
49
|
-
context?: CmssyBlockContext;
|
|
50
|
-
}) => Promise<D> | D;
|
|
51
|
-
component: ComponentType<{
|
|
52
|
-
content: C;
|
|
53
|
-
style?: S;
|
|
54
|
-
advanced?: A;
|
|
55
|
-
context?: CmssyBlockContext;
|
|
56
|
-
data?: D;
|
|
57
|
-
}>;
|
|
58
|
-
}): BlockDefinition;
|
|
59
|
-
type BlockMap = Record<string, ComponentType<{
|
|
60
|
-
content: Record<string, unknown>;
|
|
61
|
-
style?: Record<string, unknown>;
|
|
62
|
-
advanced?: Record<string, unknown>;
|
|
63
|
-
context?: CmssyBlockContext;
|
|
64
|
-
data?: unknown;
|
|
65
|
-
}>>;
|
|
66
|
-
declare function buildBlockMap(blocks: BlockDefinition[]): BlockMap;
|
|
67
|
-
declare function blocksToSchemas(blocks: BlockDefinition[]): Record<string, BlockSchema>;
|
|
68
|
-
declare function blocksToMeta(blocks: BlockDefinition[], defaults?: {
|
|
69
|
-
category?: string;
|
|
70
|
-
}): Record<string, BlockMeta>;
|
|
71
|
-
|
|
72
|
-
export { type BlockDefinition as B, type BlockMap as a, blocksToMeta as b, blocksToSchemas as c, buildBlockMap as d, defineBlock as e };
|
|
@@ -1,72 +0,0 @@
|
|
|
1
|
-
import { ComponentType } from 'react';
|
|
2
|
-
import { FieldDefinition, CmssyBlockContext, BlockMeta, BlockSchema } from '@cmssy/core';
|
|
3
|
-
|
|
4
|
-
interface BlockLoaderArgs {
|
|
5
|
-
content: Record<string, unknown>;
|
|
6
|
-
context?: CmssyBlockContext;
|
|
7
|
-
}
|
|
8
|
-
type BlockLoader = (args: BlockLoaderArgs) => Promise<unknown> | unknown;
|
|
9
|
-
interface BlockDefinition {
|
|
10
|
-
type: string;
|
|
11
|
-
label?: string;
|
|
12
|
-
category?: string;
|
|
13
|
-
icon?: string;
|
|
14
|
-
layoutPositions?: string[];
|
|
15
|
-
/**
|
|
16
|
-
* One-line semantic description of what the block is and when it belongs on a
|
|
17
|
-
* page. Surfaced to the AI page composer to guide block selection and order.
|
|
18
|
-
*/
|
|
19
|
-
description?: string;
|
|
20
|
-
props: Record<string, FieldDefinition>;
|
|
21
|
-
/**
|
|
22
|
-
* Optional server-side data loader. Run by CmssyServerPage during SSR; its
|
|
23
|
-
* result is passed to the component as the `data` prop. Not run in the
|
|
24
|
-
* editor (the component receives `data: undefined` there).
|
|
25
|
-
*
|
|
26
|
-
* The result crosses the server→client boundary when the block component is a
|
|
27
|
-
* Client Component, so it must be RSC-serializable (plain objects, arrays and
|
|
28
|
-
* primitives - no functions, class instances, etc.).
|
|
29
|
-
*/
|
|
30
|
-
loader?: BlockLoader;
|
|
31
|
-
component: ComponentType<{
|
|
32
|
-
content: Record<string, unknown>;
|
|
33
|
-
style?: Record<string, unknown>;
|
|
34
|
-
advanced?: Record<string, unknown>;
|
|
35
|
-
context?: CmssyBlockContext;
|
|
36
|
-
data?: unknown;
|
|
37
|
-
}>;
|
|
38
|
-
}
|
|
39
|
-
declare function defineBlock<C extends Record<string, unknown>, D = unknown, S extends Record<string, unknown> = Record<string, unknown>, A extends Record<string, unknown> = Record<string, unknown>>(def: {
|
|
40
|
-
type: string;
|
|
41
|
-
label?: string;
|
|
42
|
-
category?: string;
|
|
43
|
-
icon?: string;
|
|
44
|
-
layoutPositions?: string[];
|
|
45
|
-
description?: string;
|
|
46
|
-
props: Record<string, FieldDefinition>;
|
|
47
|
-
loader?: (args: {
|
|
48
|
-
content: C;
|
|
49
|
-
context?: CmssyBlockContext;
|
|
50
|
-
}) => Promise<D> | D;
|
|
51
|
-
component: ComponentType<{
|
|
52
|
-
content: C;
|
|
53
|
-
style?: S;
|
|
54
|
-
advanced?: A;
|
|
55
|
-
context?: CmssyBlockContext;
|
|
56
|
-
data?: D;
|
|
57
|
-
}>;
|
|
58
|
-
}): BlockDefinition;
|
|
59
|
-
type BlockMap = Record<string, ComponentType<{
|
|
60
|
-
content: Record<string, unknown>;
|
|
61
|
-
style?: Record<string, unknown>;
|
|
62
|
-
advanced?: Record<string, unknown>;
|
|
63
|
-
context?: CmssyBlockContext;
|
|
64
|
-
data?: unknown;
|
|
65
|
-
}>>;
|
|
66
|
-
declare function buildBlockMap(blocks: BlockDefinition[]): BlockMap;
|
|
67
|
-
declare function blocksToSchemas(blocks: BlockDefinition[]): Record<string, BlockSchema>;
|
|
68
|
-
declare function blocksToMeta(blocks: BlockDefinition[], defaults?: {
|
|
69
|
-
category?: string;
|
|
70
|
-
}): Record<string, BlockMeta>;
|
|
71
|
-
|
|
72
|
-
export { type BlockDefinition as B, type BlockMap as a, blocksToMeta as b, blocksToSchemas as c, buildBlockMap as d, defineBlock as e };
|