From 79aa27c38952763e861696e5060554c55df076e7 Mon Sep 17 00:00:00 2001 From: Cheng Shi Date: Mon, 28 Apr 2025 16:55:06 -0400 Subject: [PATCH 1/6] fix: filter out versions that were deaccessioned --- .../models/DatasetVersionSummaryInfo.ts | 4 +- .../DeaccessionDatasetModal.tsx | 54 ++++++++++--------- .../DeaccessionDatasetButton.spec.tsx | 38 +++++++++++++ 3 files changed, 68 insertions(+), 28 deletions(-) diff --git a/src/dataset/domain/models/DatasetVersionSummaryInfo.ts b/src/dataset/domain/models/DatasetVersionSummaryInfo.ts index fb18d915c..8ebe7ac32 100644 --- a/src/dataset/domain/models/DatasetVersionSummaryInfo.ts +++ b/src/dataset/domain/models/DatasetVersionSummaryInfo.ts @@ -16,8 +16,8 @@ export type DatasetVersionSummary = { } interface Deaccessioned { - deaccessionReason: string - deaccessionURL: string + reason: string + url: string } export interface SummaryUpdates { diff --git a/src/sections/dataset/deaccession-dataset/DeaccessionDatasetModal.tsx b/src/sections/dataset/deaccession-dataset/DeaccessionDatasetModal.tsx index 4b6b0ecc6..e75fd4391 100644 --- a/src/sections/dataset/deaccession-dataset/DeaccessionDatasetModal.tsx +++ b/src/sections/dataset/deaccession-dataset/DeaccessionDatasetModal.tsx @@ -1,5 +1,5 @@ import { Trans, useTranslation } from 'react-i18next' -import { Alert, Button, Form, Modal, Stack } from '@iqss/dataverse-design-system' +import { Alert, Button, Col, Form, Modal, Stack } from '@iqss/dataverse-design-system' import { DatasetVersionSummaryInfo } from '@/dataset/domain/models/DatasetVersionSummaryInfo' import { isValidURL } from '@/metadata-block-info/domain/models/fieldValidations' import { DeaccessionFormData } from './DeaccessionFormData' @@ -58,7 +58,7 @@ export function DeaccessionDatasetModal({
{publishedVersions.length > 1 && ( - + {t('deaccession.version.label')}
( <> - {publishedVersions.map( - (version) => - version.publishedOn && ( - { - const newValue = e.target.checked - ? [...field.value, e.target.value] - : field.value.filter((val) => val !== e.target.value) - - field.onChange(newValue) - }} - /> - ) - )} + {publishedVersions + .filter((version) => { + const summary = version.summary as { deaccessioned?: object } + return version.publishedOn && !summary.deaccessioned + }) + .map((version) => ( + { + const newValue = e.target.checked + ? [...field.value, e.target.value] + : field.value.filter((val) => val !== e.target.value) + field.onChange(newValue) + }} + /> + ))} )} />
)} - + {t('deaccession.reason.label')} )}> - + {t('deaccession.reasonOther.label')} - + {t('deaccession.forwardUrl.label')} { cy.get('button').contains('Yes').should('exist').click() cy.wrap(repository.deaccession).should('be.calledTwice') }) + + it('does not show deaccessioned versions in the version list', () => { + const versionsSummaries: DatasetVersionSummaryInfo[] = [ + { + id: 1, + versionNumber: '1.0', + publishedOn: '2021-01-01', + contributors: 'Contributors', + summary: { + deaccessioned: { + reason: 'IRB request.', + url: 'https://example.com' + } + } // This version is deaccessioned + }, + { + id: 2, + versionNumber: '2.0', + publishedOn: '2021-01-02', + contributors: 'Contributors', + summary: {} + } + ] + + const dataset = DatasetMother.create({ + permissions: DatasetPermissionsMother.createWithPublishingDatasetAllowed(), + version: DatasetVersionMother.createReleased(), + versionsSummaries: versionsSummaries + }) + + cy.customMount() + + cy.findByRole('button', { name: 'Deaccession Dataset' }).click() + cy.get('form').should('exist') + cy.findByText('1.0 - 2021-01-01').should('not.exist') + cy.findByText('2.0 - 2021-01-02').should('exist') + cy.get('input[type="checkbox"]').should('have.length', 1) + }) }) }) From 07c5ccb022e14b4df33e15259c3bfa6c83492eb4 Mon Sep 17 00:00:00 2001 From: Cheng Shi Date: Mon, 28 Apr 2025 17:35:15 -0400 Subject: [PATCH 2/6] fix: add loading to deaccession confirm modal --- .../DeaccessionDatasetButton.tsx | 1 + .../deaccession-dataset/ConfirmationModal.tsx | 15 +++++++++---- .../ConfirmationModal.stories.tsx | 22 +++++++++++++++++-- .../DeaccessionDatasetButton.spec.tsx | 9 +++++--- 4 files changed, 38 insertions(+), 9 deletions(-) diff --git a/src/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.tsx b/src/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.tsx index 686b7ffaa..4cc1ef05f 100644 --- a/src/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.tsx +++ b/src/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.tsx @@ -91,6 +91,7 @@ export function DeaccessionDatasetButton({ submissionStatus={submissionStatus} deaccessionError={deaccessionError} show={showConfirmationModal} + isDeaccessioning={submissionStatus === 'IsSubmitting'} onConfirm={handleConfirmDeaccession} onCancel={handleCancelConfirmation} /> diff --git a/src/sections/dataset/deaccession-dataset/ConfirmationModal.tsx b/src/sections/dataset/deaccession-dataset/ConfirmationModal.tsx index b747612d0..dbfd73e23 100644 --- a/src/sections/dataset/deaccession-dataset/ConfirmationModal.tsx +++ b/src/sections/dataset/deaccession-dataset/ConfirmationModal.tsx @@ -1,4 +1,4 @@ -import { Modal, Button, Alert } from '@iqss/dataverse-design-system' +import { Modal, Button, Alert, Spinner, Stack } from '@iqss/dataverse-design-system' import { useTranslation } from 'react-i18next' import { SubmissionStatus } from '@/sections/shared/form/DatasetMetadataForm/useSubmitDataset' @@ -6,6 +6,7 @@ interface ConfirmationModalProps { show: boolean submissionStatus: SubmissionStatus deaccessionError: string | null + isDeaccessioning: boolean onConfirm: () => void onCancel: () => void } @@ -14,6 +15,7 @@ export function ConfirmationModal({ show, submissionStatus, deaccessionError, + isDeaccessioning, onConfirm, onCancel }: ConfirmationModalProps) { @@ -35,10 +37,15 @@ export function ConfirmationModal({ )} - - diff --git a/src/stories/dataset/deaccession-dataset/ConfirmationModal.stories.tsx b/src/stories/dataset/deaccession-dataset/ConfirmationModal.stories.tsx index f2e0cb152..6dfe3f1c4 100644 --- a/src/stories/dataset/deaccession-dataset/ConfirmationModal.stories.tsx +++ b/src/stories/dataset/deaccession-dataset/ConfirmationModal.stories.tsx @@ -16,18 +16,36 @@ export const Default: Story = { {}} - onCancel={() => {}}> + onCancel={() => {}} + /> ) } + +export const WithLoading: Story = { + render: () => ( + {}} + onCancel={() => {}} + /> + ) +} + export const WithError: Story = { render: () => ( {}} - onCancel={() => {}}> + onCancel={() => {}} + /> ) } diff --git a/tests/component/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.spec.tsx b/tests/component/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.spec.tsx index f05f40686..be8285cb6 100644 --- a/tests/component/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.spec.tsx +++ b/tests/component/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.spec.tsx @@ -115,19 +115,22 @@ describe('DeaccessionDatasetButton', () => { id: 1, versionNumber: '1.0', publishedOn: '2021-01-01', - contributors: 'Contributors' + contributors: 'Contributors', + summary: {} }, { id: 2, versionNumber: '2.0', publishedOn: '2021-01-02', - contributors: 'Contributors' + contributors: 'Contributors', + summary: {} }, { id: 3, versionNumber: 'draft', publishedOn: undefined, - contributors: 'Contributors' + contributors: 'Contributors', + summary: {} } ] const dataset = DatasetMother.create({ From 1d0a947e84d2329f1703a2d067a530e8faa0b20b Mon Sep 17 00:00:00 2001 From: Cheng Shi Date: Mon, 28 Apr 2025 18:09:16 -0400 Subject: [PATCH 3/6] fix: flasky test --- .../edit-dataset-menu/DeaccessionDatasetButton.spec.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/component/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.spec.tsx b/tests/component/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.spec.tsx index be8285cb6..795385dee 100644 --- a/tests/component/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.spec.tsx +++ b/tests/component/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.spec.tsx @@ -235,7 +235,7 @@ describe('DeaccessionDatasetButton', () => { cy.findByTestId('deaccession-forward-url').type('https://example.com') cy.get('button[type="submit"]').click() cy.get('button').contains('Yes').should('exist').click() - cy.wrap(repository.deaccession).should('be.calledTwice') + cy.wrap(repository.deaccession).should('have.been.called') }) it('does not show deaccessioned versions in the version list', () => { From 19208940b3134aad5ed5b2f1096842614da945fc Mon Sep 17 00:00:00 2001 From: Cheng Shi Date: Tue, 29 Apr 2025 12:10:06 -0400 Subject: [PATCH 4/6] fix: add loading to deaccession confirm modal --- .../models/DatasetVersionSummaryInfo.ts | 4 +- .../DeaccessionDatasetButton.tsx | 11 ++--- .../deaccession-dataset/ConfirmationModal.tsx | 3 +- .../DeaccessionDatasetModal.tsx | 43 +++++++++---------- .../ConfirmationModal.stories.tsx | 5 +-- .../DeaccessionDatasetModal.stories.tsx | 16 ++++++- 6 files changed, 44 insertions(+), 38 deletions(-) diff --git a/src/dataset/domain/models/DatasetVersionSummaryInfo.ts b/src/dataset/domain/models/DatasetVersionSummaryInfo.ts index 8ebe7ac32..8de8378e7 100644 --- a/src/dataset/domain/models/DatasetVersionSummaryInfo.ts +++ b/src/dataset/domain/models/DatasetVersionSummaryInfo.ts @@ -15,9 +15,9 @@ export type DatasetVersionSummary = { | boolean } -interface Deaccessioned { +export interface Deaccessioned { reason: string - url: string + url?: string } export interface SummaryUpdates { diff --git a/src/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.tsx b/src/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.tsx index 4cc1ef05f..9c68cc92c 100644 --- a/src/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.tsx +++ b/src/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.tsx @@ -1,6 +1,7 @@ import { useState } from 'react' import { toast } from 'react-toastify' import { useContext } from 'react' +import { useForm, SubmitHandler } from 'react-hook-form' import { DatasetContext } from '@/sections/dataset/DatasetContext' import { Dataset } from '../../../../dataset/domain/models/Dataset' import { DropdownButtonItem, DropdownSeparator } from '@iqss/dataverse-design-system' @@ -10,7 +11,7 @@ import { DatasetRepository } from '@/dataset/domain/repositories/DatasetReposito import { DeaccessionFormData } from '@/sections/dataset/deaccession-dataset/DeaccessionFormData' import { useDeaccessionDataset } from '@/sections/dataset/deaccession-dataset/useDeaccessionDataset' import { ConfirmationModal } from '@/sections/dataset/deaccession-dataset/ConfirmationModal' -import { useForm, SubmitHandler } from 'react-hook-form' +import { Deaccessioned } from '@/dataset/domain/models/DatasetVersionSummaryInfo' interface DeaccessionDatasetButtonProps { dataset: Dataset @@ -31,9 +32,10 @@ export function DeaccessionDatasetButton({ onDeaccessionSucceed ) const publishedVersions = - dataset.versionsSummaries?.filter( - (version) => version.publishedOn && version.summary !== 'versionDeaccessioned' - ) || [] + dataset.versionsSummaries?.filter((version) => { + const summary = version.summary as { deaccessioned: Deaccessioned } + return version.publishedOn && !summary.deaccessioned + }) || [] const defaultVersions = publishedVersions.length === 1 ? [publishedVersions[0].versionNumber] : [] function onDeaccessionSucceed() { setShowConfirmationModal(false) @@ -91,7 +93,6 @@ export function DeaccessionDatasetButton({ submissionStatus={submissionStatus} deaccessionError={deaccessionError} show={showConfirmationModal} - isDeaccessioning={submissionStatus === 'IsSubmitting'} onConfirm={handleConfirmDeaccession} onCancel={handleCancelConfirmation} /> diff --git a/src/sections/dataset/deaccession-dataset/ConfirmationModal.tsx b/src/sections/dataset/deaccession-dataset/ConfirmationModal.tsx index dbfd73e23..4e083cbc1 100644 --- a/src/sections/dataset/deaccession-dataset/ConfirmationModal.tsx +++ b/src/sections/dataset/deaccession-dataset/ConfirmationModal.tsx @@ -6,7 +6,6 @@ interface ConfirmationModalProps { show: boolean submissionStatus: SubmissionStatus deaccessionError: string | null - isDeaccessioning: boolean onConfirm: () => void onCancel: () => void } @@ -15,11 +14,11 @@ export function ConfirmationModal({ show, submissionStatus, deaccessionError, - isDeaccessioning, onConfirm, onCancel }: ConfirmationModalProps) { const { t } = useTranslation(['dataset', 'shared']) + const isDeaccessioning = submissionStatus === SubmissionStatus.IsSubmitting return ( diff --git a/src/sections/dataset/deaccession-dataset/DeaccessionDatasetModal.tsx b/src/sections/dataset/deaccession-dataset/DeaccessionDatasetModal.tsx index e75fd4391..760adbeba 100644 --- a/src/sections/dataset/deaccession-dataset/DeaccessionDatasetModal.tsx +++ b/src/sections/dataset/deaccession-dataset/DeaccessionDatasetModal.tsx @@ -70,29 +70,26 @@ export function DeaccessionDatasetModal({ }} render={({ field }) => ( <> - {publishedVersions - .filter((version) => { - const summary = version.summary as { deaccessioned?: object } - return version.publishedOn && !summary.deaccessioned - }) - .map((version) => ( - { - const newValue = e.target.checked - ? [...field.value, e.target.value] - : field.value.filter((val) => val !== e.target.value) - field.onChange(newValue) - }} - /> - ))} + {publishedVersions.map( + (version) => + version.publishedOn && ( + { + const newValue = e.target.checked + ? [...field.value, e.target.value] + : field.value.filter((val) => val !== e.target.value) + field.onChange(newValue) + }} + /> + ) + )} )} /> diff --git a/src/stories/dataset/deaccession-dataset/ConfirmationModal.stories.tsx b/src/stories/dataset/deaccession-dataset/ConfirmationModal.stories.tsx index 6dfe3f1c4..5edf6d046 100644 --- a/src/stories/dataset/deaccession-dataset/ConfirmationModal.stories.tsx +++ b/src/stories/dataset/deaccession-dataset/ConfirmationModal.stories.tsx @@ -15,8 +15,7 @@ export const Default: Story = { render: () => ( {}} onCancel={() => {}} @@ -29,7 +28,6 @@ export const WithLoading: Story = { {}} onCancel={() => {}} @@ -42,7 +40,6 @@ export const WithError: Story = { {}} onCancel={() => {}} diff --git a/src/stories/dataset/deaccession-dataset/DeaccessionDatasetModal.stories.tsx b/src/stories/dataset/deaccession-dataset/DeaccessionDatasetModal.stories.tsx index 8f4235dab..2bca855c3 100644 --- a/src/stories/dataset/deaccession-dataset/DeaccessionDatasetModal.stories.tsx +++ b/src/stories/dataset/deaccession-dataset/DeaccessionDatasetModal.stories.tsx @@ -33,8 +33,20 @@ export const Default: Story = { control={control} errors={{}} publishedVersions={[ - { id: 1, contributors: 'contributors', versionNumber: '1.0', publishedOn: '2023-01-01' }, - { id: 2, contributors: 'contributors', versionNumber: '1.1', publishedOn: '2023-02-01' } + { + id: 1, + contributors: 'contributors', + versionNumber: '1.0', + publishedOn: '2023-01-01', + summary: {} + }, + { + id: 2, + contributors: 'contributors', + versionNumber: '1.1', + publishedOn: '2023-02-01', + summary: {} + } ]} /> ) From 7875c596b339611e40b0b63f1d39224db67bdbde Mon Sep 17 00:00:00 2001 From: Cheng Shi Date: Tue, 29 Apr 2025 12:13:46 -0400 Subject: [PATCH 5/6] fix: delete something extra --- .../dataset/deaccession-dataset/DeaccessionDatasetModal.tsx | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/src/sections/dataset/deaccession-dataset/DeaccessionDatasetModal.tsx b/src/sections/dataset/deaccession-dataset/DeaccessionDatasetModal.tsx index 760adbeba..4884fdeef 100644 --- a/src/sections/dataset/deaccession-dataset/DeaccessionDatasetModal.tsx +++ b/src/sections/dataset/deaccession-dataset/DeaccessionDatasetModal.tsx @@ -76,7 +76,7 @@ export function DeaccessionDatasetModal({ Date: Tue, 29 Apr 2025 13:08:54 -0400 Subject: [PATCH 6/6] fix: test cases --- .../DeaccessionDatasetButton.spec.tsx | 49 ++++++++++++++++++- 1 file changed, 47 insertions(+), 2 deletions(-) diff --git a/tests/component/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.spec.tsx b/tests/component/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.spec.tsx index 795385dee..63e1c987d 100644 --- a/tests/component/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.spec.tsx +++ b/tests/component/sections/dataset/dataset-action-buttons/edit-dataset-menu/DeaccessionDatasetButton.spec.tsx @@ -250,7 +250,7 @@ describe('DeaccessionDatasetButton', () => { reason: 'IRB request.', url: 'https://example.com' } - } // This version is deaccessioned + } }, { id: 2, @@ -258,6 +258,13 @@ describe('DeaccessionDatasetButton', () => { publishedOn: '2021-01-02', contributors: 'Contributors', summary: {} + }, + { + id: 3, + versionNumber: '3.0', + publishedOn: '2021-01-22', + contributors: 'Contributors', + summary: {} } ] @@ -273,7 +280,45 @@ describe('DeaccessionDatasetButton', () => { cy.get('form').should('exist') cy.findByText('1.0 - 2021-01-01').should('not.exist') cy.findByText('2.0 - 2021-01-02').should('exist') - cy.get('input[type="checkbox"]').should('have.length', 1) + cy.findByText('3.0 - 2021-01-22').should('exist') + cy.get('input[type="checkbox"]').should('have.length', 2) + }) + + it('does not show versions list in the version list if there is only one deaccessioned version available', () => { + const versionsSummaries: DatasetVersionSummaryInfo[] = [ + { + id: 1, + versionNumber: '1.0', + publishedOn: '2021-01-01', + contributors: 'Contributors', + summary: { + deaccessioned: { + reason: 'IRB request.', + url: 'https://example.com' + } + } + }, + { + id: 2, + versionNumber: '2.0', + publishedOn: '2021-01-02', + contributors: 'Contributors', + summary: {} + } + ] + + const dataset = DatasetMother.create({ + permissions: DatasetPermissionsMother.createWithPublishingDatasetAllowed(), + version: DatasetVersionMother.createReleased(), + versionsSummaries: versionsSummaries + }) + + cy.customMount() + + cy.findByRole('button', { name: 'Deaccession Dataset' }).click() + cy.get('form').should('exist') + cy.findByText('1.0 - 2021-01-01').should('not.exist') + cy.findByText('2.0 - 2021-01-02').should('not.exist') }) }) })