diff --git a/docs/useCases.md b/docs/useCases.md index d80ff7b4..db6feccc 100644 --- a/docs/useCases.md +++ b/docs/useCases.md @@ -39,6 +39,7 @@ The different use cases currently available in the package are classified below, - [Get Dataset Linked Collections](#get-dataset-linked-collections) - [Get Dataset Available Categories](#get-dataset-available-categories) - [Get Dataset Templates](#get-dataset-templates) + - [Get Dataset Available Dataset Types](#get-dataset-available-dataset-types) - [Datasets write use cases](#datasets-write-use-cases) - [Create a Dataset](#create-a-dataset) - [Update a Dataset](#update-a-dataset) @@ -809,6 +810,24 @@ getDatasetLinkedCollections _See [use case](../src/datasets/domain/useCases/GetDatasetLinkedCollections.ts) implementation_. +#### Get Dataset Available Dataset Types + +Returns a list of available dataset types that can be used at dataset creation. By default, only the type "dataset" is returned. + +###### Example call: + +```typescript +import { getDatasetAvailableDatasetTypes } from '@iqss/dataverse-client-javascript' + +/* ... */ + +getDatasetAvailableDatasetTypes.execute().then((datasetTypes: DatasetType[]) => { + /* ... */ +}) +``` + +_See [use case](../src/datasets/domain/useCases/GetDatasetAvailableDatasetTypes.ts) implementation_. + ### Datasets Write Use Cases #### Create a Dataset diff --git a/src/datasets/domain/models/DatasetType.ts b/src/datasets/domain/models/DatasetType.ts new file mode 100644 index 00000000..5475cdaf --- /dev/null +++ b/src/datasets/domain/models/DatasetType.ts @@ -0,0 +1,6 @@ +export interface DatasetType { + id: number + name: string + linkedMetadataBlocks?: string[] + availableLicenses?: string[] +} diff --git a/src/datasets/domain/repositories/IDatasetsRepository.ts b/src/datasets/domain/repositories/IDatasetsRepository.ts index 499dfed0..fb8b26d5 100644 --- a/src/datasets/domain/repositories/IDatasetsRepository.ts +++ b/src/datasets/domain/repositories/IDatasetsRepository.ts @@ -13,6 +13,7 @@ import { DatasetLinkedCollection } from '../models/DatasetLinkedCollection' import { CitationFormat } from '../models/CitationFormat' import { FormattedCitation } from '../models/FormattedCitation' import { DatasetTemplate } from '../models/DatasetTemplate' +import { DatasetType } from '../models/DatasetType' export interface IDatasetsRepository { getDataset( @@ -76,4 +77,5 @@ export interface IDatasetsRepository { includeDeaccessioned?: boolean ): Promise getDatasetTemplates(collectionIdOrAlias: number | string): Promise + getDatasetAvailableDatasetTypes(): Promise } diff --git a/src/datasets/domain/useCases/GetDatasetAvailableDatasetTypes.ts b/src/datasets/domain/useCases/GetDatasetAvailableDatasetTypes.ts new file mode 100644 index 00000000..c7dce4a5 --- /dev/null +++ b/src/datasets/domain/useCases/GetDatasetAvailableDatasetTypes.ts @@ -0,0 +1,20 @@ +import { UseCase } from '../../../core/domain/useCases/UseCase' +import { DatasetType } from '../models/DatasetType' +import { IDatasetsRepository } from '../repositories/IDatasetsRepository' + +export class GetDatasetAvailableDatasetTypes implements UseCase { + private datasetsRepository: IDatasetsRepository + + constructor(datasetsRepository: IDatasetsRepository) { + this.datasetsRepository = datasetsRepository + } + + /** + * Returns the list of available dataset types that can be selected when creating a dataset. + * + * @returns {Promise} + */ + async execute(): Promise { + return await this.datasetsRepository.getDatasetAvailableDatasetTypes() + } +} diff --git a/src/datasets/index.ts b/src/datasets/index.ts index aadd5fa8..e6de1b8c 100644 --- a/src/datasets/index.ts +++ b/src/datasets/index.ts @@ -24,6 +24,7 @@ import { LinkDataset } from './domain/useCases/LinkDataset' import { UnlinkDataset } from './domain/useCases/UnlinkDataset' import { GetDatasetLinkedCollections } from './domain/useCases/GetDatasetLinkedCollections' import { GetDatasetAvailableCategories } from './domain/useCases/GetDatasetAvailableCategories' +import { GetDatasetAvailableDatasetTypes } from './domain/useCases/GetDatasetAvailableDatasetTypes' import { GetDatasetCitationInOtherFormats } from './domain/useCases/GetDatasetCitationInOtherFormats' import { GetDatasetTemplates } from './domain/useCases/GetDatasetTemplates' @@ -64,6 +65,7 @@ const linkDataset = new LinkDataset(datasetsRepository) const unlinkDataset = new UnlinkDataset(datasetsRepository) const getDatasetLinkedCollections = new GetDatasetLinkedCollections(datasetsRepository) const getDatasetAvailableCategories = new GetDatasetAvailableCategories(datasetsRepository) +const getDatasetAvailableDatasetTypes = new GetDatasetAvailableDatasetTypes(datasetsRepository) const getDatasetCitationInOtherFormats = new GetDatasetCitationInOtherFormats(datasetsRepository) const getDatasetTemplates = new GetDatasetTemplates(datasetsRepository) @@ -89,7 +91,8 @@ export { getDatasetLinkedCollections, getDatasetAvailableCategories, getDatasetCitationInOtherFormats, - getDatasetTemplates + getDatasetTemplates, + getDatasetAvailableDatasetTypes } export { DatasetNotNumberedVersion } from './domain/models/DatasetNotNumberedVersion' export { DatasetUserPermissions } from './domain/models/DatasetUserPermissions' @@ -124,3 +127,4 @@ export { DatasetVersionSummaryStringValues } from './domain/models/DatasetVersionSummaryInfo' export { DatasetLinkedCollection } from './domain/models/DatasetLinkedCollection' +export { DatasetType } from './domain/models/DatasetType' diff --git a/src/datasets/infra/repositories/DatasetsRepository.ts b/src/datasets/infra/repositories/DatasetsRepository.ts index 9a38eaae..594744b4 100644 --- a/src/datasets/infra/repositories/DatasetsRepository.ts +++ b/src/datasets/infra/repositories/DatasetsRepository.ts @@ -28,6 +28,7 @@ import { FormattedCitation } from '../../domain/models/FormattedCitation' import { DatasetTemplate } from '../../domain/models/DatasetTemplate' import { DatasetTemplatePayload } from './transformers/DatasetTemplatePayload' import { transformDatasetTemplatePayloadToDatasetTemplate } from './transformers/datasetTemplateTransformers' +import { DatasetType } from '../../domain/models/DatasetType' export interface GetAllDatasetPreviewsQueryParams { per_page?: number @@ -373,4 +374,12 @@ export class DatasetsRepository extends ApiRepository implements IDatasetsReposi throw error }) } + + public async getDatasetAvailableDatasetTypes(): Promise { + return this.doGet(this.buildApiEndpoint(this.datasetsResourceName, 'datasetTypes')) + .then((response) => response.data.data) + .catch((error) => { + throw error + }) + } } diff --git a/test/functional/datasets/GetDatasetAvailableDatasetTypes.test.ts b/test/functional/datasets/GetDatasetAvailableDatasetTypes.test.ts new file mode 100644 index 00000000..14a1a2fd --- /dev/null +++ b/test/functional/datasets/GetDatasetAvailableDatasetTypes.test.ts @@ -0,0 +1,29 @@ +import { ApiConfig, DatasetType, getDatasetAvailableDatasetTypes } from '../../../src' +import { DataverseApiAuthMechanism } from '../../../src/core/infra/repositories/ApiConfig' +import { TestConstants } from '../../testHelpers/TestConstants' + +describe('getDatasetAvailableDatasetTypes', () => { + describe('execute', () => { + beforeAll(async () => { + ApiConfig.init( + TestConstants.TEST_API_URL, + DataverseApiAuthMechanism.API_KEY, + process.env.TEST_API_KEY + ) + }) + + test('should return available dataset types', async () => { + const actualDatasetTypes: DatasetType[] = await getDatasetAvailableDatasetTypes.execute() + const expectedDatasetTypes = [ + { + id: 1, + name: 'dataset', + linkedMetadataBlocks: [], + availableLicenses: [] + } + ] + + expect(actualDatasetTypes).toEqual(expectedDatasetTypes) + }) + }) +}) diff --git a/test/integration/datasets/DatasetsRepository.test.ts b/test/integration/datasets/DatasetsRepository.test.ts index ba9c9d79..bb44f3d2 100644 --- a/test/integration/datasets/DatasetsRepository.test.ts +++ b/test/integration/datasets/DatasetsRepository.test.ts @@ -20,7 +20,9 @@ import { CreatedDatasetIdentifiers, DatasetDTO, DatasetDeaccessionDTO, - publishDataset + publishDataset, + DatasetType, + getDatasetAvailableDatasetTypes } from '../../../src/datasets' import { ApiConfig, WriteError } from '../../../src' import { DataverseApiAuthMechanism } from '../../../src/core/infra/repositories/ApiConfig' @@ -1688,4 +1690,20 @@ describe('DatasetsRepository', () => { await deleteDatasetTemplateViaApi(actual[0].id) }) }) + + describe('getDatasetAvailableDatasetTypes', () => { + test('should return available dataset types', async () => { + const actualDatasetTypes: DatasetType[] = await getDatasetAvailableDatasetTypes.execute() + const expectedDatasetTypes = [ + { + id: 1, + name: 'dataset', + linkedMetadataBlocks: [], + availableLicenses: [] + } + ] + + expect(actualDatasetTypes).toEqual(expectedDatasetTypes) + }) + }) }) diff --git a/test/unit/datasets/GetDatasetAvailableDatasetTypes.test.ts b/test/unit/datasets/GetDatasetAvailableDatasetTypes.test.ts new file mode 100644 index 00000000..b8768f92 --- /dev/null +++ b/test/unit/datasets/GetDatasetAvailableDatasetTypes.test.ts @@ -0,0 +1,49 @@ +import { ReadError } from '../../../src' +import { DatasetType } from '../../../src' +import { IDatasetsRepository } from '../../../src/datasets/domain/repositories/IDatasetsRepository' +import { GetDatasetAvailableDatasetTypes } from '../../../src/datasets/domain/useCases/GetDatasetAvailableDatasetTypes' + +describe('GetDatasetAvailableDatasetTypes', () => { + describe('execute', () => { + test('should return datasetTypes array on repository success', async () => { + const datasetTypesRepositoryStub: IDatasetsRepository = {} as IDatasetsRepository + + const testDatasetTypes: DatasetType[] = [ + { + id: 1, + name: 'dataset', + linkedMetadataBlocks: [], + availableLicenses: [] + }, + { + id: 2, + name: 'software', + linkedMetadataBlocks: ['codeMeta20'], + availableLicenses: ['MIT', 'Apache-2.0'] + } + ] + + datasetTypesRepositoryStub.getDatasetAvailableDatasetTypes = jest + .fn() + .mockResolvedValue(testDatasetTypes) + const sut = new GetDatasetAvailableDatasetTypes(datasetTypesRepositoryStub) + + const actual = await sut.execute() + + expect(actual).toEqual(testDatasetTypes) + expect(datasetTypesRepositoryStub.getDatasetAvailableDatasetTypes).toHaveBeenCalledTimes(1) + }) + + test('should return error result on repository error', async () => { + const datasetsRepositoryStub: IDatasetsRepository = {} as IDatasetsRepository + const expectedError = new ReadError('Failed to fetch dataset types') + datasetsRepositoryStub.getDatasetAvailableDatasetTypes = jest + .fn() + .mockRejectedValue(expectedError) + const sut = new GetDatasetAvailableDatasetTypes(datasetsRepositoryStub) + + await expect(sut.execute()).rejects.toThrow(ReadError) + expect(datasetsRepositoryStub.getDatasetAvailableDatasetTypes).toHaveBeenCalledTimes(1) + }) + }) +})