diff --git a/packages/core/client/src/collection-manager/interfaces/textarea.ts b/packages/core/client/src/collection-manager/interfaces/textarea.ts index 2ccebbdeb6..19f48bc4c1 100644 --- a/packages/core/client/src/collection-manager/interfaces/textarea.ts +++ b/packages/core/client/src/collection-manager/interfaces/textarea.ts @@ -31,6 +31,12 @@ export class TextareaFieldInterface extends CollectionFieldInterface { titleUsable = true; properties = { ...defaultProps, + trim: { + type: 'boolean', + 'x-content': '{{t("Automatically remove heading and tailing spaces")}}', + 'x-decorator': 'FormItem', + 'x-component': 'Checkbox', + }, }; schemaInitialize(schema: ISchema, { block }) { if (['Table', 'Kanban'].includes(block)) { diff --git a/packages/core/database/src/__tests__/fields/text-field.test.ts b/packages/core/database/src/__tests__/fields/text-field.test.ts index b9c19e69f1..762269cb7f 100644 --- a/packages/core/database/src/__tests__/fields/text-field.test.ts +++ b/packages/core/database/src/__tests__/fields/text-field.test.ts @@ -52,4 +52,18 @@ describe('text field', () => { }); await Test.sync(); }); + + it('trim', async () => { + const collection = db.collection({ + name: 'tests', + fields: [{ type: 'text', name: 'name', trim: true }], + }); + await db.sync(); + const model = await collection.model.create({ + name: ' n1\n ', + }); + expect(model.toJSON()).toMatchObject({ + name: 'n1', + }); + }); }); diff --git a/packages/core/database/src/fields/text-field.ts b/packages/core/database/src/fields/text-field.ts index 74ca88da9b..39f1ef4670 100644 --- a/packages/core/database/src/fields/text-field.ts +++ b/packages/core/database/src/fields/text-field.ts @@ -23,9 +23,20 @@ export class TextField extends Field { this.options.defaultValue = null; } } + + additionalSequelizeOptions() { + const { name, trim } = this.options; + + return { + set(value) { + this.setDataValue(name, trim ? value?.trim() : value); + }, + }; + } } export interface TextFieldOptions extends BaseColumnFieldOptions { type: 'text'; length?: 'tiny' | 'medium' | 'long'; + trim?: boolean; }