@webiny/api-headless-cms 0.0.0-unstable.aad28a72ae → 0.0.0-unstable.cc58a6566b
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/context.d.ts +5 -2
- package/context.js +53 -19
- package/context.js.map +1 -1
- package/crud/contentEntry/afterDelete.js +0 -5
- package/crud/contentEntry/afterDelete.js.map +1 -1
- package/crud/contentEntry/beforeCreate.js +0 -3
- package/crud/contentEntry/beforeCreate.js.map +1 -1
- package/crud/contentEntry/beforeUpdate.js +0 -3
- package/crud/contentEntry/beforeUpdate.js.map +1 -1
- package/crud/contentEntry/entryDataValidation.js +1 -40
- package/crud/contentEntry/entryDataValidation.js.map +1 -1
- package/crud/contentEntry/markLockedFields.js +12 -28
- package/crud/contentEntry/markLockedFields.js.map +1 -1
- package/crud/contentEntry/referenceFieldsMapping.js +5 -61
- package/crud/contentEntry/referenceFieldsMapping.js.map +1 -1
- package/crud/contentEntry/searchableFields.js +1 -12
- package/crud/contentEntry/searchableFields.js.map +1 -1
- package/crud/contentEntry.crud.js +72 -155
- package/crud/contentEntry.crud.js.map +1 -1
- package/crud/contentModel/afterCreate.js +0 -2
- package/crud/contentModel/afterCreate.js.map +1 -1
- package/crud/contentModel/afterCreateFrom.js +0 -2
- package/crud/contentModel/afterCreateFrom.js.map +1 -1
- package/crud/contentModel/afterDelete.js +0 -2
- package/crud/contentModel/afterDelete.js.map +1 -1
- package/crud/contentModel/afterUpdate.js +0 -2
- package/crud/contentModel/afterUpdate.js.map +1 -1
- package/crud/contentModel/beforeCreate.d.ts +2 -3
- package/crud/contentModel/beforeCreate.js +7 -36
- package/crud/contentModel/beforeCreate.js.map +1 -1
- package/crud/contentModel/beforeDelete.js +0 -10
- package/crud/contentModel/beforeDelete.js.map +1 -1
- package/crud/contentModel/beforeUpdate.d.ts +2 -4
- package/crud/contentModel/beforeUpdate.js +2 -7
- package/crud/contentModel/beforeUpdate.js.map +1 -1
- package/crud/contentModel/contentModelManagerFactory.js +0 -7
- package/crud/contentModel/contentModelManagerFactory.js.map +1 -1
- package/crud/contentModel/createFieldStorageId.js +0 -3
- package/crud/contentModel/createFieldStorageId.js.map +1 -1
- package/crud/contentModel/systemFields.js.map +1 -1
- package/crud/contentModel/validateLayout.js +0 -8
- package/crud/contentModel/validateLayout.js.map +1 -1
- package/crud/contentModel/validateModel.d.ts +3 -4
- package/crud/contentModel/validateModel.js +6 -11
- package/crud/contentModel/validateModel.js.map +1 -1
- package/crud/contentModel/validateModelFields.d.ts +3 -4
- package/crud/contentModel/validateModelFields.js +73 -75
- package/crud/contentModel/validateModelFields.js.map +1 -1
- package/crud/contentModel/validation.d.ts +477 -0
- package/crud/contentModel/validation.js +97 -0
- package/crud/contentModel/validation.js.map +1 -0
- package/crud/contentModel.crud.js +63 -158
- package/crud/contentModel.crud.js.map +1 -1
- package/crud/contentModelGroup/beforeCreate.js +0 -12
- package/crud/contentModelGroup/beforeCreate.js.map +1 -1
- package/crud/contentModelGroup/beforeDelete.js +0 -8
- package/crud/contentModelGroup/beforeDelete.js.map +1 -1
- package/crud/contentModelGroup/beforeUpdate.js +0 -5
- package/crud/contentModelGroup/beforeUpdate.js.map +1 -1
- package/crud/contentModelGroup/validation.d.ts +30 -0
- package/crud/contentModelGroup/validation.js +34 -0
- package/crud/contentModelGroup/validation.js.map +1 -0
- package/crud/contentModelGroup.crud.js +21 -93
- package/crud/contentModelGroup.crud.js.map +1 -1
- package/crud/settings.crud.js +0 -12
- package/crud/settings.crud.js.map +1 -1
- package/crud/system.crud.js +2 -37
- package/crud/system.crud.js.map +1 -1
- package/fieldConverters/CmsModelDefaultFieldConverterPlugin.js +0 -13
- package/fieldConverters/CmsModelDefaultFieldConverterPlugin.js.map +1 -1
- package/fieldConverters/CmsModelDynamicZoneFieldConverterPlugin.js +0 -36
- package/fieldConverters/CmsModelDynamicZoneFieldConverterPlugin.js.map +1 -1
- package/fieldConverters/CmsModelObjectFieldConverterPlugin.js +0 -53
- package/fieldConverters/CmsModelObjectFieldConverterPlugin.js.map +1 -1
- package/fieldConverters/index.js +0 -5
- package/fieldConverters/index.js.map +1 -1
- package/graphql/buildSchemaPlugins.d.ts +8 -3
- package/graphql/buildSchemaPlugins.js +6 -14
- package/graphql/buildSchemaPlugins.js.map +1 -1
- package/graphql/createExecutableSchema.d.ts +7 -0
- package/graphql/createExecutableSchema.js +29 -0
- package/graphql/createExecutableSchema.js.map +1 -0
- package/graphql/generateSchema.d.ts +8 -0
- package/graphql/generateSchema.js +31 -0
- package/graphql/generateSchema.js.map +1 -0
- package/graphql/graphQLHandlerFactory.js +70 -92
- package/graphql/graphQLHandlerFactory.js.map +1 -1
- package/graphql/index.d.ts +1 -3
- package/graphql/index.js +2 -46
- package/graphql/index.js.map +1 -1
- package/graphql/schema/baseContentSchema.d.ts +6 -2
- package/graphql/schema/baseContentSchema.js +7 -13
- package/graphql/schema/baseContentSchema.js.map +1 -1
- package/graphql/schema/baseSchema.d.ts +3 -0
- package/graphql/schema/baseSchema.js +53 -0
- package/graphql/schema/baseSchema.js.map +1 -0
- package/graphql/schema/contentEntries.d.ts +6 -2
- package/graphql/schema/contentEntries.js +39 -65
- package/graphql/schema/contentEntries.js.map +1 -1
- package/graphql/schema/contentModelGroups.d.ts +6 -2
- package/graphql/schema/contentModelGroups.js +9 -22
- package/graphql/schema/contentModelGroups.js.map +1 -1
- package/graphql/schema/contentModels.d.ts +6 -2
- package/graphql/schema/contentModels.js +21 -23
- package/graphql/schema/contentModels.js.map +1 -1
- package/graphql/schema/createFieldResolvers.js +13 -24
- package/graphql/schema/createFieldResolvers.js.map +1 -1
- package/graphql/schema/createManageResolvers.js +0 -26
- package/graphql/schema/createManageResolvers.js.map +1 -1
- package/graphql/schema/createManageSDL.d.ts +2 -0
- package/graphql/schema/createManageSDL.js +6 -16
- package/graphql/schema/createManageSDL.js.map +1 -1
- package/graphql/schema/createPreviewResolvers.js +0 -10
- package/graphql/schema/createPreviewResolvers.js.map +1 -1
- package/graphql/schema/createReadResolvers.js +5 -10
- package/graphql/schema/createReadResolvers.js.map +1 -1
- package/graphql/schema/createReadSDL.d.ts +2 -0
- package/graphql/schema/createReadSDL.js +6 -12
- package/graphql/schema/createReadSDL.js.map +1 -1
- package/graphql/schema/resolvers/commonFieldResolvers.js +0 -2
- package/graphql/schema/resolvers/commonFieldResolvers.js.map +1 -1
- package/graphql/schema/resolvers/manage/resolveCreate.js +0 -3
- package/graphql/schema/resolvers/manage/resolveCreate.js.map +1 -1
- package/graphql/schema/resolvers/manage/resolveCreateFrom.js +0 -3
- package/graphql/schema/resolvers/manage/resolveCreateFrom.js.map +1 -1
- package/graphql/schema/resolvers/manage/resolveDelete.js +0 -6
- package/graphql/schema/resolvers/manage/resolveDelete.js.map +1 -1
- package/graphql/schema/resolvers/manage/resolveGet.js +0 -16
- package/graphql/schema/resolvers/manage/resolveGet.js.map +1 -1
- package/graphql/schema/resolvers/manage/resolveGetByIds.js +0 -3
- package/graphql/schema/resolvers/manage/resolveGetByIds.js.map +1 -1
- package/graphql/schema/resolvers/manage/resolveGetRevisions.js +0 -3
- package/graphql/schema/resolvers/manage/resolveGetRevisions.js.map +1 -1
- package/graphql/schema/resolvers/manage/resolveList.js +0 -3
- package/graphql/schema/resolvers/manage/resolveList.js.map +1 -1
- package/graphql/schema/resolvers/manage/resolvePublish.js +0 -3
- package/graphql/schema/resolvers/manage/resolvePublish.js.map +1 -1
- package/graphql/schema/resolvers/manage/resolveRepublish.js +0 -3
- package/graphql/schema/resolvers/manage/resolveRepublish.js.map +1 -1
- package/graphql/schema/resolvers/manage/resolveUnpublish.js +0 -3
- package/graphql/schema/resolvers/manage/resolveUnpublish.js.map +1 -1
- package/graphql/schema/resolvers/manage/resolveUpdate.js +0 -3
- package/graphql/schema/resolvers/manage/resolveUpdate.js.map +1 -1
- package/graphql/schema/resolvers/preview/resolveGet.js +0 -8
- package/graphql/schema/resolvers/preview/resolveGet.js.map +1 -1
- package/graphql/schema/resolvers/preview/resolveList.js +0 -3
- package/graphql/schema/resolvers/preview/resolveList.js.map +1 -1
- package/graphql/schema/resolvers/read/resolveGet.js +0 -8
- package/graphql/schema/resolvers/read/resolveGet.js.map +1 -1
- package/graphql/schema/resolvers/read/resolveList.js +0 -3
- package/graphql/schema/resolvers/read/resolveList.js.map +1 -1
- package/graphql/schema/schemaPlugins.d.ts +8 -3
- package/graphql/schema/schemaPlugins.js +63 -65
- package/graphql/schema/schemaPlugins.js.map +1 -1
- package/graphql/system.js +69 -85
- package/graphql/system.js.map +1 -1
- package/graphqlFields/boolean.js +0 -12
- package/graphqlFields/boolean.js.map +1 -1
- package/graphqlFields/datetime.js +0 -17
- package/graphqlFields/datetime.js.map +1 -1
- package/graphqlFields/dynamicZone/dynamicZoneField.js +3 -29
- package/graphqlFields/dynamicZone/dynamicZoneField.js.map +1 -1
- package/graphqlFields/dynamicZone/dynamicZoneStorage.js +2 -18
- package/graphqlFields/dynamicZone/dynamicZoneStorage.js.map +1 -1
- package/graphqlFields/dynamicZone/index.js +0 -2
- package/graphqlFields/dynamicZone/index.js.map +1 -1
- package/graphqlFields/file.js +0 -8
- package/graphqlFields/file.js.map +1 -1
- package/graphqlFields/helpers.js +0 -10
- package/graphqlFields/helpers.js.map +1 -1
- package/graphqlFields/index.js +0 -12
- package/graphqlFields/index.js.map +1 -1
- package/graphqlFields/longText.js +0 -10
- package/graphqlFields/longText.js.map +1 -1
- package/graphqlFields/number.js +0 -12
- package/graphqlFields/number.js.map +1 -1
- package/graphqlFields/object.js +1 -37
- package/graphqlFields/object.js.map +1 -1
- package/graphqlFields/ref.js +23 -53
- package/graphqlFields/ref.js.map +1 -1
- package/graphqlFields/richText.js +0 -9
- package/graphqlFields/richText.js.map +1 -1
- package/graphqlFields/text.js +0 -11
- package/graphqlFields/text.js.map +1 -1
- package/index.d.ts +3 -3
- package/index.js +2 -27
- package/index.js.map +1 -1
- package/modelManager/DefaultCmsModelManager.js +0 -16
- package/modelManager/DefaultCmsModelManager.js.map +1 -1
- package/modelManager/index.js +0 -4
- package/modelManager/index.js.map +1 -1
- package/package.json +27 -28
- package/parameters/context.js +0 -4
- package/parameters/context.js.map +1 -1
- package/parameters/header.js +0 -11
- package/parameters/header.js.map +1 -1
- package/parameters/index.js +0 -8
- package/parameters/index.js.map +1 -1
- package/parameters/manual.js +1 -8
- package/parameters/manual.js.map +1 -1
- package/parameters/path.js +0 -11
- package/parameters/path.js.map +1 -1
- package/plugins/CmsGraphQLSchemaPlugin.d.ts +5 -0
- package/plugins/CmsGraphQLSchemaPlugin.js +12 -0
- package/plugins/CmsGraphQLSchemaPlugin.js.map +1 -0
- package/plugins/CmsGraphQLSchemaSorterPlugin.d.ts +20 -0
- package/plugins/CmsGraphQLSchemaSorterPlugin.js +28 -0
- package/plugins/CmsGraphQLSchemaSorterPlugin.js.map +1 -0
- package/plugins/CmsGroupPlugin.js +0 -8
- package/plugins/CmsGroupPlugin.js.map +1 -1
- package/plugins/CmsModelFieldConverterPlugin.js +0 -5
- package/plugins/CmsModelFieldConverterPlugin.js.map +1 -1
- package/plugins/CmsModelPlugin.js +2 -38
- package/plugins/CmsModelPlugin.js.map +1 -1
- package/plugins/CmsParametersPlugin.js +0 -7
- package/plugins/CmsParametersPlugin.js.map +1 -1
- package/plugins/StorageTransformPlugin.js +0 -9
- package/plugins/StorageTransformPlugin.js.map +1 -1
- package/plugins/index.d.ts +2 -0
- package/plugins/index.js +22 -10
- package/plugins/index.js.map +1 -1
- package/storage/default.js +0 -3
- package/storage/default.js.map +1 -1
- package/storage/object.js +0 -19
- package/storage/object.js.map +1 -1
- package/types.d.ts +56 -15
- package/types.js +22 -72
- package/types.js.map +1 -1
- package/upgrades/5.33.0/index.js +3 -26
- package/upgrades/5.33.0/index.js.map +1 -1
- package/upgrades/index.js +0 -3
- package/upgrades/index.js.map +1 -1
- package/utils/access.js +11 -25
- package/utils/access.js.map +1 -1
- package/utils/converters/Converter.js +0 -13
- package/utils/converters/Converter.js.map +1 -1
- package/utils/converters/ConverterCollection.js +9 -33
- package/utils/converters/ConverterCollection.js.map +1 -1
- package/utils/converters/valueKeyStorageConverter.js +0 -26
- package/utils/converters/valueKeyStorageConverter.js.map +1 -1
- package/utils/createTypeFromFields.js +4 -15
- package/utils/createTypeFromFields.js.map +1 -1
- package/utils/createTypeName.js +0 -9
- package/utils/createTypeName.js.map +1 -1
- package/utils/entryStorage.js +10 -26
- package/utils/entryStorage.js.map +1 -1
- package/utils/filterAsync.js +0 -5
- package/utils/filterAsync.js.map +1 -1
- package/utils/getBaseFieldType.js +0 -2
- package/utils/getBaseFieldType.js.map +1 -1
- package/utils/getEntryTitle.js +0 -9
- package/utils/getEntryTitle.js.map +1 -1
- package/utils/getSchemaFromFieldPlugins.d.ts +4 -7
- package/utils/getSchemaFromFieldPlugins.js +23 -19
- package/utils/getSchemaFromFieldPlugins.js.map +1 -1
- package/utils/ownership.js +0 -8
- package/utils/ownership.js.map +1 -1
- package/utils/permissions.js +8 -23
- package/utils/permissions.js.map +1 -1
- package/utils/pluralizedTypeName.js +0 -6
- package/utils/pluralizedTypeName.js.map +1 -1
- package/utils/renderFields.js +0 -9
- package/utils/renderFields.js.map +1 -1
- package/utils/renderGetFilterFields.js +0 -13
- package/utils/renderGetFilterFields.js.map +1 -1
- package/utils/renderInputFields.js +0 -9
- package/utils/renderInputFields.js.map +1 -1
- package/utils/renderListFilterFields.js +1 -10
- package/utils/renderListFilterFields.js.map +1 -1
- package/utils/renderSortEnum.d.ts +7 -4
- package/utils/renderSortEnum.js +19 -11
- package/utils/renderSortEnum.js.map +1 -1
- package/utils/toSlug.js +0 -4
- package/utils/toSlug.js.map +1 -1
- package/validators/dateGte.js +0 -7
- package/validators/dateGte.js.map +1 -1
- package/validators/dateLte.js +0 -7
- package/validators/dateLte.js.map +1 -1
- package/validators/dynamicZone.js +0 -4
- package/validators/dynamicZone.js.map +1 -1
- package/validators/gte.js +0 -8
- package/validators/gte.js.map +1 -1
- package/validators/in.js +0 -8
- package/validators/in.js.map +1 -1
- package/validators/index.js +0 -16
- package/validators/index.js.map +1 -1
- package/validators/lte.js +0 -8
- package/validators/lte.js.map +1 -1
- package/validators/maxLength.js +0 -8
- package/validators/maxLength.js.map +1 -1
- package/validators/minLength.js +0 -8
- package/validators/minLength.js.map +1 -1
- package/validators/pattern.js +0 -9
- package/validators/pattern.js.map +1 -1
- package/validators/patternPlugins/email.js +0 -2
- package/validators/patternPlugins/email.js.map +1 -1
- package/validators/patternPlugins/index.js +0 -8
- package/validators/patternPlugins/index.js.map +1 -1
- package/validators/patternPlugins/lowerCase.js +0 -2
- package/validators/patternPlugins/lowerCase.js.map +1 -1
- package/validators/patternPlugins/lowerCaseSpace.js +0 -2
- package/validators/patternPlugins/lowerCaseSpace.js.map +1 -1
- package/validators/patternPlugins/upperCase.js +0 -2
- package/validators/patternPlugins/upperCase.js.map +1 -1
- package/validators/patternPlugins/upperCaseSpace.js +0 -2
- package/validators/patternPlugins/upperCaseSpace.js.map +1 -1
- package/validators/patternPlugins/url.js +0 -2
- package/validators/patternPlugins/url.js.map +1 -1
- package/validators/required.js +0 -5
- package/validators/required.js.map +1 -1
- package/validators/timeGte.js +0 -8
- package/validators/timeGte.js.map +1 -1
- package/validators/timeLte.js +0 -8
- package/validators/timeLte.js.map +1 -1
- package/validators/unique.js +0 -7
- package/validators/unique.js.map +1 -1
- package/crud/contentModel/createFieldModels.d.ts +0 -2
- package/crud/contentModel/createFieldModels.js +0 -26
- package/crud/contentModel/createFieldModels.js.map +0 -1
- package/crud/contentModel/fieldIdValidation.d.ts +0 -1
- package/crud/contentModel/fieldIdValidation.js +0 -25
- package/crud/contentModel/fieldIdValidation.js.map +0 -1
- package/crud/contentModel/idValidation.d.ts +0 -1
- package/crud/contentModel/idValidation.js +0 -22
- package/crud/contentModel/idValidation.js.map +0 -1
- package/crud/contentModel/models.d.ts +0 -4
- package/crud/contentModel/models.js +0 -192
- package/crud/contentModel/models.js.map +0 -1
- package/crud/index.d.ts +0 -6
- package/crud/index.js +0 -85
- package/crud/index.js.map +0 -1
- package/utils/filterModelFields.d.ts +0 -16
- package/utils/filterModelFields.js +0 -77
- package/utils/filterModelFields.js.map +0 -1
|
@@ -1,27 +1,22 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
|
|
3
3
|
var _interopRequireDefault = require("@babel/runtime/helpers/interopRequireDefault").default;
|
|
4
|
-
|
|
5
4
|
Object.defineProperty(exports, "__esModule", {
|
|
6
5
|
value: true
|
|
7
6
|
});
|
|
8
7
|
exports.validateModelFields = void 0;
|
|
9
|
-
|
|
10
8
|
var _objectSpread2 = _interopRequireDefault(require("@babel/runtime/helpers/objectSpread2"));
|
|
11
|
-
|
|
12
9
|
var _error = _interopRequireDefault(require("@webiny/error"));
|
|
13
|
-
|
|
14
10
|
var _createManageSDL = require("../../graphql/schema/createManageSDL");
|
|
15
|
-
|
|
16
11
|
var _graphqlTag = _interopRequireDefault(require("graphql-tag"));
|
|
17
|
-
|
|
18
12
|
var _createFieldStorageId = require("./createFieldStorageId");
|
|
19
|
-
|
|
20
13
|
var _getBaseFieldType = require("../../utils/getBaseFieldType");
|
|
21
|
-
|
|
14
|
+
var _plugins = require("../../plugins");
|
|
15
|
+
var _buildSchemaPlugins = require("../../graphql/buildSchemaPlugins");
|
|
16
|
+
var _createExecutableSchema = require("../../graphql/createExecutableSchema");
|
|
17
|
+
var _handlerGraphql = require("@webiny/handler-graphql");
|
|
22
18
|
const defaultTitleFieldId = "id";
|
|
23
19
|
const allowedTitleFieldTypes = ["text", "number"];
|
|
24
|
-
|
|
25
20
|
const getContentModelTitleFieldId = (fields, titleFieldId) => {
|
|
26
21
|
/**
|
|
27
22
|
* If there are no fields defined, we will return the default field
|
|
@@ -34,8 +29,6 @@ const getContentModelTitleFieldId = (fields, titleFieldId) => {
|
|
|
34
29
|
* we will take first text field that has no multiple values enabled
|
|
35
30
|
* or if initial titleFieldId is the default one also try to find first available text field
|
|
36
31
|
*/
|
|
37
|
-
|
|
38
|
-
|
|
39
32
|
if (!titleFieldId || titleFieldId === defaultTitleFieldId) {
|
|
40
33
|
const titleField = fields.find(field => {
|
|
41
34
|
return (0, _getBaseFieldType.getBaseFieldType)(field) === "text" && !field.multipleValues;
|
|
@@ -47,17 +40,13 @@ const getContentModelTitleFieldId = (fields, titleFieldId) => {
|
|
|
47
40
|
* for correct type
|
|
48
41
|
* and that it is not multiple values field
|
|
49
42
|
*/
|
|
50
|
-
|
|
51
|
-
|
|
52
43
|
const target = fields.find(f => f.fieldId === titleFieldId);
|
|
53
|
-
|
|
54
44
|
if (!target) {
|
|
55
45
|
throw new _error.default(`Field selected for the title field does not exist in the model.`, "VALIDATION_ERROR", {
|
|
56
46
|
fieldId: titleFieldId,
|
|
57
47
|
fields
|
|
58
48
|
});
|
|
59
49
|
}
|
|
60
|
-
|
|
61
50
|
if (allowedTitleFieldTypes.includes(target.type) === false) {
|
|
62
51
|
throw new _error.default(`Only ${allowedTitleFieldTypes.join(", ")} and id fields can be used as an entry title.`, "ENTRY_TITLE_FIELD_TYPE", {
|
|
63
52
|
storageId: target.storageId,
|
|
@@ -65,7 +54,6 @@ const getContentModelTitleFieldId = (fields, titleFieldId) => {
|
|
|
65
54
|
type: target.type
|
|
66
55
|
});
|
|
67
56
|
}
|
|
68
|
-
|
|
69
57
|
if (target.multipleValues) {
|
|
70
58
|
throw new _error.default(`Fields that accept multiple values cannot be used as the entry title.`, "ENTRY_TITLE_FIELD_TYPE", {
|
|
71
59
|
storageId: target.storageId,
|
|
@@ -73,18 +61,15 @@ const getContentModelTitleFieldId = (fields, titleFieldId) => {
|
|
|
73
61
|
type: target.type
|
|
74
62
|
});
|
|
75
63
|
}
|
|
76
|
-
|
|
77
64
|
return target.fieldId;
|
|
78
65
|
};
|
|
79
|
-
|
|
80
66
|
const extractInvalidField = (model, err) => {
|
|
81
67
|
var _err$source;
|
|
82
|
-
|
|
83
68
|
const sdl = ((_err$source = err.source) === null || _err$source === void 0 ? void 0 : _err$source.body) || "";
|
|
69
|
+
|
|
84
70
|
/**
|
|
85
71
|
* Find the invalid type
|
|
86
72
|
*/
|
|
87
|
-
|
|
88
73
|
const {
|
|
89
74
|
line: lineNumber
|
|
90
75
|
} = err.locations ? err.locations[0] : {
|
|
@@ -93,33 +78,25 @@ const extractInvalidField = (model, err) => {
|
|
|
93
78
|
const sdlLines = sdl.split("\n");
|
|
94
79
|
let sdlLine;
|
|
95
80
|
let gqlType;
|
|
96
|
-
|
|
97
81
|
for (let i = lineNumber; i > 0; i--) {
|
|
98
82
|
if (sdlLine && sdlLine.includes("type ")) {
|
|
99
83
|
gqlType = sdlLine.match(/type\s+(.*?)\s+{/);
|
|
100
84
|
break;
|
|
101
85
|
}
|
|
102
|
-
|
|
103
86
|
sdlLine = sdlLines[i];
|
|
104
87
|
}
|
|
105
|
-
|
|
106
88
|
let invalidField = undefined;
|
|
107
|
-
|
|
108
89
|
if (Array.isArray(gqlType)) {
|
|
109
90
|
const fieldRegex = new RegExp(`([^\\s+].*?):\\s+\\[?${gqlType[1]}!?\\]?`);
|
|
110
91
|
const matched = sdl.match(fieldRegex);
|
|
111
|
-
|
|
112
92
|
if (matched) {
|
|
113
93
|
invalidField = matched[1];
|
|
114
94
|
}
|
|
115
95
|
}
|
|
116
|
-
|
|
117
96
|
let message = `See more details in the browser console.`;
|
|
118
|
-
|
|
119
97
|
if (invalidField) {
|
|
120
98
|
message = `Please review the definition of "${invalidField}" field.`;
|
|
121
99
|
}
|
|
122
|
-
|
|
123
100
|
return {
|
|
124
101
|
data: {
|
|
125
102
|
modelId: model.modelId,
|
|
@@ -130,16 +107,14 @@ const extractInvalidField = (model, err) => {
|
|
|
130
107
|
message: [`Model "${model.modelId}" was not saved!`, message].join("\n")
|
|
131
108
|
};
|
|
132
109
|
};
|
|
133
|
-
|
|
134
110
|
const createValidateChildFields = plugins => {
|
|
135
111
|
return ({
|
|
136
112
|
fields,
|
|
137
113
|
originalFields
|
|
138
114
|
}) => {
|
|
139
|
-
if (fields.length === 0) {
|
|
115
|
+
if (fields.length === 0 && originalFields.length === 0) {
|
|
140
116
|
return;
|
|
141
117
|
}
|
|
142
|
-
|
|
143
118
|
validateFields({
|
|
144
119
|
fields,
|
|
145
120
|
originalFields,
|
|
@@ -148,7 +123,6 @@ const createValidateChildFields = plugins => {
|
|
|
148
123
|
});
|
|
149
124
|
};
|
|
150
125
|
};
|
|
151
|
-
|
|
152
126
|
const validateFields = params => {
|
|
153
127
|
const {
|
|
154
128
|
plugins,
|
|
@@ -156,23 +130,27 @@ const validateFields = params => {
|
|
|
156
130
|
originalFields,
|
|
157
131
|
lockedFields
|
|
158
132
|
} = params;
|
|
133
|
+
const idList = [];
|
|
159
134
|
const fieldIdList = [];
|
|
160
135
|
const storageIdList = [];
|
|
161
|
-
const validateChildFields = createValidateChildFields(plugins);
|
|
162
|
-
|
|
163
136
|
for (const field of fields) {
|
|
164
137
|
const baseType = (0, _getBaseFieldType.getBaseFieldType)(field);
|
|
165
138
|
const plugin = plugins.find(plugin => plugin.fieldType === baseType);
|
|
166
|
-
|
|
167
139
|
if (!plugin) {
|
|
168
140
|
throw new Error(`Cannot update content model because of the unknown "${baseType}" field.`);
|
|
169
141
|
}
|
|
170
|
-
|
|
142
|
+
/**
|
|
143
|
+
* Check the field's id against existing ones.
|
|
144
|
+
* There cannot be two fields with the same id.
|
|
145
|
+
*/
|
|
146
|
+
if (idList.includes(field.id)) {
|
|
147
|
+
throw new _error.default(`Cannot update content model because field "${field.storageId || field.fieldId}" has id "${field.id}", which is already used.`);
|
|
148
|
+
}
|
|
149
|
+
idList.push(field.id);
|
|
171
150
|
const originalField = originalFields.find(f => f.id === field.id);
|
|
172
151
|
/**
|
|
173
152
|
* Field MUST have an fieldId defined.
|
|
174
153
|
*/
|
|
175
|
-
|
|
176
154
|
if (!field.fieldId) {
|
|
177
155
|
throw new _error.default(`Field does not have an "fieldId" defined.`, "MISSING_FIELD_ID", {
|
|
178
156
|
field
|
|
@@ -191,12 +169,9 @@ const validateFields = params => {
|
|
|
191
169
|
* https://discuss.elastic.co/t/special-characters-in-field-names/10658/3
|
|
192
170
|
* https://discuss.elastic.co/t/illegal-characters-in-elasticsearch-field-names/17196/2
|
|
193
171
|
*/
|
|
194
|
-
|
|
195
|
-
|
|
196
172
|
const isLocked = lockedFields.some(lockedField => {
|
|
197
|
-
return lockedField.fieldId === field.storageId;
|
|
173
|
+
return lockedField.fieldId === field.storageId || lockedField.fieldId === field.fieldId;
|
|
198
174
|
});
|
|
199
|
-
|
|
200
175
|
if (!field.storageId) {
|
|
201
176
|
/**
|
|
202
177
|
* In case field is locked, we must set the storageId to the fieldId value.
|
|
@@ -225,32 +200,26 @@ const validateFields = params => {
|
|
|
225
200
|
* Check the field's fieldId against existing ones.
|
|
226
201
|
* There cannot be two fields with the same fieldId - outside world identifier.
|
|
227
202
|
*/
|
|
228
|
-
|
|
229
|
-
|
|
230
203
|
if (fieldIdList.includes(field.fieldId)) {
|
|
231
204
|
throw new _error.default(`Cannot update content model because field "${field.storageId}" has fieldId "${field.fieldId}", which is already used.`);
|
|
232
205
|
}
|
|
233
|
-
|
|
234
206
|
fieldIdList.push(field.fieldId);
|
|
235
207
|
/**
|
|
236
208
|
* Check the field's storageId against the existing ones.
|
|
237
209
|
* There cannot be two fields with the same storageId.
|
|
238
210
|
*/
|
|
239
|
-
|
|
240
211
|
if (storageIdList.includes(field.storageId)) {
|
|
241
212
|
throw new _error.default(`Cannot update content model because field "${field.label}" has storageId "${field.storageId}", which is already used.`);
|
|
242
213
|
}
|
|
243
|
-
|
|
244
214
|
storageIdList.push(field.storageId);
|
|
245
215
|
/**
|
|
246
216
|
* There might be some plugins which allow child fields.
|
|
247
217
|
* We use this method to validate them as well.
|
|
248
218
|
*/
|
|
249
|
-
|
|
250
219
|
if (!plugin.validateChildFields) {
|
|
251
220
|
continue;
|
|
252
221
|
}
|
|
253
|
-
|
|
222
|
+
const validateChildFields = createValidateChildFields(plugins);
|
|
254
223
|
plugin.validateChildFields({
|
|
255
224
|
field,
|
|
256
225
|
originalField,
|
|
@@ -258,29 +227,55 @@ const validateFields = params => {
|
|
|
258
227
|
});
|
|
259
228
|
}
|
|
260
229
|
};
|
|
261
|
-
|
|
262
|
-
const
|
|
230
|
+
const createGraphQLSchema = async params => {
|
|
231
|
+
const {
|
|
232
|
+
context,
|
|
233
|
+
model
|
|
234
|
+
} = params;
|
|
235
|
+
const modelPlugins = await (0, _buildSchemaPlugins.buildSchemaPlugins)({
|
|
236
|
+
context,
|
|
237
|
+
models: [model]
|
|
238
|
+
});
|
|
239
|
+
const plugins = context.plugins.byType(_handlerGraphql.GraphQLSchemaPlugin.type);
|
|
240
|
+
plugins.push(...modelPlugins);
|
|
241
|
+
return (0, _createExecutableSchema.createExecutableSchema)({
|
|
242
|
+
plugins
|
|
243
|
+
});
|
|
244
|
+
};
|
|
245
|
+
const extractErrorObject = error => {
|
|
246
|
+
return ["message", "code", "data", "stack"].reduce((output, key) => {
|
|
247
|
+
if (!error[key]) {
|
|
248
|
+
return output;
|
|
249
|
+
}
|
|
250
|
+
output[key] = error[key];
|
|
251
|
+
return output;
|
|
252
|
+
}, {});
|
|
253
|
+
};
|
|
254
|
+
const validateModelFields = async params => {
|
|
263
255
|
const {
|
|
264
256
|
model,
|
|
265
257
|
original,
|
|
266
|
-
|
|
258
|
+
context
|
|
267
259
|
} = params;
|
|
268
260
|
const {
|
|
269
261
|
titleFieldId
|
|
270
262
|
} = model;
|
|
263
|
+
const {
|
|
264
|
+
plugins
|
|
265
|
+
} = context;
|
|
266
|
+
|
|
271
267
|
/**
|
|
272
268
|
* There should be fields/locked fields in either model or data to be updated.
|
|
273
269
|
*/
|
|
274
|
-
|
|
275
270
|
const {
|
|
276
271
|
fields = [],
|
|
277
272
|
lockedFields = []
|
|
278
273
|
} = model;
|
|
274
|
+
|
|
279
275
|
/**
|
|
280
276
|
* Let's inspect the fields of the received content model. We prevent saving of a content model if it
|
|
281
277
|
* contains a field for which a "cms-model-field-to-graphql" plugin does not exist on the backend.
|
|
282
278
|
*/
|
|
283
|
-
|
|
284
279
|
const fieldTypePlugins = plugins.byType("cms-model-field-to-graphql");
|
|
285
280
|
validateFields({
|
|
286
281
|
fields,
|
|
@@ -288,8 +283,8 @@ const validateModelFields = params => {
|
|
|
288
283
|
lockedFields,
|
|
289
284
|
plugins: fieldTypePlugins
|
|
290
285
|
});
|
|
291
|
-
|
|
292
286
|
if (fields.length) {
|
|
287
|
+
const sorterPlugins = plugins.byType(_plugins.CmsGraphQLSchemaSorterPlugin.type);
|
|
293
288
|
/**
|
|
294
289
|
* Make sure that this model can be safely converted to a GraphQL SDL
|
|
295
290
|
*/
|
|
@@ -297,50 +292,57 @@ const validateModelFields = params => {
|
|
|
297
292
|
model,
|
|
298
293
|
fieldTypePlugins: fieldTypePlugins.reduce((acc, pl) => (0, _objectSpread2.default)((0, _objectSpread2.default)({}, acc), {}, {
|
|
299
294
|
[pl.fieldType]: pl
|
|
300
|
-
}), {})
|
|
295
|
+
}), {}),
|
|
296
|
+
sorterPlugins
|
|
301
297
|
});
|
|
302
|
-
|
|
303
298
|
try {
|
|
304
299
|
(0, _graphqlTag.default)(schema);
|
|
305
300
|
} catch (err) {
|
|
306
301
|
throw new _error.default(extractInvalidField(model, err));
|
|
307
302
|
}
|
|
303
|
+
/**
|
|
304
|
+
*
|
|
305
|
+
*/
|
|
306
|
+
try {
|
|
307
|
+
await createGraphQLSchema({
|
|
308
|
+
context,
|
|
309
|
+
model
|
|
310
|
+
});
|
|
311
|
+
} catch (err) {
|
|
312
|
+
throw new _error.default({
|
|
313
|
+
message: "Cannot generate GraphQL schema when testing with the given model. Please check the response for more details.",
|
|
314
|
+
code: "GRAPHQL_SCHEMA_ERROR",
|
|
315
|
+
data: {
|
|
316
|
+
modelId: model.modelId,
|
|
317
|
+
error: extractErrorObject(err)
|
|
318
|
+
}
|
|
319
|
+
});
|
|
320
|
+
}
|
|
308
321
|
}
|
|
309
|
-
|
|
310
322
|
model.titleFieldId = getContentModelTitleFieldId(fields, titleFieldId);
|
|
311
323
|
const cmsLockedFieldPlugins = plugins.byType("cms-model-locked-field");
|
|
324
|
+
|
|
312
325
|
/**
|
|
313
326
|
* We must not allow removal or changes in fields that are already in use in content entries.
|
|
314
327
|
* Locked fields still have fieldId (should be storageId) because of the old existing locked fields in the models.
|
|
315
328
|
*/
|
|
316
|
-
|
|
317
329
|
for (const lockedField of lockedFields) {
|
|
318
330
|
const existingField = fields.find(item => item.storageId === lockedField.fieldId);
|
|
331
|
+
|
|
319
332
|
/**
|
|
320
333
|
* Starting with 5.33.0 fields can be deleted.
|
|
321
334
|
* Our UI gives a warning upon locked field deletion, but if user is managing fields through API directly - we cannot do anything.
|
|
322
335
|
*/
|
|
323
|
-
|
|
324
336
|
if (!existingField) {
|
|
325
|
-
continue;
|
|
326
|
-
// `Cannot remove the field "${lockedField.fieldId}" because it's already in use in created content.`,
|
|
327
|
-
// "ENTRY_FIELD_USED",
|
|
328
|
-
// {
|
|
329
|
-
// lockedField,
|
|
330
|
-
// fields
|
|
331
|
-
// }
|
|
332
|
-
// );
|
|
337
|
+
continue;
|
|
333
338
|
}
|
|
334
|
-
|
|
335
339
|
if (lockedField.multipleValues !== existingField.multipleValues) {
|
|
336
340
|
throw new _error.default(`Cannot change "multipleValues" for the "${lockedField.fieldId}" field because it's already in use in created content.`, "ENTRY_FIELD_USED", {
|
|
337
341
|
reason: `"multipleValues" changed`,
|
|
338
342
|
field: existingField
|
|
339
343
|
});
|
|
340
344
|
}
|
|
341
|
-
|
|
342
345
|
const fieldType = (0, _getBaseFieldType.getBaseFieldType)(existingField);
|
|
343
|
-
|
|
344
346
|
if (lockedField.type !== fieldType) {
|
|
345
347
|
throw new _error.default(`Cannot change field type for the "${lockedField.fieldId}" field because it's already in use in created content.`, "ENTRY_FIELD_USED", {
|
|
346
348
|
reason: `"type" changed`,
|
|
@@ -348,18 +350,15 @@ const validateModelFields = params => {
|
|
|
348
350
|
existingFieldType: fieldType
|
|
349
351
|
});
|
|
350
352
|
}
|
|
353
|
+
|
|
351
354
|
/**
|
|
352
355
|
* Check `lockedField` invariant for specific field
|
|
353
356
|
*/
|
|
354
|
-
|
|
355
|
-
|
|
356
357
|
const lockedFieldsByType = cmsLockedFieldPlugins.filter(pl => pl.fieldType === (0, _getBaseFieldType.getBaseFieldType)(lockedField));
|
|
357
|
-
|
|
358
358
|
for (const plugin of lockedFieldsByType) {
|
|
359
359
|
if (typeof plugin.checkLockedField !== "function") {
|
|
360
360
|
continue;
|
|
361
361
|
}
|
|
362
|
-
|
|
363
362
|
plugin.checkLockedField({
|
|
364
363
|
lockedField,
|
|
365
364
|
field: existingField
|
|
@@ -367,5 +366,4 @@ const validateModelFields = params => {
|
|
|
367
366
|
}
|
|
368
367
|
}
|
|
369
368
|
};
|
|
370
|
-
|
|
371
369
|
exports.validateModelFields = validateModelFields;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"names":["defaultTitleFieldId","allowedTitleFieldTypes","getContentModelTitleFieldId","fields","titleFieldId","length","titleField","find","field","getBaseFieldType","multipleValues","fieldId","target","f","WebinyError","includes","type","join","storageId","extractInvalidField","model","err","sdl","source","body","line","lineNumber","locations","sdlLines","split","sdlLine","gqlType","i","match","invalidField","undefined","Array","isArray","fieldRegex","RegExp","matched","message","data","modelId","code","createValidateChildFields","plugins","originalFields","validateFields","lockedFields","params","fieldIdList","storageIdList","validateChildFields","baseType","plugin","fieldType","Error","originalField","id","isLocked","some","lockedField","createFieldStorageId","push","label","validate","validateModelFields","original","fieldTypePlugins","byType","schema","createManageSDL","reduce","acc","pl","gql","cmsLockedFieldPlugins","existingField","item","reason","lockedFieldType","existingFieldType","lockedFieldsByType","filter","checkLockedField"],"sources":["validateModelFields.ts"],"sourcesContent":["import {\n CmsModel,\n CmsModelField,\n CmsModelFieldToGraphQLPlugin,\n CmsModelFieldToGraphQLPluginValidateChildFieldsValidate,\n CmsModelLockedFieldPlugin,\n LockedField\n} from \"~/types\";\nimport WebinyError from \"@webiny/error\";\nimport { createManageSDL } from \"~/graphql/schema/createManageSDL\";\nimport gql from \"graphql-tag\";\nimport { PluginsContainer } from \"@webiny/plugins\";\nimport { createFieldStorageId } from \"./createFieldStorageId\";\nimport { GraphQLError } from \"graphql\";\nimport { getBaseFieldType } from \"~/utils/getBaseFieldType\";\n\nconst defaultTitleFieldId = \"id\";\n\nconst allowedTitleFieldTypes = [\"text\", \"number\"];\n\nconst getContentModelTitleFieldId = (fields: CmsModelField[], titleFieldId?: string): string => {\n /**\n * If there are no fields defined, we will return the default field\n */\n if (fields.length === 0) {\n return defaultTitleFieldId;\n }\n /**\n * if there is no title field defined either in input data or existing content model data\n * we will take first text field that has no multiple values enabled\n * or if initial titleFieldId is the default one also try to find first available text field\n */\n if (!titleFieldId || titleFieldId === defaultTitleFieldId) {\n const titleField = fields.find(field => {\n return getBaseFieldType(field) === \"text\" && !field.multipleValues;\n });\n return titleField?.fieldId || defaultTitleFieldId;\n }\n /**\n * check existing titleFieldId for existence in the model\n * for correct type\n * and that it is not multiple values field\n */\n const target = fields.find(f => f.fieldId === titleFieldId);\n if (!target) {\n throw new WebinyError(\n `Field selected for the title field does not exist in the model.`,\n \"VALIDATION_ERROR\",\n {\n fieldId: titleFieldId,\n fields\n }\n );\n }\n\n if (allowedTitleFieldTypes.includes(target.type) === false) {\n throw new WebinyError(\n `Only ${allowedTitleFieldTypes.join(\n \", \"\n )} and id fields can be used as an entry title.`,\n \"ENTRY_TITLE_FIELD_TYPE\",\n {\n storageId: target.storageId,\n fieldId: target.fieldId,\n type: target.type\n }\n );\n }\n\n if (target.multipleValues) {\n throw new WebinyError(\n `Fields that accept multiple values cannot be used as the entry title.`,\n \"ENTRY_TITLE_FIELD_TYPE\",\n {\n storageId: target.storageId,\n fieldId: target.fieldId,\n type: target.type\n }\n );\n }\n\n return target.fieldId;\n};\n\nconst extractInvalidField = (model: CmsModel, err: GraphQLError) => {\n const sdl = err.source?.body || \"\";\n\n /**\n * Find the invalid type\n */\n const { line: lineNumber } = err.locations\n ? err.locations[0]\n : {\n line: 0\n };\n const sdlLines = sdl.split(\"\\n\");\n let sdlLine;\n let gqlType;\n for (let i = lineNumber; i > 0; i--) {\n if (sdlLine && sdlLine.includes(\"type \")) {\n gqlType = sdlLine.match(/type\\s+(.*?)\\s+{/);\n break;\n }\n\n sdlLine = sdlLines[i];\n }\n\n let invalidField: string | undefined = undefined;\n if (Array.isArray(gqlType)) {\n const fieldRegex = new RegExp(`([^\\\\s+].*?):\\\\s+\\\\[?${gqlType[1]}!?\\\\]?`);\n\n const matched = sdl.match(fieldRegex);\n if (matched) {\n invalidField = matched[1];\n }\n }\n\n let message = `See more details in the browser console.`;\n if (invalidField) {\n message = `Please review the definition of \"${invalidField}\" field.`;\n }\n\n return {\n data: {\n modelId: model.modelId,\n sdl,\n invalidField\n },\n code: \"INVALID_MODEL_DEFINITION\",\n message: [`Model \"${model.modelId}\" was not saved!`, message].join(\"\\n\")\n };\n};\n\nconst createValidateChildFields = (\n plugins: CmsModelFieldToGraphQLPlugin[]\n): CmsModelFieldToGraphQLPluginValidateChildFieldsValidate => {\n return ({ fields, originalFields }) => {\n if (fields.length === 0) {\n return;\n }\n validateFields({\n fields,\n originalFields,\n plugins,\n lockedFields: []\n });\n };\n};\n\ninterface ValidateFieldsParams {\n plugins: CmsModelFieldToGraphQLPlugin[];\n fields: CmsModelField[];\n originalFields: CmsModelField[];\n lockedFields: LockedField[];\n}\nconst validateFields = (params: ValidateFieldsParams) => {\n const { plugins, fields, originalFields, lockedFields } = params;\n\n const fieldIdList: string[] = [];\n\n const storageIdList: string[] = [];\n\n const validateChildFields = createValidateChildFields(plugins);\n\n for (const field of fields) {\n const baseType = getBaseFieldType(field);\n const plugin = plugins.find(plugin => plugin.fieldType === baseType);\n\n if (!plugin) {\n throw new Error(\n `Cannot update content model because of the unknown \"${baseType}\" field.`\n );\n }\n const originalField = originalFields.find(f => f.id === field.id);\n /**\n * Field MUST have an fieldId defined.\n */\n if (!field.fieldId) {\n throw new WebinyError(`Field does not have an \"fieldId\" defined.`, \"MISSING_FIELD_ID\", {\n field\n });\n }\n /**\n * If storageId does not match a certain pattern, add that pattern, but only if field is not locked (used) already.\n * This is to avoid errors in the already installed systems.\n *\n * Why are we using the @?\n *\n * It is not part of special characters for the query syntax in the Lucene.\n *\n * Relevant links:\n * https://lucene.apache.org/core/3_4_0/queryparsersyntax.html\n * https://discuss.elastic.co/t/special-characters-in-field-names/10658/3\n * https://discuss.elastic.co/t/illegal-characters-in-elasticsearch-field-names/17196/2\n */\n const isLocked = lockedFields.some(lockedField => {\n return lockedField.fieldId === field.storageId;\n });\n if (!field.storageId) {\n /**\n * In case field is locked, we must set the storageId to the fieldId value.\n * This should not happen, because we upgrade all the fields in 5.33.0, but let's have a check just in case of some upgrade miss.\n */\n //\n if (isLocked) {\n field.storageId = field.fieldId;\n }\n /**\n * When having original field, just set the storageId to value from the originalField\n */\n //\n else if (originalField) {\n field.storageId = originalField.storageId;\n }\n /**\n * The last case is when no original field and not locked - so this is a completely new field.\n */\n //\n else {\n field.storageId = createFieldStorageId(field);\n }\n }\n /**\n * Check the field's fieldId against existing ones.\n * There cannot be two fields with the same fieldId - outside world identifier.\n */\n if (fieldIdList.includes(field.fieldId)) {\n throw new WebinyError(\n `Cannot update content model because field \"${field.storageId}\" has fieldId \"${field.fieldId}\", which is already used.`\n );\n }\n fieldIdList.push(field.fieldId);\n /**\n * Check the field's storageId against the existing ones.\n * There cannot be two fields with the same storageId.\n */\n if (storageIdList.includes(field.storageId)) {\n throw new WebinyError(\n `Cannot update content model because field \"${field.label}\" has storageId \"${field.storageId}\", which is already used.`\n );\n }\n storageIdList.push(field.storageId);\n /**\n * There might be some plugins which allow child fields.\n * We use this method to validate them as well.\n */\n if (!plugin.validateChildFields) {\n continue;\n }\n plugin.validateChildFields({\n field,\n originalField,\n validate: validateChildFields\n });\n }\n};\n\ninterface ValidateModelFieldsParams {\n model: CmsModel;\n original?: CmsModel;\n plugins: PluginsContainer;\n}\nexport const validateModelFields = (params: ValidateModelFieldsParams) => {\n const { model, original, plugins } = params;\n const { titleFieldId } = model;\n\n /**\n * There should be fields/locked fields in either model or data to be updated.\n */\n const { fields = [], lockedFields = [] } = model;\n\n /**\n * Let's inspect the fields of the received content model. We prevent saving of a content model if it\n * contains a field for which a \"cms-model-field-to-graphql\" plugin does not exist on the backend.\n */\n const fieldTypePlugins = plugins.byType<CmsModelFieldToGraphQLPlugin>(\n \"cms-model-field-to-graphql\"\n );\n\n validateFields({\n fields,\n originalFields: original?.fields || [],\n lockedFields,\n plugins: fieldTypePlugins\n });\n\n if (fields.length) {\n /**\n * Make sure that this model can be safely converted to a GraphQL SDL\n */\n const schema = createManageSDL({\n model,\n fieldTypePlugins: fieldTypePlugins.reduce(\n (acc, pl) => ({ ...acc, [pl.fieldType]: pl }),\n {}\n )\n });\n\n try {\n gql(schema);\n } catch (err) {\n throw new WebinyError(extractInvalidField(model, err));\n }\n }\n\n model.titleFieldId = getContentModelTitleFieldId(fields, titleFieldId);\n\n const cmsLockedFieldPlugins =\n plugins.byType<CmsModelLockedFieldPlugin>(\"cms-model-locked-field\");\n\n /**\n * We must not allow removal or changes in fields that are already in use in content entries.\n * Locked fields still have fieldId (should be storageId) because of the old existing locked fields in the models.\n */\n for (const lockedField of lockedFields) {\n const existingField = fields.find(item => item.storageId === lockedField.fieldId);\n\n /**\n * Starting with 5.33.0 fields can be deleted.\n * Our UI gives a warning upon locked field deletion, but if user is managing fields through API directly - we cannot do anything.\n */\n if (!existingField) {\n continue;\n // throw new WebinyError(\n // `Cannot remove the field \"${lockedField.fieldId}\" because it's already in use in created content.`,\n // \"ENTRY_FIELD_USED\",\n // {\n // lockedField,\n // fields\n // }\n // );\n }\n\n if (lockedField.multipleValues !== existingField.multipleValues) {\n throw new WebinyError(\n `Cannot change \"multipleValues\" for the \"${lockedField.fieldId}\" field because it's already in use in created content.`,\n \"ENTRY_FIELD_USED\",\n {\n reason: `\"multipleValues\" changed`,\n field: existingField\n }\n );\n }\n\n const fieldType = getBaseFieldType(existingField);\n if (lockedField.type !== fieldType) {\n throw new WebinyError(\n `Cannot change field type for the \"${lockedField.fieldId}\" field because it's already in use in created content.`,\n \"ENTRY_FIELD_USED\",\n {\n reason: `\"type\" changed`,\n lockedFieldType: lockedField.type,\n existingFieldType: fieldType\n }\n );\n }\n\n /**\n * Check `lockedField` invariant for specific field\n */\n const lockedFieldsByType = cmsLockedFieldPlugins.filter(\n pl => pl.fieldType === getBaseFieldType(lockedField)\n );\n for (const plugin of lockedFieldsByType) {\n if (typeof plugin.checkLockedField !== \"function\") {\n continue;\n }\n plugin.checkLockedField({\n lockedField,\n field: existingField\n });\n }\n }\n};\n"],"mappings":"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"}
|
|
1
|
+
{"version":3,"names":["defaultTitleFieldId","allowedTitleFieldTypes","getContentModelTitleFieldId","fields","titleFieldId","length","titleField","find","field","getBaseFieldType","multipleValues","fieldId","target","f","WebinyError","includes","type","join","storageId","extractInvalidField","model","err","sdl","source","body","line","lineNumber","locations","sdlLines","split","sdlLine","gqlType","i","match","invalidField","undefined","Array","isArray","fieldRegex","RegExp","matched","message","data","modelId","code","createValidateChildFields","plugins","originalFields","validateFields","lockedFields","params","idList","fieldIdList","storageIdList","baseType","plugin","fieldType","Error","id","push","originalField","isLocked","some","lockedField","createFieldStorageId","label","validateChildFields","validate","createGraphQLSchema","context","modelPlugins","buildSchemaPlugins","models","byType","GraphQLSchemaPlugin","createExecutableSchema","extractErrorObject","error","reduce","output","key","validateModelFields","original","fieldTypePlugins","sorterPlugins","CmsGraphQLSchemaSorterPlugin","schema","createManageSDL","acc","pl","gql","cmsLockedFieldPlugins","existingField","item","reason","lockedFieldType","existingFieldType","lockedFieldsByType","filter","checkLockedField"],"sources":["validateModelFields.ts"],"sourcesContent":["import {\n CmsContext,\n CmsModel,\n CmsModelField,\n CmsModelFieldToGraphQLPlugin,\n CmsModelFieldToGraphQLPluginValidateChildFieldsValidate,\n CmsModelLockedFieldPlugin,\n LockedField\n} from \"~/types\";\nimport WebinyError from \"@webiny/error\";\nimport { createManageSDL } from \"~/graphql/schema/createManageSDL\";\nimport gql from \"graphql-tag\";\nimport { createFieldStorageId } from \"./createFieldStorageId\";\nimport { GraphQLError } from \"graphql\";\nimport { getBaseFieldType } from \"~/utils/getBaseFieldType\";\nimport { CmsGraphQLSchemaSorterPlugin } from \"~/plugins\";\nimport { buildSchemaPlugins } from \"~/graphql/buildSchemaPlugins\";\nimport { createExecutableSchema } from \"~/graphql/createExecutableSchema\";\nimport { GraphQLSchemaPlugin } from \"@webiny/handler-graphql\";\n\nconst defaultTitleFieldId = \"id\";\n\nconst allowedTitleFieldTypes = [\"text\", \"number\"];\n\nconst getContentModelTitleFieldId = (fields: CmsModelField[], titleFieldId?: string): string => {\n /**\n * If there are no fields defined, we will return the default field\n */\n if (fields.length === 0) {\n return defaultTitleFieldId;\n }\n /**\n * if there is no title field defined either in input data or existing content model data\n * we will take first text field that has no multiple values enabled\n * or if initial titleFieldId is the default one also try to find first available text field\n */\n if (!titleFieldId || titleFieldId === defaultTitleFieldId) {\n const titleField = fields.find(field => {\n return getBaseFieldType(field) === \"text\" && !field.multipleValues;\n });\n return titleField?.fieldId || defaultTitleFieldId;\n }\n /**\n * check existing titleFieldId for existence in the model\n * for correct type\n * and that it is not multiple values field\n */\n const target = fields.find(f => f.fieldId === titleFieldId);\n if (!target) {\n throw new WebinyError(\n `Field selected for the title field does not exist in the model.`,\n \"VALIDATION_ERROR\",\n {\n fieldId: titleFieldId,\n fields\n }\n );\n }\n\n if (allowedTitleFieldTypes.includes(target.type) === false) {\n throw new WebinyError(\n `Only ${allowedTitleFieldTypes.join(\n \", \"\n )} and id fields can be used as an entry title.`,\n \"ENTRY_TITLE_FIELD_TYPE\",\n {\n storageId: target.storageId,\n fieldId: target.fieldId,\n type: target.type\n }\n );\n }\n\n if (target.multipleValues) {\n throw new WebinyError(\n `Fields that accept multiple values cannot be used as the entry title.`,\n \"ENTRY_TITLE_FIELD_TYPE\",\n {\n storageId: target.storageId,\n fieldId: target.fieldId,\n type: target.type\n }\n );\n }\n\n return target.fieldId;\n};\n\nconst extractInvalidField = (model: CmsModel, err: GraphQLError) => {\n const sdl = err.source?.body || \"\";\n\n /**\n * Find the invalid type\n */\n const { line: lineNumber } = err.locations\n ? err.locations[0]\n : {\n line: 0\n };\n const sdlLines = sdl.split(\"\\n\");\n let sdlLine;\n let gqlType;\n for (let i = lineNumber; i > 0; i--) {\n if (sdlLine && sdlLine.includes(\"type \")) {\n gqlType = sdlLine.match(/type\\s+(.*?)\\s+{/);\n break;\n }\n\n sdlLine = sdlLines[i];\n }\n\n let invalidField: string | undefined = undefined;\n if (Array.isArray(gqlType)) {\n const fieldRegex = new RegExp(`([^\\\\s+].*?):\\\\s+\\\\[?${gqlType[1]}!?\\\\]?`);\n\n const matched = sdl.match(fieldRegex);\n if (matched) {\n invalidField = matched[1];\n }\n }\n\n let message = `See more details in the browser console.`;\n if (invalidField) {\n message = `Please review the definition of \"${invalidField}\" field.`;\n }\n\n return {\n data: {\n modelId: model.modelId,\n sdl,\n invalidField\n },\n code: \"INVALID_MODEL_DEFINITION\",\n message: [`Model \"${model.modelId}\" was not saved!`, message].join(\"\\n\")\n };\n};\n\nconst createValidateChildFields = (\n plugins: CmsModelFieldToGraphQLPlugin[]\n): CmsModelFieldToGraphQLPluginValidateChildFieldsValidate => {\n return ({ fields, originalFields }) => {\n if (fields.length === 0 && originalFields.length === 0) {\n return;\n }\n validateFields({\n fields,\n originalFields,\n plugins,\n lockedFields: []\n });\n };\n};\n\ninterface ValidateFieldsParams {\n plugins: CmsModelFieldToGraphQLPlugin[];\n fields: CmsModelField[];\n originalFields: CmsModelField[];\n lockedFields: LockedField[];\n}\nconst validateFields = (params: ValidateFieldsParams) => {\n const { plugins, fields, originalFields, lockedFields } = params;\n\n const idList: string[] = [];\n const fieldIdList: string[] = [];\n const storageIdList: string[] = [];\n\n for (const field of fields) {\n const baseType = getBaseFieldType(field);\n const plugin = plugins.find(plugin => plugin.fieldType === baseType);\n\n if (!plugin) {\n throw new Error(\n `Cannot update content model because of the unknown \"${baseType}\" field.`\n );\n }\n /**\n * Check the field's id against existing ones.\n * There cannot be two fields with the same id.\n */\n if (idList.includes(field.id)) {\n throw new WebinyError(\n `Cannot update content model because field \"${\n field.storageId || field.fieldId\n }\" has id \"${field.id}\", which is already used.`\n );\n }\n idList.push(field.id);\n\n const originalField = originalFields.find(f => f.id === field.id);\n /**\n * Field MUST have an fieldId defined.\n */\n if (!field.fieldId) {\n throw new WebinyError(`Field does not have an \"fieldId\" defined.`, \"MISSING_FIELD_ID\", {\n field\n });\n }\n /**\n * If storageId does not match a certain pattern, add that pattern, but only if field is not locked (used) already.\n * This is to avoid errors in the already installed systems.\n *\n * Why are we using the @?\n *\n * It is not part of special characters for the query syntax in the Lucene.\n *\n * Relevant links:\n * https://lucene.apache.org/core/3_4_0/queryparsersyntax.html\n * https://discuss.elastic.co/t/special-characters-in-field-names/10658/3\n * https://discuss.elastic.co/t/illegal-characters-in-elasticsearch-field-names/17196/2\n */\n const isLocked = lockedFields.some(lockedField => {\n return lockedField.fieldId === field.storageId || lockedField.fieldId === field.fieldId;\n });\n if (!field.storageId) {\n /**\n * In case field is locked, we must set the storageId to the fieldId value.\n * This should not happen, because we upgrade all the fields in 5.33.0, but let's have a check just in case of some upgrade miss.\n */\n //\n if (isLocked) {\n field.storageId = field.fieldId;\n }\n /**\n * When having original field, just set the storageId to value from the originalField\n */\n //\n else if (originalField) {\n field.storageId = originalField.storageId;\n }\n /**\n * The last case is when no original field and not locked - so this is a completely new field.\n */\n //\n else {\n field.storageId = createFieldStorageId(field);\n }\n }\n /**\n * Check the field's fieldId against existing ones.\n * There cannot be two fields with the same fieldId - outside world identifier.\n */\n if (fieldIdList.includes(field.fieldId)) {\n throw new WebinyError(\n `Cannot update content model because field \"${field.storageId}\" has fieldId \"${field.fieldId}\", which is already used.`\n );\n }\n fieldIdList.push(field.fieldId);\n /**\n * Check the field's storageId against the existing ones.\n * There cannot be two fields with the same storageId.\n */\n if (storageIdList.includes(field.storageId)) {\n throw new WebinyError(\n `Cannot update content model because field \"${field.label}\" has storageId \"${field.storageId}\", which is already used.`\n );\n }\n storageIdList.push(field.storageId);\n /**\n * There might be some plugins which allow child fields.\n * We use this method to validate them as well.\n */\n if (!plugin.validateChildFields) {\n continue;\n }\n const validateChildFields = createValidateChildFields(plugins);\n plugin.validateChildFields({\n field,\n originalField,\n validate: validateChildFields\n });\n }\n};\ninterface CreateGraphQLSchemaParams {\n context: CmsContext;\n model: CmsModel;\n}\nconst createGraphQLSchema = async (params: CreateGraphQLSchemaParams): Promise<any> => {\n const { context, model } = params;\n\n const modelPlugins = await buildSchemaPlugins({\n context,\n models: [model]\n });\n\n const plugins = context.plugins.byType<GraphQLSchemaPlugin<CmsContext>>(\n GraphQLSchemaPlugin.type\n );\n plugins.push(...modelPlugins);\n\n return createExecutableSchema({\n plugins\n });\n};\n\nconst extractErrorObject = (error: any) => {\n return [\"message\", \"code\", \"data\", \"stack\"].reduce<Record<string, any>>((output, key) => {\n if (!error[key]) {\n return output;\n }\n output[key] = error[key];\n return output;\n }, {});\n};\n\ninterface ValidateModelFieldsParams {\n model: CmsModel;\n original?: CmsModel;\n context: CmsContext;\n}\nexport const validateModelFields = async (params: ValidateModelFieldsParams): Promise<void> => {\n const { model, original, context } = params;\n const { titleFieldId } = model;\n const { plugins } = context;\n\n /**\n * There should be fields/locked fields in either model or data to be updated.\n */\n const { fields = [], lockedFields = [] } = model;\n\n /**\n * Let's inspect the fields of the received content model. We prevent saving of a content model if it\n * contains a field for which a \"cms-model-field-to-graphql\" plugin does not exist on the backend.\n */\n const fieldTypePlugins = plugins.byType<CmsModelFieldToGraphQLPlugin>(\n \"cms-model-field-to-graphql\"\n );\n\n validateFields({\n fields,\n originalFields: original?.fields || [],\n lockedFields,\n plugins: fieldTypePlugins\n });\n\n if (fields.length) {\n const sorterPlugins = plugins.byType<CmsGraphQLSchemaSorterPlugin>(\n CmsGraphQLSchemaSorterPlugin.type\n );\n /**\n * Make sure that this model can be safely converted to a GraphQL SDL\n */\n const schema = createManageSDL({\n model,\n fieldTypePlugins: fieldTypePlugins.reduce(\n (acc, pl) => ({ ...acc, [pl.fieldType]: pl }),\n {}\n ),\n sorterPlugins\n });\n\n try {\n gql(schema);\n } catch (err) {\n throw new WebinyError(extractInvalidField(model, err));\n }\n /**\n *\n */\n try {\n await createGraphQLSchema({\n context,\n model\n });\n } catch (err) {\n throw new WebinyError({\n message:\n \"Cannot generate GraphQL schema when testing with the given model. Please check the response for more details.\",\n code: \"GRAPHQL_SCHEMA_ERROR\",\n data: {\n modelId: model.modelId,\n error: extractErrorObject(err)\n }\n });\n }\n }\n\n model.titleFieldId = getContentModelTitleFieldId(fields, titleFieldId);\n\n const cmsLockedFieldPlugins =\n plugins.byType<CmsModelLockedFieldPlugin>(\"cms-model-locked-field\");\n\n /**\n * We must not allow removal or changes in fields that are already in use in content entries.\n * Locked fields still have fieldId (should be storageId) because of the old existing locked fields in the models.\n */\n for (const lockedField of lockedFields) {\n const existingField = fields.find(item => item.storageId === lockedField.fieldId);\n\n /**\n * Starting with 5.33.0 fields can be deleted.\n * Our UI gives a warning upon locked field deletion, but if user is managing fields through API directly - we cannot do anything.\n */\n if (!existingField) {\n continue;\n }\n\n if (lockedField.multipleValues !== existingField.multipleValues) {\n throw new WebinyError(\n `Cannot change \"multipleValues\" for the \"${lockedField.fieldId}\" field because it's already in use in created content.`,\n \"ENTRY_FIELD_USED\",\n {\n reason: `\"multipleValues\" changed`,\n field: existingField\n }\n );\n }\n\n const fieldType = getBaseFieldType(existingField);\n if (lockedField.type !== fieldType) {\n throw new WebinyError(\n `Cannot change field type for the \"${lockedField.fieldId}\" field because it's already in use in created content.`,\n \"ENTRY_FIELD_USED\",\n {\n reason: `\"type\" changed`,\n lockedFieldType: lockedField.type,\n existingFieldType: fieldType\n }\n );\n }\n\n /**\n * Check `lockedField` invariant for specific field\n */\n const lockedFieldsByType = cmsLockedFieldPlugins.filter(\n pl => pl.fieldType === getBaseFieldType(lockedField)\n );\n for (const plugin of lockedFieldsByType) {\n if (typeof plugin.checkLockedField !== \"function\") {\n continue;\n }\n plugin.checkLockedField({\n lockedField,\n field: existingField\n });\n }\n }\n};\n"],"mappings":"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"}
|