diff --git a/cypress/integration/submission-ui.spec.ts b/cypress/integration/submission-ui.spec.ts index 3e895f85012..b985d43d0ac 100644 --- a/cypress/integration/submission-ui.spec.ts +++ b/cypress/integration/submission-ui.spec.ts @@ -155,10 +155,13 @@ const createItemProcess = { cy.get('section[class = "license-selector is-active"] ul li').eq(0).dblclick(); }, checkLicenseSelectionValue(value: string) { - cy.get('ds-submission-section-clarin-license select[id = "aspect_submission_StepTransformer_field_license"]').contains(value); + cy.get('ds-submission-section-clarin-license input[id = "aspect_submission_StepTransformer_field_license"]').should('have.value', value); }, - selectValueFromLicenseSelection(option: string) { - cy.get('ds-submission-section-clarin-license select[id = "aspect_submission_StepTransformer_field_license"]').select(option); + selectValueFromLicenseSelection(id: number) { + cy.get('ds-submission-section-clarin-license li[value = "' + id + '"]').click(); + }, + clickOnLicenseSelectionButton() { + cy.get('ds-submission-section-clarin-license input[id = "aspect_submission_StepTransformer_field_license"]').click(); }, checkResourceLicenseStatus(statusTitle: string) { cy.get('div[id = "clarin-license-header"] button i[title = "' + statusTitle + '"]').should('be.visible'); @@ -264,129 +267,131 @@ describe('Create a new submission', () => { // addEUSponsor(3); // }); - // From HERE ********** + // Test type-bind + it('should be showed chosen type value', { + retries: { + runMode: 6, + openMode: 6, + }, + defaultCommandTimeout: 10000 + },() => { + createItemProcess.clickOnSelectionInput('dc.type'); + createItemProcess.clickOnTypeSelection('Article'); + }); - // // Test type-bind - // it('should be showed chosen type value', { - // retries: { - // runMode: 6, - // openMode: 6, - // }, - // defaultCommandTimeout: 10000 - // },() => { - // createItemProcess.clickOnSelectionInput('dc.type'); - // createItemProcess.clickOnTypeSelection('Article'); - // }); - // - // // Test CMDI input field - // it('should be visible Has CMDI file input field because user is admin', { - // retries: { - // runMode: 6, - // openMode: 6, - // }, - // defaultCommandTimeout: 10000 - // },() => { - // createItemProcess.checkLocalHasCMDIVisibility(); - // }); - // - // it('The local.hasCMDI value should be sent in the response after type change', { - // retries: { - // runMode: 6, - // openMode: 6, - // }, - // defaultCommandTimeout: 10000 - // },() => { - // createItemProcess.clickOnSelectionInput('dc.type'); - // createItemProcess.clickOnTypeSelection('Article'); - // createItemProcess.checkCheckbox('local_hasCMDI'); - // createItemProcess.controlCheckedCheckbox('local_hasCMDI',true); - // createItemProcess.clickOnSave(); - // cy.reload(); - // createItemProcess.controlCheckedCheckbox('local_hasCMDI',true); - // }); - // - // it('should change the step status after accepting/declining the distribution license', { - // retries: { - // runMode: 6, - // openMode: 6, - // }, - // defaultCommandTimeout: 10000 - // },() => { - // createItemProcess.checkDistributionLicenseStep(); - // createItemProcess.checkDistributionLicenseToggle(); - // // default status value is warnings - // createItemProcess.checkDistributionLicenseStatus('Warnings'); - // // accept the distribution license agreement - // createItemProcess.clickOnDistributionLicenseToggle(); - // // after accepting the status should be valid - // createItemProcess.checkDistributionLicenseStatus('Valid'); - // // click on the toggle again and status should be changed to `Warnings` - // createItemProcess.clickOnDistributionLicenseToggle(); - // createItemProcess.checkDistributionLicenseStatus('Warnings'); - // }); - // - // it('should pick up the license from the license selector', { - // retries: { - // runMode: 6, - // openMode: 6, - // }, - // defaultCommandTimeout: 10000 - // },() => { - // createItemProcess.checkLicenseResourceStep(); - // // check default value in the license dropdown selection - // createItemProcess.checkLicenseSelectionValue('Select a License ...'); - // // pop up the license selector modal - // createItemProcess.clickOnLicenseSelectorButton(); - // // check if the modal was popped up - // createItemProcess.checkLicenseSelectorModal(); - // // pick up the first license from the modal, it is `Public Domain Mark (PD)` - // createItemProcess.pickUpLicenseFromLicenseSelector(); - // // check if the picked up license value is seen as selected value in the selection - // createItemProcess.checkLicenseSelectionValue('Public Domain Mark (PD)'); - // }); - // - // it('should select the license from the license selection dropdown and change status', { - // retries: { - // runMode: 6, - // openMode: 6, - // }, - // defaultCommandTimeout: 10000 - // },() => { - // createItemProcess.checkLicenseResourceStep(); - // // check default value in the license dropdown selection - // createItemProcess.checkLicenseSelectionValue('Select a License ...'); - // // check step status - it should be as warning - // createItemProcess.checkResourceLicenseStatus('Warnings'); - // // select `Public Domain Mark (PD)` from the selection - // createItemProcess.selectValueFromLicenseSelection('Public Domain Mark (PD)'); - // // selected value should be seen as selected value in the selection - // createItemProcess.checkLicenseSelectionValue('Public Domain Mark (PD)'); - // // check step status - it should be valid - // createItemProcess.checkResourceLicenseStatus('Valid'); - // }); - // - // it('should show warning messages if was selected non-supported license', { - // retries: { - // runMode: 6, - // openMode: 6, - // }, - // defaultCommandTimeout: 10000 - // },() => { - // createItemProcess.checkLicenseResourceStep(); - // // check default value in the license dropdown selection - // createItemProcess.checkLicenseSelectionValue('Select a License ...'); - // // check step status - it should be as warning - // createItemProcess.checkResourceLicenseStatus('Warnings'); - // // select `Select a License ...` from the selection - this license is not supported - // createItemProcess.selectValueFromLicenseSelection('Select a License ...'); - // // selected value should be seen as selected value in the selection - // createItemProcess.checkLicenseSelectionValue('Select a License ...'); - // // check step status - it should an error - // createItemProcess.checkResourceLicenseStatus('Errors'); - // // error messages should be popped up - // createItemProcess.showErrorMustChooseLicense(); - // createItemProcess.showErrorNotSupportedLicense(); - // }); + // Test CMDI input field + it('should be visible Has CMDI file input field because user is admin', { + retries: { + runMode: 6, + openMode: 6, + }, + defaultCommandTimeout: 10000 + },() => { + createItemProcess.checkLocalHasCMDIVisibility(); + }); + + it('The local.hasCMDI value should be sent in the response after type change', { + retries: { + runMode: 6, + openMode: 6, + }, + defaultCommandTimeout: 10000 + },() => { + createItemProcess.clickOnSelectionInput('dc.type'); + createItemProcess.clickOnTypeSelection('Article'); + createItemProcess.checkCheckbox('local_hasCMDI'); + createItemProcess.controlCheckedCheckbox('local_hasCMDI',true); + createItemProcess.clickOnSave(); + cy.reload(); + createItemProcess.controlCheckedCheckbox('local_hasCMDI',true); + }); + + it('should change the step status after accepting/declining the distribution license', { + retries: { + runMode: 6, + openMode: 6, + }, + defaultCommandTimeout: 10000 + },() => { + createItemProcess.checkDistributionLicenseStep(); + createItemProcess.checkDistributionLicenseToggle(); + // default status value is warnings + createItemProcess.checkDistributionLicenseStatus('Warnings'); + // accept the distribution license agreement + createItemProcess.clickOnDistributionLicenseToggle(); + // after accepting the status should be valid + createItemProcess.checkDistributionLicenseStatus('Valid'); + // click on the toggle again and status should be changed to `Warnings` + createItemProcess.clickOnDistributionLicenseToggle(); + createItemProcess.checkDistributionLicenseStatus('Warnings'); + }); + + it('should pick up the license from the license selector', { + retries: { + runMode: 6, + openMode: 6, + }, + defaultCommandTimeout: 10000 + },() => { + createItemProcess.checkLicenseResourceStep(); + // check default value in the license dropdown selection + createItemProcess.checkLicenseSelectionValue('Select a License ...'); + // pop up the license selector modal + createItemProcess.clickOnLicenseSelectorButton(); + // check if the modal was popped up + createItemProcess.checkLicenseSelectorModal(); + // pick up the first license from the modal, it is `Public Domain Mark (PD)` + createItemProcess.pickUpLicenseFromLicenseSelector(); + // check if the picked up license value is seen as selected value in the selection + createItemProcess.checkLicenseSelectionValue('Public Domain Mark (PD)'); + }); + + it('should select the license from the license selection dropdown and change status', { + retries: { + runMode: 6, + openMode: 6, + }, + defaultCommandTimeout: 10000 + },() => { + createItemProcess.checkLicenseResourceStep(); + // check default value in the license dropdown selection + createItemProcess.checkLicenseSelectionValue('Select a License ...'); + // check step status - it should be as warning + createItemProcess.checkResourceLicenseStatus('Warnings'); + // click on the dropdown button to list options + createItemProcess.clickOnLicenseSelectionButton(); + // select `Public Domain Mark (PD)` from the selection + createItemProcess.selectValueFromLicenseSelection(2); + // // selected value should be seen as selected value in the selection + createItemProcess.checkLicenseSelectionValue('GNU General Public License, version 2'); + // // check step status - it should be valid + createItemProcess.checkResourceLicenseStatus('Valid'); + }); + + it('should show warning messages if was selected non-supported license', { + retries: { + runMode: 6, + openMode: 6, + }, + defaultCommandTimeout: 10000 + },() => { + createItemProcess.checkLicenseResourceStep(); + // check default value in the license dropdown selection + createItemProcess.checkLicenseSelectionValue('Select a License ...'); + // check step status - it should be as warning + createItemProcess.checkResourceLicenseStatus('Warnings'); + // click on the dropdown button to list options + createItemProcess.clickOnLicenseSelectionButton(); + // select `Select a License ...` from the selection - this license is not supported + createItemProcess.selectValueFromLicenseSelection(0); + // selected value should be seen as selected value in the selection + createItemProcess.checkLicenseSelectionValue('Select a License ...'); + // check step status - it should an error + createItemProcess.checkResourceLicenseStatus('Errors'); + // error messages should be popped up + createItemProcess.showErrorMustChooseLicense(); + createItemProcess.showErrorNotSupportedLicense(); + }); // Author field should consist of two input fields it('Author field should consist of two input fields', { diff --git a/src/app/submission/sections/clarin-license-resource/license-4-selector.model.ts b/src/app/submission/sections/clarin-license-resource/license-4-selector.model.ts index 1e954edafc4..62aa8ddbc4d 100644 --- a/src/app/submission/sections/clarin-license-resource/license-4-selector.model.ts +++ b/src/app/submission/sections/clarin-license-resource/license-4-selector.model.ts @@ -5,4 +5,5 @@ export class License4Selector { id: number; name: string; url: string; + licenseLabel: string; } diff --git a/src/app/submission/sections/clarin-license-resource/section-license.component.html b/src/app/submission/sections/clarin-license-resource/section-license.component.html index b765eb9c88f..87e97eecd1b 100644 --- a/src/app/submission/sections/clarin-license-resource/section-license.component.html +++ b/src/app/submission/sections/clarin-license-resource/section-license.component.html @@ -1,3 +1,4 @@ +
@@ -42,17 +43,37 @@
-
- +
+
+ + +
diff --git a/src/app/submission/sections/clarin-license-resource/section-license.component.scss b/src/app/submission/sections/clarin-license-resource/section-license.component.scss index 22b4671634d..d1b014607fe 100644 --- a/src/app/submission/sections/clarin-license-resource/section-license.component.scss +++ b/src/app/submission/sections/clarin-license-resource/section-license.component.scss @@ -36,3 +36,73 @@ box-shadow: none; background-image: none; } + +.label { + display: inline; + padding: 0.25em 0.6em 0.2em; + font-size: 75%; + font-weight: bold; + line-height: 1; + color: #fff; + text-align: center; + white-space: nowrap; + vertical-align: baseline; + border-radius: 0.25em; + font-family: "Helvetica Neue",Helvetica,Arial,sans-serif; +} + +.label-PUB { + background-color: #5cb811 !important; +} + +.label-ACA, .label-PDT { + background-color: #ffab23; +} + +.label-RES { + background-color: #c62d1f; +} + +.clarin-select-input { + margin-right: 0; + border-bottom-right-radius: 0.25rem !important; + border-top-right-radius: 0.25rem !important; + align-content: start !important; + align-items: start !important; + width: 100%; +} + +.clarin-search-input-dropdown { + border-left: 0; + border-bottom-left-radius: 0; + border-top-left-radius: 0; +} + +.clarin-dropdown-item { + cursor: pointer; +} + +.scrollable-menu { + height: auto; + max-height: 300px; + overflow-x: hidden; + padding-top: 0; + border-top: 0; + width: 100%; +} + +.has-search .form-control { + padding-left: 2.375rem; +} + +.has-search .form-control-feedback { + position: absolute; + z-index: 2; + display: block; + width: 2.375rem; + height: 2.375rem; + line-height: 2.375rem; + text-align: center; + pointer-events: none; + color: #aaa; +} diff --git a/src/app/submission/sections/clarin-license-resource/section-license.component.ts b/src/app/submission/sections/clarin-license-resource/section-license.component.ts index 0207a302ff1..b9fd6d34e5c 100644 --- a/src/app/submission/sections/clarin-license-resource/section-license.component.ts +++ b/src/app/submission/sections/clarin-license-resource/section-license.component.ts @@ -86,6 +86,16 @@ export class SubmissionSectionClarinLicenseComponent extends SectionModelCompone */ licenses4Selector: License4Selector[] = []; + /** + * Filtered licenses4Selector - after searching. + */ + filteredLicenses4Selector: License4Selector[] = []; + + /** + * `Select a License` placeholder for the license dropdown button. + */ + licenseSelectorDefaultValue = ''; + /** * The form id * @type {string} @@ -154,6 +164,11 @@ export class SubmissionSectionClarinLicenseComponent extends SectionModelCompone } async ngOnInit() { + // Set default value for the license selector. + this.licenseSelectorDefaultValue = + this.translateService.instant('submission.sections.clarin-license.head.license-select-default-value'); + this.selectedLicenseName = this.licenseSelectorDefaultValue; + // initialize licenses for license selector // It must be before `super.ngOnInit();` because that method loads the metadata from the Item and compare // items license with licenses4Selector. @@ -239,13 +254,9 @@ export class SubmissionSectionClarinLicenseComponent extends SectionModelCompone /** * Select license by the license Id. */ - async selectLicense() { - if (isEmpty(this.selectedLicenseFromOptionId)) { - this.selectedLicenseName = ''; - } else { - this.selectedLicenseName = this.getLicenseNameById(this.selectedLicenseFromOptionId); - } - + async selectLicense(licenseId) { + this.selectedLicenseFromOptionId = licenseId; + this.selectedLicenseName = this.getLicenseNameById(this.selectedLicenseFromOptionId); await this.maintainLicenseSelection(); } @@ -348,7 +359,7 @@ export class SubmissionSectionClarinLicenseComponent extends SectionModelCompone */ private async selectLicenseOnInit(licenseName) { if (isEmpty(licenseName)) { - this.selectedLicenseName = ''; + this.selectedLicenseName = this.licenseSelectorDefaultValue; } else { this.selectedLicenseName = licenseName; } @@ -422,10 +433,10 @@ export class SubmissionSectionClarinLicenseComponent extends SectionModelCompone /** * From the license object list get whole object by the Id. */ - private getLicenseNameById(selectionLicenseId) { - let licenseName = ''; + protected getLicenseNameById(selectionLicenseId) { + let licenseName = this.licenseSelectorDefaultValue; this.licenses4Selector.forEach(license4Selector => { - if (String(license4Selector.id) === selectionLicenseId) { + if (license4Selector.id === selectionLicenseId) { licenseName = license4Selector.name; return; } @@ -461,9 +472,15 @@ export class SubmissionSectionClarinLicenseComponent extends SectionModelCompone private getLicenseNameFromRef() { let selectedLicenseId: string; if (isUndefined(this.licenseSelectionRef)) { - return; + return ''; } + + // Get ID of selected license from the license selector. selectedLicenseId = this.licenseSelectionRef.nativeElement.value; + if (isUndefined(selectedLicenseId)) { + return ''; + } + let selectedLicense = false; selectedLicense = selectedLicenseId.trim().length !== 0; @@ -473,12 +490,19 @@ export class SubmissionSectionClarinLicenseComponent extends SectionModelCompone return; } let licenseLabel: string; - const options = this.licenseSelectionRef.nativeElement.children; - for (const item of options) { - if (item.value === selectedLicenseId) { - licenseLabel = item.label; - } - } + + // Compare the ID of the selected license with loaded licenses from BE. + this.licenses4Selector.forEach(license4Selector => { + if (license4Selector.id !== Number(selectedLicenseId)) { + return; + } + licenseLabel = license4Selector.name; + }); + + // Reset selected value from license selector. Because if the user had chosen some clarin license, + // and then he select unsupported license the id of previous selected value is still remembered in the helper span + // with the id `secret-selected-license-from-license-selector`. + this.licenseSelectionRef.nativeElement.value = ''; return licenseLabel; } return ''; @@ -488,6 +512,11 @@ export class SubmissionSectionClarinLicenseComponent extends SectionModelCompone * Map licenses from `license-definitions.json` to the object list. */ private async loadLicenses4Selector(): Promise { + // Show PUB licenses as first. + const pubLicense4SelectorArray = []; + // Then show ACA and RES licenses. + const acaResLicense4SelectorArray = []; + await this.loadAllClarinLicenses() .then((clarinLicenseList: ClarinLicense[]) => { clarinLicenseList?.forEach(clarinLicense => { @@ -495,9 +524,21 @@ export class SubmissionSectionClarinLicenseComponent extends SectionModelCompone license4Selector.id = clarinLicense.id; license4Selector.name = clarinLicense.name; license4Selector.url = clarinLicense.definition; - this.licenses4Selector.push(license4Selector); + license4Selector.licenseLabel = clarinLicense?.clarinLicenseLabel?.label; + if (license4Selector.licenseLabel === 'PUB') { + pubLicense4SelectorArray.push(license4Selector); + } else { + acaResLicense4SelectorArray.push(license4Selector); + } }); }); + + // Sort acaResLicense4SelectorArray by the license label (ACA, RES) + acaResLicense4SelectorArray.sort((a, b) => a.licenseLabel.localeCompare(b.licenseLabel)); + + // Concat two array into one. + this.licenses4Selector = pubLicense4SelectorArray.concat(acaResLicense4SelectorArray); + this.filteredLicenses4Selector = this.licenses4Selector; } private loadAllClarinLicenses(): Promise { @@ -509,4 +550,9 @@ export class SubmissionSectionClarinLicenseComponent extends SectionModelCompone .pipe(getFirstSucceededRemoteListPayload()) .toPromise(); } + + public searchInClarinLicenses(event) { + this.filteredLicenses4Selector = this.licenses4Selector + .filter(license4Selector => license4Selector.name.toLowerCase().includes(event.target.value.toLowerCase())); + } } diff --git a/src/license-selector-creation.js b/src/license-selector-creation.js index 44932202d96..95eb30463a2 100644 --- a/src/license-selector-creation.js +++ b/src/license-selector-creation.js @@ -60,7 +60,7 @@ $(function() { for (var i = 0; i < allLic.length; i++) { if (allLic[i].href == selectedLic) { var id = allLic[i].name.replace("license_", ""); - document.getElementById('aspect_submission_StepTransformer_field_license').value = id; + document.getElementById('secret-selected-license-from-license-selector').value = id; $("#aspect_submission_StepTransformer_item_license-not-supported-message").addClass("hidden"); document.getElementById('secret-change-button').click(); return; diff --git a/src/styles/_clarin-styles.scss b/src/styles/_clarin-styles.scss new file mode 100644 index 00000000000..68f3511cb25 --- /dev/null +++ b/src/styles/_clarin-styles.scss @@ -0,0 +1,11 @@ +.label-PUB { + background-color: #5cb811; +} + +.label-ACA, .label-PDT { + background-color: #ffab23; +} + +.label-RES { + background-color: #c62d1f; +} diff --git a/src/themes/custom/styles/_global-styles.scss b/src/themes/custom/styles/_global-styles.scss index 3857f1ad0ac..ab9c407f3b2 100644 --- a/src/themes/custom/styles/_global-styles.scss +++ b/src/themes/custom/styles/_global-styles.scss @@ -2,3 +2,4 @@ // imports the base global style @import '../../../styles/_global-styles.scss'; +@import '../../../styles/_clarin-styles.scss'; diff --git a/src/themes/dspace/styles/_global-styles.scss b/src/themes/dspace/styles/_global-styles.scss index 52dd55b01da..170ccb6c9bc 100644 --- a/src/themes/dspace/styles/_global-styles.scss +++ b/src/themes/dspace/styles/_global-styles.scss @@ -2,6 +2,7 @@ // imports the base global style @import '../../../styles/_global-styles.scss'; +@import '../../../styles/_clarin-styles.scss'; .facet-filter, .setting-option { background-color: var(--bs-light);