mirror of
https://github.com/DSpace/dspace-angular.git
synced 2025-10-10 03:23:07 +00:00
finished docs and tests
This commit is contained in:
@@ -60,7 +60,6 @@ describe('EditInPlaceFieldComponent', () => {
|
|||||||
|
|
||||||
metadataFieldService = jasmine.createSpyObj({
|
metadataFieldService = jasmine.createSpyObj({
|
||||||
queryMetadataFields: observableOf(new RemoteData(false, false, true, undefined, paginatedMetadataFields)),
|
queryMetadataFields: observableOf(new RemoteData(false, false, true, undefined, paginatedMetadataFields)),
|
||||||
getAllMetadataFields: observableOf(new RemoteData(false, false, true, undefined, paginatedMetadataFields))
|
|
||||||
});
|
});
|
||||||
objectUpdatesService = jasmine.createSpyObj('objectUpdatesService',
|
objectUpdatesService = jasmine.createSpyObj('objectUpdatesService',
|
||||||
{
|
{
|
||||||
|
@@ -1,5 +1,5 @@
|
|||||||
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
|
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
|
||||||
import { CUSTOM_ELEMENTS_SCHEMA, DebugElement, NO_ERRORS_SCHEMA } from '@angular/core';
|
import { DebugElement, NO_ERRORS_SCHEMA } from '@angular/core';
|
||||||
import { of as observableOf } from 'rxjs';
|
import { of as observableOf } from 'rxjs';
|
||||||
import { getTestScheduler } from 'jasmine-marbles';
|
import { getTestScheduler } from 'jasmine-marbles';
|
||||||
import { ItemMetadataComponent } from './item-metadata.component';
|
import { ItemMetadataComponent } from './item-metadata.component';
|
||||||
@@ -22,6 +22,11 @@ import { Item } from '../../../core/shared/item.model';
|
|||||||
import { FieldChangeType } from '../../../core/data/object-updates/object-updates.actions';
|
import { FieldChangeType } from '../../../core/data/object-updates/object-updates.actions';
|
||||||
import { RemoteData } from '../../../core/data/remote-data';
|
import { RemoteData } from '../../../core/data/remote-data';
|
||||||
import { MetadatumViewModel } from '../../../core/shared/metadata.models';
|
import { MetadatumViewModel } from '../../../core/shared/metadata.models';
|
||||||
|
import { RegistryService } from '../../../core/registry/registry.service';
|
||||||
|
import { PaginatedList } from '../../../core/data/paginated-list';
|
||||||
|
import { MetadataSchema } from '../../../core/metadata/metadataschema.model';
|
||||||
|
import { MetadataField } from '../../../core/metadata/metadatafield.model';
|
||||||
|
import { Metadata } from '../../../core/shared/metadata.utils';
|
||||||
|
|
||||||
let comp: ItemMetadataComponent;
|
let comp: ItemMetadataComponent;
|
||||||
let fixture: ComponentFixture<ItemMetadataComponent>;
|
let fixture: ComponentFixture<ItemMetadataComponent>;
|
||||||
@@ -33,8 +38,23 @@ const warningNotification: INotification = new Notification('id', NotificationTy
|
|||||||
const successNotification: INotification = new Notification('id', NotificationType.Success, 'success');
|
const successNotification: INotification = new Notification('id', NotificationType.Success, 'success');
|
||||||
const date = new Date();
|
const date = new Date();
|
||||||
const router = new RouterStub();
|
const router = new RouterStub();
|
||||||
|
let metadataFieldService;
|
||||||
|
let paginatedMetadataFields;
|
||||||
let routeStub;
|
let routeStub;
|
||||||
|
|
||||||
|
const mdSchema = Object.assign(new MetadataSchema(), { prefix: 'dc' });
|
||||||
|
const mdField1 = Object.assign(new MetadataField(), {
|
||||||
|
schema: mdSchema,
|
||||||
|
element: 'contributor',
|
||||||
|
qualifier: 'author'
|
||||||
|
});
|
||||||
|
const mdField2 = Object.assign(new MetadataField(), { schema: mdSchema, element: 'title' });
|
||||||
|
const mdField3 = Object.assign(new MetadataField(), {
|
||||||
|
schema: mdSchema,
|
||||||
|
element: 'description',
|
||||||
|
qualifier: 'abstract'
|
||||||
|
});
|
||||||
|
|
||||||
let itemService;
|
let itemService;
|
||||||
const notificationsService = jasmine.createSpyObj('notificationsService',
|
const notificationsService = jasmine.createSpyObj('notificationsService',
|
||||||
{
|
{
|
||||||
@@ -83,7 +103,18 @@ let scheduler: TestScheduler;
|
|||||||
let item;
|
let item;
|
||||||
describe('ItemMetadataComponent', () => {
|
describe('ItemMetadataComponent', () => {
|
||||||
beforeEach(async(() => {
|
beforeEach(async(() => {
|
||||||
item = Object.assign(new Item(), { metadata: [metadatum1, metadatum2, metadatum3] }, { lastModified: date });
|
item = Object.assign(new Item(), {
|
||||||
|
metadata: {
|
||||||
|
[metadatum1.key]: [metadatum1],
|
||||||
|
[metadatum2.key]: [metadatum2],
|
||||||
|
[metadatum3.key]: [metadatum3]
|
||||||
|
}
|
||||||
|
},
|
||||||
|
{
|
||||||
|
lastModified: date
|
||||||
|
}
|
||||||
|
)
|
||||||
|
;
|
||||||
itemService = jasmine.createSpyObj('itemService', {
|
itemService = jasmine.createSpyObj('itemService', {
|
||||||
update: observableOf(new RemoteData(false, false, true, undefined, item)),
|
update: observableOf(new RemoteData(false, false, true, undefined, item)),
|
||||||
commitUpdates: {}
|
commitUpdates: {}
|
||||||
@@ -93,6 +124,11 @@ describe('ItemMetadataComponent', () => {
|
|||||||
data: observableOf({ item: new RemoteData(false, false, true, null, item) })
|
data: observableOf({ item: new RemoteData(false, false, true, null, item) })
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
paginatedMetadataFields = new PaginatedList(undefined, [mdField1, mdField2, mdField3]);
|
||||||
|
|
||||||
|
metadataFieldService = jasmine.createSpyObj({
|
||||||
|
getAllMetadataFields: observableOf(new RemoteData(false, false, true, undefined, paginatedMetadataFields))
|
||||||
|
});
|
||||||
scheduler = getTestScheduler();
|
scheduler = getTestScheduler();
|
||||||
objectUpdatesService = jasmine.createSpyObj('objectUpdatesService',
|
objectUpdatesService = jasmine.createSpyObj('objectUpdatesService',
|
||||||
{
|
{
|
||||||
@@ -122,7 +158,8 @@ describe('ItemMetadataComponent', () => {
|
|||||||
{ provide: Router, useValue: router },
|
{ provide: Router, useValue: router },
|
||||||
{ provide: ActivatedRoute, useValue: routeStub },
|
{ provide: ActivatedRoute, useValue: routeStub },
|
||||||
{ provide: NotificationsService, useValue: notificationsService },
|
{ provide: NotificationsService, useValue: notificationsService },
|
||||||
{ provide: GLOBAL_CONFIG, useValue: { notifications: { timeOut: 10 } } as any }
|
{ provide: GLOBAL_CONFIG, useValue: { notifications: { timeOut: 10 } } as any },
|
||||||
|
{ provide: RegistryService, useValue: metadataFieldService },
|
||||||
], schemas: [
|
], schemas: [
|
||||||
NO_ERRORS_SCHEMA
|
NO_ERRORS_SCHEMA
|
||||||
]
|
]
|
||||||
@@ -176,9 +213,9 @@ describe('ItemMetadataComponent', () => {
|
|||||||
});
|
});
|
||||||
|
|
||||||
it('it should call reinstateFieldUpdates on the objectUpdatesService with the correct url and metadata', () => {
|
it('it should call reinstateFieldUpdates on the objectUpdatesService with the correct url and metadata', () => {
|
||||||
expect(objectUpdatesService.getUpdatedFields).toHaveBeenCalledWith(url, comp.item.metadata);
|
expect(objectUpdatesService.getUpdatedFields).toHaveBeenCalledWith(url, comp.item.metadataAsList);
|
||||||
expect(itemService.update).toHaveBeenCalledWith(comp.item);
|
expect(itemService.update).toHaveBeenCalledWith(Object.assign(comp.item, { metadata: Metadata.toMetadataMap(comp.item.metadataAsList) }));
|
||||||
expect(objectUpdatesService.getFieldUpdates).toHaveBeenCalledWith(url, comp.item.metadata);
|
expect(objectUpdatesService.getFieldUpdates).toHaveBeenCalledWith(url, comp.item.metadataAsList);
|
||||||
});
|
});
|
||||||
});
|
});
|
||||||
|
|
||||||
|
@@ -72,7 +72,7 @@ export class ItemMetadataComponent implements OnInit {
|
|||||||
* Set up and initialize all fields
|
* Set up and initialize all fields
|
||||||
*/
|
*/
|
||||||
ngOnInit(): void {
|
ngOnInit(): void {
|
||||||
this.metadataFields$ = this.findMetadataFields()
|
this.metadataFields$ = this.findMetadataFields();
|
||||||
this.route.parent.data.pipe(map((data) => data.item))
|
this.route.parent.data.pipe(map((data) => data.item))
|
||||||
.pipe(
|
.pipe(
|
||||||
first(),
|
first(),
|
||||||
|
@@ -19,6 +19,7 @@ export class EPerson extends DSpaceObject {
|
|||||||
|
|
||||||
public selfRegistered: boolean;
|
public selfRegistered: boolean;
|
||||||
|
|
||||||
|
/** Getter to retrieve the EPerson's full name as a string */
|
||||||
get name(): string {
|
get name(): string {
|
||||||
return this.firstMetadataValue('eperson.firstname') + ' ' + this.firstMetadataValue('eperson.lastname');
|
return this.firstMetadataValue('eperson.firstname') + ' ' + this.firstMetadataValue('eperson.lastname');
|
||||||
}
|
}
|
||||||
|
@@ -1,4 +1,9 @@
|
|||||||
import { MetadataMap, MetadataValue, MetadataValueFilter } from './metadata.models';
|
import {
|
||||||
|
MetadataMap,
|
||||||
|
MetadataValue,
|
||||||
|
MetadataValueFilter,
|
||||||
|
MetadatumViewModel
|
||||||
|
} from './metadata.models';
|
||||||
import { Metadata } from './metadata.utils';
|
import { Metadata } from './metadata.utils';
|
||||||
import { CacheableObject } from '../cache/object-cache.reducer';
|
import { CacheableObject } from '../cache/object-cache.reducer';
|
||||||
import { RemoteData } from '../data/remote-data';
|
import { RemoteData } from '../data/remote-data';
|
||||||
@@ -40,7 +45,10 @@ export class DSpaceObject implements CacheableObject, ListableObject {
|
|||||||
*/
|
*/
|
||||||
metadata: MetadataMap;
|
metadata: MetadataMap;
|
||||||
|
|
||||||
get metadataAsList() {
|
/**
|
||||||
|
* Retrieve the current metadata as a list of MetadatumViewModels
|
||||||
|
*/
|
||||||
|
get metadataAsList(): MetadatumViewModel[] {
|
||||||
return Metadata.toViewModelList(this.metadata);
|
return Metadata.toViewModelList(this.metadata);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@@ -1,5 +1,6 @@
|
|||||||
import * as uuidv4 from 'uuid/v4';
|
import * as uuidv4 from 'uuid/v4';
|
||||||
import { autoserialize, Serialize, Deserialize } from 'cerialize';
|
import { autoserialize, Serialize, Deserialize } from 'cerialize';
|
||||||
|
/* tslint:disable:max-classes-per-file */
|
||||||
|
|
||||||
/** A map of metadata keys to an ordered list of MetadataValue objects. */
|
/** A map of metadata keys to an ordered list of MetadataValue objects. */
|
||||||
export class MetadataMap {
|
export class MetadataMap {
|
||||||
@@ -9,7 +10,6 @@ export class MetadataMap {
|
|||||||
/** A single metadata value and its properties. */
|
/** A single metadata value and its properties. */
|
||||||
|
|
||||||
export class MetadataValue {
|
export class MetadataValue {
|
||||||
|
|
||||||
/** The uuid. */
|
/** The uuid. */
|
||||||
uuid: string = uuidv4();
|
uuid: string = uuidv4();
|
||||||
|
|
||||||
@@ -20,7 +20,6 @@ export class MetadataValue {
|
|||||||
/** The string value. */
|
/** The string value. */
|
||||||
@autoserialize
|
@autoserialize
|
||||||
value: string;
|
value: string;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/** Constraints for matching metadata values. */
|
/** Constraints for matching metadata values. */
|
||||||
@@ -55,7 +54,10 @@ export class MetadatumViewModel {
|
|||||||
order: number;
|
order: number;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** Serializer used for MetadataMaps.
|
||||||
|
* This is necessary because Cerialize has trouble instantiating the MetadataValues using their constructor
|
||||||
|
* when they are inside arrays which also represent the values in a map.
|
||||||
|
*/
|
||||||
export const MetadataMapSerializer = {
|
export const MetadataMapSerializer = {
|
||||||
Serialize(map: MetadataMap): any {
|
Serialize(map: MetadataMap): any {
|
||||||
const json = {};
|
const json = {};
|
||||||
@@ -73,3 +75,4 @@ export const MetadataMapSerializer = {
|
|||||||
return metadataMap;
|
return metadataMap;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
/* tslint:enable:max-classes-per-file */
|
||||||
|
@@ -149,7 +149,7 @@ export class Metadata {
|
|||||||
* @param {MetadataMap} mdMap The source map.
|
* @param {MetadataMap} mdMap The source map.
|
||||||
* @param {string|string[]} keyOrKeys The metadata key(s) in scope. Wildcards are supported; see above.
|
* @param {string|string[]} keyOrKeys The metadata key(s) in scope. Wildcards are supported; see above.
|
||||||
*/
|
*/
|
||||||
private static resolveKeys(mdMap: MetadataMap, keyOrKeys: string | string[]): string[] {
|
private static resolveKeys(mdMap: MetadataMap = {}, keyOrKeys: string | string[]): string[] {
|
||||||
const inputKeys: string[] = keyOrKeys instanceof Array ? keyOrKeys : [keyOrKeys];
|
const inputKeys: string[] = keyOrKeys instanceof Array ? keyOrKeys : [keyOrKeys];
|
||||||
const outputKeys: string[] = [];
|
const outputKeys: string[] = [];
|
||||||
for (const inputKey of inputKeys) {
|
for (const inputKey of inputKeys) {
|
||||||
@@ -167,33 +167,51 @@ export class Metadata {
|
|||||||
return outputKeys;
|
return outputKeys;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static toViewModelList(mdMap: MetadataMap) {
|
/**
|
||||||
|
* Creates an array of MetadatumViewModels from an existing MetadataMap.
|
||||||
|
*
|
||||||
|
* @param {MetadataMap} mdMap The source map.
|
||||||
|
* @returns {MetadatumViewModel[]} List of metadata view models based on the source map.
|
||||||
|
*/
|
||||||
|
public static toViewModelList(mdMap: MetadataMap): MetadatumViewModel[] {
|
||||||
let metadatumList: MetadatumViewModel[] = [];
|
let metadatumList: MetadatumViewModel[] = [];
|
||||||
Object.keys(mdMap)
|
Object.keys(mdMap)
|
||||||
.sort()
|
.sort()
|
||||||
.forEach((key: string) => {
|
.forEach((key: string) => {
|
||||||
const fields = mdMap[key].map(
|
const fields = mdMap[key].map(
|
||||||
(metadataValue: MetadataValue, index: number) =>
|
(metadataValue: MetadataValue, index: number) =>
|
||||||
Object.assign(
|
Object.assign(
|
||||||
{},
|
{},
|
||||||
metadataValue,
|
metadataValue,
|
||||||
{
|
{
|
||||||
order: index,
|
order: index,
|
||||||
key
|
key
|
||||||
}));
|
}));
|
||||||
metadatumList = [...metadatumList, ...fields];
|
metadatumList = [...metadatumList, ...fields];
|
||||||
});
|
});
|
||||||
return metadatumList;
|
return metadatumList;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static toMetadataMap(viewModelList: MetadatumViewModel[]) {
|
/**
|
||||||
|
* Creates an MetadataMap from an existing array of MetadatumViewModels.
|
||||||
|
*
|
||||||
|
* @param {MetadatumViewModel[]} viewModelList The source list.
|
||||||
|
* @returns {MetadataMap} Map with metadata values based on the source list.
|
||||||
|
*/
|
||||||
|
public static toMetadataMap(viewModelList: MetadatumViewModel[]): MetadataMap {
|
||||||
const metadataMap: MetadataMap = {};
|
const metadataMap: MetadataMap = {};
|
||||||
const groupedList = groupBy(viewModelList, (viewModel) => viewModel.key);
|
const groupedList = groupBy(viewModelList, (viewModel) => viewModel.key);
|
||||||
Object.keys(groupedList)
|
Object.keys(groupedList)
|
||||||
.sort()
|
.sort()
|
||||||
.forEach((key: string) => {
|
.forEach((key: string) => {
|
||||||
const orderedValues = sortBy(groupedList[key], ['order']);
|
const orderedValues = sortBy(groupedList[key], ['order']);
|
||||||
metadataMap[key] = orderedValues.map((value: MetadataValue, index: number) => Object.assign({}, value, { order: index }))
|
metadataMap[key] = orderedValues.map((value: MetadataValue) => {
|
||||||
|
const val = Object.assign({}, value);
|
||||||
|
delete (val as any).order;
|
||||||
|
delete (val as any).key;
|
||||||
|
return val;
|
||||||
|
}
|
||||||
|
)
|
||||||
});
|
});
|
||||||
return metadataMap;
|
return metadataMap;
|
||||||
}
|
}
|
||||||
|
@@ -83,10 +83,10 @@ export class ComColFormComponent<T extends DSpaceObject> implements OnInit {
|
|||||||
onSubmit() {
|
onSubmit() {
|
||||||
const formMetadata = new Object() as MetadataMap;
|
const formMetadata = new Object() as MetadataMap;
|
||||||
this.formModel.forEach((fieldModel: DynamicInputModel) => {
|
this.formModel.forEach((fieldModel: DynamicInputModel) => {
|
||||||
const value: MetadataValue = Object.assign(new MetadataValue(), {
|
const value: MetadataValue = {
|
||||||
value: fieldModel.value as string,
|
value: fieldModel.value as string,
|
||||||
language: null
|
language: null
|
||||||
});
|
} as any;
|
||||||
if (formMetadata.hasOwnProperty(fieldModel.name)) {
|
if (formMetadata.hasOwnProperty(fieldModel.name)) {
|
||||||
formMetadata[fieldModel.name].push(value);
|
formMetadata[fieldModel.name].push(value);
|
||||||
} else {
|
} else {
|
||||||
|
Reference in New Issue
Block a user