@firecms/core 3.0.0-canary.282 → 3.0.0-canary.284
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/core/EntityEditView.d.ts +2 -2
- package/dist/form/EntityForm.d.ts +3 -1
- package/dist/form/index.d.ts +2 -1
- package/dist/index.es.js +166 -113
- package/dist/index.es.js.map +1 -1
- package/dist/index.umd.js +164 -111
- package/dist/index.umd.js.map +1 -1
- package/dist/preview/components/UserPreview.d.ts +1 -1
- package/dist/types/collections.d.ts +7 -0
- package/package.json +5 -5
- package/src/components/PropertyConfigBadge.tsx +2 -2
- package/src/components/UserDisplay.tsx +2 -1
- package/src/core/EntityEditView.tsx +13 -10
- package/src/core/EntityEditViewFormActions.tsx +33 -18
- package/src/form/EntityForm.tsx +49 -25
- package/src/form/EntityFormActions.tsx +30 -15
- package/src/form/PropertyFieldBinding.tsx +4 -0
- package/src/form/components/ErrorFocus.tsx +22 -29
- package/src/form/index.tsx +5 -1
- package/src/hooks/useBuildNavigationController.tsx +3 -2
- package/src/preview/components/UserPreview.tsx +7 -2
- package/src/preview/property_previews/ArrayPropertyPreview.tsx +1 -1
- package/src/types/collections.ts +8 -0
- package/src/util/entity_cache.ts +0 -1
package/dist/index.umd.js
CHANGED
|
@@ -5848,7 +5848,7 @@
|
|
|
5848
5848
|
}
|
|
5849
5849
|
let t3;
|
|
5850
5850
|
if ($[11] !== t2) {
|
|
5851
|
-
t3 = /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex flex-col gap-2", children: t2 });
|
|
5851
|
+
t3 = /* @__PURE__ */ jsxRuntime.jsx("div", { className: "w-full flex flex-col gap-2", children: t2 });
|
|
5852
5852
|
$[11] = t2;
|
|
5853
5853
|
$[12] = t3;
|
|
5854
5854
|
} else {
|
|
@@ -6829,7 +6829,7 @@
|
|
|
6829
6829
|
if (!user) {
|
|
6830
6830
|
let t12;
|
|
6831
6831
|
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
|
|
6832
|
-
t12 = /* @__PURE__ */ jsxRuntime.jsx(
|
|
6832
|
+
t12 = /* @__PURE__ */ jsxRuntime.jsx(EmptyValue, {});
|
|
6833
6833
|
$[0] = t12;
|
|
6834
6834
|
} else {
|
|
6835
6835
|
t12 = $[0];
|
|
@@ -6905,7 +6905,7 @@
|
|
|
6905
6905
|
return t8;
|
|
6906
6906
|
}
|
|
6907
6907
|
function UserPreview(t0) {
|
|
6908
|
-
const $ = reactCompilerRuntime.c(
|
|
6908
|
+
const $ = reactCompilerRuntime.c(8);
|
|
6909
6909
|
const {
|
|
6910
6910
|
value
|
|
6911
6911
|
} = t0;
|
|
@@ -6913,25 +6913,46 @@
|
|
|
6913
6913
|
getUser
|
|
6914
6914
|
} = useInternalUserManagementController();
|
|
6915
6915
|
if (!value) {
|
|
6916
|
-
|
|
6916
|
+
let t12;
|
|
6917
|
+
if ($[0] === Symbol.for("react.memo_cache_sentinel")) {
|
|
6918
|
+
t12 = /* @__PURE__ */ jsxRuntime.jsx(EmptyValue, {});
|
|
6919
|
+
$[0] = t12;
|
|
6920
|
+
} else {
|
|
6921
|
+
t12 = $[0];
|
|
6922
|
+
}
|
|
6923
|
+
return t12;
|
|
6917
6924
|
}
|
|
6918
6925
|
let t1;
|
|
6919
|
-
if ($[
|
|
6926
|
+
if ($[1] !== getUser || $[2] !== value) {
|
|
6920
6927
|
t1 = getUser(value);
|
|
6921
|
-
$[
|
|
6922
|
-
$[
|
|
6923
|
-
$[
|
|
6928
|
+
$[1] = getUser;
|
|
6929
|
+
$[2] = value;
|
|
6930
|
+
$[3] = t1;
|
|
6924
6931
|
} else {
|
|
6925
|
-
t1 = $[
|
|
6932
|
+
t1 = $[3];
|
|
6926
6933
|
}
|
|
6927
6934
|
const user = t1;
|
|
6935
|
+
if (!user) {
|
|
6936
|
+
let t22;
|
|
6937
|
+
if ($[4] !== value) {
|
|
6938
|
+
t22 = /* @__PURE__ */ jsxRuntime.jsxs(ui.Typography, { variant: "caption", color: "secondary", children: [
|
|
6939
|
+
"User not found: ",
|
|
6940
|
+
value
|
|
6941
|
+
] });
|
|
6942
|
+
$[4] = value;
|
|
6943
|
+
$[5] = t22;
|
|
6944
|
+
} else {
|
|
6945
|
+
t22 = $[5];
|
|
6946
|
+
}
|
|
6947
|
+
return t22;
|
|
6948
|
+
}
|
|
6928
6949
|
let t2;
|
|
6929
|
-
if ($[
|
|
6950
|
+
if ($[6] !== user) {
|
|
6930
6951
|
t2 = /* @__PURE__ */ jsxRuntime.jsx(UserDisplay, { user });
|
|
6931
|
-
$[
|
|
6932
|
-
$[
|
|
6952
|
+
$[6] = user;
|
|
6953
|
+
$[7] = t2;
|
|
6933
6954
|
} else {
|
|
6934
|
-
t2 = $[
|
|
6955
|
+
t2 = $[7];
|
|
6935
6956
|
}
|
|
6936
6957
|
return t2;
|
|
6937
6958
|
}
|
|
@@ -14966,61 +14987,60 @@
|
|
|
14966
14987
|
] });
|
|
14967
14988
|
}
|
|
14968
14989
|
const ErrorFocus = (t0) => {
|
|
14969
|
-
const $ = reactCompilerRuntime.c(
|
|
14990
|
+
const $ = reactCompilerRuntime.c(10);
|
|
14970
14991
|
const {
|
|
14971
14992
|
containerRef
|
|
14972
14993
|
} = t0;
|
|
14973
14994
|
const {
|
|
14974
|
-
isSubmitting,
|
|
14975
14995
|
isValidating,
|
|
14976
|
-
errors
|
|
14996
|
+
errors,
|
|
14997
|
+
version
|
|
14977
14998
|
} = formex.useFormex();
|
|
14999
|
+
const prevVersion = React.useRef(version);
|
|
14978
15000
|
let t1;
|
|
14979
|
-
|
|
14980
|
-
if ($[0] !== containerRef || $[1] !== errors || $[2] !== isSubmitting || $[3] !== isValidating) {
|
|
15001
|
+
if ($[0] !== containerRef?.current || $[1] !== errors || $[2] !== isValidating || $[3] !== version) {
|
|
14981
15002
|
t1 = () => {
|
|
15003
|
+
if (version === prevVersion.current) {
|
|
15004
|
+
return;
|
|
15005
|
+
}
|
|
14982
15006
|
const keys = Object.keys(errors);
|
|
14983
|
-
if (keys.length > 0
|
|
15007
|
+
if (!isValidating && keys.length > 0) {
|
|
14984
15008
|
const errorElement = containerRef?.current?.querySelector(`#form_field_${keys[0]}`);
|
|
14985
|
-
if (errorElement
|
|
14986
|
-
|
|
14987
|
-
|
|
14988
|
-
|
|
14989
|
-
|
|
14990
|
-
top: scrollableParent.scrollTop + top - 196,
|
|
14991
|
-
behavior: "smooth"
|
|
14992
|
-
});
|
|
14993
|
-
}
|
|
15009
|
+
if (errorElement) {
|
|
15010
|
+
errorElement.scrollIntoView({
|
|
15011
|
+
behavior: "smooth",
|
|
15012
|
+
block: "center"
|
|
15013
|
+
});
|
|
14994
15014
|
const input = errorElement.querySelector("input");
|
|
14995
15015
|
if (input) {
|
|
14996
15016
|
input.focus();
|
|
14997
15017
|
}
|
|
14998
15018
|
}
|
|
15019
|
+
prevVersion.current = version;
|
|
14999
15020
|
}
|
|
15000
15021
|
};
|
|
15001
|
-
|
|
15002
|
-
$[0] = containerRef;
|
|
15022
|
+
$[0] = containerRef?.current;
|
|
15003
15023
|
$[1] = errors;
|
|
15004
|
-
$[2] =
|
|
15005
|
-
$[3] =
|
|
15024
|
+
$[2] = isValidating;
|
|
15025
|
+
$[3] = version;
|
|
15006
15026
|
$[4] = t1;
|
|
15007
|
-
$[5] = t2;
|
|
15008
15027
|
} else {
|
|
15009
15028
|
t1 = $[4];
|
|
15010
|
-
|
|
15029
|
+
}
|
|
15030
|
+
let t2;
|
|
15031
|
+
if ($[5] !== containerRef || $[6] !== errors || $[7] !== isValidating || $[8] !== version) {
|
|
15032
|
+
t2 = [isValidating, errors, containerRef, version];
|
|
15033
|
+
$[5] = containerRef;
|
|
15034
|
+
$[6] = errors;
|
|
15035
|
+
$[7] = isValidating;
|
|
15036
|
+
$[8] = version;
|
|
15037
|
+
$[9] = t2;
|
|
15038
|
+
} else {
|
|
15039
|
+
t2 = $[9];
|
|
15011
15040
|
}
|
|
15012
15041
|
React.useEffect(t1, t2);
|
|
15013
15042
|
return null;
|
|
15014
15043
|
};
|
|
15015
|
-
const isScrollable = (ele) => {
|
|
15016
|
-
const hasScrollableContent = ele && ele.scrollHeight > ele.clientHeight;
|
|
15017
|
-
const overflowYStyle = ele ? window.getComputedStyle(ele).overflowY : null;
|
|
15018
|
-
const isOverflowHidden = overflowYStyle && overflowYStyle.indexOf("hidden") !== -1;
|
|
15019
|
-
return hasScrollableContent && !isOverflowHidden;
|
|
15020
|
-
};
|
|
15021
|
-
const getScrollableParent = (ele) => {
|
|
15022
|
-
return !ele || ele === document.body ? document.body : isScrollable(ele) ? ele : getScrollableParent(ele.parentNode);
|
|
15023
|
-
};
|
|
15024
15044
|
function EntityFormActions(t0) {
|
|
15025
15045
|
const $ = reactCompilerRuntime.c(16);
|
|
15026
15046
|
const {
|
|
@@ -15041,7 +15061,7 @@
|
|
|
15041
15061
|
const context = useFireCMSContext();
|
|
15042
15062
|
const sideEntityController = useSideEntityController();
|
|
15043
15063
|
let t1;
|
|
15044
|
-
if ($[0] !== collection || $[1] !== context || $[2] !== disabled || $[3] !== entity || $[4] !== formContext || $[5] !== formex2
|
|
15064
|
+
if ($[0] !== collection || $[1] !== context || $[2] !== disabled || $[3] !== entity || $[4] !== formContext || $[5] !== formex2 || $[6] !== fullIdPath || $[7] !== fullPath || $[8] !== layout || $[9] !== navigateBack || $[10] !== openEntityMode || $[11] !== pluginActions || $[12] !== savingError || $[13] !== sideEntityController || $[14] !== status) {
|
|
15045
15065
|
t1 = layout === "bottom" ? buildBottomActions$1({
|
|
15046
15066
|
fullPath,
|
|
15047
15067
|
fullIdPath,
|
|
@@ -15050,13 +15070,13 @@
|
|
|
15050
15070
|
collection,
|
|
15051
15071
|
context,
|
|
15052
15072
|
sideEntityController,
|
|
15053
|
-
isSubmitting: formex2.isSubmitting,
|
|
15054
15073
|
disabled,
|
|
15055
15074
|
status,
|
|
15056
15075
|
pluginActions,
|
|
15057
15076
|
openEntityMode,
|
|
15058
15077
|
navigateBack,
|
|
15059
|
-
formContext
|
|
15078
|
+
formContext,
|
|
15079
|
+
formex: formex2
|
|
15060
15080
|
}) : buildSideActions$1({
|
|
15061
15081
|
fullPath,
|
|
15062
15082
|
fullIdPath,
|
|
@@ -15065,18 +15085,18 @@
|
|
|
15065
15085
|
collection,
|
|
15066
15086
|
context,
|
|
15067
15087
|
sideEntityController,
|
|
15068
|
-
isSubmitting: formex2.isSubmitting,
|
|
15069
15088
|
disabled,
|
|
15070
15089
|
status,
|
|
15071
15090
|
pluginActions,
|
|
15072
|
-
openEntityMode
|
|
15091
|
+
openEntityMode,
|
|
15092
|
+
formex: formex2
|
|
15073
15093
|
});
|
|
15074
15094
|
$[0] = collection;
|
|
15075
15095
|
$[1] = context;
|
|
15076
15096
|
$[2] = disabled;
|
|
15077
15097
|
$[3] = entity;
|
|
15078
15098
|
$[4] = formContext;
|
|
15079
|
-
$[5] = formex2
|
|
15099
|
+
$[5] = formex2;
|
|
15080
15100
|
$[6] = fullIdPath;
|
|
15081
15101
|
$[7] = fullPath;
|
|
15082
15102
|
$[8] = layout;
|
|
@@ -15101,14 +15121,15 @@
|
|
|
15101
15121
|
collection,
|
|
15102
15122
|
context,
|
|
15103
15123
|
sideEntityController,
|
|
15104
|
-
isSubmitting,
|
|
15105
15124
|
disabled,
|
|
15106
15125
|
status,
|
|
15107
15126
|
pluginActions,
|
|
15108
15127
|
openEntityMode,
|
|
15109
15128
|
navigateBack,
|
|
15110
|
-
formContext
|
|
15129
|
+
formContext,
|
|
15130
|
+
formex: formex2
|
|
15111
15131
|
}) {
|
|
15132
|
+
const hasErrors = Object.keys(formex2.errors).length > 0 && formex2.submitCount > 0;
|
|
15112
15133
|
return /* @__PURE__ */ jsxRuntime.jsxs(ui.DialogActions, { position: "absolute", children: [
|
|
15113
15134
|
savingError && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "text-right", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { color: "error", children: savingError.message }) }),
|
|
15114
15135
|
entity && (formActions ?? []).length > 0 && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex-grow flex overflow-auto no-scrollbar", children: (formActions ?? []).map((action) => /* @__PURE__ */ jsxRuntime.jsx(ui.IconButton, { color: "primary", onClick: (event) => {
|
|
@@ -15127,8 +15148,8 @@
|
|
|
15127
15148
|
});
|
|
15128
15149
|
}, children: action.icon }, action.name)) }),
|
|
15129
15150
|
pluginActions,
|
|
15130
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "text", disabled: disabled || isSubmitting, color: "primary", type: "reset", children: status === "existing" ? "Discard" : "Clear" }),
|
|
15131
|
-
/* @__PURE__ */ jsxRuntime.jsxs(ui.Button, { variant: "filled", color: "primary", type: "submit", disabled: disabled || isSubmitting, children: [
|
|
15151
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "text", disabled: disabled || formex2.isSubmitting, color: "primary", type: "reset", children: status === "existing" ? "Discard" : "Clear" }),
|
|
15152
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Button, { variant: "filled", color: "primary", type: "submit", disabled: disabled || formex2.isSubmitting, startIcon: hasErrors ? /* @__PURE__ */ jsxRuntime.jsx(ui.ErrorIcon, {}) : void 0, children: [
|
|
15132
15153
|
status === "existing" && "Save",
|
|
15133
15154
|
status === "copy" && "Create copy",
|
|
15134
15155
|
status === "new" && "Create"
|
|
@@ -15145,22 +15166,35 @@
|
|
|
15145
15166
|
collection,
|
|
15146
15167
|
context,
|
|
15147
15168
|
sideEntityController,
|
|
15148
|
-
isSubmitting,
|
|
15149
15169
|
disabled,
|
|
15150
15170
|
status,
|
|
15151
|
-
pluginActions
|
|
15171
|
+
pluginActions,
|
|
15172
|
+
formex: formex2
|
|
15152
15173
|
}) {
|
|
15174
|
+
const hasErrors = Object.keys(formex2.errors).length > 0 && formex2.submitCount > 0;
|
|
15153
15175
|
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cls("overflow-auto h-full flex flex-col gap-2 w-80 2xl:w-96 px-4 py-16 sticky top-0 border-l", ui.defaultBorderMixin), children: [
|
|
15154
|
-
/* @__PURE__ */ jsxRuntime.jsxs(ui.LoadingButton, { fullWidth: true, variant: "filled", color: "primary", type: "submit", size: "large", disabled: disabled || isSubmitting, children: [
|
|
15176
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.LoadingButton, { fullWidth: true, variant: "filled", color: "primary", type: "submit", size: "large", startIcon: hasErrors ? /* @__PURE__ */ jsxRuntime.jsx(ui.ErrorIcon, {}) : void 0, disabled: disabled || formex2.isSubmitting, children: [
|
|
15155
15177
|
status === "existing" && "Save",
|
|
15156
15178
|
status === "copy" && "Create copy",
|
|
15157
15179
|
status === "new" && "Create"
|
|
15158
15180
|
] }),
|
|
15159
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { fullWidth: true, variant: "text", disabled: disabled || isSubmitting, type: "reset", children: status === "existing" ? "Discard" : "Clear" }),
|
|
15181
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { fullWidth: true, variant: "text", disabled: disabled || formex2.isSubmitting, type: "reset", children: status === "existing" ? "Discard" : "Clear" }),
|
|
15160
15182
|
pluginActions,
|
|
15161
15183
|
savingError && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "text-right", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { color: "error", children: savingError.message }) })
|
|
15162
15184
|
] });
|
|
15163
15185
|
}
|
|
15186
|
+
function extractTouchedValues(values, touched) {
|
|
15187
|
+
let acc = {};
|
|
15188
|
+
if (!touched || typeof touched !== "object") {
|
|
15189
|
+
return acc;
|
|
15190
|
+
}
|
|
15191
|
+
Object.entries(touched).forEach(([key, value]) => {
|
|
15192
|
+
if (value) {
|
|
15193
|
+
acc = formex.setIn(acc, key, formex.getIn(values, key));
|
|
15194
|
+
}
|
|
15195
|
+
});
|
|
15196
|
+
return acc;
|
|
15197
|
+
}
|
|
15164
15198
|
function EntityForm({
|
|
15165
15199
|
path,
|
|
15166
15200
|
fullIdPath,
|
|
@@ -15218,7 +15252,7 @@
|
|
|
15218
15252
|
const customizationController = useCustomizationController();
|
|
15219
15253
|
const context = useFireCMSContext();
|
|
15220
15254
|
const analyticsController = useAnalyticsController();
|
|
15221
|
-
const [underlyingChanges
|
|
15255
|
+
const [underlyingChanges] = React.useState({});
|
|
15222
15256
|
const [customIdLoading, setCustomIdLoading] = React.useState(false);
|
|
15223
15257
|
const mustSetCustomId = (status === "new" || status === "copy") && Boolean(collection.customId) && collection.customId !== "optional";
|
|
15224
15258
|
const initialEntityId = React.useMemo(() => {
|
|
@@ -15266,16 +15300,30 @@
|
|
|
15266
15300
|
formexController.setSubmitting(false);
|
|
15267
15301
|
});
|
|
15268
15302
|
};
|
|
15303
|
+
const baseInitialValues = getInitialEntityValues(authController, collection, path, status, entity, customizationController.propertyConfigs);
|
|
15304
|
+
const initialValues = initialDirtyValues ? mergeDeep(baseInitialValues, initialDirtyValues) : baseInitialValues;
|
|
15305
|
+
const initialDirty = Boolean(initialDirtyValues) && initialDirtyValues && Object.keys(initialDirtyValues).length > 0;
|
|
15269
15306
|
const formex$1 = formexProp ?? formex.useCreateFormex({
|
|
15270
|
-
initialValues
|
|
15271
|
-
initialDirty
|
|
15307
|
+
initialValues,
|
|
15308
|
+
initialDirty,
|
|
15309
|
+
initialTouched: initialDirtyValues ? formex.flattenKeys(initialDirtyValues).reduce((previousValue, currentValue) => ({
|
|
15310
|
+
...previousValue,
|
|
15311
|
+
[currentValue]: true
|
|
15312
|
+
}), {}) : {},
|
|
15272
15313
|
onSubmit,
|
|
15273
15314
|
onReset: () => {
|
|
15274
15315
|
clearDirtyCache();
|
|
15275
15316
|
onValuesModified?.(false);
|
|
15276
15317
|
},
|
|
15277
|
-
|
|
15278
|
-
|
|
15318
|
+
onValuesChangeDeferred: (values_0, controller) => {
|
|
15319
|
+
const key = status === "new" || status === "copy" ? path + "#new" : path + "/" + entityId;
|
|
15320
|
+
if (controller.dirty) {
|
|
15321
|
+
const touchedValues = extractTouchedValues(values_0, controller.touched);
|
|
15322
|
+
saveEntityToCache(key, touchedValues);
|
|
15323
|
+
}
|
|
15324
|
+
},
|
|
15325
|
+
validation: (values_1) => {
|
|
15326
|
+
return validationSchema?.validate(values_1, {
|
|
15279
15327
|
abortEarly: false
|
|
15280
15328
|
}).then(() => {
|
|
15281
15329
|
return {};
|
|
@@ -15358,7 +15406,7 @@
|
|
|
15358
15406
|
console.error(e_3);
|
|
15359
15407
|
}, [entityId, path, snackbarController]);
|
|
15360
15408
|
const saveEntity = ({
|
|
15361
|
-
values:
|
|
15409
|
+
values: values_2,
|
|
15362
15410
|
previousValues,
|
|
15363
15411
|
entityId: entityId_0,
|
|
15364
15412
|
collection: collection_0,
|
|
@@ -15367,7 +15415,7 @@
|
|
|
15367
15415
|
return saveEntityWithCallbacks({
|
|
15368
15416
|
path: path_0,
|
|
15369
15417
|
entityId: entityId_0,
|
|
15370
|
-
values:
|
|
15418
|
+
values: values_2,
|
|
15371
15419
|
previousValues,
|
|
15372
15420
|
collection: collection_0,
|
|
15373
15421
|
status,
|
|
@@ -15383,34 +15431,34 @@
|
|
|
15383
15431
|
collection: collection_1,
|
|
15384
15432
|
path: path_1,
|
|
15385
15433
|
entityId: entityId_1,
|
|
15386
|
-
values:
|
|
15434
|
+
values: values_3,
|
|
15387
15435
|
previousValues: previousValues_0,
|
|
15388
15436
|
autoSave: autoSave_0
|
|
15389
15437
|
}) => {
|
|
15390
15438
|
if (!status) return;
|
|
15391
15439
|
if (autoSave_0) {
|
|
15392
|
-
setValuesToBeSaved(
|
|
15440
|
+
setValuesToBeSaved(values_3);
|
|
15393
15441
|
} else {
|
|
15394
15442
|
return saveEntity({
|
|
15395
15443
|
collection: collection_1,
|
|
15396
15444
|
path: path_1,
|
|
15397
15445
|
entityId: entityId_1,
|
|
15398
|
-
values:
|
|
15446
|
+
values: values_3,
|
|
15399
15447
|
previousValues: previousValues_0
|
|
15400
15448
|
});
|
|
15401
15449
|
}
|
|
15402
15450
|
};
|
|
15403
15451
|
const lastSavedValues = React.useRef(entity?.values);
|
|
15404
|
-
const save = (
|
|
15405
|
-
lastSavedValues.current =
|
|
15452
|
+
const save = (values_4) => {
|
|
15453
|
+
lastSavedValues.current = values_4;
|
|
15406
15454
|
return onSaveEntityRequest({
|
|
15407
15455
|
collection: resolvedCollection,
|
|
15408
15456
|
path,
|
|
15409
15457
|
entityId,
|
|
15410
|
-
values:
|
|
15458
|
+
values: values_4,
|
|
15411
15459
|
previousValues: entity?.values,
|
|
15412
15460
|
autoSave: autoSave ?? false
|
|
15413
|
-
}).then((
|
|
15461
|
+
}).then(() => {
|
|
15414
15462
|
const eventName = status === "new" ? "new_entity_saved" : status === "copy" ? "entity_copied" : status === "existing" ? "entity_edited" : "unmapped_event";
|
|
15415
15463
|
analyticsController.onAnalyticsEvent?.(eventName, {
|
|
15416
15464
|
path
|
|
@@ -15444,7 +15492,8 @@
|
|
|
15444
15492
|
type: "error",
|
|
15445
15493
|
message: "Error updating id, check the console"
|
|
15446
15494
|
});
|
|
15447
|
-
|
|
15495
|
+
console.error(error);
|
|
15496
|
+
}, [snackbarController]);
|
|
15448
15497
|
const pluginActions = [];
|
|
15449
15498
|
const plugins = customizationController.plugins;
|
|
15450
15499
|
const actionsDisabled = disabled || formex$1.isSubmitting || status === "existing" && !formex$1.dirty || Boolean(disabledProp);
|
|
@@ -15493,20 +15542,12 @@
|
|
|
15493
15542
|
onValuesModified?.(modified);
|
|
15494
15543
|
}
|
|
15495
15544
|
}, [formex$1.dirty]);
|
|
15496
|
-
const deferredValues = React.useDeferredValue(formex$1.values);
|
|
15497
15545
|
const modified = formex$1.dirty;
|
|
15498
15546
|
const uniqueFieldValidator = React.useCallback(({
|
|
15499
15547
|
name,
|
|
15500
|
-
value
|
|
15501
|
-
property
|
|
15548
|
+
value
|
|
15502
15549
|
}) => dataSource.checkUniqueField(path, name, value, entityId, collection), [dataSource, path, entityId]);
|
|
15503
15550
|
const validationSchema = React.useMemo(() => entityId ? getYupEntitySchema(entityId, resolvedCollection.properties, uniqueFieldValidator) : void 0, [entityId, resolvedCollection.properties, uniqueFieldValidator]);
|
|
15504
|
-
React.useEffect(() => {
|
|
15505
|
-
const key = status === "new" || status === "copy" ? path + "#new" : path + "/" + entityId;
|
|
15506
|
-
if (modified) {
|
|
15507
|
-
saveEntityToCache(key, deferredValues);
|
|
15508
|
-
}
|
|
15509
|
-
}, [deferredValues, modified, path, entityId, status]);
|
|
15510
15551
|
useOnAutoSave(autoSave, formex$1, lastSavedValues, save);
|
|
15511
15552
|
React.useEffect(() => {
|
|
15512
15553
|
if (!autoSave && !formex$1.isSubmitting && underlyingChanges && entity) {
|
|
@@ -15525,18 +15566,18 @@
|
|
|
15525
15566
|
return /* @__PURE__ */ jsxRuntime.jsx(Builder, { collection, entity, modifiedValues: formex$1.values, formContext });
|
|
15526
15567
|
}
|
|
15527
15568
|
return /* @__PURE__ */ jsxRuntime.jsx(FormLayout, { children: formFieldKeys.map((key_1) => {
|
|
15528
|
-
const
|
|
15529
|
-
if (
|
|
15569
|
+
const property = resolvedCollection.properties[key_1];
|
|
15570
|
+
if (property) {
|
|
15530
15571
|
const underlyingValueHasChanged = !!underlyingChanges && Object.keys(underlyingChanges).includes(key_1) && formex$1.touched[key_1];
|
|
15531
|
-
const disabled_0 = disabledProp || !autoSave && formex$1.isSubmitting || isReadOnly(
|
|
15532
|
-
const hidden = isHidden(
|
|
15572
|
+
const disabled_0 = disabledProp || !autoSave && formex$1.isSubmitting || isReadOnly(property) || Boolean(property.disabled);
|
|
15573
|
+
const hidden = isHidden(property);
|
|
15533
15574
|
if (hidden) return null;
|
|
15534
|
-
const widthPercentage =
|
|
15575
|
+
const widthPercentage = property.widthPercentage ?? 100;
|
|
15535
15576
|
const cmsFormFieldProps = {
|
|
15536
15577
|
propertyKey: key_1,
|
|
15537
15578
|
disabled: disabled_0,
|
|
15538
|
-
property
|
|
15539
|
-
includeDescription:
|
|
15579
|
+
property,
|
|
15580
|
+
includeDescription: property.description || property.longDescription,
|
|
15540
15581
|
underlyingValueHasChanged: underlyingValueHasChanged && !autoSave,
|
|
15541
15582
|
context: formContext,
|
|
15542
15583
|
partOfArray: false,
|
|
@@ -15592,7 +15633,7 @@
|
|
|
15592
15633
|
}
|
|
15593
15634
|
const dialogActions = /* @__PURE__ */ jsxRuntime.jsx(EntityFormActionsComponent, { collection: resolvedCollection, path, fullPath: path, fullIdPath, entity, layout: forceActionsAtTheBottom ? "bottom" : "side", savingError, formex: formex$1, disabled: actionsDisabled, status, pluginActions: pluginActions ?? [], openEntityMode, showDefaultActions, navigateBack, formContext });
|
|
15594
15635
|
return /* @__PURE__ */ jsxRuntime.jsx(formex.Formex, { value: formex$1, children: /* @__PURE__ */ jsxRuntime.jsxs("form", { onSubmit: formex$1.handleSubmit, onReset: () => formex$1.resetForm({
|
|
15595
|
-
values:
|
|
15636
|
+
values: baseInitialValues
|
|
15596
15637
|
}), noValidate: true, className: ui.cls("flex-1 flex flex-row w-full overflow-y-auto justify-center", className), children: [
|
|
15597
15638
|
/* @__PURE__ */ jsxRuntime.jsx("div", { id: `form_${path}`, className: ui.cls("relative flex flex-row max-w-4xl lg:max-w-3xl xl:max-w-4xl 2xl:max-w-6xl w-full h-fit"), children: /* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cls("flex flex-col w-full pt-12 pb-16 px-4 sm:px-8 md:px-10"), children: [
|
|
15598
15639
|
formex$1.dirty ? /* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "Local unsaved changes", className: "self-end sticky top-4 z-10", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Chip, { size: "small", colorScheme: "orangeDarker", children: /* @__PURE__ */ jsxRuntime.jsx(ui.EditIcon, { size: "smallest" }) }) }) : /* @__PURE__ */ jsxRuntime.jsx(ui.Tooltip, { title: "In sync with the database", className: "self-end sticky top-4 z-10", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Chip, { size: "small", children: /* @__PURE__ */ jsxRuntime.jsx(ui.CheckIcon, { size: "smallest" }) }) }),
|
|
@@ -17776,6 +17817,13 @@
|
|
|
17776
17817
|
} = t0;
|
|
17777
17818
|
const authController = useAuthController();
|
|
17778
17819
|
const customizationController = useCustomizationController();
|
|
17820
|
+
if (propertyKey === "created_by") {
|
|
17821
|
+
console.log("Rendering field for created_by", {
|
|
17822
|
+
propertyKey,
|
|
17823
|
+
property,
|
|
17824
|
+
context
|
|
17825
|
+
});
|
|
17826
|
+
}
|
|
17779
17827
|
let t1;
|
|
17780
17828
|
if ($[0] !== authController || $[1] !== autoFocus || $[2] !== context || $[3] !== customizationController.propertyConfigs || $[4] !== disabledProp || $[5] !== includeDescription || $[6] !== index || $[7] !== minimalistView || $[8] !== onPropertyChange || $[9] !== partOfArray || $[10] !== property || $[11] !== propertyKey || $[12] !== size || $[13] !== underlyingValueHasChanged) {
|
|
17781
17829
|
t1 = (fieldProps) => {
|
|
@@ -20640,7 +20688,7 @@
|
|
|
20640
20688
|
propertyConfig,
|
|
20641
20689
|
disabled
|
|
20642
20690
|
} = t0;
|
|
20643
|
-
const classes = "h-8 w-8
|
|
20691
|
+
const classes = "h-8 w-8 flex items-center justify-center rounded-full shadow text-white " + (disabled ? "bg-surface-400 dark:bg-surface-600" : "");
|
|
20644
20692
|
let t1;
|
|
20645
20693
|
if ($[0] !== classes || $[1] !== disabled || $[2] !== propertyConfig) {
|
|
20646
20694
|
const defaultPropertyConfig = typeof propertyConfig?.property === "object" ? getDefaultFieldConfig(propertyConfig.property) : void 0;
|
|
@@ -20655,7 +20703,7 @@
|
|
|
20655
20703
|
} else {
|
|
20656
20704
|
t3 = $[5];
|
|
20657
20705
|
}
|
|
20658
|
-
t1 = /* @__PURE__ */ jsxRuntime.jsx("div", { className: classes, style: t3, children: propertyConfig?.Icon ? getIconForWidget(propertyConfig, "
|
|
20706
|
+
t1 = /* @__PURE__ */ jsxRuntime.jsx("div", { className: classes, style: t3, children: propertyConfig?.Icon ? getIconForWidget(propertyConfig, "small") : getIconForWidget(defaultPropertyConfig, "small") });
|
|
20659
20707
|
$[0] = classes;
|
|
20660
20708
|
$[1] = disabled;
|
|
20661
20709
|
$[2] = propertyConfig;
|
|
@@ -21991,7 +22039,8 @@
|
|
|
21991
22039
|
}, []);
|
|
21992
22040
|
const isUrlCollectionPath = React.useCallback((path_1) => removeInitialAndTrailingSlashes(path_1 + "/").startsWith(removeInitialAndTrailingSlashes(fullCollectionPath) + "/"), [fullCollectionPath]);
|
|
21993
22041
|
const urlPathToDataPath = React.useCallback((path_2) => {
|
|
21994
|
-
|
|
22042
|
+
const decodedPath = decodeURIComponent(path_2);
|
|
22043
|
+
if (decodedPath.startsWith(fullCollectionPath)) return decodedPath.replace(fullCollectionPath, "");
|
|
21995
22044
|
throw Error("Expected path starting with " + fullCollectionPath);
|
|
21996
22045
|
}, [fullCollectionPath]);
|
|
21997
22046
|
const resolveIdsFrom = React.useCallback((path_3) => {
|
|
@@ -22797,14 +22846,14 @@
|
|
|
22797
22846
|
collection,
|
|
22798
22847
|
context,
|
|
22799
22848
|
sideEntityController,
|
|
22800
|
-
isSubmitting: formex2.isSubmitting,
|
|
22801
22849
|
disabled,
|
|
22802
22850
|
status,
|
|
22803
22851
|
sideDialogContext,
|
|
22804
22852
|
pluginActions,
|
|
22805
22853
|
openEntityMode,
|
|
22806
22854
|
navigateBack,
|
|
22807
|
-
formContext
|
|
22855
|
+
formContext,
|
|
22856
|
+
formex: formex2
|
|
22808
22857
|
}) : buildSideActions({
|
|
22809
22858
|
savingError,
|
|
22810
22859
|
entity,
|
|
@@ -22812,14 +22861,14 @@
|
|
|
22812
22861
|
collection,
|
|
22813
22862
|
context,
|
|
22814
22863
|
sideEntityController,
|
|
22815
|
-
isSubmitting: formex2.isSubmitting,
|
|
22816
22864
|
sideDialogContext,
|
|
22817
22865
|
disabled,
|
|
22818
22866
|
status,
|
|
22819
22867
|
pluginActions,
|
|
22820
22868
|
openEntityMode,
|
|
22821
22869
|
navigateBack,
|
|
22822
|
-
formContext
|
|
22870
|
+
formContext,
|
|
22871
|
+
formex: formex2
|
|
22823
22872
|
});
|
|
22824
22873
|
}
|
|
22825
22874
|
function buildBottomActions({
|
|
@@ -22829,15 +22878,16 @@
|
|
|
22829
22878
|
collection,
|
|
22830
22879
|
context,
|
|
22831
22880
|
sideEntityController,
|
|
22832
|
-
isSubmitting,
|
|
22833
22881
|
disabled,
|
|
22834
22882
|
status,
|
|
22835
22883
|
sideDialogContext,
|
|
22836
22884
|
pluginActions,
|
|
22837
22885
|
openEntityMode,
|
|
22838
22886
|
navigateBack,
|
|
22839
|
-
formContext
|
|
22887
|
+
formContext,
|
|
22888
|
+
formex: formex2
|
|
22840
22889
|
}) {
|
|
22890
|
+
const hasErrors = Object.keys(formex2.errors).length > 0 && formex2.submitCount > 0;
|
|
22841
22891
|
const canClose = openEntityMode === "side_panel";
|
|
22842
22892
|
return /* @__PURE__ */ jsxRuntime.jsxs(ui.DialogActions, { position: "absolute", children: [
|
|
22843
22893
|
savingError && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "text-right", children: /* @__PURE__ */ jsxRuntime.jsx(ui.Typography, { color: "error", children: savingError.message }) }),
|
|
@@ -22857,15 +22907,16 @@
|
|
|
22857
22907
|
return /* @__PURE__ */ jsxRuntime.jsx(EntityActionButton, { action, enabled: isEnabled, props }, action.key);
|
|
22858
22908
|
}) }),
|
|
22859
22909
|
pluginActions,
|
|
22860
|
-
/* @__PURE__ */ jsxRuntime.jsx(
|
|
22861
|
-
/* @__PURE__ */ jsxRuntime.
|
|
22910
|
+
hasErrors ? /* @__PURE__ */ jsxRuntime.jsx(ErrorTooltip, { title: "This form has errors", children: /* @__PURE__ */ jsxRuntime.jsx(ui.ErrorIcon, { className: "ml-4", color: "error", size: "smallest" }) }) : null,
|
|
22911
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { variant: "text", color: "primary", disabled: disabled || formex2.isSubmitting, type: "reset", children: status === "existing" ? "Discard" : "Clear" }),
|
|
22912
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.Button, { variant: canClose ? "text" : "filled", color: "primary", type: "submit", disabled: disabled || formex2.isSubmitting, onClick: () => {
|
|
22862
22913
|
sideDialogContext.setPendingClose(false);
|
|
22863
22914
|
}, children: [
|
|
22864
22915
|
status === "existing" && "Save",
|
|
22865
22916
|
status === "copy" && "Create copy",
|
|
22866
22917
|
status === "new" && "Create"
|
|
22867
22918
|
] }),
|
|
22868
|
-
canClose && /* @__PURE__ */ jsxRuntime.jsxs(ui.LoadingButton, { variant: "filled", color: "primary", type: "submit", loading: isSubmitting, disabled, onClick: () => {
|
|
22919
|
+
canClose && /* @__PURE__ */ jsxRuntime.jsxs(ui.LoadingButton, { variant: "filled", color: "primary", type: "submit", loading: formex2.isSubmitting, disabled, onClick: () => {
|
|
22869
22920
|
sideDialogContext.setPendingClose?.(true);
|
|
22870
22921
|
}, children: [
|
|
22871
22922
|
status === "existing" && "Save and close",
|
|
@@ -22881,24 +22932,25 @@
|
|
|
22881
22932
|
collection,
|
|
22882
22933
|
context,
|
|
22883
22934
|
sideEntityController,
|
|
22884
|
-
isSubmitting,
|
|
22885
22935
|
disabled,
|
|
22886
22936
|
status,
|
|
22887
22937
|
sideDialogContext,
|
|
22888
22938
|
pluginActions,
|
|
22889
22939
|
openEntityMode,
|
|
22890
22940
|
navigateBack,
|
|
22891
|
-
formContext
|
|
22941
|
+
formContext,
|
|
22942
|
+
formex: formex2
|
|
22892
22943
|
}) {
|
|
22944
|
+
const hasErrors = Object.keys(formex2.errors).length > 0 && formex2.submitCount > 0;
|
|
22893
22945
|
return /* @__PURE__ */ jsxRuntime.jsxs("div", { className: ui.cls("overflow-auto h-full flex flex-col gap-2 w-80 2xl:w-96 px-4 py-16 sticky top-0 border-l", ui.defaultBorderMixin), children: [
|
|
22894
|
-
/* @__PURE__ */ jsxRuntime.jsxs(ui.LoadingButton, { fullWidth: true, variant: "filled", color: "primary", type: "submit", size: "large", disabled: disabled || isSubmitting, onClick: () => {
|
|
22946
|
+
/* @__PURE__ */ jsxRuntime.jsxs(ui.LoadingButton, { fullWidth: true, variant: "filled", color: "primary", type: "submit", size: "large", startIcon: hasErrors ? /* @__PURE__ */ jsxRuntime.jsx(ui.ErrorIcon, {}) : void 0, disabled: disabled || formex2.isSubmitting, onClick: () => {
|
|
22895
22947
|
sideDialogContext.setPendingClose?.(false);
|
|
22896
22948
|
}, children: [
|
|
22897
22949
|
status === "existing" && "Save",
|
|
22898
22950
|
status === "copy" && "Create copy",
|
|
22899
22951
|
status === "new" && "Create"
|
|
22900
22952
|
] }),
|
|
22901
|
-
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { fullWidth: true, variant: "text", disabled: disabled || isSubmitting, type: "reset", children: status === "existing" ? "Discard" : "Clear" }),
|
|
22953
|
+
/* @__PURE__ */ jsxRuntime.jsx(ui.Button, { fullWidth: true, variant: "text", disabled: disabled || formex2.isSubmitting, type: "reset", children: status === "existing" ? "Discard" : "Clear" }),
|
|
22902
22954
|
pluginActions,
|
|
22903
22955
|
formActions.length > 0 && /* @__PURE__ */ jsxRuntime.jsx("div", { className: "flex flex-row flex-wrap mt-2", children: formActions.map((action) => {
|
|
22904
22956
|
const props = {
|
|
@@ -23126,7 +23178,8 @@
|
|
|
23126
23178
|
databaseId: props.databaseId,
|
|
23127
23179
|
useCache: false
|
|
23128
23180
|
});
|
|
23129
|
-
const
|
|
23181
|
+
const enableLocalChangesBackup = props.collection.enableLocalChangesBackup !== void 0 ? props.collection.enableLocalChangesBackup : true;
|
|
23182
|
+
const initialDirtyValues = enableLocalChangesBackup ? entityId ? getEntityFromCache(props.path + "/" + entityId) : getEntityFromCache(props.path + "#new") : void 0;
|
|
23130
23183
|
const authController = useAuthController();
|
|
23131
23184
|
const initialStatus = props.copy ? "copy" : entityId ? "existing" : "new";
|
|
23132
23185
|
const [status, setStatus] = React.useState(initialStatus);
|
|
@@ -23137,13 +23190,13 @@
|
|
|
23137
23190
|
return entity ? canEditEntity(props.collection, authController, props.path, entity ?? null) : void 0;
|
|
23138
23191
|
}
|
|
23139
23192
|
}, [authController, entity, status]);
|
|
23140
|
-
if (dataLoading && !
|
|
23193
|
+
if (dataLoading && !initialDirtyValues || (!entity || canEdit === void 0) && (status === "existing" || status === "copy")) {
|
|
23141
23194
|
return /* @__PURE__ */ jsxRuntime.jsx(CircularProgressCenter, {});
|
|
23142
23195
|
}
|
|
23143
|
-
if (entityId && !entity && !
|
|
23196
|
+
if (entityId && !entity && !initialDirtyValues) {
|
|
23144
23197
|
console.error(`Entity with id ${entityId} not found in collection ${props.path}`);
|
|
23145
23198
|
}
|
|
23146
|
-
return /* @__PURE__ */ jsxRuntime.jsx(EntityEditViewInner, { ...props, entityId, entity,
|
|
23199
|
+
return /* @__PURE__ */ jsxRuntime.jsx(EntityEditViewInner, { ...props, entityId, entity, initialDirtyValues, dataLoading, status, setStatus, canEdit });
|
|
23147
23200
|
}
|
|
23148
23201
|
function EntityEditViewInner({
|
|
23149
23202
|
path,
|
|
@@ -23156,7 +23209,7 @@
|
|
|
23156
23209
|
onSaved,
|
|
23157
23210
|
onTabChange,
|
|
23158
23211
|
entity,
|
|
23159
|
-
|
|
23212
|
+
initialDirtyValues,
|
|
23160
23213
|
dataLoading,
|
|
23161
23214
|
layout = "side_panel",
|
|
23162
23215
|
barActions,
|
|
@@ -23284,7 +23337,7 @@
|
|
|
23284
23337
|
/* @__PURE__ */ jsxRuntime.jsx(EntityView, { className: "px-8 h-full overflow-auto", entity, path, collection }),
|
|
23285
23338
|
/* @__PURE__ */ jsxRuntime.jsx("div", { className: "h-16" })
|
|
23286
23339
|
] }) }) : null;
|
|
23287
|
-
const entityView = /* @__PURE__ */ jsxRuntime.jsx(EntityForm, { fullIdPath, collection, path, entityId: entityId ?? usedEntity?.id, onValuesModified, entity, initialDirtyValues
|
|
23340
|
+
const entityView = /* @__PURE__ */ jsxRuntime.jsx(EntityForm, { fullIdPath, collection, path, entityId: entityId ?? usedEntity?.id, onValuesModified, entity, initialDirtyValues, openEntityMode: layout, forceActionsAtTheBottom: actionsAtTheBottom, initialStatus: status, className: ui.cls((!mainViewVisible || !canEdit) && !selectedSecondaryForm ? "hidden" : "", formProps?.className), EntityFormActionsComponent: EntityEditViewFormActions, disabled: !canEdit, ...formProps, onEntityChange: (entity_0) => {
|
|
23288
23341
|
setUsedEntity(entity_0);
|
|
23289
23342
|
formProps?.onEntityChange?.(entity_0);
|
|
23290
23343
|
}, onStatusChange: (status_0) => {
|