Skip to content

Commit

Permalink
feat(IntegrationDatasetLocks): integrate locks userPersistentId
Browse files Browse the repository at this point in the history
  • Loading branch information
MellyGray committed Nov 6, 2023
1 parent 5e9b75e commit 892109a
Show file tree
Hide file tree
Showing 14 changed files with 155 additions and 63 deletions.
19 changes: 13 additions & 6 deletions src/dataset/domain/models/Dataset.ts
Original file line number Diff line number Diff line change
Expand Up @@ -259,7 +259,7 @@ export interface DatasetPermissions {
}

export interface DatasetLock {
id: number
userPersistentId: string
reason: DatasetLockReason
}

Expand Down Expand Up @@ -302,8 +302,8 @@ export class Dataset {
return this.metadataBlocks[0].fields.title
}

public get isLockedFromPublishing(): boolean {
return this.isLockedFromEdits
public checkIsLockedFromPublishing(userPersistentId: string): boolean {
return this.checkIsLockedFromEdits(userPersistentId)
}

public get isLocked(): boolean {
Expand All @@ -314,12 +314,19 @@ export class Dataset {
return this.locks.some((lock) => lock.reason === DatasetLockReason.WORKFLOW)
}

public get isLockedFromEdits(): boolean {
public checkIsLockedFromEdits(userPersistentId: string): boolean {
const lockedReasonIsInReview = this.locks.some(
(lock) => lock.reason === DatasetLockReason.IN_REVIEW
)
// If the lock reason is workflow and the workflow userId is the same as the current user, then the user can edit
// TODO - Ask how we want to manage pending workflows

if (
this.locks.some(
(lock) =>
lock.reason === DatasetLockReason.WORKFLOW && lock.userPersistentId === userPersistentId
)
) {
return false
}

return this.isLocked && !(lockedReasonIsInReview && this.permissions.canPublishDataset)
}
Expand Down
2 changes: 1 addition & 1 deletion src/dataset/infrastructure/mappers/JSDatasetMapper.ts
Original file line number Diff line number Diff line change
Expand Up @@ -193,7 +193,7 @@ export class JSDatasetMapper {
static toLocks(jsDatasetLocks: JSDatasetLock[]): DatasetLock[] {
return jsDatasetLocks.map((jsDatasetLock) => {
return {
id: 0,
userPersistentId: jsDatasetLock.userId,
reason: jsDatasetLock.lockType as unknown as DatasetLockReason
}
})
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,13 +4,16 @@ import { EditDatasetPermissionsMenu } from './EditDatasetPermissionsMenu'
import { DeleteDatasetButton } from './DeleteDatasetButton'
import { DeaccessionDatasetButton } from './DeaccessionDatasetButton'
import { useTranslation } from 'react-i18next'
import { useSession } from '../../../session/SessionContext'

interface EditDatasetMenuProps {
dataset: Dataset
}

export function EditDatasetMenu({ dataset }: EditDatasetMenuProps) {
if (!dataset.permissions.canUpdateDataset) {
const { user } = useSession()

if (!user || !dataset.permissions.canUpdateDataset) {
return <></>
}

Expand All @@ -21,7 +24,7 @@ export function EditDatasetMenu({ dataset }: EditDatasetMenuProps) {
title={t('datasetActionButtons.editDataset.title')}
asButtonGroup
variant="secondary"
disabled={dataset.isLockedFromEdits}>
disabled={dataset.checkIsLockedFromEdits(user.persistentId)}>
<DropdownButtonItem disabled={!dataset.hasValidTermsOfAccess}>
{t('datasetActionButtons.editDataset.filesUpload')}
</DropdownButtonItem>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -2,15 +2,18 @@ import { Dataset, DatasetPublishingStatus } from '../../../../dataset/domain/mod
import { DropdownButton, DropdownButtonItem } from '@iqss/dataverse-design-system'
import { ChangeCurationStatusMenu } from './ChangeCurationStatusMenu'
import { useTranslation } from 'react-i18next'
import { useSession } from '../../../session/SessionContext'

interface PublishDatasetMenuProps {
dataset: Dataset
}

export function PublishDatasetMenu({ dataset }: PublishDatasetMenuProps) {
const { user } = useSession()
if (
!dataset.version.isLatest ||
dataset.version.publishingStatus !== DatasetPublishingStatus.DRAFT ||
!user ||
!dataset.permissions.canPublishDataset
) {
return <></>
Expand All @@ -24,7 +27,9 @@ export function PublishDatasetMenu({ dataset }: PublishDatasetMenuProps) {
asButtonGroup
variant="secondary"
disabled={
dataset.isLockedFromPublishing || !dataset.hasValidTermsOfAccess || !dataset.isValid
dataset.checkIsLockedFromPublishing(user.persistentId) ||
!dataset.hasValidTermsOfAccess ||
!dataset.isValid
}>
<DropdownButtonItem>{t('datasetActionButtons.publish.publish')}</DropdownButtonItem>
{dataset.version.isInReview && (
Expand Down
Original file line number Diff line number Diff line change
@@ -1,17 +1,20 @@
import { Dataset, DatasetPublishingStatus } from '../../../../dataset/domain/models/Dataset'
import { Button } from '@iqss/dataverse-design-system'
import { useTranslation } from 'react-i18next'
import { useSession } from '../../../session/SessionContext'

interface SubmitForReviewButtonProps {
dataset: Dataset
}

export function SubmitForReviewButton({ dataset }: SubmitForReviewButtonProps) {
const { user } = useSession()
if (
!dataset.version.isLatest ||
dataset.version.publishingStatus !== DatasetPublishingStatus.DRAFT ||
dataset.isLockedInWorkflow ||
dataset.permissions.canPublishDataset ||
!user ||
!dataset.permissions.canUpdateDataset
) {
return <></>
Expand All @@ -22,7 +25,9 @@ export function SubmitForReviewButton({ dataset }: SubmitForReviewButtonProps) {
<Button
variant="secondary"
disabled={
dataset.isLockedFromPublishing || !dataset.hasValidTermsOfAccess || !dataset.isValid
dataset.checkIsLockedFromPublishing(user.persistentId) ||
!dataset.hasValidTermsOfAccess ||
!dataset.isValid
}>
{dataset.version.isInReview
? t('datasetActionButtons.submitForReview.disabled')
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ export function DatasetUploadFilesButton() {
<Button
onClick={handleClick}
icon={<PlusLg className={styles.icon} />}
disabled={dataset.isLockedFromEdits}>
disabled={dataset.checkIsLockedFromEdits(user.persistentId)}>
{t('datasetActionButtons.uploadFiles')}
</Button>
)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -30,7 +30,7 @@ export function EditFilesMenu({ files, fileSelection }: EditFilesMenuProps) {
variant="secondary"
id="edit-files-menu"
title={t('actions.editFilesMenu.title')}
disabled={dataset.isLockedFromEdits || !dataset.hasValidTermsOfAccess}
disabled={dataset.checkIsLockedFromEdits(user.persistentId) || !dataset.hasValidTermsOfAccess}
icon={<PencilFill className={styles.icon} />}>
<EditFilesOptions files={files} fileSelection={fileSelection} />
</DropdownButton>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ export function FileOptionsMenu({ file }: { file: File }) {
<Tooltip placement="top" overlay={<span>{t('actions.optionsMenu.title')}</span>}>
<Button
id={`file-options-file-${file.id}`}
disabled={dataset.isLockedFromEdits}
disabled={dataset.checkIsLockedFromEdits(user.persistentId)}
variant="secondary"
icon={
<ThreeDotsVertical
Expand All @@ -47,7 +47,7 @@ export function FileOptionsMenu({ file }: { file: File }) {
<DropdownButton
id={`file-options-file-${file.id}`}
title=""
disabled={dataset.isLockedFromEdits}
disabled={dataset.checkIsLockedFromEdits(user.persistentId)}
asButtonGroup
variant="secondary"
icon={<ThreeDotsVertical aria-label={t('actions.optionsMenu.title')} />}>
Expand Down
2 changes: 1 addition & 1 deletion tests/component/dataset/domain/models/DatasetMother.ts
Original file line number Diff line number Diff line change
Expand Up @@ -166,7 +166,7 @@ export class DatasetPermissionsMother {
export class DatasetLockMother {
static create(props?: Partial<DatasetLock>): DatasetLock {
return {
id: faker.datatype.number(),
userPersistentId: faker.internet.userName(),
reason: faker.helpers.arrayElement(Object.values(DatasetLockReason)),
...props
}
Expand Down
Original file line number Diff line number Diff line change
@@ -1,11 +1,16 @@
import chai from 'chai'
import chaiAsPromised from 'chai-as-promised'
import { JSDatasetMapper } from '../../../../../src/dataset/infrastructure/mappers/JSDatasetMapper'
import { DatasetVersionState } from '@iqss/dataverse-client-javascript'
import {
DatasetLockType,
DatasetVersionState,
DatasetLock as JSDatasetLock
} from '@iqss/dataverse-client-javascript'
import {
CitationMetadataBlock,
DatasetMetadataBlock
} from '@iqss/dataverse-client-javascript/dist/datasets/domain/models/Dataset'
import { DatasetLockReason } from '../../../../../src/dataset/domain/models/Dataset'

chai.use(chaiAsPromised)
const expect = chai.expect
Expand Down Expand Up @@ -51,6 +56,13 @@ const jsDataset = {
const citation =
'Finch, Fiona, 2023, "Darwin\'s Finches", <a href="https://doi.org/10.5072/FK2/B4B2MJ" target="_blank">https://doi.org/10.5072/FK2/B4B2MJ</a>, Root, DRAFT VERSION'
const datasetSummaryFields = ['dsDescription', 'subject', 'keyword', 'publication', 'notesText']
const jsDatasetLocks: JSDatasetLock[] = [
{
lockType: DatasetLockType.IN_REVIEW,
userId: 'dataverseAdmin',
datasetPersistentId: 'doi:10.5072/FK2/B4B2MJ'
}
]
const expectedDataset = {
persistentId: 'doi:10.5072/FK2/B4B2MJ',
version: {
Expand Down Expand Up @@ -116,7 +128,12 @@ const expectedDataset = {
canManageFilesPermissions: true,
canDeleteDataset: true
},
locks: [],
locks: [
{
userPersistentId: 'dataverseAdmin',
reason: DatasetLockReason.IN_REVIEW
}
],
hasValidTermsOfAccess: true,
isValid: true,
isReleased: false,
Expand Down Expand Up @@ -176,7 +193,12 @@ const expectedDatasetAlternateVersion = {
uri: 'http://creativecommons.org/publicdomain/zero/1.0',
iconUri: 'https://licensebuttons.net/p/zero/1.0/88x31.png'
},
locks: [],
locks: [
{
userPersistentId: 'dataverseAdmin',
reason: DatasetLockReason.IN_REVIEW
}
],
metadataBlocks: [
{
name: 'citation',
Expand Down Expand Up @@ -208,14 +230,20 @@ const expectedDatasetAlternateVersion = {
}
describe('JS Dataset Mapper', () => {
it('maps jsDataset model to the domain Dataset model', () => {
const mapped = JSDatasetMapper.toDataset(jsDataset, citation, datasetSummaryFields)
const mapped = JSDatasetMapper.toDataset(
jsDataset,
citation,
datasetSummaryFields,
jsDatasetLocks
)
expect(expectedDataset).to.deep.equal(mapped)
})
it('maps jsDataset model to the domain Dataset model for alternate version', () => {
const mappedWithAlternate = JSDatasetMapper.toDataset(
jsDataset,
citation,
datasetSummaryFields,
jsDatasetLocks,
'4.0'
)

Expand Down Expand Up @@ -255,7 +283,8 @@ describe('JS Dataset Mapper', () => {
JSDatasetMapper.toDataset(
jsDatasetWithAlternativePersistentId,
citation,
datasetSummaryFields
datasetSummaryFields,
jsDatasetLocks
)
)
})
Expand Down Expand Up @@ -290,7 +319,12 @@ describe('JS Dataset Mapper', () => {
}

expect(expectedDatasetWithCitationDate).to.deep.equal(
JSDatasetMapper.toDataset(jsDatasetWithCitationDate, citation, datasetSummaryFields)
JSDatasetMapper.toDataset(
jsDatasetWithCitationDate,
citation,
datasetSummaryFields,
jsDatasetLocks
)
)
})

Expand Down Expand Up @@ -323,7 +357,12 @@ describe('JS Dataset Mapper', () => {
]
}
expect(expectedDatasetWithPublicationDate).to.deep.equal(
JSDatasetMapper.toDataset(jsDatasetWithPublicationDate, citation, datasetSummaryFields)
JSDatasetMapper.toDataset(
jsDatasetWithPublicationDate,
citation,
datasetSummaryFields,
jsDatasetLocks
)
)
})
})
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ describe('EditDatasetMenu', () => {
isReleased: true
})

cy.customMount(<EditDatasetMenu dataset={dataset} />)
cy.mountAuthenticated(<EditDatasetMenu dataset={dataset} />)

cy.findByRole('button', { name: 'Edit Dataset' }).should('exist').should('be.enabled').click()

Expand All @@ -30,13 +30,27 @@ describe('EditDatasetMenu', () => {
cy.findByRole('button', { name: 'Deaccession Dataset' }).should('exist')
})

it('does not render if the user is not authenticated', () => {
const dataset = DatasetMother.create({
permissions: DatasetPermissionsMother.createWithAllAllowed(),
locks: [],
hasValidTermsOfAccess: true,
version: DatasetVersionMother.createReleasedWithLatestVersionIsADraft(),
isReleased: true
})

cy.customMount(<EditDatasetMenu dataset={dataset} />)

cy.findByRole('button', { name: 'Edit Dataset' }).should('not.exist')
})

it('does not render the EditDatasetMenu if the user does not have update dataset permissions', () => {
const dataset = DatasetMother.create({
permissions: DatasetPermissionsMother.createWithUpdateDatasetNotAllowed(),
locks: []
})

cy.customMount(<EditDatasetMenu dataset={dataset} />)
cy.mountAuthenticated(<EditDatasetMenu dataset={dataset} />)

cy.findByRole('button', { name: 'Edit Dataset' }).should('not.exist')
})
Expand All @@ -47,7 +61,7 @@ describe('EditDatasetMenu', () => {
locks: [DatasetLockMother.createLockedInEditInProgress()]
})

cy.customMount(<EditDatasetMenu dataset={dataset} />)
cy.mountAuthenticated(<EditDatasetMenu dataset={dataset} />)

cy.findByRole('button', { name: 'Edit Dataset' }).should('exist').should('be.disabled')
})
Expand All @@ -59,7 +73,7 @@ describe('EditDatasetMenu', () => {
hasValidTermsOfAccess: true
})

cy.customMount(<EditDatasetMenu dataset={dataset} />)
cy.mountAuthenticated(<EditDatasetMenu dataset={dataset} />)

cy.findByRole('button', { name: 'Edit Dataset' }).click()
cy.findByRole('button', { name: 'Files (Upload)' })
Expand All @@ -77,7 +91,7 @@ describe('EditDatasetMenu', () => {
hasValidTermsOfAccess: false
})

cy.customMount(<EditDatasetMenu dataset={dataset} />)
cy.mountAuthenticated(<EditDatasetMenu dataset={dataset} />)

cy.findByRole('button', { name: 'Edit Dataset' }).click()
cy.findByRole('button', { name: 'Files (Upload)' })
Expand Down
Loading

0 comments on commit 892109a

Please sign in to comment.