@strapi/content-type-builder 5.58.0 → 5.60.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/admin/components/AIChat/FeedbackModal.js +13 -7
- package/dist/admin/components/AIChat/FeedbackModal.js.map +1 -1
- package/dist/admin/components/AIChat/FeedbackModal.mjs +14 -8
- package/dist/admin/components/AIChat/FeedbackModal.mjs.map +1 -1
- package/dist/admin/components/AIChat/UploadCodeModal.js +12 -6
- package/dist/admin/components/AIChat/UploadCodeModal.js.map +1 -1
- package/dist/admin/components/AIChat/UploadCodeModal.mjs +13 -7
- package/dist/admin/components/AIChat/UploadCodeModal.mjs.map +1 -1
- package/dist/admin/components/AIChat/UploadFigmaModal.js +12 -6
- package/dist/admin/components/AIChat/UploadFigmaModal.js.map +1 -1
- package/dist/admin/components/AIChat/UploadFigmaModal.mjs +13 -7
- package/dist/admin/components/AIChat/UploadFigmaModal.mjs.map +1 -1
- package/dist/admin/components/AIChat/components/Attachments/components/Attachment.js +6 -3
- package/dist/admin/components/AIChat/components/Attachments/components/Attachment.js.map +1 -1
- package/dist/admin/components/AIChat/components/Attachments/components/Attachment.mjs +7 -4
- package/dist/admin/components/AIChat/components/Attachments/components/Attachment.mjs.map +1 -1
- package/dist/admin/components/AIChat/components/Collapsible.js +9 -4
- package/dist/admin/components/AIChat/components/Collapsible.js.map +1 -1
- package/dist/admin/components/AIChat/components/Collapsible.mjs +10 -5
- package/dist/admin/components/AIChat/components/Collapsible.mjs.map +1 -1
- package/dist/admin/components/AIChat/components/Dropzone.js +13 -6
- package/dist/admin/components/AIChat/components/Dropzone.js.map +1 -1
- package/dist/admin/components/AIChat/components/Dropzone.mjs +14 -7
- package/dist/admin/components/AIChat/components/Dropzone.mjs.map +1 -1
- package/dist/admin/components/AIChat/components/FloatingPanel.js +11 -4
- package/dist/admin/components/AIChat/components/FloatingPanel.js.map +1 -1
- package/dist/admin/components/AIChat/components/FloatingPanel.mjs +12 -5
- package/dist/admin/components/AIChat/components/FloatingPanel.mjs.map +1 -1
- package/dist/admin/components/AIChat/components/FullScreenImage.js +16 -8
- package/dist/admin/components/AIChat/components/FullScreenImage.js.map +1 -1
- package/dist/admin/components/AIChat/components/FullScreenImage.mjs +17 -9
- package/dist/admin/components/AIChat/components/FullScreenImage.mjs.map +1 -1
- package/dist/admin/components/AIChat/components/Input.js +6 -3
- package/dist/admin/components/AIChat/components/Input.js.map +1 -1
- package/dist/admin/components/AIChat/components/Input.mjs +7 -4
- package/dist/admin/components/AIChat/components/Input.mjs.map +1 -1
- package/dist/admin/components/AIChat/components/Messages/Message.js +88 -12
- package/dist/admin/components/AIChat/components/Messages/Message.js.map +1 -1
- package/dist/admin/components/AIChat/components/Messages/Message.mjs +87 -13
- package/dist/admin/components/AIChat/components/Messages/Message.mjs.map +1 -1
- package/dist/admin/components/AIChat/components/StepModal.js +44 -17
- package/dist/admin/components/AIChat/components/StepModal.js.map +1 -1
- package/dist/admin/components/AIChat/components/StepModal.mjs +45 -18
- package/dist/admin/components/AIChat/components/StepModal.mjs.map +1 -1
- package/dist/admin/components/AIChat/providers/ChatProvider.js +79 -27
- package/dist/admin/components/AIChat/providers/ChatProvider.js.map +1 -1
- package/dist/admin/components/AIChat/providers/ChatProvider.mjs +80 -28
- package/dist/admin/components/AIChat/providers/ChatProvider.mjs.map +1 -1
- package/dist/admin/components/AIChat/providers/SchemaProvider.js +6 -3
- package/dist/admin/components/AIChat/providers/SchemaProvider.js.map +1 -1
- package/dist/admin/components/AIChat/providers/SchemaProvider.mjs +7 -4
- package/dist/admin/components/AIChat/providers/SchemaProvider.mjs.map +1 -1
- package/dist/admin/components/AttributeOptions/AttributeOption.js +2 -2
- package/dist/admin/components/AttributeOptions/AttributeOption.js.map +1 -1
- package/dist/admin/components/AttributeOptions/AttributeOption.mjs +2 -2
- package/dist/admin/components/AttributeOptions/AttributeOption.mjs.map +1 -1
- package/dist/admin/components/ContentTypeBuilderNav/lib/buildFolderTree.js.map +1 -1
- package/dist/admin/components/ContentTypeBuilderNav/lib/buildFolderTree.mjs.map +1 -1
- package/dist/admin/components/ContentTypeBuilderNav/lib/dropProjection.js.map +1 -1
- package/dist/admin/components/ContentTypeBuilderNav/lib/dropProjection.mjs.map +1 -1
- package/dist/admin/components/CustomRadioGroup/CustomRadioGroup.js +2 -1
- package/dist/admin/components/CustomRadioGroup/CustomRadioGroup.js.map +1 -1
- package/dist/admin/components/CustomRadioGroup/CustomRadioGroup.mjs +2 -1
- package/dist/admin/components/CustomRadioGroup/CustomRadioGroup.mjs.map +1 -1
- package/dist/admin/components/DataManager/DataManagerProvider.js +317 -275
- package/dist/admin/components/DataManager/DataManagerProvider.js.map +1 -1
- package/dist/admin/components/DataManager/DataManagerProvider.mjs +319 -277
- package/dist/admin/components/DataManager/DataManagerProvider.mjs.map +1 -1
- package/dist/admin/components/DataManager/RenameMigrationModal.js.map +1 -1
- package/dist/admin/components/DataManager/RenameMigrationModal.mjs.map +1 -1
- package/dist/admin/components/DataManager/reducer.js +31 -4
- package/dist/admin/components/DataManager/reducer.js.map +1 -1
- package/dist/admin/components/DataManager/reducer.mjs +31 -4
- package/dist/admin/components/DataManager/reducer.mjs.map +1 -1
- package/dist/admin/components/DynamicZoneList.js +2 -1
- package/dist/admin/components/DynamicZoneList.js.map +1 -1
- package/dist/admin/components/DynamicZoneList.mjs +2 -1
- package/dist/admin/components/DynamicZoneList.mjs.map +1 -1
- package/dist/admin/components/FormModal/attributes/ConditionForm.js +2 -1
- package/dist/admin/components/FormModal/attributes/ConditionForm.js.map +1 -1
- package/dist/admin/components/FormModal/attributes/ConditionForm.mjs +2 -1
- package/dist/admin/components/FormModal/attributes/ConditionForm.mjs.map +1 -1
- package/dist/admin/components/FormModal/attributes/types.js +2 -2
- package/dist/admin/components/FormModal/attributes/types.js.map +1 -1
- package/dist/admin/components/FormModal/attributes/types.mjs +2 -2
- package/dist/admin/components/FormModal/attributes/types.mjs.map +1 -1
- package/dist/admin/components/FormModal/forms/forms.js +1 -1
- package/dist/admin/components/FormModal/forms/forms.js.map +1 -1
- package/dist/admin/components/FormModal/forms/forms.mjs +1 -1
- package/dist/admin/components/FormModal/forms/forms.mjs.map +1 -1
- package/dist/admin/components/GenericInputs.js +2 -1
- package/dist/admin/components/GenericInputs.js.map +1 -1
- package/dist/admin/components/GenericInputs.mjs +2 -1
- package/dist/admin/components/GenericInputs.mjs.map +1 -1
- package/dist/admin/components/TabForm.js.map +1 -1
- package/dist/admin/components/TabForm.mjs.map +1 -1
- package/dist/admin/src/components/AIChat/components/FullScreenImage.d.ts +8 -0
- package/dist/admin/src/components/AIChat/components/Messages/Message.d.ts +20 -0
- package/dist/admin/utils/folderTelemetry.js.map +1 -1
- package/dist/admin/utils/folderTelemetry.mjs.map +1 -1
- package/dist/admin/utils/formAPI.js.map +1 -1
- package/dist/admin/utils/formAPI.mjs.map +1 -1
- package/dist/server/controllers/validation/common.js +1 -1
- package/dist/server/controllers/validation/common.js.map +1 -1
- package/dist/server/controllers/validation/common.mjs +1 -1
- package/dist/server/controllers/validation/common.mjs.map +1 -1
- package/dist/server/controllers/validation/schema.js +3 -2
- package/dist/server/controllers/validation/schema.js.map +1 -1
- package/dist/server/controllers/validation/schema.mjs +4 -3
- package/dist/server/controllers/validation/schema.mjs.map +1 -1
- package/dist/server/register.js.map +1 -1
- package/dist/server/register.mjs.map +1 -1
- package/dist/server/services/migration-builder/index.js.map +1 -1
- package/dist/server/services/migration-builder/index.mjs.map +1 -1
- package/dist/server/services/schema.js +34 -1
- package/dist/server/services/schema.js.map +1 -1
- package/dist/server/services/schema.mjs +34 -1
- package/dist/server/services/schema.mjs.map +1 -1
- package/dist/server/src/controllers/validation/schema.d.ts.map +1 -1
- package/dist/server/src/register.d.ts.map +1 -1
- package/dist/server/src/services/migration-builder/index.d.ts.map +1 -1
- package/dist/server/src/services/schema-builder/types.d.ts.map +1 -1
- package/dist/server/src/services/schema.d.ts.map +1 -1
- package/dist/server/src/utils/uid-target.d.ts +18 -0
- package/dist/server/src/utils/uid-target.d.ts.map +1 -0
- package/dist/server/utils/uid-target.js +34 -0
- package/dist/server/utils/uid-target.js.map +1 -0
- package/dist/server/utils/uid-target.mjs +31 -0
- package/dist/server/utils/uid-target.mjs.map +1 -0
- package/package.json +6 -6
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.mjs","sources":["../../../../server/src/services/migration-builder/index.ts"],"sourcesContent":["import path from 'node:path';\n\nimport { contentTypes as contentTypesUtils } from '@strapi/utils';\nimport type { Core } from '@strapi/types';\n\n/**\n * The CTB-level attribute definition of the *new* side of a rename hop (the\n * `properties` the admin sends for `newName`). Only the storage-relevant keys\n * are inspected; see `isCompatibleRename`.\n */\nexport interface RenameAttributeDefinition {\n type?: string;\n relation?: string;\n target?: string;\n component?: string;\n repeatable?: boolean;\n customField?: string;\n targetAttribute?: string | null;\n inversedBy?: string;\n mappedBy?: string;\n configurable?: boolean;\n [key: string]: unknown;\n}\n\nexport interface RenameNames {\n oldName: string;\n newName: string;\n /**\n * Definition of the attribute under its new name, when known. Used to refuse\n * hops that also change the attribute's storage (e.g. `string` -> `integer`,\n * or a relation retargeted): renaming the column and letting schema sync\n * alter its type in place can fail on Postgres/MySQL, whereas the legacy\n * drop-and-recreate path is always safe.\n */\n newAttribute?: RenameAttributeDefinition;\n}\n\nexport type UnsupportedRenameReason =\n | 'model-not-found'\n | 'attribute-not-found'\n | 'unsupported-type'\n | 'type-changed'\n | 'target-occupied';\n\nexport interface UnsupportedRename {\n uid: string;\n oldName: string;\n newName: string;\n reason: UnsupportedRenameReason;\n}\n\n/**\n * Whether a relation definition has a counterpart on its target. The live\n * schema carries `inversedBy` / `mappedBy`; the CTB payload carries\n * `targetAttribute`.\n */\nconst isBidirectionalRelation = (attribute: RenameAttributeDefinition): boolean =>\n Boolean(attribute.inversedBy || attribute.mappedBy || attribute.targetAttribute);\n\n/**\n * Whether the storage of `oldAttribute` can host `newAttribute` after a plain\n * rename of its physical artifact. Anything else must go through the legacy\n * drop-and-recreate path, so the hop is reported as `type-changed`.\n *\n * `resolveType` maps a definition to its storage type. The builder passes one\n * that resolves custom fields (sent as `type: 'customField'` by the admin, but\n * already converted to their underlying type in the live schema).\n */\nexport const isCompatibleRename = (\n oldAttribute: RenameAttributeDefinition | undefined,\n newAttribute: RenameAttributeDefinition | undefined,\n resolveType: (attribute: RenameAttributeDefinition) => string | undefined = (attribute) =>\n attribute.type\n): boolean => {\n const oldType = oldAttribute ? resolveType(oldAttribute) : undefined;\n const newType = newAttribute ? resolveType(newAttribute) : undefined;\n\n // Without both definitions there is nothing to compare; the metadata-based\n // classification is the only guard we have.\n if (!oldAttribute || !newAttribute || !oldType || !newType) {\n return true;\n }\n\n if (oldType !== newType) {\n return false;\n }\n\n // A different custom field on the same underlying type is still a different\n // field.\n if (\n (oldAttribute.customField || newAttribute.customField) &&\n oldAttribute.customField !== newAttribute.customField\n ) {\n return false;\n }\n\n switch (newType) {\n case 'relation':\n // `manyWay` and a bidirectional `oneToMany` share `relation: 'oneToMany'`,\n // but switching between them moves join-table ownership.\n return (\n oldAttribute.relation === newAttribute.relation &&\n oldAttribute.target === newAttribute.target &&\n isBidirectionalRelation(oldAttribute) === isBidirectionalRelation(newAttribute)\n );\n case 'component':\n return (\n oldAttribute.component === newAttribute.component &&\n Boolean(oldAttribute.repeatable) === Boolean(newAttribute.repeatable)\n );\n default:\n return true;\n }\n};\n\nexport interface BuiltMigration {\n filename: string;\n content: string;\n}\n\n/**\n * How a renamed attribute maps to a physical database artifact, resolved from\n * `strapi.db.metadata` (the live, pre-rename schema). The `from` field is the\n * current physical identifier and moves forward at each hop so rename chains and\n * user-routed swaps replay verbatim.\n *\n * - `scalarColumn` / `joinColumn`: a column on the model's own table. Scalar\n * columns resolve names via `getColumnName`; relation join columns (`<field>_id`)\n * via `getJoinColumnAttributeIdName`.\n * - `joinTable`: a relation backed by a join/link table (the table name encodes\n * the owning attribute name).\n * - `component`: a component or dynamic zone — the attribute name is a *value* in\n * the per-type link table's `field` column, so it is an `UPDATE`, not DDL.\n * - `media`: like `component`, but stored in the shared `files_related_morphs`\n * table, so the `UPDATE` is additionally scoped by `related_type` (the uid).\n * - `skip`: recognised but needs no DB change (e.g. the inverse side of a\n * bidirectional relation — the join table is named from the owning side).\n * - `unsupported`: cannot be migrated automatically (polymorphic morph relations,\n * which are not creatable through the CTB UI anyway).\n */\ntype Resolved =\n | { kind: 'scalarColumn'; table: string; from: string }\n | { kind: 'joinColumn'; table: string; from: string }\n | { kind: 'joinTable'; from: string }\n | { kind: 'component'; table: string; fieldColumn: string; from: string }\n | {\n kind: 'media';\n table: string;\n fieldColumn: string;\n typeColumn: string;\n typeValue: string;\n from: string;\n }\n | { kind: 'skip' }\n | { kind: 'unsupported'; reason: UnsupportedRename['reason'] };\n\ninterface MigrationBuilderDeps {\n strapi: Core.Strapi;\n}\n\n/**\n * The database metadata shapes the builder reads, derived from `Core.Strapi`\n * so the Content-Type Builder does not depend on `@strapi/database` directly.\n */\ntype ModelMeta = NonNullable<ReturnType<Core.Strapi['db']['metadata']['get']>>;\n\n/**\n * A metadata attribute, widened with the relation/join keys the builder\n * inspects (the metadata union only declares them on some members).\n */\ntype AttributeMeta = ModelMeta['attributes'][string] & {\n relation?: string;\n mappedBy?: string;\n morphColumn?: unknown;\n joinColumn?: { name?: string };\n joinTable?: JoinTableMeta;\n};\n\ninterface JoinTableMeta {\n name?: string;\n on?: Record<string, unknown>;\n morphColumn?: { typeColumn?: { name?: string } };\n}\n\ntype SchemaModel = Parameters<typeof contentTypesUtils.getNonVisibleAttributes>[0];\n\n/**\n * Per-uid `origin -> current name` of every received hop, accepted or refused:\n * the logical field is the same field even when its data cannot be carried.\n */\nexport type AttributeRenamesMapping = Record<string, Record<string, string>>;\n\nconst MIGRATION_NAME = 'rename-fields';\n\nexport const createMigrationBuilder = ({ strapi }: MigrationBuilderDeps) => {\n const { db } = strapi;\n\n const migrationFileBuilder = db.migrations.createFileBuilder();\n const unsupported: UnsupportedRename[] = [];\n\n // Physical-name rules shared with the metadata loader, so the *new* side of a\n // rename is derived exactly as `db.metadata` will derive it after the reload.\n const { naming } = db.metadata;\n\n /**\n * The app's *source* migrations dir. Generated files always land here (see\n * `writeFiles`), and it is also the dir discovery reads from when\n * `useTypescriptMigrations` is off or no tsconfig `outDir` resolves.\n */\n const sourceMigrationsDir = () => path.join(strapi.dirs.app.root, 'database', 'migrations');\n\n let format: 'javascript' | 'typescript' | undefined;\n\n /**\n * Mirror the database's discovery decision (`Strapi.ts`): it reads from\n * `<outDir>/database/migrations` only when `useTypescriptMigrations` is on\n * *and* a tsconfig `outDir` resolves. In that case the source file must be\n * `.ts` so `tsc` carries it into `dist`. Otherwise discovery reads the source\n * dir and only loads `.js`, so a `.ts` file would never run.\n *\n * Memoised so the fallback warning is logged once per builder (both `build`\n * and `writeFiles` call this).\n */\n const getFormat = (): 'javascript' | 'typescript' => {\n if (format) {\n return format;\n }\n\n const useTSM = strapi.config.get('database.settings.useTypescriptMigrations') === true;\n const discoveryDir = db.config.settings.migrations?.dir;\n const discoversFromDist =\n typeof discoveryDir === 'string' &&\n path.resolve(discoveryDir) !== path.resolve(sourceMigrationsDir());\n\n if (useTSM && !discoversFromDist) {\n strapi.log.warn(\n 'database.settings.useTypescriptMigrations is enabled but no TypeScript outDir was resolved for this app; ' +\n 'writing the rename migration as JavaScript so it is discovered from database/migrations.'\n );\n }\n\n format = useTSM && discoversFromDist ? 'typescript' : 'javascript';\n return format;\n };\n\n // Artifacts \"in flight\" for the current save, i.e. produced by an earlier\n // rename hop in this same batch (e.g. the intermediate `tmp` field a user\n // routes a swap through). Keyed per uid by the *logical* field name the hop\n // produced; the value records how that field resolves to a physical artifact\n // and its current `from` identifier, so a continuation hop replays from the\n // right place instead of being treated as a brand-new, unknown attribute.\n const inFlight = new Map<string, Map<string, Resolved>>();\n\n // CTB-level definition of each in-flight field (per uid, by logical name), so\n // a continuation hop can still be checked for a storage change against the\n // definition the chain started from.\n const inFlightDefinitions = new Map<string, Map<string, RenameAttributeDefinition>>();\n\n // Logical names vacated by an earlier accepted hop of this batch (per uid). A\n // refused hop never vacates its source: the artifact stays live until schema\n // sync drops it. A hop may only target a name that is free: not live in the\n // pre-reload schema (unless an earlier accepted hop vacated it) and not\n // produced by an earlier hop still in flight. At migration time the schema-sync drop of a still-live field has\n // not happened yet, so renaming onto it would collide and the runtime guard\n // would silently skip the hop. Refusing it here surfaces the problem (e.g. a\n // truncated chain sent by a client) instead of losing data.\n const vacated = new Map<string, Set<string>>();\n\n const isTargetOccupied = (uid: string, newName: string): boolean => {\n if (inFlight.get(uid)?.has(newName)) {\n return true;\n }\n return Boolean(schemaAttributeOf(uid, newName)) && !(vacated.get(uid)?.has(newName) ?? false);\n };\n\n const trackVacated = (uid: string, oldName: string, newName: string): void => {\n let names = vacated.get(uid);\n if (!names) {\n names = new Set<string>();\n vacated.set(uid, names);\n }\n names.add(oldName);\n // The target is occupied again by the in-flight field.\n names.delete(newName);\n };\n\n const markInFlight = (uid: string, name: string, resolved: Resolved): void => {\n let entries = inFlight.get(uid);\n if (!entries) {\n entries = new Map<string, Resolved>();\n inFlight.set(uid, entries);\n }\n entries.set(name, resolved);\n };\n\n // Per uid, logical origin name -> current name, folded over every received hop.\n const origins = new Map<string, Map<string, string>>();\n\n const trackOrigin = (uid: string, oldName: string, newName: string): void => {\n let byOrigin = origins.get(uid);\n if (!byOrigin) {\n byOrigin = new Map<string, string>();\n origins.set(uid, byOrigin);\n }\n\n for (const [origin, current] of byOrigin) {\n if (current === oldName) {\n byOrigin.set(origin, newName);\n return;\n }\n }\n\n // A name that is already an origin but no longer current was re-occupied by\n // something this save did not rename; do not overwrite its logical field.\n if (!byOrigin.has(oldName)) {\n byOrigin.set(oldName, newName);\n }\n };\n\n const isMorphRelation = (attribute: AttributeMeta): boolean =>\n typeof attribute.relation === 'string' && attribute.relation.startsWith('morph');\n\n const schemaModelOf = (\n uid: string\n ): { attributes?: Record<string, RenameAttributeDefinition> } | undefined => {\n const contentTypes = strapi.contentTypes as Record<string, unknown> | undefined;\n const components = strapi.components as Record<string, unknown> | undefined;\n return (contentTypes?.[uid] ?? components?.[uid]) as\n | { attributes?: Record<string, RenameAttributeDefinition> }\n | undefined;\n };\n\n const schemaAttributeOf = (uid: string, name: string): RenameAttributeDefinition | undefined =>\n schemaModelOf(uid)?.attributes?.[name];\n\n /**\n * The type an attribute is stored as. Custom fields are sent by the admin as\n * `type: 'customField'`, while the live schema already carries their\n * underlying type, so both sides are resolved through the registry.\n */\n const storageTypeOf = (attribute: RenameAttributeDefinition): string | undefined => {\n if (attribute.type !== 'customField' && typeof attribute.customField !== 'string') {\n return attribute.type;\n }\n\n try {\n const customField = strapi.get('custom-fields').get(attribute.customField as string) as\n | { type?: string }\n | undefined;\n return customField?.type ?? attribute.type;\n } catch {\n // Unknown custom field (e.g. its plugin was removed).\n return attribute.type;\n }\n };\n\n const schemaTypeOf = (uid: string, name: string): string | undefined =>\n schemaAttributeOf(uid, name)?.type;\n\n // Resolves the shared upload morph table (e.g. `files_related_morphs`) and its\n // `related_type` column from the file model's `related` morph attribute. This\n // is the single table every media field across all types writes to, keyed by\n // (`field` = attribute name, `related_type` = owning uid).\n const resolveUploadMorphTable = ():\n | { table: string; fieldColumn: string; typeColumn: string }\n | undefined => {\n if (!db.metadata.has('plugin::upload.file')) {\n return undefined;\n }\n const fileMeta = db.metadata.get('plugin::upload.file');\n const related = fileMeta.attributes?.related as\n | (AttributeMeta & { morphColumn?: JoinTableMeta['morphColumn'] })\n | undefined;\n const joinTable = related?.joinTable;\n const morphColumn = joinTable?.morphColumn ?? related?.morphColumn;\n if (!joinTable?.name || !morphColumn?.typeColumn?.name) {\n return undefined;\n }\n return {\n table: joinTable.name,\n fieldColumn: db.metadata.identifiers.FIELD_COLUMN,\n typeColumn: morphColumn.typeColumn.name,\n };\n };\n\n /**\n * Classifies the *first* hop of a rename by inspecting the live metadata, which\n * still reflects the pre-rename schema. Continuation hops never reach here —\n * they inherit their classification from the in-flight map.\n */\n const classifyMedia = (\n uid: string,\n oldName: string,\n joinTable: JoinTableMeta | undefined,\n upload: ReturnType<typeof resolveUploadMorphTable>\n ): Resolved | undefined => {\n // Media: the attribute name is a value in the shared `files_related_morphs`\n // `field` column, scoped by `related_type` (the owning uid). Detect it by\n // schema type OR by the join table being the shared upload table — the\n // latter guard is critical so a media field can never fall through to the\n // unscoped component branch and corrupt other types' media on the shared\n // table.\n const isMedia =\n schemaTypeOf(uid, oldName) === 'media' || (!!upload && joinTable?.name === upload.table);\n if (!isMedia) {\n return undefined;\n }\n if (!upload) {\n return { kind: 'unsupported', reason: 'unsupported-type' };\n }\n return {\n kind: 'media',\n table: upload.table,\n fieldColumn: upload.fieldColumn,\n typeColumn: upload.typeColumn,\n typeValue: uid,\n from: oldName,\n };\n };\n\n const classifyComponent = (\n oldName: string,\n joinTable: JoinTableMeta | undefined\n ): Resolved | undefined => {\n const on = joinTable?.on;\n if (!joinTable?.name || !on || typeof on !== 'object') {\n return undefined;\n }\n const fieldColumn = Object.keys(on).find((key) => on[key] === oldName);\n if (!fieldColumn) {\n return undefined;\n }\n return { kind: 'component', table: joinTable.name, fieldColumn, from: oldName };\n };\n\n const classifyRelation = (\n meta: ModelMeta,\n attribute: AttributeMeta,\n joinTable: JoinTableMeta | undefined\n ): Resolved => {\n // Polymorphic morph relations need shared-table handling and are not\n // creatable through the CTB UI, so they are left unsupported.\n if (isMorphRelation(attribute) || attribute.morphColumn) {\n return { kind: 'unsupported', reason: 'unsupported-type' };\n }\n\n // Join column on the owner's own table (`<field>_id`), e.g. useJoinTable:false.\n // The inverse side of a bidirectional join-column relation also carries a\n // `joinColumn` (pointing at `id`), but owns no column.\n if (attribute.joinColumn?.name && !joinTable) {\n if (attribute.mappedBy) {\n return { kind: 'skip' };\n }\n return { kind: 'joinColumn', table: meta.tableName, from: attribute.joinColumn.name };\n }\n\n if (joinTable?.name) {\n // The inverse side of a bidirectional relation: the join table is named\n // from the owning attribute, so renaming this side touches no artifact.\n if (attribute.mappedBy) {\n return { kind: 'skip' };\n }\n return { kind: 'joinTable', from: joinTable.name };\n }\n\n return { kind: 'unsupported', reason: 'unsupported-type' };\n };\n\n /**\n * Whether the schema lets users rename this attribute at all. System\n * attributes (`documentId`, `createdBy`, `locale`, `publishedAt`, review\n * workflow stages…) are also in the metadata and would otherwise be renamed\n * away, only for sync to re-add them empty.\n */\n const isRenamableAttribute = (uid: string, name: string): boolean => {\n const schemaAttribute = schemaAttributeOf(uid, name);\n // Same rule as payload validation applies to a hop's old name: `status` is\n // only reserved with draft and publish, and a legacy field may carry it.\n if (\n schemaAttribute?.configurable === false ||\n contentTypesUtils.isReservedAttributeName(name, { draftAndPublish: false })\n ) {\n return false;\n }\n\n const model = schemaModelOf(uid);\n return !contentTypesUtils.getNonVisibleAttributes(model as SchemaModel).includes(name);\n };\n\n const classify = (uid: string, oldName: string): Resolved => {\n if (!schemaAttributeOf(uid, oldName)) {\n return { kind: 'unsupported', reason: 'attribute-not-found' };\n }\n\n if (!isRenamableAttribute(uid, oldName)) {\n return { kind: 'unsupported', reason: 'unsupported-type' };\n }\n\n const meta = db.metadata.get(uid);\n const attribute = meta.attributes?.[oldName] as AttributeMeta | undefined;\n\n if (!attribute) {\n return { kind: 'unsupported', reason: 'attribute-not-found' };\n }\n\n const joinTable = attribute.joinTable;\n const upload = resolveUploadMorphTable();\n const media = classifyMedia(uid, oldName, joinTable, upload);\n if (media) {\n return media;\n }\n\n const component = classifyComponent(oldName, joinTable);\n if (component) {\n return component;\n }\n\n if (attribute.type === 'relation') {\n return classifyRelation(meta, attribute, joinTable);\n }\n\n // Plain scalar column on the model's own table.\n if ('columnName' in attribute && attribute.columnName) {\n return { kind: 'scalarColumn', table: meta.tableName, from: attribute.columnName };\n }\n\n return { kind: 'unsupported', reason: 'unsupported-type' };\n };\n\n /**\n * Computes the destination identifier for a resolved artifact given the new\n * field name, and the next in-flight state (with `from` advanced to `to`).\n */\n const advance = (uid: string, resolved: Resolved, oldName: string, newName: string): Resolved => {\n const meta = db.metadata.get(uid);\n const comment = `${uid}: rename field \"${oldName}\" -> \"${newName}\"`;\n\n switch (resolved.kind) {\n case 'scalarColumn':\n case 'joinColumn': {\n const to =\n resolved.kind === 'joinColumn'\n ? naming.joinColumnName(newName)\n : naming.columnName(newName);\n if (resolved.from !== to) {\n migrationFileBuilder.renameColumn({\n table: resolved.table,\n from: resolved.from,\n to,\n comment,\n });\n }\n return { ...resolved, from: to };\n }\n case 'joinTable': {\n const to = naming.joinTableName(meta.tableName, newName);\n if (resolved.from !== to) {\n migrationFileBuilder.renameTable({ from: resolved.from, to, comment });\n }\n return { ...resolved, from: to };\n }\n case 'component': {\n const to = newName;\n if (resolved.from !== to) {\n migrationFileBuilder.updateRows({\n table: resolved.table,\n guardColumn: resolved.fieldColumn,\n where: { [resolved.fieldColumn]: resolved.from },\n set: { [resolved.fieldColumn]: to },\n comment,\n });\n }\n return { ...resolved, from: to };\n }\n case 'media': {\n const to = newName;\n if (resolved.from !== to) {\n migrationFileBuilder.updateRows({\n table: resolved.table,\n guardColumn: resolved.fieldColumn,\n where: {\n [resolved.fieldColumn]: resolved.from,\n [resolved.typeColumn]: resolved.typeValue,\n },\n set: { [resolved.fieldColumn]: to },\n comment,\n });\n }\n return { ...resolved, from: to };\n }\n default:\n return resolved;\n }\n };\n\n /**\n * Records one rename hop exactly in the order the user performed it. Because the\n * Content-Type Builder forbids two fields sharing a name at any instant, the\n * recorded path is inherently collision-free: replaying each hop verbatim never\n * targets an occupied artifact, so no synthetic temporary name is ever needed\n * (a \"swap\" is already expressed by the user's own intermediate-name hop).\n */\n const addRename = (uid: string, { oldName, newName, newAttribute }: RenameNames): void => {\n // `metadata.get` throws when the model is unknown, so guard with `has` first.\n if (!db.metadata.has(uid)) {\n unsupported.push({ uid, oldName, newName, reason: 'model-not-found' });\n return;\n }\n\n trackOrigin(uid, oldName, newName);\n\n if (isTargetOccupied(uid, newName)) {\n unsupported.push({ uid, oldName, newName, reason: 'target-occupied' });\n // Keep the chain consistent so a later continuation hop stays silent. The\n // source is not vacated: its artifact was not moved.\n markInFlight(uid, newName, { kind: 'unsupported', reason: 'target-occupied' });\n return;\n }\n\n const entries = inFlight.get(uid);\n const definitions = inFlightDefinitions.get(uid);\n const oldAttribute = definitions?.get(oldName) ?? schemaAttributeOf(uid, oldName);\n let resolved = entries?.get(oldName) ?? classify(uid, oldName);\n\n // A rename that also changes the attribute's storage cannot be expressed as a\n // rename of the physical artifact: leave it to the drop-and-recreate path.\n if (\n resolved.kind !== 'unsupported' &&\n !isCompatibleRename(oldAttribute, newAttribute, storageTypeOf)\n ) {\n resolved = { kind: 'unsupported', reason: 'type-changed' };\n }\n\n if (newAttribute ?? oldAttribute) {\n let byName = inFlightDefinitions.get(uid);\n if (!byName) {\n byName = new Map();\n inFlightDefinitions.set(uid, byName);\n }\n byName.set(newName, (newAttribute ?? oldAttribute) as RenameAttributeDefinition);\n }\n\n if (resolved.kind === 'unsupported') {\n unsupported.push({ uid, oldName, newName, reason: resolved.reason });\n // Keep the chain consistent so a later continuation hop stays silent. The\n // source keeps its in-flight entry and is not vacated: its physical\n // artifact stays where it is until schema sync drops it.\n markInFlight(uid, newName, resolved);\n return;\n }\n\n // Accepted from here on: the source name is free and the field moves.\n entries?.delete(oldName);\n definitions?.delete(oldName);\n trackVacated(uid, oldName, newName);\n\n if (resolved.kind === 'skip') {\n markInFlight(uid, newName, resolved);\n return;\n }\n\n const next = advance(uid, resolved, oldName, newName);\n markInFlight(uid, newName, next);\n };\n\n return {\n addRenameAttribute(uid: string, names: RenameNames): void {\n addRename(uid, names);\n },\n\n /**\n * The composed `origin -> final` name of every schema attribute that\n * received hops in this save, per uid. Identity entries (`a -> b -> a`) and\n * origins that are not schema attributes are left out.\n */\n attributeRenamesMapping(): AttributeRenamesMapping {\n const mapping: AttributeRenamesMapping = {};\n\n for (const [uid, byOrigin] of origins) {\n for (const [origin, final] of byOrigin) {\n if (origin === final || !schemaAttributeOf(uid, origin)) {\n continue;\n }\n mapping[uid] ??= {};\n mapping[uid][origin] = final;\n }\n }\n\n return mapping;\n },\n\n /**\n * Adds the logical op that carries this save's renames to the stores keyed\n * by attribute name (admin field permissions, via handlers registered on\n * the database). Call it after every hop so it is the last operation.\n */\n addAttributeRenames(renames: AttributeRenamesMapping): void {\n if (Object.keys(renames).length === 0) {\n return;\n }\n\n migrationFileBuilder.attributeRenames({\n renames,\n comment:\n \"Update stores keyed by attribute name (admin field permissions) for this save's renames\",\n });\n },\n\n hasChanges(): boolean {\n return migrationFileBuilder.hasChanges();\n },\n\n getUnsupported(): UnsupportedRename[] {\n return [...unsupported];\n },\n\n getOperations() {\n return migrationFileBuilder.getOperations();\n },\n\n build(): BuiltMigration | null {\n return migrationFileBuilder.build({ name: MIGRATION_NAME, format: getFormat() });\n },\n\n async writeFiles(): Promise<string | null> {\n // Always write to the app's *source* migrations dir, never the database's\n // configured dir: when `useTypescriptMigrations` is enabled that points at\n // build output (e.g. `dist/database/migrations`), which is gitignored and\n // wiped on the next build, so the generated migration would not be a\n // portable record.\n const dir = sourceMigrationsDir();\n return migrationFileBuilder.writeFiles({ name: MIGRATION_NAME, format: getFormat(), dir });\n },\n };\n};\n\nexport type MigrationBuilder = ReturnType<typeof createMigrationBuilder>;\n"],"names":["isBidirectionalRelation","attribute","Boolean","inversedBy","mappedBy","targetAttribute","isCompatibleRename","oldAttribute","newAttribute","resolveType","type","oldType","undefined","newType","customField","relation","target","component","repeatable","MIGRATION_NAME","createMigrationBuilder","strapi","db","migrationFileBuilder","migrations","createFileBuilder","unsupported","naming","metadata","sourceMigrationsDir","path","join","dirs","app","root","format","getFormat","useTSM","config","get","discoveryDir","settings","dir","discoversFromDist","resolve","log","warn","inFlight","Map","inFlightDefinitions","vacated","isTargetOccupied","uid","newName","has","schemaAttributeOf","trackVacated","oldName","names","Set","set","add","delete","markInFlight","name","resolved","entries","origins","trackOrigin","byOrigin","origin","current","isMorphRelation","startsWith","schemaModelOf","contentTypes","components","attributes","storageTypeOf","schemaTypeOf","resolveUploadMorphTable","fileMeta","related","joinTable","morphColumn","typeColumn","table","fieldColumn","identifiers","FIELD_COLUMN","classifyMedia","upload","isMedia","kind","reason","typeValue","from","classifyComponent","on","Object","keys","find","key","classifyRelation","meta","joinColumn","tableName","isRenamableAttribute","schemaAttribute","configurable","contentTypesUtils","isReservedAttributeName","draftAndPublish","model","getNonVisibleAttributes","includes","classify","media","columnName","advance","comment","to","joinColumnName","renameColumn","joinTableName","renameTable","updateRows","guardColumn","where","addRename","push","definitions","byName","next","addRenameAttribute","attributeRenamesMapping","mapping","final","addAttributeRenames","renames","length","attributeRenames","hasChanges","getUnsupported","getOperations","build","writeFiles"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"index.mjs","sources":["../../../../server/src/services/migration-builder/index.ts"],"sourcesContent":["import path from 'node:path';\n\nimport { contentTypes as contentTypesUtils } from '@strapi/utils';\nimport type { Core } from '@strapi/types';\n\n/**\n * The CTB-level attribute definition of the *new* side of a rename hop (the\n * `properties` the admin sends for `newName`). Only the storage-relevant keys\n * are inspected; see `isCompatibleRename`.\n */\nexport interface RenameAttributeDefinition {\n type?: string;\n relation?: string;\n target?: string;\n component?: string;\n repeatable?: boolean;\n customField?: string;\n targetAttribute?: string | null;\n inversedBy?: string;\n mappedBy?: string;\n configurable?: boolean;\n [key: string]: unknown;\n}\n\nexport interface RenameNames {\n oldName: string;\n newName: string;\n /**\n * Definition of the attribute under its new name, when known. Used to refuse\n * hops that also change the attribute's storage (e.g. `string` -> `integer`,\n * or a relation retargeted): renaming the column and letting schema sync\n * alter its type in place can fail on Postgres/MySQL, whereas the legacy\n * drop-and-recreate path is always safe.\n */\n newAttribute?: RenameAttributeDefinition;\n}\n\nexport type UnsupportedRenameReason =\n | 'model-not-found'\n | 'attribute-not-found'\n | 'unsupported-type'\n | 'type-changed'\n | 'target-occupied';\n\nexport interface UnsupportedRename {\n uid: string;\n oldName: string;\n newName: string;\n reason: UnsupportedRenameReason;\n}\n\n/**\n * Whether a relation definition has a counterpart on its target. The live\n * schema carries `inversedBy` / `mappedBy`; the CTB payload carries\n * `targetAttribute`.\n */\nconst isBidirectionalRelation = (attribute: RenameAttributeDefinition): boolean =>\n Boolean(attribute.inversedBy || attribute.mappedBy || attribute.targetAttribute);\n\n/**\n * Whether the storage of `oldAttribute` can host `newAttribute` after a plain\n * rename of its physical artifact. Anything else must go through the legacy\n * drop-and-recreate path, so the hop is reported as `type-changed`.\n *\n * `resolveType` maps a definition to its storage type. The builder passes one\n * that resolves custom fields (sent as `type: 'customField'` by the admin, but\n * already converted to their underlying type in the live schema).\n */\nexport const isCompatibleRename = (\n oldAttribute: RenameAttributeDefinition | undefined,\n newAttribute: RenameAttributeDefinition | undefined,\n resolveType: (attribute: RenameAttributeDefinition) => string | undefined = (attribute) =>\n attribute.type\n): boolean => {\n const oldType = oldAttribute ? resolveType(oldAttribute) : undefined;\n const newType = newAttribute ? resolveType(newAttribute) : undefined;\n\n // Without both definitions there is nothing to compare; the metadata-based\n // classification is the only guard we have.\n if (!oldAttribute || !newAttribute || !oldType || !newType) {\n return true;\n }\n\n if (oldType !== newType) {\n return false;\n }\n\n // A different custom field on the same underlying type is still a different\n // field.\n if (\n (oldAttribute.customField || newAttribute.customField) &&\n oldAttribute.customField !== newAttribute.customField\n ) {\n return false;\n }\n\n switch (newType) {\n case 'relation':\n // `manyWay` and a bidirectional `oneToMany` share `relation: 'oneToMany'`,\n // but switching between them moves join-table ownership.\n return (\n oldAttribute.relation === newAttribute.relation &&\n oldAttribute.target === newAttribute.target &&\n isBidirectionalRelation(oldAttribute) === isBidirectionalRelation(newAttribute)\n );\n case 'component':\n return (\n oldAttribute.component === newAttribute.component &&\n Boolean(oldAttribute.repeatable) === Boolean(newAttribute.repeatable)\n );\n default:\n return true;\n }\n};\n\nexport interface BuiltMigration {\n filename: string;\n content: string;\n}\n\n/**\n * How a renamed attribute maps to a physical database artifact, resolved from\n * `strapi.db.metadata` (the live, pre-rename schema). The `from` field is the\n * current physical identifier and moves forward at each hop so rename chains and\n * user-routed swaps replay verbatim.\n *\n * - `scalarColumn` / `joinColumn`: a column on the model's own table. Scalar\n * columns resolve names via `getColumnName`; relation join columns (`<field>_id`)\n * via `getJoinColumnAttributeIdName`.\n * - `joinTable`: a relation backed by a join/link table (the table name encodes\n * the owning attribute name).\n * - `component`: a component or dynamic zone — the attribute name is a *value* in\n * the per-type link table's `field` column, so it is an `UPDATE`, not DDL.\n * - `media`: like `component`, but stored in the shared `files_related_morphs`\n * table, so the `UPDATE` is additionally scoped by `related_type` (the uid).\n * - `skip`: recognised but needs no DB change (e.g. the inverse side of a\n * bidirectional relation — the join table is named from the owning side).\n * - `unsupported`: cannot be migrated automatically (polymorphic morph relations,\n * which are not creatable through the CTB UI anyway).\n */\ntype Resolved =\n | { kind: 'scalarColumn'; table: string; from: string }\n | { kind: 'joinColumn'; table: string; from: string }\n | { kind: 'joinTable'; from: string }\n | { kind: 'component'; table: string; fieldColumn: string; from: string }\n | {\n kind: 'media';\n table: string;\n fieldColumn: string;\n typeColumn: string;\n typeValue: string;\n from: string;\n }\n | { kind: 'skip' }\n | { kind: 'unsupported'; reason: UnsupportedRename['reason'] };\n\ninterface MigrationBuilderDeps {\n strapi: Core.Strapi;\n}\n\n/**\n * The database metadata shapes the builder reads, derived from `Core.Strapi`\n * so the Content-Type Builder does not depend on `@strapi/database` directly.\n */\ntype ModelMeta = NonNullable<ReturnType<Core.Strapi['db']['metadata']['get']>>;\n\n/**\n * A metadata attribute, widened with the relation/join keys the builder\n * inspects (the metadata union only declares them on some members).\n */\ntype AttributeMeta = ModelMeta['attributes'][string] & {\n relation?: string;\n mappedBy?: string;\n morphColumn?: unknown;\n joinColumn?: { name?: string };\n joinTable?: JoinTableMeta;\n};\n\ninterface JoinTableMeta {\n name?: string;\n on?: Record<string, unknown>;\n morphColumn?: { typeColumn?: { name?: string } };\n}\n\ntype SchemaModel = Parameters<typeof contentTypesUtils.getNonVisibleAttributes>[0];\n\n/**\n * Per-uid `origin -> current name` of every received hop, accepted or refused:\n * the logical field is the same field even when its data cannot be carried.\n */\nexport type AttributeRenamesMapping = Record<string, Record<string, string>>;\n\nconst MIGRATION_NAME = 'rename-fields';\n\nexport const createMigrationBuilder = ({ strapi }: MigrationBuilderDeps) => {\n const { db } = strapi;\n\n const migrationFileBuilder = db.migrations.createFileBuilder();\n const unsupported: UnsupportedRename[] = [];\n\n // Physical-name rules shared with the metadata loader, so the *new* side of a\n // rename is derived exactly as `db.metadata` will derive it after the reload.\n const { naming } = db.metadata;\n\n /**\n * The app's *source* migrations dir. Generated files always land here (see\n * `writeFiles`), and it is also the dir discovery reads from when\n * `useTypescriptMigrations` is off or no tsconfig `outDir` resolves.\n */\n const sourceMigrationsDir = () => path.join(strapi.dirs.app.root, 'database', 'migrations');\n\n let format: 'javascript' | 'typescript' | undefined;\n\n /**\n * Mirror the database's discovery decision (`Strapi.ts`): it reads from\n * `<outDir>/database/migrations` only when `useTypescriptMigrations` is on\n * *and* a tsconfig `outDir` resolves. In that case the source file must be\n * `.ts` so `tsc` carries it into `dist`. Otherwise discovery reads the source\n * dir and only loads `.js`, so a `.ts` file would never run.\n *\n * Memoised so the fallback warning is logged once per builder (both `build`\n * and `writeFiles` call this).\n */\n const getFormat = (): 'javascript' | 'typescript' => {\n if (format) {\n return format;\n }\n\n const useTSM = strapi.config.get('database.settings.useTypescriptMigrations') === true;\n const discoveryDir = db.config.settings.migrations?.dir;\n const discoversFromDist =\n typeof discoveryDir === 'string' &&\n path.resolve(discoveryDir) !== path.resolve(sourceMigrationsDir());\n\n if (useTSM && !discoversFromDist) {\n strapi.log.warn(\n 'database.settings.useTypescriptMigrations is enabled but no TypeScript outDir was resolved for this app; ' +\n 'writing the rename migration as JavaScript so it is discovered from database/migrations.'\n );\n }\n\n format = useTSM && discoversFromDist ? 'typescript' : 'javascript';\n return format;\n };\n\n // Artifacts \"in flight\" for the current save, i.e. produced by an earlier\n // rename hop in this same batch (e.g. the intermediate `tmp` field a user\n // routes a swap through). Keyed per uid by the *logical* field name the hop\n // produced; the value records how that field resolves to a physical artifact\n // and its current `from` identifier, so a continuation hop replays from the\n // right place instead of being treated as a brand-new, unknown attribute.\n const inFlight = new Map<string, Map<string, Resolved>>();\n\n // CTB-level definition of each in-flight field (per uid, by logical name), so\n // a continuation hop can still be checked for a storage change against the\n // definition the chain started from.\n const inFlightDefinitions = new Map<string, Map<string, RenameAttributeDefinition>>();\n\n // Logical names vacated by an earlier accepted hop of this batch (per uid). A\n // refused hop never vacates its source: the artifact stays live until schema\n // sync drops it. A hop may only target a name that is free: not live in the\n // pre-reload schema (unless an earlier accepted hop vacated it) and not\n // produced by an earlier hop still in flight. At migration time the schema-sync drop of a still-live field has\n // not happened yet, so renaming onto it would collide and the runtime guard\n // would silently skip the hop. Refusing it here surfaces the problem (e.g. a\n // truncated chain sent by a client) instead of losing data.\n const vacated = new Map<string, Set<string>>();\n\n const isTargetOccupied = (uid: string, newName: string): boolean => {\n if (inFlight.get(uid)?.has(newName)) {\n return true;\n }\n return Boolean(schemaAttributeOf(uid, newName)) && !(vacated.get(uid)?.has(newName) ?? false);\n };\n\n const trackVacated = (uid: string, oldName: string, newName: string): void => {\n let names = vacated.get(uid);\n if (!names) {\n names = new Set<string>();\n vacated.set(uid, names);\n }\n names.add(oldName);\n // The target is occupied again by the in-flight field.\n names.delete(newName);\n };\n\n const markInFlight = (uid: string, name: string, resolved: Resolved): void => {\n let entries = inFlight.get(uid);\n if (!entries) {\n entries = new Map<string, Resolved>();\n inFlight.set(uid, entries);\n }\n entries.set(name, resolved);\n };\n\n // Per uid, logical origin name -> current name, folded over every received hop.\n const origins = new Map<string, Map<string, string>>();\n\n const trackOrigin = (uid: string, oldName: string, newName: string): void => {\n let byOrigin = origins.get(uid);\n if (!byOrigin) {\n byOrigin = new Map<string, string>();\n origins.set(uid, byOrigin);\n }\n\n for (const [origin, current] of byOrigin) {\n if (current === oldName) {\n byOrigin.set(origin, newName);\n return;\n }\n }\n\n // A name that is already an origin but no longer current was re-occupied by\n // something this save did not rename; do not overwrite its logical field.\n if (!byOrigin.has(oldName)) {\n byOrigin.set(oldName, newName);\n }\n };\n\n const isMorphRelation = (attribute: AttributeMeta): boolean =>\n typeof attribute.relation === 'string' && attribute.relation.startsWith('morph');\n\n const schemaModelOf = (\n uid: string\n ): { attributes?: Record<string, RenameAttributeDefinition> } | undefined => {\n const contentTypes = strapi.contentTypes as Record<string, unknown> | undefined;\n const components = strapi.components as Record<string, unknown> | undefined;\n return (contentTypes?.[uid] ?? components?.[uid]) as\n { attributes?: Record<string, RenameAttributeDefinition> } | undefined;\n };\n\n const schemaAttributeOf = (uid: string, name: string): RenameAttributeDefinition | undefined =>\n schemaModelOf(uid)?.attributes?.[name];\n\n /**\n * The type an attribute is stored as. Custom fields are sent by the admin as\n * `type: 'customField'`, while the live schema already carries their\n * underlying type, so both sides are resolved through the registry.\n */\n const storageTypeOf = (attribute: RenameAttributeDefinition): string | undefined => {\n if (attribute.type !== 'customField' && typeof attribute.customField !== 'string') {\n return attribute.type;\n }\n\n try {\n const customField = strapi.get('custom-fields').get(attribute.customField as string) as\n { type?: string } | undefined;\n return customField?.type ?? attribute.type;\n } catch {\n // Unknown custom field (e.g. its plugin was removed).\n return attribute.type;\n }\n };\n\n const schemaTypeOf = (uid: string, name: string): string | undefined =>\n schemaAttributeOf(uid, name)?.type;\n\n // Resolves the shared upload morph table (e.g. `files_related_morphs`) and its\n // `related_type` column from the file model's `related` morph attribute. This\n // is the single table every media field across all types writes to, keyed by\n // (`field` = attribute name, `related_type` = owning uid).\n const resolveUploadMorphTable = ():\n { table: string; fieldColumn: string; typeColumn: string } | undefined => {\n if (!db.metadata.has('plugin::upload.file')) {\n return undefined;\n }\n const fileMeta = db.metadata.get('plugin::upload.file');\n const related = fileMeta.attributes?.related as\n (AttributeMeta & { morphColumn?: JoinTableMeta['morphColumn'] }) | undefined;\n const joinTable = related?.joinTable;\n const morphColumn = joinTable?.morphColumn ?? related?.morphColumn;\n if (!joinTable?.name || !morphColumn?.typeColumn?.name) {\n return undefined;\n }\n return {\n table: joinTable.name,\n fieldColumn: db.metadata.identifiers.FIELD_COLUMN,\n typeColumn: morphColumn.typeColumn.name,\n };\n };\n\n /**\n * Classifies the *first* hop of a rename by inspecting the live metadata, which\n * still reflects the pre-rename schema. Continuation hops never reach here —\n * they inherit their classification from the in-flight map.\n */\n const classifyMedia = (\n uid: string,\n oldName: string,\n joinTable: JoinTableMeta | undefined,\n upload: ReturnType<typeof resolveUploadMorphTable>\n ): Resolved | undefined => {\n // Media: the attribute name is a value in the shared `files_related_morphs`\n // `field` column, scoped by `related_type` (the owning uid). Detect it by\n // schema type OR by the join table being the shared upload table — the\n // latter guard is critical so a media field can never fall through to the\n // unscoped component branch and corrupt other types' media on the shared\n // table.\n const isMedia =\n schemaTypeOf(uid, oldName) === 'media' || (!!upload && joinTable?.name === upload.table);\n if (!isMedia) {\n return undefined;\n }\n if (!upload) {\n return { kind: 'unsupported', reason: 'unsupported-type' };\n }\n return {\n kind: 'media',\n table: upload.table,\n fieldColumn: upload.fieldColumn,\n typeColumn: upload.typeColumn,\n typeValue: uid,\n from: oldName,\n };\n };\n\n const classifyComponent = (\n oldName: string,\n joinTable: JoinTableMeta | undefined\n ): Resolved | undefined => {\n const on = joinTable?.on;\n if (!joinTable?.name || !on || typeof on !== 'object') {\n return undefined;\n }\n const fieldColumn = Object.keys(on).find((key) => on[key] === oldName);\n if (!fieldColumn) {\n return undefined;\n }\n return { kind: 'component', table: joinTable.name, fieldColumn, from: oldName };\n };\n\n const classifyRelation = (\n meta: ModelMeta,\n attribute: AttributeMeta,\n joinTable: JoinTableMeta | undefined\n ): Resolved => {\n // Polymorphic morph relations need shared-table handling and are not\n // creatable through the CTB UI, so they are left unsupported.\n if (isMorphRelation(attribute) || attribute.morphColumn) {\n return { kind: 'unsupported', reason: 'unsupported-type' };\n }\n\n // Join column on the owner's own table (`<field>_id`), e.g. useJoinTable:false.\n // The inverse side of a bidirectional join-column relation also carries a\n // `joinColumn` (pointing at `id`), but owns no column.\n if (attribute.joinColumn?.name && !joinTable) {\n if (attribute.mappedBy) {\n return { kind: 'skip' };\n }\n return { kind: 'joinColumn', table: meta.tableName, from: attribute.joinColumn.name };\n }\n\n if (joinTable?.name) {\n // The inverse side of a bidirectional relation: the join table is named\n // from the owning attribute, so renaming this side touches no artifact.\n if (attribute.mappedBy) {\n return { kind: 'skip' };\n }\n return { kind: 'joinTable', from: joinTable.name };\n }\n\n return { kind: 'unsupported', reason: 'unsupported-type' };\n };\n\n /**\n * Whether the schema lets users rename this attribute at all. System\n * attributes (`documentId`, `createdBy`, `locale`, `publishedAt`, review\n * workflow stages…) are also in the metadata and would otherwise be renamed\n * away, only for sync to re-add them empty.\n */\n const isRenamableAttribute = (uid: string, name: string): boolean => {\n const schemaAttribute = schemaAttributeOf(uid, name);\n // Same rule as payload validation applies to a hop's old name: `status` is\n // only reserved with draft and publish, and a legacy field may carry it.\n if (\n schemaAttribute?.configurable === false ||\n contentTypesUtils.isReservedAttributeName(name, { draftAndPublish: false })\n ) {\n return false;\n }\n\n const model = schemaModelOf(uid);\n return !contentTypesUtils.getNonVisibleAttributes(model as SchemaModel).includes(name);\n };\n\n const classify = (uid: string, oldName: string): Resolved => {\n if (!schemaAttributeOf(uid, oldName)) {\n return { kind: 'unsupported', reason: 'attribute-not-found' };\n }\n\n if (!isRenamableAttribute(uid, oldName)) {\n return { kind: 'unsupported', reason: 'unsupported-type' };\n }\n\n const meta = db.metadata.get(uid);\n const attribute = meta.attributes?.[oldName] as AttributeMeta | undefined;\n\n if (!attribute) {\n return { kind: 'unsupported', reason: 'attribute-not-found' };\n }\n\n const joinTable = attribute.joinTable;\n const upload = resolveUploadMorphTable();\n const media = classifyMedia(uid, oldName, joinTable, upload);\n if (media) {\n return media;\n }\n\n const component = classifyComponent(oldName, joinTable);\n if (component) {\n return component;\n }\n\n if (attribute.type === 'relation') {\n return classifyRelation(meta, attribute, joinTable);\n }\n\n // Plain scalar column on the model's own table.\n if ('columnName' in attribute && attribute.columnName) {\n return { kind: 'scalarColumn', table: meta.tableName, from: attribute.columnName };\n }\n\n return { kind: 'unsupported', reason: 'unsupported-type' };\n };\n\n /**\n * Computes the destination identifier for a resolved artifact given the new\n * field name, and the next in-flight state (with `from` advanced to `to`).\n */\n const advance = (uid: string, resolved: Resolved, oldName: string, newName: string): Resolved => {\n const meta = db.metadata.get(uid);\n const comment = `${uid}: rename field \"${oldName}\" -> \"${newName}\"`;\n\n switch (resolved.kind) {\n case 'scalarColumn':\n case 'joinColumn': {\n const to =\n resolved.kind === 'joinColumn'\n ? naming.joinColumnName(newName)\n : naming.columnName(newName);\n if (resolved.from !== to) {\n migrationFileBuilder.renameColumn({\n table: resolved.table,\n from: resolved.from,\n to,\n comment,\n });\n }\n return { ...resolved, from: to };\n }\n case 'joinTable': {\n const to = naming.joinTableName(meta.tableName, newName);\n if (resolved.from !== to) {\n migrationFileBuilder.renameTable({ from: resolved.from, to, comment });\n }\n return { ...resolved, from: to };\n }\n case 'component': {\n const to = newName;\n if (resolved.from !== to) {\n migrationFileBuilder.updateRows({\n table: resolved.table,\n guardColumn: resolved.fieldColumn,\n where: { [resolved.fieldColumn]: resolved.from },\n set: { [resolved.fieldColumn]: to },\n comment,\n });\n }\n return { ...resolved, from: to };\n }\n case 'media': {\n const to = newName;\n if (resolved.from !== to) {\n migrationFileBuilder.updateRows({\n table: resolved.table,\n guardColumn: resolved.fieldColumn,\n where: {\n [resolved.fieldColumn]: resolved.from,\n [resolved.typeColumn]: resolved.typeValue,\n },\n set: { [resolved.fieldColumn]: to },\n comment,\n });\n }\n return { ...resolved, from: to };\n }\n default:\n return resolved;\n }\n };\n\n /**\n * Records one rename hop exactly in the order the user performed it. Because the\n * Content-Type Builder forbids two fields sharing a name at any instant, the\n * recorded path is inherently collision-free: replaying each hop verbatim never\n * targets an occupied artifact, so no synthetic temporary name is ever needed\n * (a \"swap\" is already expressed by the user's own intermediate-name hop).\n */\n const addRename = (uid: string, { oldName, newName, newAttribute }: RenameNames): void => {\n // `metadata.get` throws when the model is unknown, so guard with `has` first.\n if (!db.metadata.has(uid)) {\n unsupported.push({ uid, oldName, newName, reason: 'model-not-found' });\n return;\n }\n\n trackOrigin(uid, oldName, newName);\n\n if (isTargetOccupied(uid, newName)) {\n unsupported.push({ uid, oldName, newName, reason: 'target-occupied' });\n // Keep the chain consistent so a later continuation hop stays silent. The\n // source is not vacated: its artifact was not moved.\n markInFlight(uid, newName, { kind: 'unsupported', reason: 'target-occupied' });\n return;\n }\n\n const entries = inFlight.get(uid);\n const definitions = inFlightDefinitions.get(uid);\n const oldAttribute = definitions?.get(oldName) ?? schemaAttributeOf(uid, oldName);\n let resolved = entries?.get(oldName) ?? classify(uid, oldName);\n\n // A rename that also changes the attribute's storage cannot be expressed as a\n // rename of the physical artifact: leave it to the drop-and-recreate path.\n if (\n resolved.kind !== 'unsupported' &&\n !isCompatibleRename(oldAttribute, newAttribute, storageTypeOf)\n ) {\n resolved = { kind: 'unsupported', reason: 'type-changed' };\n }\n\n if (newAttribute ?? oldAttribute) {\n let byName = inFlightDefinitions.get(uid);\n if (!byName) {\n byName = new Map();\n inFlightDefinitions.set(uid, byName);\n }\n byName.set(newName, (newAttribute ?? oldAttribute) as RenameAttributeDefinition);\n }\n\n if (resolved.kind === 'unsupported') {\n unsupported.push({ uid, oldName, newName, reason: resolved.reason });\n // Keep the chain consistent so a later continuation hop stays silent. The\n // source keeps its in-flight entry and is not vacated: its physical\n // artifact stays where it is until schema sync drops it.\n markInFlight(uid, newName, resolved);\n return;\n }\n\n // Accepted from here on: the source name is free and the field moves.\n entries?.delete(oldName);\n definitions?.delete(oldName);\n trackVacated(uid, oldName, newName);\n\n if (resolved.kind === 'skip') {\n markInFlight(uid, newName, resolved);\n return;\n }\n\n const next = advance(uid, resolved, oldName, newName);\n markInFlight(uid, newName, next);\n };\n\n return {\n addRenameAttribute(uid: string, names: RenameNames): void {\n addRename(uid, names);\n },\n\n /**\n * The composed `origin -> final` name of every schema attribute that\n * received hops in this save, per uid. Identity entries (`a -> b -> a`) and\n * origins that are not schema attributes are left out.\n */\n attributeRenamesMapping(): AttributeRenamesMapping {\n const mapping: AttributeRenamesMapping = {};\n\n for (const [uid, byOrigin] of origins) {\n for (const [origin, final] of byOrigin) {\n if (origin === final || !schemaAttributeOf(uid, origin)) {\n continue;\n }\n mapping[uid] ??= {};\n mapping[uid][origin] = final;\n }\n }\n\n return mapping;\n },\n\n /**\n * Adds the logical op that carries this save's renames to the stores keyed\n * by attribute name (admin field permissions, via handlers registered on\n * the database). Call it after every hop so it is the last operation.\n */\n addAttributeRenames(renames: AttributeRenamesMapping): void {\n if (Object.keys(renames).length === 0) {\n return;\n }\n\n migrationFileBuilder.attributeRenames({\n renames,\n comment:\n \"Update stores keyed by attribute name (admin field permissions) for this save's renames\",\n });\n },\n\n hasChanges(): boolean {\n return migrationFileBuilder.hasChanges();\n },\n\n getUnsupported(): UnsupportedRename[] {\n return [...unsupported];\n },\n\n getOperations() {\n return migrationFileBuilder.getOperations();\n },\n\n build(): BuiltMigration | null {\n return migrationFileBuilder.build({ name: MIGRATION_NAME, format: getFormat() });\n },\n\n async writeFiles(): Promise<string | null> {\n // Always write to the app's *source* migrations dir, never the database's\n // configured dir: when `useTypescriptMigrations` is enabled that points at\n // build output (e.g. `dist/database/migrations`), which is gitignored and\n // wiped on the next build, so the generated migration would not be a\n // portable record.\n const dir = sourceMigrationsDir();\n return migrationFileBuilder.writeFiles({ name: MIGRATION_NAME, format: getFormat(), dir });\n },\n };\n};\n\nexport type MigrationBuilder = ReturnType<typeof createMigrationBuilder>;\n"],"names":["isBidirectionalRelation","attribute","Boolean","inversedBy","mappedBy","targetAttribute","isCompatibleRename","oldAttribute","newAttribute","resolveType","type","oldType","undefined","newType","customField","relation","target","component","repeatable","MIGRATION_NAME","createMigrationBuilder","strapi","db","migrationFileBuilder","migrations","createFileBuilder","unsupported","naming","metadata","sourceMigrationsDir","path","join","dirs","app","root","format","getFormat","useTSM","config","get","discoveryDir","settings","dir","discoversFromDist","resolve","log","warn","inFlight","Map","inFlightDefinitions","vacated","isTargetOccupied","uid","newName","has","schemaAttributeOf","trackVacated","oldName","names","Set","set","add","delete","markInFlight","name","resolved","entries","origins","trackOrigin","byOrigin","origin","current","isMorphRelation","startsWith","schemaModelOf","contentTypes","components","attributes","storageTypeOf","schemaTypeOf","resolveUploadMorphTable","fileMeta","related","joinTable","morphColumn","typeColumn","table","fieldColumn","identifiers","FIELD_COLUMN","classifyMedia","upload","isMedia","kind","reason","typeValue","from","classifyComponent","on","Object","keys","find","key","classifyRelation","meta","joinColumn","tableName","isRenamableAttribute","schemaAttribute","configurable","contentTypesUtils","isReservedAttributeName","draftAndPublish","model","getNonVisibleAttributes","includes","classify","media","columnName","advance","comment","to","joinColumnName","renameColumn","joinTableName","renameTable","updateRows","guardColumn","where","addRename","push","definitions","byName","next","addRenameAttribute","attributeRenamesMapping","mapping","final","addAttributeRenames","renames","length","attributeRenames","hasChanges","getUnsupported","getOperations","build","writeFiles"],"mappings":"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"}
|
|
@@ -6,6 +6,7 @@ var index$1 = require('./schema-builder/index.js');
|
|
|
6
6
|
var index = require('./migration-builder/index.js');
|
|
7
7
|
var schemaMutation = require('./schema-mutation.js');
|
|
8
8
|
var index$2 = require('../utils/index.js');
|
|
9
|
+
var uidTarget = require('../utils/uid-target.js');
|
|
9
10
|
var schema = require('../controllers/validation/schema.js');
|
|
10
11
|
var contentTypes = require('./content-types.js');
|
|
11
12
|
|
|
@@ -45,7 +46,7 @@ const removeDeletedUIDTargetFieldsOnUpdates = (schema)=>{
|
|
|
45
46
|
contentType.attributes.forEach((attribute)=>{
|
|
46
47
|
if (attribute.action === 'update') {
|
|
47
48
|
const { properties } = attribute;
|
|
48
|
-
if (properties.type === 'uid' && properties.targetField && !contentType.attributes.
|
|
49
|
+
if (properties.type === 'uid' && properties.targetField && !contentType.attributes.some((attr)=>attr.action !== 'delete' && attr.name === properties.targetField)) {
|
|
49
50
|
properties.targetField = undefined;
|
|
50
51
|
}
|
|
51
52
|
}
|
|
@@ -104,6 +105,37 @@ const removeDeletedUIDTargetFieldsOnUpdates = (schema)=>{
|
|
|
104
105
|
});
|
|
105
106
|
});
|
|
106
107
|
};
|
|
108
|
+
/**
|
|
109
|
+
* Keeps a uid field attached to its target when that target is renamed in this
|
|
110
|
+
* save. A `targetField` that names a saved (non-deleted) attribute of the
|
|
111
|
+
* payload is left alone: the caller already resolved it. When the renamed
|
|
112
|
+
* target is not a string or text field (custom fields are resolved to their
|
|
113
|
+
* underlying type), the uid is detached.
|
|
114
|
+
*/ const renameUIDTargetFieldsOnUpdates = (schema)=>{
|
|
115
|
+
schema.contentTypes.forEach((contentType)=>{
|
|
116
|
+
if (contentType.action !== 'update' || !Array.isArray(contentType.renames)) {
|
|
117
|
+
return;
|
|
118
|
+
}
|
|
119
|
+
const finalNames = composeRenames(contentType.renames);
|
|
120
|
+
const savedAttributes = contentType.attributes.filter((attr)=>attr.action !== 'delete');
|
|
121
|
+
const saved = new Set(savedAttributes.map((attr)=>attr.name));
|
|
122
|
+
contentType.attributes.forEach((attribute)=>{
|
|
123
|
+
if (attribute.action !== 'update') {
|
|
124
|
+
return;
|
|
125
|
+
}
|
|
126
|
+
const { properties } = attribute;
|
|
127
|
+
if (properties.type !== 'uid' || !properties.targetField) {
|
|
128
|
+
return;
|
|
129
|
+
}
|
|
130
|
+
const finalName = finalNames.get(properties.targetField);
|
|
131
|
+
if (!finalName || saved.has(properties.targetField)) {
|
|
132
|
+
return;
|
|
133
|
+
}
|
|
134
|
+
const target = savedAttributes.find((attr)=>attr.name === finalName);
|
|
135
|
+
properties.targetField = target && uidTarget.isValidUidTarget(target.properties) ? finalName : undefined;
|
|
136
|
+
});
|
|
137
|
+
});
|
|
138
|
+
};
|
|
107
139
|
const getAttributeRenameMigrationMode = ()=>{
|
|
108
140
|
return strapi.plugin('content-type-builder').config('renameMigrations.attributes', 'prompt-before-save');
|
|
109
141
|
};
|
|
@@ -413,6 +445,7 @@ const updateSchema = async (schema)=>{
|
|
|
413
445
|
contentTypes$1.filter((contentType)=>contentType.action === 'delete').forEach((contentType)=>contentTypes.assertCTBOwnedApplicationContentType(contentType.uid));
|
|
414
446
|
// pre-process data
|
|
415
447
|
removeEmptyDefaultsOnUpdates(schema);
|
|
448
|
+
renameUIDTargetFieldsOnUpdates(schema);
|
|
416
449
|
removeDeletedUIDTargetFieldsOnUpdates(schema);
|
|
417
450
|
renameConditionVarsOnUpdates(schema);
|
|
418
451
|
const upsertedUids = new Map();
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"schema.js","sources":["../../../server/src/services/schema.ts"],"sourcesContent":["import { contentTypes as contentTypesUtils, errors } from '@strapi/utils';\nimport { mapValues } from 'lodash';\n\nimport type { Schema } from '@strapi/types';\n\nimport createBuilder from './schema-builder';\nimport { createMigrationBuilder } from './migration-builder';\nimport type {\n AttributeRenamesMapping,\n RenameAttributeDefinition,\n UnsupportedRename,\n} from './migration-builder';\nimport { finalizeSchemaMutation, rollbackSchemaMutation } from './schema-mutation';\nimport { getService } from '../utils';\nimport { validateUpdateSchema } from '../controllers/validation/schema';\nimport type { Schema as CTBSchema } from '../controllers/validation/schema';\nimport type { AttributeRenameMigrationMode } from '../config';\nimport {\n assertCTBOwnedApplicationContentType,\n getRestrictRelationsTo,\n isContentTypeVisible,\n} from './content-types';\nimport type { CoreContentStructureService } from './content-structure';\n\ntype ContentTypeKind = 'collectionType' | 'singleType';\n\nconst removeEmptyDefaultsOnUpdates = (schema: CTBSchema) => {\n schema.components.forEach((component) => {\n if (component.action === 'delete') {\n return;\n }\n\n component.attributes.forEach((attribute) => {\n if (attribute.action === 'update') {\n const { properties } = attribute;\n\n if ('default' in properties && properties.default === '') {\n properties.default = undefined;\n }\n }\n });\n });\n\n schema.contentTypes.forEach((contentType) => {\n if (contentType.action === 'delete') {\n return;\n }\n\n contentType.attributes.forEach((attribute) => {\n if (attribute.action === 'update') {\n const { properties } = attribute;\n\n if ('default' in properties && properties.default === '') {\n properties.default = undefined;\n }\n }\n });\n });\n};\n\nconst removeDeletedUIDTargetFieldsOnUpdates = (schema: CTBSchema) => {\n schema.contentTypes.forEach((contentType) => {\n if (contentType.action === 'delete') {\n return;\n }\n\n contentType.attributes.forEach((attribute) => {\n if (attribute.action === 'update') {\n const { properties } = attribute;\n\n if (\n properties.type === 'uid' &&\n properties.targetField &&\n !contentType.attributes.find((attr) => attr.name === properties.targetField)\n ) {\n properties.targetField = undefined;\n }\n }\n });\n });\n};\n\n/**\n * Composes the ordered rename hops of an updated type into an origin -> final\n * name map (`a -> b, b -> c` gives `a -> c`).\n */\nconst composeRenames = (hops: { oldName?: string; newName?: string }[]): Map<string, string> => {\n const originByName = new Map<string, string>();\n\n hops.forEach(({ oldName, newName }) => {\n if (!oldName || !newName || oldName === newName) {\n return;\n }\n\n const origin = originByName.get(oldName) ?? oldName;\n originByName.delete(oldName);\n originByName.set(newName, origin);\n });\n\n return new Map([...originByName].map(([name, origin]) => [origin, name]));\n};\n\n/**\n * Makes field conditions follow the renames of this save: a condition whose\n * `var` still names the origin of a rename is pointed at the field's final name.\n *\n * A `var` that names an attribute of the saved type is left alone: the caller\n * already rewrote it, or (in a swap) it cannot be told apart from one that was.\n */\nconst renameConditionVarsOnUpdates = (schema: CTBSchema) => {\n type AttributeEntry = {\n action?: string;\n name?: string;\n properties?: { conditions?: { visible?: Record<string, unknown> } };\n };\n type Entry = {\n action?: string;\n renames?: { oldName?: string; newName?: string }[];\n attributes?: AttributeEntry[];\n };\n\n const entries = [\n ...(schema.contentTypes as unknown as Entry[]),\n ...(schema.components as unknown as Entry[]),\n ];\n\n entries.forEach((entry) => {\n if (entry.action !== 'update' || !Array.isArray(entry.renames)) {\n return;\n }\n\n const renames = composeRenames(entry.renames);\n const savedAttributes = (entry.attributes ?? []).filter(\n (attribute) => attribute.action !== 'delete'\n );\n const saved = new Set(savedAttributes.map((attribute) => attribute.name));\n\n savedAttributes.forEach((attribute) => {\n Object.values(attribute.properties?.conditions?.visible ?? {}).forEach((rule) => {\n const fieldVar: unknown = Array.isArray(rule) ? rule[0] : undefined;\n\n if (\n typeof fieldVar !== 'object' ||\n fieldVar === null ||\n !('var' in fieldVar) ||\n typeof fieldVar.var !== 'string' ||\n saved.has(fieldVar.var)\n ) {\n return;\n }\n\n const finalName = renames.get(fieldVar.var);\n\n if (finalName !== undefined && saved.has(finalName)) {\n fieldVar.var = finalName;\n }\n });\n });\n });\n};\n\ninterface CollectedRename {\n uid: string;\n oldName: string;\n newName: string;\n newAttribute?: RenameAttributeDefinition;\n}\n\nconst getAttributeRenameMigrationMode = (): AttributeRenameMigrationMode => {\n return strapi\n .plugin('content-type-builder')\n .config('renameMigrations.attributes', 'prompt-before-save');\n};\n\n/**\n * Collects attribute renames from the update-schema payload. The admin sends an\n * ordered `renames` array per updated content-type / component: the exact path\n * of rename hops the user performed (e.g. `a -> tmp`, `b -> a`, `tmp -> b` for a\n * swap). Order is preserved so the generated migration can replay each hop\n * verbatim — which is inherently collision-free because the Content-Type Builder\n * never allows two fields to share a name at any instant.\n */\nconst collectRenames = (schema: CTBSchema): CollectedRename[] => {\n const renames: CollectedRename[] = [];\n\n type RenameHop = { oldName?: string; newName?: string };\n type AttributeEntry = { action?: string; name?: string; properties?: RenameAttributeDefinition };\n type RenameAwareEntry = {\n action?: string;\n uid: string;\n renames?: RenameHop[];\n attributes?: AttributeEntry[];\n };\n\n const collectFrom = (entries: RenameAwareEntry[]) => {\n entries\n .filter((entry) => entry.action === 'update' && Array.isArray(entry.renames))\n .forEach((entry) => {\n // Only the last hop onto a name produces the field that carries the\n // final definition: in `a -> b, b -> c, x -> b` the first `b` is `a`'s\n // intermediate name and the final `b` is `x`'s field.\n const lastHopByNewName = new Map<string, number>();\n entry.renames!.forEach((hop, index) => {\n if (hop.newName) {\n lastHopByNewName.set(hop.newName, index);\n }\n });\n\n entry.renames!.forEach((hop, index) => {\n if (hop.oldName && hop.newName && hop.oldName !== hop.newName) {\n // The definition the field ends up with in this save, so the builder\n // can refuse hops that also change the field's storage (type,\n // relation target, component…). Intermediate hops of a chain get no\n // definition and are checked when the chain completes.\n const newAttribute =\n lastHopByNewName.get(hop.newName) === index\n ? entry.attributes?.find(\n (attribute) => attribute.action !== 'delete' && attribute.name === hop.newName\n )?.properties\n : undefined;\n\n renames.push({\n uid: entry.uid,\n oldName: hop.oldName,\n newName: hop.newName,\n newAttribute,\n });\n }\n });\n });\n };\n\n collectFrom(schema.contentTypes as unknown as RenameAwareEntry[]);\n collectFrom(schema.components as unknown as RenameAwareEntry[]);\n\n return renames;\n};\n\n/**\n * Drops renames whose final name is not an attribute after this save (it was\n * deleted in the same save), so no store is pointed at a field that is gone.\n */\nconst keepSavedAttributes = (\n schema: CTBSchema,\n mapping: AttributeRenamesMapping\n): AttributeRenamesMapping => {\n type Entry = { action?: string; uid: string; attributes?: { action?: string; name?: string }[] };\n const entries = [\n ...(schema.contentTypes as unknown as Entry[]),\n ...(schema.components as unknown as Entry[]),\n ];\n\n const result: AttributeRenamesMapping = {};\n\n for (const [uid, renames] of Object.entries(mapping)) {\n const entry = entries.find((candidate) => candidate.uid === uid);\n const saved = new Set(\n (entry?.attributes ?? [])\n .filter((attribute) => attribute.action !== 'delete' && attribute.name)\n .map((attribute) => attribute.name as string)\n );\n\n for (const [origin, final] of Object.entries(renames)) {\n if (saved.has(final)) {\n result[uid] ??= {};\n result[uid][origin] = final;\n }\n }\n }\n\n return result;\n};\n\nconst describeUnsupportedReason = (reason: UnsupportedRename['reason']): string => {\n switch (reason) {\n case 'type-changed':\n return 'the field type, relation or component also changed';\n case 'unsupported-type':\n return 'the field type cannot be migrated (e.g. polymorphic relation)';\n case 'attribute-not-found':\n return 'the field is not in the current schema';\n case 'target-occupied':\n return 'the target field still exists in the current schema';\n case 'model-not-found':\n default:\n return 'the type is not in the current schema';\n }\n};\n\n/**\n * Generates a single data-preserving rename migration for the accepted renames\n * in this save. Must run before the server reloads, while `strapi.db.metadata`\n * still reflects the old (pre-rename) schema. Resolves to the written file's\n * path (so a failed save can remove it), or `null` when nothing was written.\n */\nconst generateRenameMigrations = async (schema: CTBSchema): Promise<string | null> => {\n // In prompt modes the admin strips refused renames before sending the payload.\n if (getAttributeRenameMigrationMode() === 'never') {\n return null;\n }\n\n const renames = collectRenames(schema);\n if (renames.length === 0) {\n return null;\n }\n\n const migrationBuilder = createMigrationBuilder({ strapi });\n\n for (const { uid, oldName, newName, newAttribute } of renames) {\n migrationBuilder.addRenameAttribute(uid, { oldName, newName, newAttribute });\n }\n\n const attributeRenames = keepSavedAttributes(schema, migrationBuilder.attributeRenamesMapping());\n if (Object.keys(attributeRenames).length > 0) {\n migrationBuilder.addAttributeRenames(attributeRenames);\n }\n\n const unsupported = migrationBuilder.getUnsupported();\n if (unsupported.length > 0) {\n const fields = unsupported\n .map((u) => `${u.uid}.${u.oldName} (${describeUnsupportedReason(u.reason)})`)\n .join(', ');\n strapi.log.warn(\n `[content-type-builder] Could not generate a rename migration for ${unsupported.length} field(s): ${fields}. Data in these fields may not be preserved.`\n );\n }\n\n if (migrationBuilder.hasChanges()) {\n return migrationBuilder.writeFiles();\n }\n\n return null;\n};\n\n/**\n * Renames a single attribute on a content-type or component and generates the\n * data-preserving migration in one step. Used by the `strapi rename:field` CLI\n * command so scripted / non-UI workflows get the same behaviour as the admin.\n *\n * It reuses the regular `updateSchema` path (and therefore the same rename\n * resolver via `generateRenameMigrations`), so the migration is resolved against\n * the pre-reload `strapi.db.metadata` exactly like the admin save. The caller is\n * responsible for not reloading before this resolves (the CLI simply exits).\n *\n * Unlike the admin, there is no one to confirm a data-losing rename, so it\n * refuses before touching the schema when the rename cannot be migrated.\n */\nexport const renameAttribute = async (\n uid: string,\n oldName: string,\n newName: string\n): Promise<void> => {\n const { ApplicationError } = errors;\n\n if (!oldName || !newName) {\n throw new ApplicationError('Both an old and a new attribute name are required');\n }\n\n if (oldName === newName) {\n throw new ApplicationError(`Cannot rename \"${oldName}\" to itself`);\n }\n\n if (getAttributeRenameMigrationMode() === 'never') {\n throw new ApplicationError(\n 'Rename migrations are disabled (`renameMigrations.attributes: never`); rename the field in the Content-Type Builder instead'\n );\n }\n\n const contentType = (strapi.contentTypes as Record<string, any>)[uid];\n const component = (strapi.components as Record<string, any>)[uid];\n const model = contentType ?? component;\n\n if (!model) {\n throw new ApplicationError(`No content-type or component found for uid \"${uid}\"`);\n }\n\n if (!model.attributes?.[oldName]) {\n throw new ApplicationError(`Attribute \"${oldName}\" does not exist on \"${uid}\"`);\n }\n\n if (model.attributes?.[newName]) {\n throw new ApplicationError(`Attribute \"${newName}\" already exists on \"${uid}\"`);\n }\n\n // Reuse the formatted, CTB-visible attributes (same shape the admin sends) so\n // the schema edit matches an admin save and the renamed key is the only change.\n const formattedSchema = await getSchema();\n const isComponent = Boolean(component);\n const entry = isComponent\n ? (formattedSchema.components as Record<string, any>)[uid]\n : (formattedSchema.contentTypes as Record<string, any>)[uid];\n\n // Custom fields are exposed with their underlying type; the admin sends them\n // back as `customField` so the schema file keeps them as custom fields.\n const toPayloadProperties = (properties: Record<string, any>) =>\n properties.customField ? { ...properties, type: 'customField' } : properties;\n\n const attributes = entry.attributes.map(({ name, ...properties }: Record<string, any>) => ({\n action: 'update',\n name: name === oldName ? newName : name,\n properties: toPayloadProperties(properties),\n }));\n\n // Dry run: the field keeps its definition, so only the rename itself can be\n // refused (system attribute, unsupported relation, occupied target…).\n const { name: _name, ...oldProperties } = entry.attributes.find(\n (attribute: Record<string, any>) => attribute.name === oldName\n ) ?? { name: oldName };\n const probe = createMigrationBuilder({ strapi });\n probe.addRenameAttribute(uid, {\n oldName,\n newName,\n newAttribute: toPayloadProperties(oldProperties),\n });\n\n const refused = probe.getUnsupported();\n if (refused.length > 0) {\n throw new ApplicationError(\n `Cannot rename \"${oldName}\" on \"${uid}\" without losing its data: ${refused\n .map(({ reason }) => describeUnsupportedReason(reason))\n .join(', ')}`\n );\n }\n\n const renames = [{ oldName, newName }];\n\n const payload = isComponent\n ? {\n contentTypes: [],\n components: [\n {\n action: 'update',\n uid,\n category: model.category,\n displayName: model.info?.displayName,\n icon: model.info?.icon,\n description: model.info?.description,\n pluginOptions: model.pluginOptions,\n renames,\n attributes,\n },\n ],\n }\n : {\n contentTypes: [\n {\n action: 'update',\n uid,\n kind: model.kind,\n displayName: model.info?.displayName,\n description: model.info?.description,\n draftAndPublish: Boolean(model.options?.draftAndPublish),\n options: model.options,\n pluginOptions: model.pluginOptions,\n renames,\n attributes,\n },\n ],\n components: [],\n };\n\n // Same checks as an admin save (name rules, reserved names, snake-case\n // uniqueness: `fooBar` next to an existing `foo_bar` would share a column).\n const { data } = await validateUpdateSchema({ data: payload });\n\n await updateSchema(data as CTBSchema);\n};\n\nconst formatAttributes = (model: any) => {\n const { getVisibleAttributes } = contentTypesUtils;\n\n // only get attributes that can be seen in the CTB\n return getVisibleAttributes(model).map((key) => {\n return { ...formatAttribute(model.attributes[key]), name: key };\n });\n};\n\nexport const formatAttribute = (attribute: Schema.Attribute.AnyAttribute & Record<string, any>) => {\n if (attribute.type === 'relation') {\n return {\n ...attribute,\n targetAttribute: attribute.inversedBy || attribute.mappedBy || null,\n // Explicitly preserve conditions if they exist\n ...(attribute.conditions && { conditions: attribute.conditions }),\n };\n }\n\n return attribute;\n};\n\nexport const getSchema = async () => {\n const contentTypes = mapValues(strapi.contentTypes, (contentType) => {\n const {\n uid,\n options,\n globalId,\n pluginOptions,\n kind,\n modelName,\n plugin,\n collectionName,\n info,\n modelType,\n } = contentType;\n\n return {\n uid,\n modelName,\n kind,\n globalId,\n options,\n pluginOptions,\n plugin,\n collectionName,\n info,\n modelType,\n attributes: formatAttributes(contentType),\n visible: isContentTypeVisible(contentType),\n restrictRelationsTo: getRestrictRelationsTo(contentType),\n };\n });\n\n const components = mapValues(strapi.components, (component) => {\n const { uid, globalId, modelName, collectionName, info, category, modelType } = component;\n\n return {\n uid,\n modelName,\n globalId,\n modelType,\n collectionName,\n category,\n info,\n attributes: formatAttributes(component),\n };\n });\n\n const coreContentStructure: CoreContentStructureService = strapi.get('content-structure');\n const contentStructure = await coreContentStructure.getCleanedFile();\n\n return {\n contentStructure,\n contentTypes,\n components,\n settings: {\n renameMigrations: {\n attributes: getAttributeRenameMigrationMode(),\n },\n },\n };\n};\n\nexport const updateSchema = async (schema: CTBSchema) => {\n const builder = createBuilder();\n const apiHandler = getService('api-handler') as typeof import('./api-handler');\n\n const { components, contentTypes, contentStructure } = schema;\n\n // Reject protected/plugin deletes before builders, API backups, or folder reconciliation can\n // mutate anything. This is the server-side invariant for crafted update requests.\n contentTypes\n .filter((contentType) => contentType.action === 'delete')\n .forEach((contentType) => assertCTBOwnedApplicationContentType(contentType.uid));\n\n // pre-process data\n removeEmptyDefaultsOnUpdates(schema);\n removeDeletedUIDTargetFieldsOnUpdates(schema);\n renameConditionVarsOnUpdates(schema);\n\n const upsertedUids = new Map<string, ContentTypeKind>();\n const deletedUids = new Set<string>();\n const generatedApiNames: string[] = [];\n const backedUpApiUids: string[] = [];\n let schemaAlreadyRolledBack = false;\n let migrationFilePath: string | null = null;\n const APIsToDelete = contentTypes\n .filter((contentType) => contentType.action === 'delete')\n .map((contentType) => contentType.uid);\n\n try {\n for (const contentType of contentTypes) {\n if (contentType.action === 'create') {\n upsertedUids.set(contentType.uid, contentType.kind ?? 'collectionType');\n } else if (contentType.action === 'update' && contentType.kind) {\n // A kind switch in the same save must override the registry's stale kind,\n // otherwise a folder assignment into the new section fails validation.\n upsertedUids.set(contentType.uid, contentType.kind);\n } else if (contentType.action === 'delete') {\n deletedUids.add(contentType.uid);\n }\n }\n\n // Validate folder references before anything is written. This will throw if invalid.\n getService('content-structure').validateFromUpdate({\n incomingStructure: contentStructure,\n upsertedUids,\n deletedUids,\n });\n\n // we pre create empty typesk\n for (const contentType of contentTypes) {\n if (contentType.action === 'create') {\n builder.createContentType({\n ...contentType,\n attributes: {},\n });\n }\n }\n\n // we pre create empty types\n for (const component of components) {\n if (component.action === 'create') {\n builder.createComponent({\n ...component,\n attributes: {},\n });\n }\n }\n\n for (const contentType of contentTypes) {\n const { action, uid } = contentType;\n\n if (action === 'create') {\n builder.createContentTypeAttributes(\n uid,\n contentType.attributes.reduce((acc: any, attr: any) => {\n acc[attr.name] = attr.properties;\n return acc;\n }, {})\n );\n\n if (!contentType.plugin) {\n // Track before generation because a generator failure can leave a partial skeleton.\n generatedApiNames.push(contentType.singularName);\n await getService('content-types').generateAPI({\n displayName: contentType!.displayName,\n singularName: contentType!.singularName,\n pluralName: contentType!.pluralName,\n kind: contentType!.kind,\n });\n }\n }\n\n if (action === 'update') {\n builder.editContentType({\n ...contentType,\n attributes: contentType.attributes.reduce((acc: any, attr: any) => {\n if (attr.action === 'delete') {\n return acc;\n }\n\n acc[attr.name] = attr.properties;\n return acc;\n }, {}),\n });\n }\n\n if (action === 'delete') {\n builder.deleteContentType(uid);\n await apiHandler.backup(uid);\n backedUpApiUids.push(uid);\n }\n }\n\n for (const component of components) {\n const { action, uid } = component;\n\n if (action === 'create') {\n builder.createComponentAttributes(\n uid,\n component.attributes.reduce((acc: any, attr: any) => {\n acc[attr.name] = attr.properties;\n return acc;\n }, {})\n );\n }\n\n if (action === 'update') {\n builder.editComponent({\n ...component,\n attributes: component.attributes.reduce((acc: any, attr: any) => {\n if (attr.action === 'delete') {\n return acc;\n }\n\n acc[attr.name] = attr.properties;\n return acc;\n }, {}),\n });\n }\n\n if (action === 'delete') {\n builder.deleteComponent(uid);\n }\n }\n\n // run sanity checks on the schema\n // Relations target existing types\n // Bidirectional relation have their counterpart in the schema\n // Components target existing components\n // Nested components target existing components\n // Dynamic zones target existing components\n\n // Generate rename migrations before reloading, while strapi.db.metadata still\n // reflects the pre-rename schema (the controller triggers the reload after this).\n migrationFilePath = await generateRenameMigrations(schema);\n\n const schemaFilesWritten = await builder.writeFiles();\n\n if (!schemaFilesWritten) {\n schemaAlreadyRolledBack = true;\n throw new errors.ApplicationError('Invalid schema edition');\n }\n\n for (const uid of APIsToDelete) {\n await apiHandler.clear(uid, { preserveBackup: true });\n }\n\n // Commit the single folder file last. Every preceding filesystem mutation can be restored.\n await getService('content-structure').commitFromUpdate({\n incomingStructure: contentStructure,\n deletedUids,\n });\n } catch (error) {\n await rollbackSchemaMutation({\n builder,\n apiHandler,\n backedUpApiUids,\n generatedApiNames,\n schemaAlreadyRolledBack,\n migrationFilePath,\n });\n\n throw error;\n }\n\n // Backup cleanup is deliberately outside the compensating boundary: at this point all\n // user-visible artifacts, including groups.json, have committed.\n for (const error of await finalizeSchemaMutation({ apiHandler, backedUpApiUids })) {\n strapi.log.error(error);\n }\n\n for (const contentType of contentTypes) {\n if (contentType.action === 'delete') {\n strapi.eventHub.emit('content-type.delete', {\n contentType: builder.contentTypes.get(contentType.uid),\n });\n }\n\n if (contentType.action === 'update') {\n strapi.eventHub.emit('content-type.update', {\n contentType: builder.contentTypes.get(contentType.uid),\n });\n }\n\n if (contentType.action === 'create') {\n strapi.eventHub.emit('content-type.create', {\n contentType: builder.contentTypes.get(contentType.uid),\n });\n }\n }\n\n for (const component of components) {\n if (component.action === 'delete') {\n strapi.eventHub.emit('component.delete', {\n component: builder.components.get(component.uid),\n });\n }\n\n if (component.action === 'update') {\n strapi.eventHub.emit('component.update', {\n component: builder.components.get(component.uid),\n });\n }\n\n if (component.action === 'create') {\n strapi.eventHub.emit('component.create', {\n component: builder.components.get(component.uid),\n });\n }\n }\n};\n"],"names":["removeEmptyDefaultsOnUpdates","schema","components","forEach","component","action","attributes","attribute","properties","default","undefined","contentTypes","contentType","removeDeletedUIDTargetFieldsOnUpdates","type","targetField","find","attr","name","composeRenames","hops","originByName","Map","oldName","newName","origin","get","delete","set","map","renameConditionVarsOnUpdates","entries","entry","Array","isArray","renames","savedAttributes","filter","saved","Set","Object","values","conditions","visible","rule","fieldVar","var","has","finalName","getAttributeRenameMigrationMode","strapi","plugin","config","collectRenames","collectFrom","lastHopByNewName","hop","index","newAttribute","push","uid","keepSavedAttributes","mapping","result","candidate","final","describeUnsupportedReason","reason","generateRenameMigrations","length","migrationBuilder","createMigrationBuilder","addRenameAttribute","attributeRenames","attributeRenamesMapping","keys","addAttributeRenames","unsupported","getUnsupported","fields","u","join","log","warn","hasChanges","writeFiles","renameAttribute","ApplicationError","errors","model","formattedSchema","getSchema","isComponent","Boolean","toPayloadProperties","customField","_name","oldProperties","probe","refused","payload","category","displayName","info","icon","description","pluginOptions","kind","draftAndPublish","options","data","validateUpdateSchema","updateSchema","formatAttributes","getVisibleAttributes","contentTypesUtils","key","formatAttribute","targetAttribute","inversedBy","mappedBy","mapValues","globalId","modelName","collectionName","modelType","isContentTypeVisible","restrictRelationsTo","getRestrictRelationsTo","coreContentStructure","contentStructure","getCleanedFile","settings","renameMigrations","builder","createBuilder","apiHandler","getService","assertCTBOwnedApplicationContentType","upsertedUids","deletedUids","generatedApiNames","backedUpApiUids","schemaAlreadyRolledBack","migrationFilePath","APIsToDelete","add","validateFromUpdate","incomingStructure","createContentType","createComponent","createContentTypeAttributes","reduce","acc","singularName","generateAPI","pluralName","editContentType","deleteContentType","backup","createComponentAttributes","editComponent","deleteComponent","schemaFilesWritten","clear","preserveBackup","commitFromUpdate","error","rollbackSchemaMutation","finalizeSchemaMutation","eventHub","emit"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"schema.js","sources":["../../../server/src/services/schema.ts"],"sourcesContent":["import { contentTypes as contentTypesUtils, errors } from '@strapi/utils';\nimport { mapValues } from 'lodash';\n\nimport type { Schema } from '@strapi/types';\n\nimport createBuilder from './schema-builder';\nimport { createMigrationBuilder } from './migration-builder';\nimport type {\n AttributeRenamesMapping,\n RenameAttributeDefinition,\n UnsupportedRename,\n} from './migration-builder';\nimport { finalizeSchemaMutation, rollbackSchemaMutation } from './schema-mutation';\nimport { getService } from '../utils';\nimport { isValidUidTarget } from '../utils/uid-target';\nimport { validateUpdateSchema } from '../controllers/validation/schema';\nimport type { Schema as CTBSchema } from '../controllers/validation/schema';\nimport type { AttributeRenameMigrationMode } from '../config';\nimport {\n assertCTBOwnedApplicationContentType,\n getRestrictRelationsTo,\n isContentTypeVisible,\n} from './content-types';\nimport type { CoreContentStructureService } from './content-structure';\n\ntype ContentTypeKind = 'collectionType' | 'singleType';\n\nconst removeEmptyDefaultsOnUpdates = (schema: CTBSchema) => {\n schema.components.forEach((component) => {\n if (component.action === 'delete') {\n return;\n }\n\n component.attributes.forEach((attribute) => {\n if (attribute.action === 'update') {\n const { properties } = attribute;\n\n if ('default' in properties && properties.default === '') {\n properties.default = undefined;\n }\n }\n });\n });\n\n schema.contentTypes.forEach((contentType) => {\n if (contentType.action === 'delete') {\n return;\n }\n\n contentType.attributes.forEach((attribute) => {\n if (attribute.action === 'update') {\n const { properties } = attribute;\n\n if ('default' in properties && properties.default === '') {\n properties.default = undefined;\n }\n }\n });\n });\n};\n\nconst removeDeletedUIDTargetFieldsOnUpdates = (schema: CTBSchema) => {\n schema.contentTypes.forEach((contentType) => {\n if (contentType.action === 'delete') {\n return;\n }\n\n contentType.attributes.forEach((attribute) => {\n if (attribute.action === 'update') {\n const { properties } = attribute;\n\n if (\n properties.type === 'uid' &&\n properties.targetField &&\n !contentType.attributes.some(\n (attr) => attr.action !== 'delete' && attr.name === properties.targetField\n )\n ) {\n properties.targetField = undefined;\n }\n }\n });\n });\n};\n\n/**\n * Composes the ordered rename hops of an updated type into an origin -> final\n * name map (`a -> b, b -> c` gives `a -> c`).\n */\nconst composeRenames = (hops: { oldName?: string; newName?: string }[]): Map<string, string> => {\n const originByName = new Map<string, string>();\n\n hops.forEach(({ oldName, newName }) => {\n if (!oldName || !newName || oldName === newName) {\n return;\n }\n\n const origin = originByName.get(oldName) ?? oldName;\n originByName.delete(oldName);\n originByName.set(newName, origin);\n });\n\n return new Map([...originByName].map(([name, origin]) => [origin, name]));\n};\n\n/**\n * Makes field conditions follow the renames of this save: a condition whose\n * `var` still names the origin of a rename is pointed at the field's final name.\n *\n * A `var` that names an attribute of the saved type is left alone: the caller\n * already rewrote it, or (in a swap) it cannot be told apart from one that was.\n */\nconst renameConditionVarsOnUpdates = (schema: CTBSchema) => {\n type AttributeEntry = {\n action?: string;\n name?: string;\n properties?: { conditions?: { visible?: Record<string, unknown> } };\n };\n type Entry = {\n action?: string;\n renames?: { oldName?: string; newName?: string }[];\n attributes?: AttributeEntry[];\n };\n\n const entries = [\n ...(schema.contentTypes as unknown as Entry[]),\n ...(schema.components as unknown as Entry[]),\n ];\n\n entries.forEach((entry) => {\n if (entry.action !== 'update' || !Array.isArray(entry.renames)) {\n return;\n }\n\n const renames = composeRenames(entry.renames);\n const savedAttributes = (entry.attributes ?? []).filter(\n (attribute) => attribute.action !== 'delete'\n );\n const saved = new Set(savedAttributes.map((attribute) => attribute.name));\n\n savedAttributes.forEach((attribute) => {\n Object.values(attribute.properties?.conditions?.visible ?? {}).forEach((rule) => {\n const fieldVar: unknown = Array.isArray(rule) ? rule[0] : undefined;\n\n if (\n typeof fieldVar !== 'object' ||\n fieldVar === null ||\n !('var' in fieldVar) ||\n typeof fieldVar.var !== 'string' ||\n saved.has(fieldVar.var)\n ) {\n return;\n }\n\n const finalName = renames.get(fieldVar.var);\n\n if (finalName !== undefined && saved.has(finalName)) {\n fieldVar.var = finalName;\n }\n });\n });\n });\n};\n\n/**\n * Keeps a uid field attached to its target when that target is renamed in this\n * save. A `targetField` that names a saved (non-deleted) attribute of the\n * payload is left alone: the caller already resolved it. When the renamed\n * target is not a string or text field (custom fields are resolved to their\n * underlying type), the uid is detached.\n */\nconst renameUIDTargetFieldsOnUpdates = (schema: CTBSchema) => {\n schema.contentTypes.forEach((contentType) => {\n if (contentType.action !== 'update' || !Array.isArray(contentType.renames)) {\n return;\n }\n\n const finalNames = composeRenames(contentType.renames);\n const savedAttributes = contentType.attributes.filter((attr) => attr.action !== 'delete');\n const saved = new Set(savedAttributes.map((attr) => attr.name));\n\n contentType.attributes.forEach((attribute) => {\n if (attribute.action !== 'update') {\n return;\n }\n\n const { properties } = attribute;\n\n if (properties.type !== 'uid' || !properties.targetField) {\n return;\n }\n\n const finalName = finalNames.get(properties.targetField);\n\n if (!finalName || saved.has(properties.targetField)) {\n return;\n }\n\n const target = savedAttributes.find((attr) => attr.name === finalName);\n\n properties.targetField =\n target && isValidUidTarget(target.properties) ? finalName : undefined;\n });\n });\n};\n\ninterface CollectedRename {\n uid: string;\n oldName: string;\n newName: string;\n newAttribute?: RenameAttributeDefinition;\n}\n\nconst getAttributeRenameMigrationMode = (): AttributeRenameMigrationMode => {\n return strapi\n .plugin('content-type-builder')\n .config('renameMigrations.attributes', 'prompt-before-save');\n};\n\n/**\n * Collects attribute renames from the update-schema payload. The admin sends an\n * ordered `renames` array per updated content-type / component: the exact path\n * of rename hops the user performed (e.g. `a -> tmp`, `b -> a`, `tmp -> b` for a\n * swap). Order is preserved so the generated migration can replay each hop\n * verbatim — which is inherently collision-free because the Content-Type Builder\n * never allows two fields to share a name at any instant.\n */\nconst collectRenames = (schema: CTBSchema): CollectedRename[] => {\n const renames: CollectedRename[] = [];\n\n type RenameHop = { oldName?: string; newName?: string };\n type AttributeEntry = { action?: string; name?: string; properties?: RenameAttributeDefinition };\n type RenameAwareEntry = {\n action?: string;\n uid: string;\n renames?: RenameHop[];\n attributes?: AttributeEntry[];\n };\n\n const collectFrom = (entries: RenameAwareEntry[]) => {\n entries\n .filter((entry) => entry.action === 'update' && Array.isArray(entry.renames))\n .forEach((entry) => {\n // Only the last hop onto a name produces the field that carries the\n // final definition: in `a -> b, b -> c, x -> b` the first `b` is `a`'s\n // intermediate name and the final `b` is `x`'s field.\n const lastHopByNewName = new Map<string, number>();\n entry.renames!.forEach((hop, index) => {\n if (hop.newName) {\n lastHopByNewName.set(hop.newName, index);\n }\n });\n\n entry.renames!.forEach((hop, index) => {\n if (hop.oldName && hop.newName && hop.oldName !== hop.newName) {\n // The definition the field ends up with in this save, so the builder\n // can refuse hops that also change the field's storage (type,\n // relation target, component…). Intermediate hops of a chain get no\n // definition and are checked when the chain completes.\n const newAttribute =\n lastHopByNewName.get(hop.newName) === index\n ? entry.attributes?.find(\n (attribute) => attribute.action !== 'delete' && attribute.name === hop.newName\n )?.properties\n : undefined;\n\n renames.push({\n uid: entry.uid,\n oldName: hop.oldName,\n newName: hop.newName,\n newAttribute,\n });\n }\n });\n });\n };\n\n collectFrom(schema.contentTypes as unknown as RenameAwareEntry[]);\n collectFrom(schema.components as unknown as RenameAwareEntry[]);\n\n return renames;\n};\n\n/**\n * Drops renames whose final name is not an attribute after this save (it was\n * deleted in the same save), so no store is pointed at a field that is gone.\n */\nconst keepSavedAttributes = (\n schema: CTBSchema,\n mapping: AttributeRenamesMapping\n): AttributeRenamesMapping => {\n type Entry = { action?: string; uid: string; attributes?: { action?: string; name?: string }[] };\n const entries = [\n ...(schema.contentTypes as unknown as Entry[]),\n ...(schema.components as unknown as Entry[]),\n ];\n\n const result: AttributeRenamesMapping = {};\n\n for (const [uid, renames] of Object.entries(mapping)) {\n const entry = entries.find((candidate) => candidate.uid === uid);\n const saved = new Set(\n (entry?.attributes ?? [])\n .filter((attribute) => attribute.action !== 'delete' && attribute.name)\n .map((attribute) => attribute.name as string)\n );\n\n for (const [origin, final] of Object.entries(renames)) {\n if (saved.has(final)) {\n result[uid] ??= {};\n result[uid][origin] = final;\n }\n }\n }\n\n return result;\n};\n\nconst describeUnsupportedReason = (reason: UnsupportedRename['reason']): string => {\n switch (reason) {\n case 'type-changed':\n return 'the field type, relation or component also changed';\n case 'unsupported-type':\n return 'the field type cannot be migrated (e.g. polymorphic relation)';\n case 'attribute-not-found':\n return 'the field is not in the current schema';\n case 'target-occupied':\n return 'the target field still exists in the current schema';\n case 'model-not-found':\n default:\n return 'the type is not in the current schema';\n }\n};\n\n/**\n * Generates a single data-preserving rename migration for the accepted renames\n * in this save. Must run before the server reloads, while `strapi.db.metadata`\n * still reflects the old (pre-rename) schema. Resolves to the written file's\n * path (so a failed save can remove it), or `null` when nothing was written.\n */\nconst generateRenameMigrations = async (schema: CTBSchema): Promise<string | null> => {\n // In prompt modes the admin strips refused renames before sending the payload.\n if (getAttributeRenameMigrationMode() === 'never') {\n return null;\n }\n\n const renames = collectRenames(schema);\n if (renames.length === 0) {\n return null;\n }\n\n const migrationBuilder = createMigrationBuilder({ strapi });\n\n for (const { uid, oldName, newName, newAttribute } of renames) {\n migrationBuilder.addRenameAttribute(uid, { oldName, newName, newAttribute });\n }\n\n const attributeRenames = keepSavedAttributes(schema, migrationBuilder.attributeRenamesMapping());\n if (Object.keys(attributeRenames).length > 0) {\n migrationBuilder.addAttributeRenames(attributeRenames);\n }\n\n const unsupported = migrationBuilder.getUnsupported();\n if (unsupported.length > 0) {\n const fields = unsupported\n .map((u) => `${u.uid}.${u.oldName} (${describeUnsupportedReason(u.reason)})`)\n .join(', ');\n strapi.log.warn(\n `[content-type-builder] Could not generate a rename migration for ${unsupported.length} field(s): ${fields}. Data in these fields may not be preserved.`\n );\n }\n\n if (migrationBuilder.hasChanges()) {\n return migrationBuilder.writeFiles();\n }\n\n return null;\n};\n\n/**\n * Renames a single attribute on a content-type or component and generates the\n * data-preserving migration in one step. Used by the `strapi rename:field` CLI\n * command so scripted / non-UI workflows get the same behaviour as the admin.\n *\n * It reuses the regular `updateSchema` path (and therefore the same rename\n * resolver via `generateRenameMigrations`), so the migration is resolved against\n * the pre-reload `strapi.db.metadata` exactly like the admin save. The caller is\n * responsible for not reloading before this resolves (the CLI simply exits).\n *\n * Unlike the admin, there is no one to confirm a data-losing rename, so it\n * refuses before touching the schema when the rename cannot be migrated.\n */\nexport const renameAttribute = async (\n uid: string,\n oldName: string,\n newName: string\n): Promise<void> => {\n const { ApplicationError } = errors;\n\n if (!oldName || !newName) {\n throw new ApplicationError('Both an old and a new attribute name are required');\n }\n\n if (oldName === newName) {\n throw new ApplicationError(`Cannot rename \"${oldName}\" to itself`);\n }\n\n if (getAttributeRenameMigrationMode() === 'never') {\n throw new ApplicationError(\n 'Rename migrations are disabled (`renameMigrations.attributes: never`); rename the field in the Content-Type Builder instead'\n );\n }\n\n const contentType = (strapi.contentTypes as Record<string, any>)[uid];\n const component = (strapi.components as Record<string, any>)[uid];\n const model = contentType ?? component;\n\n if (!model) {\n throw new ApplicationError(`No content-type or component found for uid \"${uid}\"`);\n }\n\n if (!model.attributes?.[oldName]) {\n throw new ApplicationError(`Attribute \"${oldName}\" does not exist on \"${uid}\"`);\n }\n\n if (model.attributes?.[newName]) {\n throw new ApplicationError(`Attribute \"${newName}\" already exists on \"${uid}\"`);\n }\n\n // Reuse the formatted, CTB-visible attributes (same shape the admin sends) so\n // the schema edit matches an admin save and the renamed key is the only change.\n const formattedSchema = await getSchema();\n const isComponent = Boolean(component);\n const entry = isComponent\n ? (formattedSchema.components as Record<string, any>)[uid]\n : (formattedSchema.contentTypes as Record<string, any>)[uid];\n\n // Custom fields are exposed with their underlying type; the admin sends them\n // back as `customField` so the schema file keeps them as custom fields.\n const toPayloadProperties = (properties: Record<string, any>) =>\n properties.customField ? { ...properties, type: 'customField' } : properties;\n\n const attributes = entry.attributes.map(({ name, ...properties }: Record<string, any>) => ({\n action: 'update',\n name: name === oldName ? newName : name,\n properties: toPayloadProperties(properties),\n }));\n\n // Dry run: the field keeps its definition, so only the rename itself can be\n // refused (system attribute, unsupported relation, occupied target…).\n const { name: _name, ...oldProperties } = entry.attributes.find(\n (attribute: Record<string, any>) => attribute.name === oldName\n ) ?? { name: oldName };\n const probe = createMigrationBuilder({ strapi });\n probe.addRenameAttribute(uid, {\n oldName,\n newName,\n newAttribute: toPayloadProperties(oldProperties),\n });\n\n const refused = probe.getUnsupported();\n if (refused.length > 0) {\n throw new ApplicationError(\n `Cannot rename \"${oldName}\" on \"${uid}\" without losing its data: ${refused\n .map(({ reason }) => describeUnsupportedReason(reason))\n .join(', ')}`\n );\n }\n\n const renames = [{ oldName, newName }];\n\n const payload = isComponent\n ? {\n contentTypes: [],\n components: [\n {\n action: 'update',\n uid,\n category: model.category,\n displayName: model.info?.displayName,\n icon: model.info?.icon,\n description: model.info?.description,\n pluginOptions: model.pluginOptions,\n renames,\n attributes,\n },\n ],\n }\n : {\n contentTypes: [\n {\n action: 'update',\n uid,\n kind: model.kind,\n displayName: model.info?.displayName,\n description: model.info?.description,\n draftAndPublish: Boolean(model.options?.draftAndPublish),\n options: model.options,\n pluginOptions: model.pluginOptions,\n renames,\n attributes,\n },\n ],\n components: [],\n };\n\n // Same checks as an admin save (name rules, reserved names, snake-case\n // uniqueness: `fooBar` next to an existing `foo_bar` would share a column).\n const { data } = await validateUpdateSchema({ data: payload });\n\n await updateSchema(data as CTBSchema);\n};\n\nconst formatAttributes = (model: any) => {\n const { getVisibleAttributes } = contentTypesUtils;\n\n // only get attributes that can be seen in the CTB\n return getVisibleAttributes(model).map((key) => {\n return { ...formatAttribute(model.attributes[key]), name: key };\n });\n};\n\nexport const formatAttribute = (attribute: Schema.Attribute.AnyAttribute & Record<string, any>) => {\n if (attribute.type === 'relation') {\n return {\n ...attribute,\n targetAttribute: attribute.inversedBy || attribute.mappedBy || null,\n // Explicitly preserve conditions if they exist\n ...(attribute.conditions && { conditions: attribute.conditions }),\n };\n }\n\n return attribute;\n};\n\nexport const getSchema = async () => {\n const contentTypes = mapValues(strapi.contentTypes, (contentType) => {\n const {\n uid,\n options,\n globalId,\n pluginOptions,\n kind,\n modelName,\n plugin,\n collectionName,\n info,\n modelType,\n } = contentType;\n\n return {\n uid,\n modelName,\n kind,\n globalId,\n options,\n pluginOptions,\n plugin,\n collectionName,\n info,\n modelType,\n attributes: formatAttributes(contentType),\n visible: isContentTypeVisible(contentType),\n restrictRelationsTo: getRestrictRelationsTo(contentType),\n };\n });\n\n const components = mapValues(strapi.components, (component) => {\n const { uid, globalId, modelName, collectionName, info, category, modelType } = component;\n\n return {\n uid,\n modelName,\n globalId,\n modelType,\n collectionName,\n category,\n info,\n attributes: formatAttributes(component),\n };\n });\n\n const coreContentStructure: CoreContentStructureService = strapi.get('content-structure');\n const contentStructure = await coreContentStructure.getCleanedFile();\n\n return {\n contentStructure,\n contentTypes,\n components,\n settings: {\n renameMigrations: {\n attributes: getAttributeRenameMigrationMode(),\n },\n },\n };\n};\n\nexport const updateSchema = async (schema: CTBSchema) => {\n const builder = createBuilder();\n const apiHandler = getService('api-handler') as typeof import('./api-handler');\n\n const { components, contentTypes, contentStructure } = schema;\n\n // Reject protected/plugin deletes before builders, API backups, or folder reconciliation can\n // mutate anything. This is the server-side invariant for crafted update requests.\n contentTypes\n .filter((contentType) => contentType.action === 'delete')\n .forEach((contentType) => assertCTBOwnedApplicationContentType(contentType.uid));\n\n // pre-process data\n removeEmptyDefaultsOnUpdates(schema);\n renameUIDTargetFieldsOnUpdates(schema);\n removeDeletedUIDTargetFieldsOnUpdates(schema);\n renameConditionVarsOnUpdates(schema);\n\n const upsertedUids = new Map<string, ContentTypeKind>();\n const deletedUids = new Set<string>();\n const generatedApiNames: string[] = [];\n const backedUpApiUids: string[] = [];\n let schemaAlreadyRolledBack = false;\n let migrationFilePath: string | null = null;\n const APIsToDelete = contentTypes\n .filter((contentType) => contentType.action === 'delete')\n .map((contentType) => contentType.uid);\n\n try {\n for (const contentType of contentTypes) {\n if (contentType.action === 'create') {\n upsertedUids.set(contentType.uid, contentType.kind ?? 'collectionType');\n } else if (contentType.action === 'update' && contentType.kind) {\n // A kind switch in the same save must override the registry's stale kind,\n // otherwise a folder assignment into the new section fails validation.\n upsertedUids.set(contentType.uid, contentType.kind);\n } else if (contentType.action === 'delete') {\n deletedUids.add(contentType.uid);\n }\n }\n\n // Validate folder references before anything is written. This will throw if invalid.\n getService('content-structure').validateFromUpdate({\n incomingStructure: contentStructure,\n upsertedUids,\n deletedUids,\n });\n\n // we pre create empty typesk\n for (const contentType of contentTypes) {\n if (contentType.action === 'create') {\n builder.createContentType({\n ...contentType,\n attributes: {},\n });\n }\n }\n\n // we pre create empty types\n for (const component of components) {\n if (component.action === 'create') {\n builder.createComponent({\n ...component,\n attributes: {},\n });\n }\n }\n\n for (const contentType of contentTypes) {\n const { action, uid } = contentType;\n\n if (action === 'create') {\n builder.createContentTypeAttributes(\n uid,\n contentType.attributes.reduce((acc: any, attr: any) => {\n acc[attr.name] = attr.properties;\n return acc;\n }, {})\n );\n\n if (!contentType.plugin) {\n // Track before generation because a generator failure can leave a partial skeleton.\n generatedApiNames.push(contentType.singularName);\n await getService('content-types').generateAPI({\n displayName: contentType!.displayName,\n singularName: contentType!.singularName,\n pluralName: contentType!.pluralName,\n kind: contentType!.kind,\n });\n }\n }\n\n if (action === 'update') {\n builder.editContentType({\n ...contentType,\n attributes: contentType.attributes.reduce((acc: any, attr: any) => {\n if (attr.action === 'delete') {\n return acc;\n }\n\n acc[attr.name] = attr.properties;\n return acc;\n }, {}),\n });\n }\n\n if (action === 'delete') {\n builder.deleteContentType(uid);\n await apiHandler.backup(uid);\n backedUpApiUids.push(uid);\n }\n }\n\n for (const component of components) {\n const { action, uid } = component;\n\n if (action === 'create') {\n builder.createComponentAttributes(\n uid,\n component.attributes.reduce((acc: any, attr: any) => {\n acc[attr.name] = attr.properties;\n return acc;\n }, {})\n );\n }\n\n if (action === 'update') {\n builder.editComponent({\n ...component,\n attributes: component.attributes.reduce((acc: any, attr: any) => {\n if (attr.action === 'delete') {\n return acc;\n }\n\n acc[attr.name] = attr.properties;\n return acc;\n }, {}),\n });\n }\n\n if (action === 'delete') {\n builder.deleteComponent(uid);\n }\n }\n\n // run sanity checks on the schema\n // Relations target existing types\n // Bidirectional relation have their counterpart in the schema\n // Components target existing components\n // Nested components target existing components\n // Dynamic zones target existing components\n\n // Generate rename migrations before reloading, while strapi.db.metadata still\n // reflects the pre-rename schema (the controller triggers the reload after this).\n migrationFilePath = await generateRenameMigrations(schema);\n\n const schemaFilesWritten = await builder.writeFiles();\n\n if (!schemaFilesWritten) {\n schemaAlreadyRolledBack = true;\n throw new errors.ApplicationError('Invalid schema edition');\n }\n\n for (const uid of APIsToDelete) {\n await apiHandler.clear(uid, { preserveBackup: true });\n }\n\n // Commit the single folder file last. Every preceding filesystem mutation can be restored.\n await getService('content-structure').commitFromUpdate({\n incomingStructure: contentStructure,\n deletedUids,\n });\n } catch (error) {\n await rollbackSchemaMutation({\n builder,\n apiHandler,\n backedUpApiUids,\n generatedApiNames,\n schemaAlreadyRolledBack,\n migrationFilePath,\n });\n\n throw error;\n }\n\n // Backup cleanup is deliberately outside the compensating boundary: at this point all\n // user-visible artifacts, including groups.json, have committed.\n for (const error of await finalizeSchemaMutation({ apiHandler, backedUpApiUids })) {\n strapi.log.error(error);\n }\n\n for (const contentType of contentTypes) {\n if (contentType.action === 'delete') {\n strapi.eventHub.emit('content-type.delete', {\n contentType: builder.contentTypes.get(contentType.uid),\n });\n }\n\n if (contentType.action === 'update') {\n strapi.eventHub.emit('content-type.update', {\n contentType: builder.contentTypes.get(contentType.uid),\n });\n }\n\n if (contentType.action === 'create') {\n strapi.eventHub.emit('content-type.create', {\n contentType: builder.contentTypes.get(contentType.uid),\n });\n }\n }\n\n for (const component of components) {\n if (component.action === 'delete') {\n strapi.eventHub.emit('component.delete', {\n component: builder.components.get(component.uid),\n });\n }\n\n if (component.action === 'update') {\n strapi.eventHub.emit('component.update', {\n component: builder.components.get(component.uid),\n });\n }\n\n if (component.action === 'create') {\n strapi.eventHub.emit('component.create', {\n component: builder.components.get(component.uid),\n });\n }\n }\n};\n"],"names":["removeEmptyDefaultsOnUpdates","schema","components","forEach","component","action","attributes","attribute","properties","default","undefined","contentTypes","contentType","removeDeletedUIDTargetFieldsOnUpdates","type","targetField","some","attr","name","composeRenames","hops","originByName","Map","oldName","newName","origin","get","delete","set","map","renameConditionVarsOnUpdates","entries","entry","Array","isArray","renames","savedAttributes","filter","saved","Set","Object","values","conditions","visible","rule","fieldVar","var","has","finalName","renameUIDTargetFieldsOnUpdates","finalNames","target","find","isValidUidTarget","getAttributeRenameMigrationMode","strapi","plugin","config","collectRenames","collectFrom","lastHopByNewName","hop","index","newAttribute","push","uid","keepSavedAttributes","mapping","result","candidate","final","describeUnsupportedReason","reason","generateRenameMigrations","length","migrationBuilder","createMigrationBuilder","addRenameAttribute","attributeRenames","attributeRenamesMapping","keys","addAttributeRenames","unsupported","getUnsupported","fields","u","join","log","warn","hasChanges","writeFiles","renameAttribute","ApplicationError","errors","model","formattedSchema","getSchema","isComponent","Boolean","toPayloadProperties","customField","_name","oldProperties","probe","refused","payload","category","displayName","info","icon","description","pluginOptions","kind","draftAndPublish","options","data","validateUpdateSchema","updateSchema","formatAttributes","getVisibleAttributes","contentTypesUtils","key","formatAttribute","targetAttribute","inversedBy","mappedBy","mapValues","globalId","modelName","collectionName","modelType","isContentTypeVisible","restrictRelationsTo","getRestrictRelationsTo","coreContentStructure","contentStructure","getCleanedFile","settings","renameMigrations","builder","createBuilder","apiHandler","getService","assertCTBOwnedApplicationContentType","upsertedUids","deletedUids","generatedApiNames","backedUpApiUids","schemaAlreadyRolledBack","migrationFilePath","APIsToDelete","add","validateFromUpdate","incomingStructure","createContentType","createComponent","createContentTypeAttributes","reduce","acc","singularName","generateAPI","pluralName","editContentType","deleteContentType","backup","createComponentAttributes","editComponent","deleteComponent","schemaFilesWritten","clear","preserveBackup","commitFromUpdate","error","rollbackSchemaMutation","finalizeSchemaMutation","eventHub","emit"],"mappings":"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"}
|
|
@@ -4,6 +4,7 @@ import createBuilder from './schema-builder/index.mjs';
|
|
|
4
4
|
import { createMigrationBuilder } from './migration-builder/index.mjs';
|
|
5
5
|
import { rollbackSchemaMutation, finalizeSchemaMutation } from './schema-mutation.mjs';
|
|
6
6
|
import { getService } from '../utils/index.mjs';
|
|
7
|
+
import { isValidUidTarget } from '../utils/uid-target.mjs';
|
|
7
8
|
import { validateUpdateSchema } from '../controllers/validation/schema.mjs';
|
|
8
9
|
import { getRestrictRelationsTo, isContentTypeVisible, assertCTBOwnedApplicationContentType } from './content-types.mjs';
|
|
9
10
|
|
|
@@ -43,7 +44,7 @@ const removeDeletedUIDTargetFieldsOnUpdates = (schema)=>{
|
|
|
43
44
|
contentType.attributes.forEach((attribute)=>{
|
|
44
45
|
if (attribute.action === 'update') {
|
|
45
46
|
const { properties } = attribute;
|
|
46
|
-
if (properties.type === 'uid' && properties.targetField && !contentType.attributes.
|
|
47
|
+
if (properties.type === 'uid' && properties.targetField && !contentType.attributes.some((attr)=>attr.action !== 'delete' && attr.name === properties.targetField)) {
|
|
47
48
|
properties.targetField = undefined;
|
|
48
49
|
}
|
|
49
50
|
}
|
|
@@ -102,6 +103,37 @@ const removeDeletedUIDTargetFieldsOnUpdates = (schema)=>{
|
|
|
102
103
|
});
|
|
103
104
|
});
|
|
104
105
|
};
|
|
106
|
+
/**
|
|
107
|
+
* Keeps a uid field attached to its target when that target is renamed in this
|
|
108
|
+
* save. A `targetField` that names a saved (non-deleted) attribute of the
|
|
109
|
+
* payload is left alone: the caller already resolved it. When the renamed
|
|
110
|
+
* target is not a string or text field (custom fields are resolved to their
|
|
111
|
+
* underlying type), the uid is detached.
|
|
112
|
+
*/ const renameUIDTargetFieldsOnUpdates = (schema)=>{
|
|
113
|
+
schema.contentTypes.forEach((contentType)=>{
|
|
114
|
+
if (contentType.action !== 'update' || !Array.isArray(contentType.renames)) {
|
|
115
|
+
return;
|
|
116
|
+
}
|
|
117
|
+
const finalNames = composeRenames(contentType.renames);
|
|
118
|
+
const savedAttributes = contentType.attributes.filter((attr)=>attr.action !== 'delete');
|
|
119
|
+
const saved = new Set(savedAttributes.map((attr)=>attr.name));
|
|
120
|
+
contentType.attributes.forEach((attribute)=>{
|
|
121
|
+
if (attribute.action !== 'update') {
|
|
122
|
+
return;
|
|
123
|
+
}
|
|
124
|
+
const { properties } = attribute;
|
|
125
|
+
if (properties.type !== 'uid' || !properties.targetField) {
|
|
126
|
+
return;
|
|
127
|
+
}
|
|
128
|
+
const finalName = finalNames.get(properties.targetField);
|
|
129
|
+
if (!finalName || saved.has(properties.targetField)) {
|
|
130
|
+
return;
|
|
131
|
+
}
|
|
132
|
+
const target = savedAttributes.find((attr)=>attr.name === finalName);
|
|
133
|
+
properties.targetField = target && isValidUidTarget(target.properties) ? finalName : undefined;
|
|
134
|
+
});
|
|
135
|
+
});
|
|
136
|
+
};
|
|
105
137
|
const getAttributeRenameMigrationMode = ()=>{
|
|
106
138
|
return strapi.plugin('content-type-builder').config('renameMigrations.attributes', 'prompt-before-save');
|
|
107
139
|
};
|
|
@@ -411,6 +443,7 @@ const updateSchema = async (schema)=>{
|
|
|
411
443
|
contentTypes.filter((contentType)=>contentType.action === 'delete').forEach((contentType)=>assertCTBOwnedApplicationContentType(contentType.uid));
|
|
412
444
|
// pre-process data
|
|
413
445
|
removeEmptyDefaultsOnUpdates(schema);
|
|
446
|
+
renameUIDTargetFieldsOnUpdates(schema);
|
|
414
447
|
removeDeletedUIDTargetFieldsOnUpdates(schema);
|
|
415
448
|
renameConditionVarsOnUpdates(schema);
|
|
416
449
|
const upsertedUids = new Map();
|