From 74d489eab7321b08c2f30bcdb99d6cbc843a079a Mon Sep 17 00:00:00 2001 From: Aleksander Sklorz Date: Wed, 11 Oct 2023 11:14:10 +0200 Subject: [PATCH 1/8] ACS-6085 Prevent user from renaming library to name containing only spaces --- .../library-metadata-form.component.html | 2 +- .../library-metadata-form.component.ts | 30 +++++++++++++++++-- 2 files changed, 28 insertions(+), 4 deletions(-) diff --git a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.html b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.html index 6faceb3f67..2202212058 100644 --- a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.html +++ b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.html @@ -92,7 +92,7 @@ /> {{ 'LIBRARY.HINTS.SITE_TITLE_EXISTS' | translate }} - {{ 'LIBRARY.ERRORS.TITLE_TOO_LONG' | translate }} + {{ titleErrorTranslationKey | translate }} diff --git a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.ts b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.ts index 0f14836eae..dd864e21f5 100644 --- a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.ts +++ b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.ts @@ -23,7 +23,16 @@ */ import { Component, Input, OnChanges, OnDestroy, OnInit, ViewEncapsulation } from '@angular/core'; -import { UntypedFormGroup, UntypedFormControl, Validators, FormGroupDirective, NgForm, FormsModule, ReactiveFormsModule } from '@angular/forms'; +import { + UntypedFormGroup, + UntypedFormControl, + Validators, + FormGroupDirective, + NgForm, + FormsModule, + ReactiveFormsModule, + FormControl +} from '@angular/forms'; import { QueriesApi, SiteEntry, SitePaging } from '@alfresco/js-api'; import { Store } from '@ngrx/store'; import { @@ -77,11 +86,17 @@ export class InstantErrorStateMatcher implements ErrorStateMatcher { }) export class LibraryMetadataFormComponent implements OnInit, OnChanges, OnDestroy { private _queriesApi: QueriesApi; + private _titleErrorTranslationKey: string; + get queriesApi(): QueriesApi { this._queriesApi = this._queriesApi ?? new QueriesApi(this.alfrescoApiService.getInstance()); return this._queriesApi; } + get titleErrorTranslationKey(): string { + return this._titleErrorTranslationKey; + } + @Input() node: SiteEntry; @@ -96,7 +111,7 @@ export class LibraryMetadataFormComponent implements OnInit, OnChanges, OnDestro form: UntypedFormGroup = new UntypedFormGroup({ id: new UntypedFormControl({ value: '', disabled: true }), - title: new UntypedFormControl({ value: '' }, [Validators.required, Validators.maxLength(256)]), + title: new UntypedFormControl({ value: '' }, [Validators.required, Validators.maxLength(256), this.validateEmptyName]), description: new UntypedFormControl({ value: '' }, [Validators.maxLength(512)]), visibility: new UntypedFormControl(this.libraryType[0].value) }); @@ -124,7 +139,12 @@ export class LibraryMetadataFormComponent implements OnInit, OnChanges, OnDestro ngOnInit() { this.updateForm(this.node); - + this.form.controls.title.statusChanges + .pipe(takeUntil(this.onDestroy$)) + .subscribe( + () => + (this._titleErrorTranslationKey = this.form.controls.title.errors?.empty ? 'LIBRARY.ERRORS.ONLY_SPACES' : 'LIBRARY.ERRORS.TITLE_TOO_LONG') + ); this.form.controls['title'].valueChanges .pipe( debounceTime(300), @@ -199,4 +219,8 @@ export class LibraryMetadataFormComponent implements OnInit, OnChanges, OnDestro ) .subscribe(handle); } + + private validateEmptyName(control: FormControl) { + return control.value.length && !control.value.trim() ? { empty: true } : null; + } } From 1f37a56b3bc1346caf1be37bdc090fde00eb5ebe Mon Sep 17 00:00:00 2001 From: Aleksander Sklorz Date: Wed, 11 Oct 2023 15:05:31 +0200 Subject: [PATCH 2/8] ACS-6085 Trimmed value --- .../library-metadata-form.component.ts | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.ts b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.ts index dd864e21f5..c00c3d58c8 100644 --- a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.ts +++ b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.ts @@ -184,7 +184,12 @@ export class LibraryMetadataFormComponent implements OnInit, OnChanges, OnDestro update() { if (this.canUpdateLibrary && this.form.valid) { this.form.markAsPristine(); - this.store.dispatch(new UpdateLibraryAction(this.form.value)); + this.store.dispatch( + new UpdateLibraryAction({ + ...this.form.value, + title: this.form.value.title.trim() + }) + ); } } @@ -202,7 +207,7 @@ export class LibraryMetadataFormComponent implements OnInit, OnChanges, OnDestro private findLibraryByTitle(libraryTitle: string): Observable { return from( this.queriesApi - .findSites(libraryTitle, { + .findSites(libraryTitle.trim(), { maxItems: 1, fields: ['title'] }) From 235d53ec5bb8aff0c0a1181b039dfdf1823b5f8a Mon Sep 17 00:00:00 2001 From: Aleksander Sklorz Date: Thu, 12 Oct 2023 11:13:15 +0200 Subject: [PATCH 3/8] ACS-6085 Unit tests for titleErrorTranslationKey and update function --- .../library-metadata-form.component.spec.ts | 35 +++++++++++++++++++ 1 file changed, 35 insertions(+) diff --git a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.spec.ts b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.spec.ts index 988f70d4be..1665941bea 100644 --- a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.spec.ts +++ b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.spec.ts @@ -167,6 +167,20 @@ describe('LibraryMetadataFormComponent', () => { expect(store.dispatch).toHaveBeenCalledWith(new UpdateLibraryAction(siteEntryModel)); }); + it('should update library node with trimmed title', () => { + component.node.entry.role = Site.RoleEnum.SiteManager; + siteEntryModel.title = ' some title '; + component.ngOnInit(); + + component.update(); + expect(store.dispatch).toHaveBeenCalledWith( + new UpdateLibraryAction({ + ...siteEntryModel, + title: siteEntryModel.title.trim() + }) + ); + }); + it('should call markAsPristine on form when updating valid form and has permission to update', () => { component.node.entry.role = Site.RoleEnum.SiteManager; spyOn(component.form, 'markAsPristine'); @@ -293,4 +307,25 @@ describe('LibraryMetadataFormComponent', () => { tick(500); expect(component.libraryTitleExists).toBe(false); })); + + it('should set proper titleErrorTranslationKey when there is error for empty title', () => { + component.ngOnInit(); + + component.form.controls.title.setValue(' '); + expect(component.titleErrorTranslationKey).toBe('LIBRARY.ERRORS.ONLY_SPACES'); + }); + + it('should set proper titleErrorTranslationKey when there is error for required', () => { + component.ngOnInit(); + + component.form.controls.title.setValue(''); + expect(component.titleErrorTranslationKey).toBe('LIBRARY.ERRORS.TITLE_TOO_LONG'); + }); + + it('should set proper titleErrorTranslationKey when there is error for too long title', () => { + component.ngOnInit(); + + component.form.controls.title.setValue('t'.repeat(257)); + expect(component.titleErrorTranslationKey).toBe('LIBRARY.ERRORS.TITLE_TOO_LONG'); + }); }); From 9c064ef77f6d27c661d4cb211f3b3e2087649fcc Mon Sep 17 00:00:00 2001 From: Aleksander Sklorz Date: Thu, 12 Oct 2023 15:04:08 +0200 Subject: [PATCH 4/8] ACS-6085 Unit tests --- .../library-metadata-form.component.spec.ts | 18 ++++++++++++++++++ 1 file changed, 18 insertions(+) diff --git a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.spec.ts b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.spec.ts index 1665941bea..c8e776afef 100644 --- a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.spec.ts +++ b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.spec.ts @@ -170,6 +170,7 @@ describe('LibraryMetadataFormComponent', () => { it('should update library node with trimmed title', () => { component.node.entry.role = Site.RoleEnum.SiteManager; siteEntryModel.title = ' some title '; + component.node.entry.title = siteEntryModel.title; component.ngOnInit(); component.update(); @@ -278,6 +279,23 @@ describe('LibraryMetadataFormComponent', () => { expect(component.libraryTitleExists).toBe(true); })); + it('should call findSites on queriesApi with trimmed title', fakeAsync(() => { + const title = ' test '; + spyOn(component.queriesApi, 'findSites').and.returnValue( + Promise.resolve({ + list: { entries: [{ entry: { title } }] } + } as SitePaging) + ); + component.ngOnInit(); + + component.form.controls.title.setValue(title); + tick(300); + expect(component.queriesApi.findSites).toHaveBeenCalledWith(title.trim(), { + maxItems: 1, + fields: ['title'] + }); + })); + it('should not warn if library name input is the same with library node data', fakeAsync(() => { spyOn(component['queriesApi'], 'findSites').and.returnValue( Promise.resolve({ From d98f5a5c061bf182287d2f79d96d287a0152e48a Mon Sep 17 00:00:00 2001 From: Aleksander Sklorz Date: Thu, 12 Oct 2023 15:05:09 +0200 Subject: [PATCH 5/8] ACS-6085 Removed redundant code --- .../library-metadata-form.component.spec.ts | 7 ------- 1 file changed, 7 deletions(-) diff --git a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.spec.ts b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.spec.ts index c8e776afef..59d09da5b6 100644 --- a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.spec.ts +++ b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.spec.ts @@ -333,13 +333,6 @@ describe('LibraryMetadataFormComponent', () => { expect(component.titleErrorTranslationKey).toBe('LIBRARY.ERRORS.ONLY_SPACES'); }); - it('should set proper titleErrorTranslationKey when there is error for required', () => { - component.ngOnInit(); - - component.form.controls.title.setValue(''); - expect(component.titleErrorTranslationKey).toBe('LIBRARY.ERRORS.TITLE_TOO_LONG'); - }); - it('should set proper titleErrorTranslationKey when there is error for too long title', () => { component.ngOnInit(); From c3cb2fcf582df5d0b93e75f05a52df30a442a651 Mon Sep 17 00:00:00 2001 From: Aleksander Sklorz Date: Thu, 12 Oct 2023 15:08:11 +0200 Subject: [PATCH 6/8] ACS-6085 Set type for validateEmptyName function --- .../library-metadata-tab/library-metadata-form.component.ts | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-) diff --git a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.ts b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.ts index c00c3d58c8..f1f6174217 100644 --- a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.ts +++ b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.ts @@ -31,7 +31,8 @@ import { NgForm, FormsModule, ReactiveFormsModule, - FormControl + FormControl, + ValidationErrors } from '@angular/forms'; import { QueriesApi, SiteEntry, SitePaging } from '@alfresco/js-api'; import { Store } from '@ngrx/store'; @@ -225,7 +226,7 @@ export class LibraryMetadataFormComponent implements OnInit, OnChanges, OnDestro .subscribe(handle); } - private validateEmptyName(control: FormControl) { + private validateEmptyName(control: FormControl): ValidationErrors { return control.value.length && !control.value.trim() ? { empty: true } : null; } } From 717c2970fc7e1e8a766005185d40612d549d17c9 Mon Sep 17 00:00:00 2001 From: Aleksander Sklorz Date: Fri, 13 Oct 2023 11:20:46 +0200 Subject: [PATCH 7/8] ACS-6085 Rename error translation key for required error --- projects/aca-content/assets/i18n/en.json | 2 +- .../library-metadata-form.component.spec.ts | 9 ++++++++- .../library-metadata-form.component.ts | 4 +++- 3 files changed, 12 insertions(+), 3 deletions(-) diff --git a/projects/aca-content/assets/i18n/en.json b/projects/aca-content/assets/i18n/en.json index bab98e67e3..a3a48e7ad3 100644 --- a/projects/aca-content/assets/i18n/en.json +++ b/projects/aca-content/assets/i18n/en.json @@ -488,7 +488,7 @@ "CONFLICT": "This Library ID is already used. Check the trashcan.", "ID_TOO_LONG": "Use 72 characters or less for the URL name", "DESCRIPTION_TOO_LONG": "Use 512 characters or less for description", - "TITLE_TOO_LONG": "Use 256 characters or less for title", + "TITLE_TOO_LONG_OR_MISSING": "Use 256 characters or less for title", "ILLEGAL_CHARACTERS": "Use numbers and letters only", "ONLY_SPACES": "Library name can't contain only spaces", "LIBRARY_UPDATE_ERROR": "There was an error updating library properties" diff --git a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.spec.ts b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.spec.ts index 59d09da5b6..80881c92ed 100644 --- a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.spec.ts +++ b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.spec.ts @@ -337,6 +337,13 @@ describe('LibraryMetadataFormComponent', () => { component.ngOnInit(); component.form.controls.title.setValue('t'.repeat(257)); - expect(component.titleErrorTranslationKey).toBe('LIBRARY.ERRORS.TITLE_TOO_LONG'); + expect(component.titleErrorTranslationKey).toBe('LIBRARY.ERRORS.TITLE_TOO_LONG_OR_MISSING'); + }); + + it('should set proper titleErrorTranslationKey when there is error for missing title', () => { + component.ngOnInit(); + + component.form.controls.title.setValue(''); + expect(component.titleErrorTranslationKey).toBe('LIBRARY.ERRORS.TITLE_TOO_LONG_OR_MISSING'); }); }); diff --git a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.ts b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.ts index f1f6174217..d443168966 100644 --- a/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.ts +++ b/projects/aca-content/src/lib/components/info-drawer/library-metadata-tab/library-metadata-form.component.ts @@ -144,7 +144,9 @@ export class LibraryMetadataFormComponent implements OnInit, OnChanges, OnDestro .pipe(takeUntil(this.onDestroy$)) .subscribe( () => - (this._titleErrorTranslationKey = this.form.controls.title.errors?.empty ? 'LIBRARY.ERRORS.ONLY_SPACES' : 'LIBRARY.ERRORS.TITLE_TOO_LONG') + (this._titleErrorTranslationKey = this.form.controls.title.errors?.empty + ? 'LIBRARY.ERRORS.ONLY_SPACES' + : 'LIBRARY.ERRORS.TITLE_TOO_LONG_OR_MISSING') ); this.form.controls['title'].valueChanges .pipe( From d1fb0ebb97177dddd662601a1d8ecb6000a7990e Mon Sep 17 00:00:00 2001 From: Aleksander Sklorz Date: Fri, 13 Oct 2023 13:36:35 +0200 Subject: [PATCH 8/8] ACS-6085 Empty commit