Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
35 changes: 35 additions & 0 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

95 changes: 71 additions & 24 deletions src/published-data/dto/update-published-data.v4.dto.ts
Original file line number Diff line number Diff line change
Expand Up @@ -6,50 +6,97 @@ import {
IsOptional,
IsString,
} from "class-validator";
import { PartialType } from "@nestjs/swagger";
import {
ApiProperty,
ApiPropertyOptional,
ApiTags,
PartialType,
} from "@nestjs/swagger";
import { PublishedDataStatus } from "../interfaces/published-data.interface";
import { OwnableDto } from "src/common/dto/ownable.dto";

export class UpdatePublishedDataV4Dto {
/**
* A name or title by which a resource is known. This field has the semantics of Dublin Core
* [dcmi:title](https://www.dublincore.org/specifications/dublin-core/dcmi-terms/terms/title/)
* and [DataCite title](https://datacite-metadata-schema.readthedocs.io/en/4.6/properties/title/).
*/
@ApiTags("publishedData")
export class UpdatePublishedDataV4Dto extends OwnableDto {
@ApiProperty({
type: String,
required: true,
description:
"A name or title by which a resource is known. This field has the semantics of Dublin Core" +
" [dcmi:title](https://www.dublincore.org/specifications/dublin-core/dcmi-terms/terms/title/)" +
" and [DataCite title](https://datacite-metadata-schema.readthedocs.io/en/4.6/properties/title/).",
})
@IsString()
readonly title: string;

/**
* A brief description of the resource and the context in which the resource was created. This field has the semantics of
* [DataCite description](https://datacite-metadata-schema.readthedocs.io/en/4.6/properties/description/)
* with [Abstract](https://datacite-metadata-schema.readthedocs.io/en/4.6/appendices/appendix-1/descriptionType/#abstract).
*/
@ApiProperty({
type: String,
required: true,
description:
"A brief description of the resource and the context in which the resource was created. This field has the semantics" +
" of [DataCite description](https://datacite-metadata-schema.readthedocs.io/en/4.6/properties/description/)" +
" with [Abstract descriptionType](https://datacite-metadata-schema.readthedocs.io/en/4.6/appendices/appendix-1/descriptionType/#abstract).",
})
@IsString()
readonly abstract: string;

/**
* Array of one or more Dataset persistent identifier (pid) values that make up the published data.
*/
@ApiProperty({
type: [String],
required: false,
description:
"Array of one or more datasets' persistent identifier values that" +
" are part of this published data record.",
})
@IsArray()
@IsString({ each: true })
readonly datasetPids: string[];

/**
* Time when doi is successfully registered
*/
@ApiPropertyOptional({
type: [String],
description:
"Array of one or more proposal identifier values that " +
"are part of this published data record.",
})
@IsOptional()
@IsArray()
@IsString({ each: true })
readonly proposalIds?: string[];

@ApiPropertyOptional({
type: [String],
description:
"Array of one or more samples identifier values that " +
"are part of this published data record.",
})
@IsOptional()
@IsArray()
@IsString({ each: true })
readonly sampleIds?: string[];

@ApiProperty({
type: Date,
required: false,
description: "Time when doi is successfully registered with registrar",
})
@IsDateString()
@IsOptional()
readonly registeredTime?: Date;

/**
* Indication of position in publication workflow e.g. registred, private, public
*/
@ApiProperty({
enum: PublishedDataStatus,
description:
"Indication of position in publication workflow e.g. registred, private, public",
})
@IsEnum(PublishedDataStatus)
@IsOptional()
readonly status?: string;

/**
* JSON object containing the metadata. This will cover most optional fields of the DataCite schema, and will require a mapping from metadata subfields to DataCite Schema definitions.
*/
@ApiProperty({
type: Object,
required: false,
default: {},
description:
"JSON object containing the metadata. This will cover most optional fields of the DataCite schema, and will require a mapping from metadata subfields to DataCite Schema definitions",
})
@IsObject()
@IsOptional()
readonly metadata?: Record<string, unknown>;
Expand Down
1 change: 1 addition & 0 deletions src/published-data/published-data.v4.controller.ts
Original file line number Diff line number Diff line change
Expand Up @@ -96,6 +96,7 @@ export class PublishedDataV4Controller {
async create(
@Body() createPublishedDataDto: CreatePublishedDataV4Dto,
): Promise<PublishedData> {
console.log("published data v4 create");
return this.publishedDataService.create(createPublishedDataDto);
}

Expand Down
34 changes: 27 additions & 7 deletions src/published-data/schemas/published-data.schema.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
import { Prop, Schema, SchemaFactory } from "@nestjs/mongoose";
import { ApiProperty } from "@nestjs/swagger";
import { Document } from "mongoose";
import { QueryableClass } from "src/common/schemas/queryable.schema";
import { v4 as uuidv4 } from "uuid";
import { PublishedDataStatus } from "../interfaces/published-data.interface";
import crypto from "crypto";
import { OwnableClass } from "src/common/schemas/ownable.schema";

export type PublishedDataDocument = PublishedData & Document;

Expand All @@ -15,7 +15,7 @@ export type PublishedDataDocument = PublishedData & Document;
},
timestamps: true,
})
export class PublishedData extends QueryableClass {
export class PublishedData extends OwnableClass {
@Prop({
type: String,
unique: true,
Expand Down Expand Up @@ -102,18 +102,38 @@ export class PublishedData extends QueryableClass {

@ApiProperty({
type: [String],
required: true,
required: false,
description:
"Array of one or more Dataset persistent identifier (pid) values that" +
" make up the published data.",
"Array of one or more datasets' persistent identifier values that" +
" are part of the published data record.",
})
@Prop({ type: [String], required: true })
@Prop({ type: [String], required: false })
datasetPids: string[];

@ApiProperty({
type: [String],
required: false,
description:
"Array of one or more proposals identifier values that" +
" are part of this published data record.",
})
@Prop({ type: [String], required: false })
proposalIds: string[];

@ApiProperty({
type: [String],
required: false,
description:
"Array of one or more samples identifier values that" +
" are part of this published data record.",
})
@Prop({ type: [String], required: false })
sampleIds: string[];

@ApiProperty({
type: Date,
required: false,
description: "Time when doi is successfully registered",
description: "Time when doi is successfully registered with registrar",
})
@Prop({ type: Date, index: true, required: false })
registeredTime?: Date;
Expand Down
73 changes: 53 additions & 20 deletions test/PublishedData.js → test/PublishedData_V3.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,6 @@ const sandbox = require("sinon").createSandbox();

let accessTokenArchiveManager = null,
accessTokenAdminIngestor = null,

idOrigDatablock = null,
pid = null,
pidnonpublic = null,
Expand All @@ -28,7 +27,7 @@ const nonpublictestdataset = {
ownerGroup: "examplenonpublicgroup",
};

describe("1600: PublishedData: Test of access to published data", () => {
describe("1600: PublishedData: Test of access to published data V3", () => {
before(async () => {
db.collection("Dataset").deleteMany({});
db.collection("PublishedData").deleteMany({});
Expand Down Expand Up @@ -58,23 +57,53 @@ describe("1600: PublishedData: Test of access to published data", () => {
.expect(TestData.EntryCreatedStatusCode)
.expect("Content-Type", /json/)
.then((res) => {
res.body.should.have.property("affiliation").and.equal(publishedData.affiliation);
res.body.should.have.property("creator").and.deep.equal(publishedData.creator);
res.body.should.have.property("publisher").and.equal(publishedData.publisher);
res.body.should.have.property("publicationYear").and.equal(publishedData.publicationYear);
res.body.should.have
.property("affiliation")
.and.equal(publishedData.affiliation);
res.body.should.have
.property("creator")
.and.deep.equal(publishedData.creator);
res.body.should.have
.property("publisher")
.and.equal(publishedData.publisher);
res.body.should.have
.property("publicationYear")
.and.equal(publishedData.publicationYear);
res.body.should.have.property("title").and.equal(publishedData.title);
res.body.should.have.property("url").and.equal(publishedData.url);
res.body.should.have.property("abstract").and.equal(publishedData.abstract);
res.body.should.have.property("dataDescription").and.equal(publishedData.dataDescription);
res.body.should.have.property("resourceType").and.equal(publishedData.resourceType);
res.body.should.have.property("numberOfFiles").and.equal(publishedData.numberOfFiles);
res.body.should.have.property("sizeOfArchive").and.equal(publishedData.sizeOfArchive);
res.body.should.have.property("pidArray").and.deep.equal(publishedData.pidArray);
res.body.should.have.property("authors").and.deep.equal(publishedData.authors);
res.body.should.have.property("scicatUser").and.equal(publishedData.scicatUser);
res.body.should.have.property("thumbnail").and.equal(publishedData.thumbnail);
res.body.should.have.property("relatedPublications").and.deep.equal(publishedData.relatedPublications);
res.body.should.have.property("downloadLink").and.equal(publishedData.downloadLink);
res.body.should.have
.property("abstract")
.and.equal(publishedData.abstract);
res.body.should.have
.property("dataDescription")
.and.equal(publishedData.dataDescription);
res.body.should.have
.property("resourceType")
.and.equal(publishedData.resourceType);
res.body.should.have
.property("numberOfFiles")
.and.equal(publishedData.numberOfFiles);
res.body.should.have
.property("sizeOfArchive")
.and.equal(publishedData.sizeOfArchive);
res.body.should.have
.property("pidArray")
.and.deep.equal(publishedData.pidArray);
res.body.should.have
.property("authors")
.and.deep.equal(publishedData.authors);
res.body.should.have
.property("scicatUser")
.and.equal(publishedData.scicatUser);
res.body.should.have
.property("thumbnail")
.and.equal(publishedData.thumbnail);
res.body.should.have
.property("relatedPublications")
.and.deep.equal(publishedData.relatedPublications);
res.body.should.have
.property("downloadLink")
.and.equal(publishedData.downloadLink);
res.body.should.have.property("status").and.equal(publishedData.status);
doi = encodeURIComponent(res.body["doi"]);
});
Expand Down Expand Up @@ -149,7 +178,7 @@ describe("1600: PublishedData: Test of access to published data", () => {
.get("/api/v3/PublishedData/" + doi)
.set("Accept", "application/json")
.set({ Authorization: `Bearer ${accessTokenAdminIngestor}` })
.expect(TestData.SuccessfulGetStatusCode)
.expect(TestData.SuccessfulPostStatusCode)
.expect("Content-Type", /json/)
.then((res) => {
res.body.should.have.property("status").and.equal("registered");
Expand Down Expand Up @@ -216,14 +245,18 @@ describe("1600: PublishedData: Test of access to published data", () => {
it("0066: should fetch published data with filter", async () => {
const filter = { where: { creator: "New Creator" } };
await request(appUrl)
.get(`/api/v3/PublishedData?filter=${encodeURIComponent(JSON.stringify(filter))}`)
.get(
`/api/v3/PublishedData?filter=${encodeURIComponent(JSON.stringify(filter))}`,
)
.set("Accept", "application/json")
.set({ Authorization: `Bearer ${accessTokenAdminIngestor}` })
.expect(TestData.SuccessfulGetStatusCode)
.expect("Content-Type", /json/)
.then((res) => {
res.body.length.should.equal(1);
res.body[0].should.have.property("creator").and.deep.equal(["New Creator"]);
res.body[0].should.have
.property("creator")
.and.deep.equal(["New Creator"]);
res.body[0].should.have.property("thumbnail");
});
return request(appUrl)
Expand Down
6 changes: 4 additions & 2 deletions test/PublishedDataV4.js → test/PublishedData_V4.js
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,7 @@ const nonpublictestdataset = {
ownerGroup: "examplenonpublicgroup",
};

describe("1600: PublishedDataV4: Test of access to published data v4 endpoints", () => {
describe("1610: PublishedDataV4: Test of access to published data v4 endpoints", () => {
before(async () => {
db.collection("Dataset").deleteMany({});
db.collection("PublishedData").deleteMany({});
Expand Down Expand Up @@ -100,7 +100,9 @@ describe("1600: PublishedDataV4: Test of access to published data v4 endpoints",
.expect(TestData.EntryCreatedStatusCode)
.expect("Content-Type", /json/)
.then((res) => {
res.body.should.have.property("title").and.be.string;
res.body.should.have
.property("title")
.and.be.string(publishedData.title);
res.body.should.have.property("metadata");
res.body.metadata.should.have.property("publisher");
res.body.should.have.property("status").and.equal(defaultStatus);
Expand Down
1 change: 1 addition & 0 deletions test/TestData.js
Original file line number Diff line number Diff line change
Expand Up @@ -1353,6 +1353,7 @@ const TestData = {
landingPage: "doi.ess.eu/detail/",
},
datasetPids: [],
ownerGroup: "admin",
},

InstrumentCorrect1: {
Expand Down
Loading