mirror of
https://github.com/DSpace/dspace-angular.git
synced 2025-10-12 12:33:07 +00:00
fixes
This commit is contained in:
@@ -10,20 +10,37 @@ import { RelationshipTypeService } from './relationship-type.service';
|
||||
import { of as observableOf } from 'rxjs';
|
||||
import { ItemType } from '../shared/item-relationships/item-type.model';
|
||||
|
||||
fdescribe('RelationshipTypeService', () => {
|
||||
describe('RelationshipTypeService', () => {
|
||||
let service: RelationshipTypeService;
|
||||
let requestService : RequestService;
|
||||
let restEndpointURL;
|
||||
let halService: any;
|
||||
let publicationTypeString;
|
||||
let personTypeString;
|
||||
let orgUnitTypeString;
|
||||
let publicationType;
|
||||
let personType;
|
||||
let orgUnitType;
|
||||
|
||||
const restEndpointURL = 'https://rest.api/relationshiptypes';
|
||||
const halService: any = new HALEndpointServiceStub(restEndpointURL);
|
||||
const publicationTypeString = 'Publication';
|
||||
const personTypeString = 'Person';
|
||||
const orgUnitTypeString = 'OrgUnit';
|
||||
const publicationType = Object.assign(new ItemType(), {label: publicationTypeString});
|
||||
const personType = Object.assign(new ItemType(), {label: personTypeString});
|
||||
const orgUnitType = Object.assign(new ItemType(), {label: orgUnitTypeString});
|
||||
let relationshipType1;
|
||||
|
||||
const relationshipType1 = Object.assign(new RelationshipType(), {
|
||||
|
||||
let relationshipType2;
|
||||
|
||||
let buildList;
|
||||
let rdbService;
|
||||
|
||||
function init() {
|
||||
restEndpointURL = 'https://rest.api/relationshiptypes';
|
||||
halService = new HALEndpointServiceStub(restEndpointURL);
|
||||
publicationTypeString = 'Publication';
|
||||
personTypeString = 'Person';
|
||||
orgUnitTypeString = 'OrgUnit';
|
||||
publicationType = Object.assign(new ItemType(), {label: publicationTypeString});
|
||||
personType = Object.assign(new ItemType(), {label: personTypeString});
|
||||
orgUnitType = Object.assign(new ItemType(), {label: orgUnitTypeString});
|
||||
|
||||
relationshipType1 = Object.assign(new RelationshipType(), {
|
||||
id: '1',
|
||||
uuid: '1',
|
||||
leftwardType: 'isAuthorOfPublication',
|
||||
@@ -33,7 +50,7 @@ fdescribe('RelationshipTypeService', () => {
|
||||
});
|
||||
|
||||
|
||||
const relationshipType2 = Object.assign(new RelationshipType(), {
|
||||
relationshipType2 = Object.assign(new RelationshipType(), {
|
||||
id: '2',
|
||||
uuid: '2',
|
||||
leftwardType: 'isOrgUnitOfPublication',
|
||||
@@ -42,9 +59,10 @@ fdescribe('RelationshipTypeService', () => {
|
||||
rightType: createSuccessfulRemoteDataObject$(orgUnitType)
|
||||
});
|
||||
|
||||
const buildList = createSuccessfulRemoteDataObject(new PaginatedList(new PageInfo(), [relationshipType1, relationshipType2]));
|
||||
const rdbService = getMockRemoteDataBuildService(undefined, observableOf(buildList));
|
||||
buildList = createSuccessfulRemoteDataObject(new PaginatedList(new PageInfo(), [relationshipType1, relationshipType2]));
|
||||
rdbService = getMockRemoteDataBuildService(undefined, observableOf(buildList));
|
||||
|
||||
}
|
||||
function initTestService() {
|
||||
return new RelationshipTypeService(
|
||||
requestService,
|
||||
@@ -54,6 +72,7 @@ fdescribe('RelationshipTypeService', () => {
|
||||
}
|
||||
|
||||
beforeEach(() => {
|
||||
init();
|
||||
requestService = getMockRequestService();
|
||||
service = initTestService();
|
||||
});
|
||||
|
@@ -137,7 +137,7 @@ export class RelationshipService extends DataService<Relationship> {
|
||||
this.requestService.hasByHrefObservable(item.self)
|
||||
).pipe(
|
||||
filter(([existsInOC, existsInRC]) => !existsInOC && !existsInRC),
|
||||
tap(t => console.log(t)),
|
||||
take(1),
|
||||
switchMap(() => this.itemService.findByHref(item.self).pipe(take(1)))
|
||||
).subscribe();
|
||||
}
|
||||
@@ -330,7 +330,6 @@ export class RelationshipService extends DataService<Relationship> {
|
||||
}),
|
||||
// skipWhile((relationshipRD: RemoteData<Relationship>) => !relationshipRD.isSuccessful)
|
||||
tap((relationshipRD: RemoteData<Relationship>) => {
|
||||
console.log(relationshipRD.payload);
|
||||
if (relationshipRD.hasSucceeded) {
|
||||
this.removeRelationshipItemsFromCache(item1);
|
||||
this.removeRelationshipItemsFromCache(item2);
|
||||
|
@@ -22,7 +22,9 @@ import { PersonItemMetadataListElementComponent } from './metadata-representatio
|
||||
import { OrgUnitItemMetadataListElementComponent } from './metadata-representations/org-unit/org-unit-item-metadata-list-element.component';
|
||||
import { PersonSearchResultListSubmissionElementComponent } from './submission/item-list-elements/person/person-search-result-list-submission-element.component';
|
||||
import { PersonInputSuggestionsComponent } from './submission/item-list-elements/person/person-suggestions/person-input-suggestions.component';
|
||||
import { NameVariantModalComponent } from './submission/item-list-elements/person/name-variant-modal/name-variant-modal.component';
|
||||
import { NameVariantModalComponent } from './submission/name-variant-modal/name-variant-modal.component';
|
||||
import { OrgUnitInputSuggestionsComponent } from './submission/item-list-elements/org-unit/org-unit-suggestions/org-unit-input-suggestions.component';
|
||||
import { OrgUnitSearchResultListSubmissionElementComponent } from './submission/item-list-elements/org-unit/org-unit-search-result-list-submission-element.component';
|
||||
|
||||
const ENTRY_COMPONENTS = [
|
||||
OrgUnitComponent,
|
||||
@@ -44,7 +46,9 @@ const ENTRY_COMPONENTS = [
|
||||
ProjectSearchResultGridElementComponent,
|
||||
PersonSearchResultListSubmissionElementComponent,
|
||||
PersonInputSuggestionsComponent,
|
||||
NameVariantModalComponent
|
||||
NameVariantModalComponent,
|
||||
OrgUnitSearchResultListSubmissionElementComponent,
|
||||
OrgUnitInputSuggestionsComponent
|
||||
];
|
||||
|
||||
@NgModule({
|
||||
|
@@ -0,0 +1,20 @@
|
||||
<div class="d-flex">
|
||||
<div class="person-thumbnail pr-2">
|
||||
<!-- <ds-thumbnail [thumbnail]="dso.getThumbnail() | async" [defaultImage]="'assets/images/orgunit-placeholder.svg'"></ds-thumbnail>-->
|
||||
</div>
|
||||
<div class="flex-grow-1">
|
||||
<ds-org-unit-input-suggestions [suggestions]="allSuggestions" [(ngModel)]="selectedName" (clickSuggestion)="select($event)"
|
||||
(submitSuggestion)="selectCustom($event)"></ds-org-unit-input-suggestions>
|
||||
<span class="text-muted">
|
||||
<span *ngIf="dso.allMetadata('organization.address.addressLocality').length > 0"
|
||||
class="item-list-job-title">
|
||||
<span [innerHTML]="firstMetadataValue(['organization.address.addressLocality'])"><span [innerHTML]="firstMetadataValue(['organization.address.addressLocality'])"></span></span>
|
||||
<span *ngIf="dso.allMetadata('organization.address.addressCountry').length > 0">, </span>
|
||||
</span>
|
||||
<span *ngIf="dso.allMetadata('organization.address.addressCountry').length > 0"
|
||||
class="item-list-job-title">
|
||||
<span [innerHTML]="firstMetadataValue(['organization.address.addressCountry'])"><span [innerHTML]="firstMetadataValue(['organization.address.addressCountry'])"></span></span>
|
||||
</span>
|
||||
</span>
|
||||
</div>
|
||||
</div>
|
@@ -0,0 +1,7 @@
|
||||
@import '../../../../../../styles/variables';
|
||||
|
||||
$submission-relationship-thumbnail-width: 80px;
|
||||
|
||||
.person-thumbnail {
|
||||
width: $submission-relationship-thumbnail-width;
|
||||
}
|
@@ -0,0 +1,125 @@
|
||||
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
|
||||
import { ChangeDetectionStrategy, NO_ERRORS_SCHEMA } from '@angular/core';
|
||||
import { By } from '@angular/platform-browser';
|
||||
import { of as observableOf } from 'rxjs';
|
||||
import { ItemSearchResult } from '../../../../../shared/object-collection/shared/item-search-result.model';
|
||||
import { OrgUnitSearchResultListSubmissionElementComponent } from './org-unit-search-result-list-submission-element.component';
|
||||
import { Item } from '../../../../../core/shared/item.model';
|
||||
import { TruncatePipe } from '../../../../../shared/utils/truncate.pipe';
|
||||
import { TruncatableService } from '../../../../../shared/truncatable/truncatable.service';
|
||||
import { RelationshipService } from '../../../../../core/data/relationship.service';
|
||||
import { NotificationsService } from '../../../../../shared/notifications/notifications.service';
|
||||
import { TranslateService } from '@ngx-translate/core';
|
||||
import { NgbModal } from '@ng-bootstrap/ng-bootstrap';
|
||||
import { ItemDataService } from '../../../../../core/data/item-data.service';
|
||||
import { SelectableListService } from '../../../../../shared/object-list/selectable-list/selectable-list.service';
|
||||
import { Store } from '@ngrx/store';
|
||||
import { createSuccessfulRemoteDataObject$ } from '../../../../../shared/testing/utils';
|
||||
import { PaginatedList } from '../../../../../core/data/paginated-list';
|
||||
|
||||
let personListElementComponent: OrgUnitSearchResultListSubmissionElementComponent;
|
||||
let fixture: ComponentFixture<OrgUnitSearchResultListSubmissionElementComponent>;
|
||||
|
||||
let mockItemWithMetadata: ItemSearchResult;
|
||||
let mockItemWithoutMetadata: ItemSearchResult;
|
||||
|
||||
let nameVariant;
|
||||
let mockRelationshipService;
|
||||
|
||||
|
||||
function init() {
|
||||
mockItemWithMetadata = Object.assign(
|
||||
new ItemSearchResult(),
|
||||
{
|
||||
indexableObject: Object.assign(new Item(), {
|
||||
bundles: createSuccessfulRemoteDataObject$(new PaginatedList(undefined, [])),
|
||||
metadata: {
|
||||
'dc.title': [
|
||||
{
|
||||
language: 'en_US',
|
||||
value: 'This is just another title'
|
||||
}
|
||||
],
|
||||
'person.jobTitle': [
|
||||
{
|
||||
language: 'en_US',
|
||||
value: 'Developer'
|
||||
}
|
||||
]
|
||||
}
|
||||
})
|
||||
});
|
||||
mockItemWithoutMetadata = Object.assign(
|
||||
new ItemSearchResult(),
|
||||
{
|
||||
indexableObject: Object.assign(new Item(), {
|
||||
bundles: createSuccessfulRemoteDataObject$(new PaginatedList(undefined, [])),
|
||||
metadata: {
|
||||
'dc.title': [
|
||||
{
|
||||
language: 'en_US',
|
||||
value: 'This is just another title'
|
||||
}
|
||||
]
|
||||
}
|
||||
})
|
||||
});
|
||||
|
||||
nameVariant = "Doe J.";
|
||||
mockRelationshipService = {
|
||||
getNameVariant: () => observableOf(nameVariant)
|
||||
};
|
||||
}
|
||||
|
||||
describe('PersonSearchResultListElementSubmissionComponent', () => {
|
||||
beforeEach(async(() => {
|
||||
init();
|
||||
TestBed.configureTestingModule({
|
||||
declarations: [OrgUnitSearchResultListSubmissionElementComponent, TruncatePipe],
|
||||
providers: [
|
||||
{ provide: TruncatableService, useValue: {} },
|
||||
{ provide: RelationshipService, useValue: mockRelationshipService },
|
||||
{ provide: NotificationsService, useValue: {} },
|
||||
{ provide: TranslateService, useValue: {} },
|
||||
{ provide: NgbModal, useValue: {} },
|
||||
{ provide: ItemDataService, useValue: {} },
|
||||
{ provide: SelectableListService, useValue: {} },
|
||||
{ provide: Store, useValue: {}}
|
||||
],
|
||||
|
||||
schemas: [NO_ERRORS_SCHEMA]
|
||||
}).overrideComponent(OrgUnitSearchResultListSubmissionElementComponent, {
|
||||
set: { changeDetection: ChangeDetectionStrategy.Default }
|
||||
}).compileComponents();
|
||||
}));
|
||||
|
||||
beforeEach(async(() => {
|
||||
fixture = TestBed.createComponent(OrgUnitSearchResultListSubmissionElementComponent);
|
||||
personListElementComponent = fixture.componentInstance;
|
||||
|
||||
}));
|
||||
|
||||
describe('When the item has a job title', () => {
|
||||
beforeEach(() => {
|
||||
personListElementComponent.object = mockItemWithMetadata;
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
it('should show the job title span', () => {
|
||||
const jobTitleField = fixture.debugElement.query(By.css('span.item-list-job-title'));
|
||||
expect(jobTitleField).not.toBeNull();
|
||||
});
|
||||
});
|
||||
|
||||
describe('When the item has no job title', () => {
|
||||
beforeEach(() => {
|
||||
personListElementComponent.object = mockItemWithoutMetadata;
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
it('should not show the job title span', () => {
|
||||
const jobTitleField = fixture.debugElement.query(By.css('span.item-list-job-title'));
|
||||
expect(jobTitleField).toBeNull();
|
||||
});
|
||||
});
|
||||
});
|
@@ -0,0 +1,98 @@
|
||||
import { Component, OnInit } from '@angular/core';
|
||||
import { SearchResultListElementComponent } from '../../../../../shared/object-list/search-result-list-element/search-result-list-element.component';
|
||||
import { ItemSearchResult } from '../../../../../shared/object-collection/shared/item-search-result.model';
|
||||
import { listableObjectComponent } from '../../../../../shared/object-collection/shared/listable-object/listable-object.decorator';
|
||||
import { ViewMode } from '../../../../../core/shared/view-mode.model';
|
||||
import { Item } from '../../../../../core/shared/item.model';
|
||||
import { Context } from '../../../../../core/shared/context.model';
|
||||
import { RelationshipService } from '../../../../../core/data/relationship.service';
|
||||
import { TruncatableService } from '../../../../../shared/truncatable/truncatable.service';
|
||||
import { take } from 'rxjs/operators';
|
||||
import { NotificationsService } from '../../../../../shared/notifications/notifications.service';
|
||||
import { TranslateService } from '@ngx-translate/core';
|
||||
import { NgbModal } from '@ng-bootstrap/ng-bootstrap';
|
||||
import { MetadataValue } from '../../../../../core/shared/metadata.models';
|
||||
import { ItemDataService } from '../../../../../core/data/item-data.service';
|
||||
import { SelectableListService } from '../../../../../shared/object-list/selectable-list/selectable-list.service';
|
||||
import { NameVariantModalComponent } from '../../name-variant-modal/name-variant-modal.component';
|
||||
|
||||
@listableObjectComponent('OrgUnitSearchResult', ViewMode.ListElement, Context.Workspace)
|
||||
@Component({
|
||||
selector: 'ds-person-search-result-list-submission-element',
|
||||
styleUrls: ['./org-unit-search-result-list-submission-element.component.scss'],
|
||||
templateUrl: './org-unit-search-result-list-submission-element.component.html'
|
||||
})
|
||||
|
||||
/**
|
||||
* The component for displaying a list element for an item search result of the type Person
|
||||
*/
|
||||
export class OrgUnitSearchResultListSubmissionElementComponent extends SearchResultListElementComponent<ItemSearchResult, Item> implements OnInit {
|
||||
allSuggestions: string[];
|
||||
selectedName: string;
|
||||
alternativeField = 'dc.title.alternative';
|
||||
|
||||
constructor(protected truncatableService: TruncatableService,
|
||||
private relationshipService: RelationshipService,
|
||||
private notificationsService: NotificationsService,
|
||||
private translateService: TranslateService,
|
||||
private modalService: NgbModal,
|
||||
private itemDataService: ItemDataService,
|
||||
private selectableListService: SelectableListService) {
|
||||
super(truncatableService);
|
||||
}
|
||||
|
||||
ngOnInit() {
|
||||
super.ngOnInit();
|
||||
const defaultValue = this.firstMetadataValue('organization.legalName');
|
||||
const alternatives = this.allMetadataValues(this.alternativeField);
|
||||
this.allSuggestions = [defaultValue, ...alternatives];
|
||||
|
||||
this.relationshipService.getNameVariant(this.listID, this.dso.uuid)
|
||||
.pipe(take(1))
|
||||
.subscribe((nameVariant: string) => {
|
||||
this.selectedName = nameVariant || defaultValue;
|
||||
}
|
||||
);
|
||||
}
|
||||
|
||||
select(value) {
|
||||
this.selectableListService.isObjectSelected(this.listID, this.object)
|
||||
.pipe(take(1))
|
||||
.subscribe((selected) => {
|
||||
if (!selected) {
|
||||
this.selectableListService.selectSingle(this.listID, this.object);
|
||||
}
|
||||
});
|
||||
this.relationshipService.setNameVariant(this.listID, this.dso.uuid, value);
|
||||
}
|
||||
|
||||
selectCustom(value) {
|
||||
if (!this.allSuggestions.includes(value)) {
|
||||
this.openModal(value)
|
||||
.then(() => {
|
||||
|
||||
const newName: MetadataValue = new MetadataValue();
|
||||
newName.value = value;
|
||||
|
||||
const existingNames: MetadataValue[] = this.dso.metadata[this.alternativeField] || [];
|
||||
const alternativeNames = { [this.alternativeField]: [...existingNames, newName] };
|
||||
const updatedItem =
|
||||
Object.assign({}, this.dso, {
|
||||
metadata: {
|
||||
...this.dso.metadata,
|
||||
...alternativeNames
|
||||
},
|
||||
});
|
||||
this.itemDataService.update(updatedItem).pipe(take(1)).subscribe();
|
||||
})
|
||||
}
|
||||
this.select(value);
|
||||
}
|
||||
|
||||
openModal(value): Promise<any> {
|
||||
const modalRef = this.modalService.open(NameVariantModalComponent, { centered: true });
|
||||
const modalComp = modalRef.componentInstance;
|
||||
modalComp.value = value;
|
||||
return modalRef.result;
|
||||
}
|
||||
}
|
@@ -0,0 +1,24 @@
|
||||
<form #form="ngForm" (ngSubmit)="onSubmit(value)"
|
||||
[action]="action" (keydown)="onKeydown($event)"
|
||||
(keydown.arrowdown)="shiftFocusDown($event)"
|
||||
(keydown.arrowup)="shiftFocusUp($event)" (keydown.esc)="close()"
|
||||
(dsClickOutside)="close();">
|
||||
<input #inputField type="text" [(ngModel)]="value" [name]="name"
|
||||
class="form-control suggestion_input"
|
||||
(focus)="open()"
|
||||
(click)="open()"
|
||||
[ngClass]="{'is-invalid': !valid}"
|
||||
[dsDebounce]="debounceTime" (onDebounce)="find($event)"
|
||||
[placeholder]="placeholder"
|
||||
[ngModelOptions]="{standalone: true}" autocomplete="off"/>
|
||||
<input type="submit" class="d-none"/>
|
||||
<div class="autocomplete dropdown-menu" [ngClass]="{'show': (show | async) && isNotEmpty(suggestions)}">
|
||||
<div class="dropdown-list">
|
||||
<div *ngFor="let suggestionOption of suggestions">
|
||||
<a href="#" class="d-block dropdown-item" (click)="onClickSuggestion(suggestionOption)" #suggestion>
|
||||
<span [innerHTML]="suggestionOption"></span>
|
||||
</a>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</form>
|
@@ -0,0 +1,18 @@
|
||||
form {
|
||||
z-index: 1;
|
||||
&:before {
|
||||
position: absolute;
|
||||
font-weight: 900;
|
||||
font-family: "Font Awesome 5 Free";
|
||||
content: "\f0d7";
|
||||
top: 7px;
|
||||
right: 0;
|
||||
height: 20px;
|
||||
width: 20px;
|
||||
z-index: -1;
|
||||
}
|
||||
|
||||
input.suggestion_input {
|
||||
background: transparent;
|
||||
}
|
||||
}
|
@@ -0,0 +1,48 @@
|
||||
import { Component, forwardRef, Input, OnInit } from '@angular/core';
|
||||
import { NG_VALUE_ACCESSOR } from '@angular/forms';
|
||||
import { InputSuggestionsComponent } from '../../../../../../shared/input-suggestions/input-suggestions.component';
|
||||
|
||||
@Component({
|
||||
selector: 'ds-org-unit-input-suggestions',
|
||||
styleUrls: ['./org-unit-input-suggestions.component.scss', './../../../../../../shared/input-suggestions/input-suggestions.component.scss'],
|
||||
templateUrl: './org-unit-input-suggestions.component.html',
|
||||
providers: [
|
||||
{
|
||||
provide: NG_VALUE_ACCESSOR,
|
||||
// Usage of forwardRef necessary https://github.com/angular/angular.io/issues/1151
|
||||
// tslint:disable-next-line:no-forward-ref
|
||||
useExisting: forwardRef(() => OrgUnitInputSuggestionsComponent),
|
||||
multi: true
|
||||
}
|
||||
]
|
||||
})
|
||||
|
||||
/**
|
||||
* Component representing a form with a autocomplete functionality
|
||||
*/
|
||||
export class OrgUnitInputSuggestionsComponent extends InputSuggestionsComponent implements OnInit {
|
||||
/**
|
||||
* The suggestions that should be shown
|
||||
*/
|
||||
@Input() suggestions: string[] = [];
|
||||
|
||||
ngOnInit() {
|
||||
if (this.suggestions.length > 0) {
|
||||
this.value = this.suggestions[0]
|
||||
}
|
||||
}
|
||||
|
||||
onSubmit(data) {
|
||||
this.value = data;
|
||||
this.submitSuggestion.emit(data);
|
||||
}
|
||||
|
||||
onClickSuggestion(data) {
|
||||
this.value = data;
|
||||
this.clickSuggestion.emit(data);
|
||||
this.close();
|
||||
this.blockReopen = true;
|
||||
this.queryInput.nativeElement.focus();
|
||||
return false;
|
||||
}
|
||||
}
|
@@ -1,6 +1,6 @@
|
||||
<div class="d-flex">
|
||||
<div class="person-thumbnail pr-2">
|
||||
<ds-thumbnail [thumbnail]="dso.getThumbnail() | async" [defaultImage]="'assets/images/person-placeholder.svg'"></ds-thumbnail>
|
||||
<!-- <ds-thumbnail [thumbnail]="dso.getThumbnail() | async" [defaultImage]="'assets/images/person-placeholder.svg'"></ds-thumbnail>-->
|
||||
</div>
|
||||
<div class="flex-grow-1">
|
||||
<ds-person-input-suggestions [suggestions]="allSuggestions" [(ngModel)]="selectedName" (clickSuggestion)="select($event)" (submitSuggestion)="selectCustom($event)"></ds-person-input-suggestions>
|
||||
|
@@ -20,7 +20,15 @@ import { PaginatedList } from '../../../../../core/data/paginated-list';
|
||||
let personListElementComponent: PersonSearchResultListSubmissionElementComponent;
|
||||
let fixture: ComponentFixture<PersonSearchResultListSubmissionElementComponent>;
|
||||
|
||||
const mockItemWithMetadata: ItemSearchResult = Object.assign(
|
||||
let mockItemWithMetadata: ItemSearchResult;
|
||||
let mockItemWithoutMetadata: ItemSearchResult;
|
||||
|
||||
let nameVariant;
|
||||
let mockRelationshipService;
|
||||
|
||||
|
||||
function init() {
|
||||
mockItemWithMetadata = Object.assign(
|
||||
new ItemSearchResult(),
|
||||
{
|
||||
indexableObject: Object.assign(new Item(), {
|
||||
@@ -41,7 +49,7 @@ const mockItemWithMetadata: ItemSearchResult = Object.assign(
|
||||
}
|
||||
})
|
||||
});
|
||||
const mockItemWithoutMetadata: ItemSearchResult = Object.assign(
|
||||
mockItemWithoutMetadata = Object.assign(
|
||||
new ItemSearchResult(),
|
||||
{
|
||||
indexableObject: Object.assign(new Item(), {
|
||||
@@ -57,13 +65,15 @@ const mockItemWithoutMetadata: ItemSearchResult = Object.assign(
|
||||
})
|
||||
});
|
||||
|
||||
const nameVariant = "Doe J.";
|
||||
const mockRelationshipService = {
|
||||
nameVariant = "Doe J.";
|
||||
mockRelationshipService = {
|
||||
getNameVariant: () => observableOf(nameVariant)
|
||||
};
|
||||
}
|
||||
|
||||
describe('PersonSearchResultListElementSubmissionComponent', () => {
|
||||
beforeEach(async(() => {
|
||||
init();
|
||||
TestBed.configureTestingModule({
|
||||
declarations: [PersonSearchResultListSubmissionElementComponent, TruncatePipe],
|
||||
providers: [
|
||||
|
@@ -11,7 +11,7 @@ import { take } from 'rxjs/operators';
|
||||
import { NotificationsService } from '../../../../../shared/notifications/notifications.service';
|
||||
import { TranslateService } from '@ngx-translate/core';
|
||||
import { NgbModal } from '@ng-bootstrap/ng-bootstrap';
|
||||
import { NameVariantModalComponent } from './name-variant-modal/name-variant-modal.component';
|
||||
import { NameVariantModalComponent } from '../../name-variant-modal/name-variant-modal.component';
|
||||
import { MetadataValue } from '../../../../../core/shared/metadata.models';
|
||||
import { ItemDataService } from '../../../../../core/data/item-data.service';
|
||||
import { SelectableListService } from '../../../../../shared/object-list/selectable-list/selectable-list.service';
|
||||
|
@@ -81,7 +81,7 @@ import { SelectableListService } from '../../../object-list/selectable-list/sele
|
||||
import { DsDynamicDisabledComponent } from './models/disabled/dynamic-disabled.component';
|
||||
import { DYNAMIC_FORM_CONTROL_TYPE_DISABLED } from './models/disabled/dynamic-disabled.model';
|
||||
import { DsDynamicLookupRelationModalComponent } from './relation-lookup-modal/dynamic-lookup-relation-modal.component';
|
||||
import { getAllSucceededRemoteData, getRemoteDataPayload, getSucceededRemoteData } from '../../../../core/shared/operators';
|
||||
import { getAllSucceededRemoteData, getRemoteDataPayload, getSucceededRemoteData, obsLog } from '../../../../core/shared/operators';
|
||||
import { RemoteData } from '../../../../core/data/remote-data';
|
||||
import { Item } from '../../../../core/shared/item.model';
|
||||
import { ItemDataService } from '../../../../core/data/item-data.service';
|
||||
@@ -94,6 +94,7 @@ import { PaginatedList } from '../../../../core/data/paginated-list';
|
||||
import { ItemSearchResult } from '../../../object-collection/shared/item-search-result.model';
|
||||
import { ItemMetadataRepresentation } from '../../../../core/shared/metadata-representation/item/item-metadata-representation.model';
|
||||
import { MetadataValue } from '../../../../core/shared/metadata.models';
|
||||
import * as uuidv4 from 'uuid/v4';
|
||||
|
||||
export function dsDynamicFormControlMapFn(model: DynamicFormControlModel): Type<DynamicFormControl> | null {
|
||||
switch (model.type) {
|
||||
@@ -205,6 +206,7 @@ export class DsDynamicFormControlContainerComponent extends DynamicFormControlCo
|
||||
protected validationService: DynamicFormValidationService,
|
||||
protected translateService: TranslateService,
|
||||
private modalService: NgbModal,
|
||||
private relationService: RelationshipService,
|
||||
private selectableListService: SelectableListService,
|
||||
private itemService: ItemDataService,
|
||||
private relationshipService: RelationshipService,
|
||||
@@ -216,6 +218,7 @@ export class DsDynamicFormControlContainerComponent extends DynamicFormControlCo
|
||||
}
|
||||
|
||||
ngOnInit(): void {
|
||||
const q = uuidv4();
|
||||
this.hasRelationLookup = hasValue(this.model.relationship);
|
||||
if (this.hasRelationLookup) {
|
||||
this.listId = 'list-' + this.model.relationship.relationshipType;
|
||||
@@ -226,7 +229,7 @@ export class DsDynamicFormControlContainerComponent extends DynamicFormControlCo
|
||||
switchMap((submissionObject: SubmissionObject) => (submissionObject.item as Observable<RemoteData<Item>>).pipe(getAllSucceededRemoteData(), getRemoteDataPayload())));
|
||||
this.item$.pipe(
|
||||
take(1),
|
||||
switchMap((item: Item) => this.relationshipService.getRelatedItemsByLabel(item, this.model.relationship.relationshipType)),
|
||||
switchMap((item: Item) => this.relationService.getRelatedItemsByLabel(item, this.model.relationship.relationshipType)),
|
||||
map((items: RemoteData<PaginatedList<Item>>) => items.payload.page.map((item) => Object.assign(new ItemSearchResult(), { indexableObject: item }))),
|
||||
).subscribe((relatedItems: SearchResult<Item>[]) => this.selectableListService.select(this.listId, relatedItems));
|
||||
|
||||
|
@@ -0,0 +1,129 @@
|
||||
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
|
||||
import { TranslateModule } from '@ngx-translate/core';
|
||||
import { RouterTestingModule } from '@angular/router/testing';
|
||||
import { NgZone, NO_ERRORS_SCHEMA } from '@angular/core';
|
||||
import { of as observableOf, Subscription } from 'rxjs';
|
||||
import { DsDynamicLookupRelationModalComponent } from './dynamic-lookup-relation-modal.component';
|
||||
import { NgbActiveModal, NgbModule } from '@ng-bootstrap/ng-bootstrap';
|
||||
import { SelectableListService } from '../../../../object-list/selectable-list/selectable-list.service';
|
||||
import { RelationshipService } from '../../../../../core/data/relationship.service';
|
||||
import { RelationshipTypeService } from '../../../../../core/data/relationship-type.service';
|
||||
import { Store } from '@ngrx/store';
|
||||
import { Item } from '../../../../../core/shared/item.model';
|
||||
import { ItemSearchResult } from '../../../../object-collection/shared/item-search-result.model';
|
||||
import { RelationshipOptions } from '../../models/relationship-options.model';
|
||||
import { AddRelationshipAction, RemoveRelationshipAction } from './relationship.actions';
|
||||
|
||||
describe('DsDynamicLookupRelationModalComponent', () => {
|
||||
let component: DsDynamicLookupRelationModalComponent;
|
||||
let fixture: ComponentFixture<DsDynamicLookupRelationModalComponent>;
|
||||
let item;
|
||||
let item1;
|
||||
let item2;
|
||||
let searchResult1;
|
||||
let searchResult2;
|
||||
let listID;
|
||||
let selection$;
|
||||
let selectableListService;
|
||||
let relationship;
|
||||
let nameVariant;
|
||||
let metadataField;
|
||||
|
||||
function init() {
|
||||
item = Object.assign(new Item(), { uuid: '7680ca97-e2bd-4398-bfa7-139a8673dc42', metadata: {} });
|
||||
item1 = Object.assign(new Item(), { uuid: 'e1c51c69-896d-42dc-8221-1d5f2ad5516e' });
|
||||
item2 = Object.assign(new Item(), { uuid: 'c8279647-1acc-41ae-b036-951d5f65649b' });
|
||||
searchResult1 = Object.assign(new ItemSearchResult(), { indexableObject: item1 });
|
||||
searchResult2 = Object.assign(new ItemSearchResult(), { indexableObject: item2 });
|
||||
listID = '6b0c8221-fcb4-47a8-b483-ca32363fffb3';
|
||||
selection$ = observableOf([searchResult1, searchResult2]);
|
||||
selectableListService = { getSelectableList: () => selection$ };
|
||||
relationship = { filter: 'filter', relationshipType: 'isAuthorOfPublication', nameVariants: true } as RelationshipOptions;
|
||||
nameVariant = 'Doe, J.';
|
||||
metadataField = 'dc.contributor.author';
|
||||
}
|
||||
|
||||
beforeEach(async(() => {
|
||||
init();
|
||||
TestBed.configureTestingModule({
|
||||
declarations: [DsDynamicLookupRelationModalComponent],
|
||||
imports: [TranslateModule.forRoot(), RouterTestingModule.withRoutes([]), NgbModule.forRoot()],
|
||||
providers: [
|
||||
{
|
||||
provide: SelectableListService, useValue: selectableListService
|
||||
},
|
||||
{
|
||||
provide: RelationshipService, useValue: { getNameVariant: () => observableOf(nameVariant) }
|
||||
},
|
||||
{ provide: RelationshipTypeService, useValue: {} },
|
||||
{
|
||||
provide: Store, useValue: {
|
||||
dispatch: () => {
|
||||
}
|
||||
}
|
||||
},
|
||||
{ provide: NgZone, useValue: new NgZone({}) },
|
||||
NgbActiveModal
|
||||
],
|
||||
schemas: [NO_ERRORS_SCHEMA]
|
||||
})
|
||||
.compileComponents();
|
||||
}));
|
||||
|
||||
beforeEach(() => {
|
||||
fixture = TestBed.createComponent(DsDynamicLookupRelationModalComponent);
|
||||
component = fixture.componentInstance;
|
||||
component.listId = listID;
|
||||
component.relationshipOptions = relationship;
|
||||
component.item = item;
|
||||
component.metadataFields = metadataField;
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
it('should create', () => {
|
||||
expect(component).toBeTruthy();
|
||||
});
|
||||
|
||||
describe('close', () => {
|
||||
beforeEach(() => {
|
||||
spyOn(component.modal, 'close');
|
||||
});
|
||||
|
||||
it('should call close on the modal', () => {
|
||||
component.close();
|
||||
expect(component.modal.close).toHaveBeenCalled();
|
||||
})
|
||||
});
|
||||
|
||||
describe('select', () => {
|
||||
beforeEach(() => {
|
||||
spyOn((component as any).store, 'dispatch');
|
||||
});
|
||||
|
||||
it('should dispatch an AddRelationshipAction for each selected object', () => {
|
||||
component.select(searchResult1, searchResult2);
|
||||
const action = new AddRelationshipAction(component.item, searchResult1.indexableObject, relationship.relationshipType, nameVariant);
|
||||
const action2 = new AddRelationshipAction(component.item, searchResult2.indexableObject, relationship.relationshipType, nameVariant);
|
||||
|
||||
expect((component as any).store.dispatch).toHaveBeenCalledWith(action);
|
||||
expect((component as any).store.dispatch).toHaveBeenCalledWith(action2);
|
||||
})
|
||||
});
|
||||
|
||||
describe('deselect', () => {
|
||||
beforeEach(() => {
|
||||
component.subMap[searchResult1.indexableObject.uuid] = new Subscription();
|
||||
component.subMap[searchResult2.indexableObject.uuid] = new Subscription();
|
||||
spyOn((component as any).store, 'dispatch');
|
||||
});
|
||||
|
||||
it('should dispatch an RemoveRelationshipAction for each deselected object', () => {
|
||||
component.deselect(searchResult1, searchResult2);
|
||||
const action = new RemoveRelationshipAction(component.item, searchResult1.indexableObject, relationship.relationshipType);
|
||||
const action2 = new RemoveRelationshipAction(component.item, searchResult2.indexableObject, relationship.relationshipType);
|
||||
|
||||
expect((component as any).store.dispatch).toHaveBeenCalledWith(action);
|
||||
expect((component as any).store.dispatch).toHaveBeenCalledWith(action2);
|
||||
})
|
||||
});
|
||||
});
|
@@ -66,6 +66,8 @@ export class DsDynamicLookupRelationModalComponent implements OnInit, OnDestroy
|
||||
if (this.relationshipOptions.nameVariants) {
|
||||
this.context = Context.Workspace;
|
||||
}
|
||||
|
||||
// this.setExistingNameVariants();
|
||||
}
|
||||
|
||||
close() {
|
||||
@@ -99,7 +101,7 @@ export class DsDynamicLookupRelationModalComponent implements OnInit, OnDestroy
|
||||
});
|
||||
}
|
||||
|
||||
addNameVariantSubscription(sri: SearchResult<Item>) {
|
||||
private addNameVariantSubscription(sri: SearchResult<Item>) {
|
||||
const nameVariant$ = this.relationshipService.getNameVariant(this.listId, sri.indexableObject.uuid);
|
||||
this.subMap[sri.indexableObject.uuid] = nameVariant$.pipe(
|
||||
skip(1),
|
||||
@@ -115,11 +117,12 @@ export class DsDynamicLookupRelationModalComponent implements OnInit, OnDestroy
|
||||
);
|
||||
}
|
||||
|
||||
setExistingNameVariants() {
|
||||
const virtualMDs$: Observable<MetadataValue[]> = this.item.allMetadata(this.metadataFields).filter((mdValue) => mdValue.isVirtual);
|
||||
private setExistingNameVariants() {
|
||||
const virtualMDs: MetadataValue[] = this.item.allMetadata(this.metadataFields).filter((mdValue) => mdValue.isVirtual);
|
||||
|
||||
const relatedItemPairs$: Observable<[Item, Item][]> = virtualMDs$.pipe(
|
||||
switchMap((mds: MetadataValue[]) => combineLatest(mds.map((md: MetadataValue) => this.relationshipService.findById(md.virtualValue).pipe(getSucceededRemoteData(), getRemoteDataPayload())))),
|
||||
const relatedItemPairs$: Observable<[Item, Item][]> =
|
||||
combineLatest(virtualMDs.map((md: MetadataValue) => this.relationshipService.findById(md.virtualValue).pipe(getSucceededRemoteData(), getRemoteDataPayload())))
|
||||
.pipe(
|
||||
switchMap((relationships: Relationship[]) => combineLatest(relationships.map((relationship: Relationship) =>
|
||||
combineLatest(
|
||||
relationship.leftItem.pipe(getSucceededRemoteData(), getRemoteDataPayload()),
|
||||
@@ -133,7 +136,7 @@ export class DsDynamicLookupRelationModalComponent implements OnInit, OnDestroy
|
||||
map(([relatedItemPairs,]: [[Item, Item][]]) => relatedItemPairs.map(([left, right]: [Item, Item]) => left.uuid === this.item.uuid ? left : right))
|
||||
);
|
||||
|
||||
combineLatest(virtualMDs$, relatedItems$).pipe(take(1)).subscribe(([virtualMDs, relatedItems]) => {
|
||||
relatedItems$.pipe(take(1)).subscribe((relatedItems) => {
|
||||
let index: number = 0;
|
||||
virtualMDs.forEach(
|
||||
(md: MetadataValue) => {
|
||||
@@ -145,7 +148,6 @@ export class DsDynamicLookupRelationModalComponent implements OnInit, OnDestroy
|
||||
)
|
||||
}
|
||||
|
||||
|
||||
ngOnDestroy() {
|
||||
Object.values(this.subMap).forEach((subscription) => subscription.unsubscribe());
|
||||
}
|
||||
|
@@ -7,15 +7,29 @@ class NullAction implements Action {
|
||||
type = null;
|
||||
}
|
||||
|
||||
const listID1 = 'dbfb81de-2930-4de6-ba2e-ea21c8534ee9';
|
||||
const listID2 = 'd7f2c48d-e1e2-4996-ab8d-e271cabec78a';
|
||||
const itemID1 = 'd1c81d4f-6b05-4844-986b-372d2e39c6aa';
|
||||
const itemID2 = 'fe4ca421-d897-417f-9436-9724262d5c69';
|
||||
const variantList1Item1 = 'Test Name Variant 1';
|
||||
const variantList1Item1Update = 'Test Name Variant 1 Update';
|
||||
const variantList1Item2 = 'Test Name Variant 2';
|
||||
let listID1;
|
||||
let listID2;
|
||||
let itemID1;
|
||||
let itemID2;
|
||||
let variantList1Item1;
|
||||
let variantList1Item1Update;
|
||||
let variantList1Item2;
|
||||
|
||||
function init() {
|
||||
listID1 = 'dbfb81de-2930-4de6-ba2e-ea21c8534ee9';
|
||||
listID2 = 'd7f2c48d-e1e2-4996-ab8d-e271cabec78a';
|
||||
itemID1 = 'd1c81d4f-6b05-4844-986b-372d2e39c6aa';
|
||||
itemID2 = 'fe4ca421-d897-417f-9436-9724262d5c69';
|
||||
variantList1Item1 = 'Test Name Variant 1';
|
||||
variantList1Item1Update = 'Test Name Variant 1 Update';
|
||||
variantList1Item2 = 'Test Name Variant 2';
|
||||
}
|
||||
|
||||
|
||||
describe('nameVariantReducer', () => {
|
||||
beforeEach(() => {
|
||||
init();
|
||||
});
|
||||
|
||||
it('should return the current state when no valid actions have been made', () => {
|
||||
const state = { [listID1]: { [itemID1]: variantList1Item1 } };
|
||||
|
@@ -19,42 +19,64 @@ describe('RelationshipEffects', () => {
|
||||
let relationEffects: RelationshipEffects;
|
||||
let actions: Observable<any>;
|
||||
|
||||
const testUUID1 = '20e24c2f-a00a-467c-bdee-c929e79bf08d';
|
||||
const testUUID2 = '7f66a4d0-8557-4e77-8b1e-19930895f10a';
|
||||
const leftTypeString = 'Publication';
|
||||
const rightTypeString = 'Person';
|
||||
const leftType = Object.assign(new ItemType(), {label: leftTypeString});
|
||||
const rightType = Object.assign(new ItemType(), {label: rightTypeString});
|
||||
const leftTypeMD = Object.assign(new MetadataValue(), { value: leftTypeString });
|
||||
const rightTypeMD = Object.assign(new MetadataValue(), { value: rightTypeString });
|
||||
const relationshipID = '1234';
|
||||
let testUUID1;
|
||||
let testUUID2;
|
||||
let leftTypeString;
|
||||
let rightTypeString;
|
||||
let leftType;
|
||||
let rightType;
|
||||
let leftTypeMD;
|
||||
let rightTypeMD;
|
||||
let relationshipID;
|
||||
let identifier;
|
||||
|
||||
let leftItem = Object.assign(new Item(), {
|
||||
let leftItem;
|
||||
|
||||
let rightItem;
|
||||
|
||||
let relationshipType: RelationshipType;
|
||||
|
||||
let relationship;
|
||||
let mockRelationshipService;
|
||||
let mockRelationshipTypeService;
|
||||
|
||||
|
||||
function init() {
|
||||
testUUID1 = '20e24c2f-a00a-467c-bdee-c929e79bf08d';
|
||||
testUUID2 = '7f66a4d0-8557-4e77-8b1e-19930895f10a';
|
||||
leftTypeString = 'Publication';
|
||||
rightTypeString = 'Person';
|
||||
leftType = Object.assign(new ItemType(), {label: leftTypeString});
|
||||
rightType = Object.assign(new ItemType(), {label: rightTypeString});
|
||||
leftTypeMD = Object.assign(new MetadataValue(), { value: leftTypeString });
|
||||
rightTypeMD = Object.assign(new MetadataValue(), { value: rightTypeString });
|
||||
relationshipID = '1234';
|
||||
|
||||
leftItem = Object.assign(new Item(), {
|
||||
uuid: testUUID1,
|
||||
metadata: { 'relationship.type': [leftTypeMD] }
|
||||
});
|
||||
|
||||
let rightItem = Object.assign(new Item(), {
|
||||
rightItem = Object.assign(new Item(), {
|
||||
uuid: testUUID2,
|
||||
metadata: { 'relationship.type': [rightTypeMD] }
|
||||
});
|
||||
|
||||
let relationshipType: RelationshipType = Object.assign(new RelationshipType(), {
|
||||
relationshipType = Object.assign(new RelationshipType(), {
|
||||
leftwardType: 'isAuthorOfPublication',
|
||||
rightwardType: 'isPublicationOfAuthor',
|
||||
leftType: createSuccessfulRemoteDataObject$(leftType),
|
||||
rightType: createSuccessfulRemoteDataObject$(rightType)
|
||||
});
|
||||
|
||||
let relationship = Object.assign(new Relationship(),
|
||||
relationship = Object.assign(new Relationship(),
|
||||
{
|
||||
uuid: relationshipID,
|
||||
leftItem: createSuccessfulRemoteDataObject$(leftItem),
|
||||
rightItem: createSuccessfulRemoteDataObject$(rightItem),
|
||||
relationshipType: createSuccessfulRemoteDataObject$(relationshipType)
|
||||
});
|
||||
const mockRelationshipService = {
|
||||
mockRelationshipService = {
|
||||
getRelationshipByItemsAndLabel:
|
||||
() => observableOf(relationship),
|
||||
deleteRelationship: () => {
|
||||
@@ -64,12 +86,13 @@ describe('RelationshipEffects', () => {
|
||||
/* Do nothing */
|
||||
}
|
||||
};
|
||||
const mockRelationshipTypeService = {
|
||||
mockRelationshipTypeService = {
|
||||
getRelationshipTypeByLabelAndTypes:
|
||||
() => observableOf(relationshipType)
|
||||
};
|
||||
|
||||
}
|
||||
beforeEach(async(() => {
|
||||
init();
|
||||
TestBed.configureTestingModule({
|
||||
providers: [
|
||||
RelationshipEffects,
|
||||
|
@@ -51,7 +51,6 @@ export class RelationshipEffects {
|
||||
take(1)
|
||||
).subscribe(
|
||||
(type) => {
|
||||
debugger;
|
||||
if (this.initialActionMap[identifier] === type) {
|
||||
if (type === RelationshipActionTypes.ADD_RELATIONSHIP) {
|
||||
let nameVariant = (action as AddRelationshipAction).payload.nameVariant;
|
||||
|
@@ -0,0 +1,140 @@
|
||||
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
|
||||
import { TranslateModule } from '@ngx-translate/core';
|
||||
import { DsDynamicLookupRelationSearchTabComponent } from './dynamic-lookup-relation-search-tab.component';
|
||||
import { SearchService } from '../../../../../../core/shared/search/search.service';
|
||||
import { SelectableListService } from '../../../../../object-list/selectable-list/selectable-list.service';
|
||||
import { SearchConfigurationService } from '../../../../../../core/shared/search/search-configuration.service';
|
||||
import { RouteService } from '../../../../../../core/services/route.service';
|
||||
import { RouterTestingModule } from '@angular/router/testing';
|
||||
import { NO_ERRORS_SCHEMA } from '@angular/core';
|
||||
import { VarDirective } from '../../../../../utils/var.directive';
|
||||
import { RelationshipOptions } from '../../../models/relationship-options.model';
|
||||
import { of as observableOf } from 'rxjs';
|
||||
import { PaginatedSearchOptions } from '../../../../../search/paginated-search-options.model';
|
||||
import { createSuccessfulRemoteDataObject$ } from '../../../../../testing/utils';
|
||||
import { PaginatedList } from '../../../../../../core/data/paginated-list';
|
||||
import { ItemSearchResult } from '../../../../../object-collection/shared/item-search-result.model';
|
||||
import { Item } from '../../../../../../core/shared/item.model';
|
||||
|
||||
describe('DsDynamicLookupRelationSearchTabComponent', () => {
|
||||
let component: DsDynamicLookupRelationSearchTabComponent;
|
||||
let fixture: ComponentFixture<DsDynamicLookupRelationSearchTabComponent>;
|
||||
let relationship;
|
||||
let pSearchOptions;
|
||||
let item1;
|
||||
let item2;
|
||||
let item3;
|
||||
let searchResult1;
|
||||
let searchResult2;
|
||||
let searchResult3;
|
||||
let listID;
|
||||
let selection$;
|
||||
|
||||
let results;
|
||||
let selectableListService;
|
||||
|
||||
function init() {
|
||||
relationship = { filter: 'filter', relationshipType: 'isAuthorOfPublication', nameVariants: true } as RelationshipOptions;
|
||||
pSearchOptions = new PaginatedSearchOptions({});
|
||||
item1 = Object.assign(new Item(), { uuid: 'e1c51c69-896d-42dc-8221-1d5f2ad5516e' });
|
||||
item2 = Object.assign(new Item(), { uuid: 'c8279647-1acc-41ae-b036-951d5f65649b' });
|
||||
item3 = Object.assign(new Item(), { uuid: 'c3bcbff5-ec0c-4831-8e4c-94b9c933ccac' });
|
||||
searchResult1 = Object.assign(new ItemSearchResult(), { indexableObject: item1 });
|
||||
searchResult2 = Object.assign(new ItemSearchResult(), { indexableObject: item2 });
|
||||
searchResult3 = Object.assign(new ItemSearchResult(), { indexableObject: item3 });
|
||||
listID = '6b0c8221-fcb4-47a8-b483-ca32363fffb3';
|
||||
selection$ = observableOf([searchResult1, searchResult2]);
|
||||
|
||||
results = new PaginatedList(undefined, [searchResult1, searchResult2, searchResult3]);
|
||||
selectableListService = jasmine.createSpyObj('selectableListService', ['deselect', 'select', 'deselectAll']);
|
||||
}
|
||||
|
||||
beforeEach(async(() => {
|
||||
init();
|
||||
TestBed.configureTestingModule({
|
||||
declarations: [DsDynamicLookupRelationSearchTabComponent, VarDirective],
|
||||
imports: [TranslateModule.forRoot(), RouterTestingModule.withRoutes([])],
|
||||
providers: [
|
||||
{ provide: SearchService, useValue: { search: () => createSuccessfulRemoteDataObject$(results) } },
|
||||
{
|
||||
provide: SelectableListService, useValue: selectableListService
|
||||
},
|
||||
{
|
||||
provide: SearchConfigurationService, useValue: {
|
||||
paginatedSearchOptions: observableOf(pSearchOptions)
|
||||
}
|
||||
},
|
||||
{
|
||||
provide: RouteService, useValue: {
|
||||
setParameter: () => {
|
||||
// do nothing
|
||||
}
|
||||
}
|
||||
},
|
||||
],
|
||||
schemas: [NO_ERRORS_SCHEMA]
|
||||
})
|
||||
.compileComponents();
|
||||
}));
|
||||
|
||||
beforeEach(() => {
|
||||
fixture = TestBed.createComponent(DsDynamicLookupRelationSearchTabComponent);
|
||||
component = fixture.componentInstance;
|
||||
component.relationship = relationship;
|
||||
component.selection$ = selection$;
|
||||
component.listId = listID;
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
it('should create', () => {
|
||||
expect(component).toBeTruthy();
|
||||
});
|
||||
|
||||
describe('selectPage', () => {
|
||||
beforeEach(() => {
|
||||
spyOn(component.selectObject, 'emit');
|
||||
component.selectPage([searchResult1, searchResult2, searchResult3]);
|
||||
});
|
||||
|
||||
it('should emit the page filtered from already selected objects and call select on the service for all objects', () => {
|
||||
expect(component.selectObject.emit).toHaveBeenCalledWith(searchResult3);
|
||||
expect(selectableListService.select).toHaveBeenCalledWith(listID, [searchResult1, searchResult2, searchResult3]);
|
||||
});
|
||||
});
|
||||
|
||||
describe('deselectPage', () => {
|
||||
beforeEach(() => {
|
||||
spyOn(component.deselectObject, 'emit');
|
||||
component.deselectPage([searchResult1, searchResult2, searchResult3]);
|
||||
});
|
||||
|
||||
it('should emit the page filtered from not yet selected objects and call select on the service for all objects', () => {
|
||||
expect(component.deselectObject.emit).toHaveBeenCalledWith(searchResult1, searchResult2);
|
||||
expect(selectableListService.deselect).toHaveBeenCalledWith(listID, [searchResult1, searchResult2, searchResult3]);
|
||||
});
|
||||
});
|
||||
|
||||
describe('selectAll', () => {
|
||||
beforeEach(() => {
|
||||
spyOn(component.selectObject, 'emit');
|
||||
component.selectAll();
|
||||
});
|
||||
|
||||
it('should emit the page filtered from already selected objects and call select on the service for all objects', () => {
|
||||
expect(component.selectObject.emit).toHaveBeenCalledWith(searchResult3);
|
||||
expect(selectableListService.select).toHaveBeenCalledWith(listID, [searchResult1, searchResult2, searchResult3]);
|
||||
});
|
||||
});
|
||||
|
||||
describe('deselectAll', () => {
|
||||
beforeEach(() => {
|
||||
spyOn(component.deselectObject, 'emit');
|
||||
component.deselectAll();
|
||||
});
|
||||
|
||||
it('should emit the page filtered from not yet selected objects and call select on the service for all objects', () => {
|
||||
expect(component.deselectObject.emit).toHaveBeenCalledWith(searchResult1, searchResult2);
|
||||
expect(selectableListService.deselectAll).toHaveBeenCalledWith(listID);
|
||||
});
|
||||
});
|
||||
});
|
@@ -100,7 +100,7 @@ export class DsDynamicLookupRelationSearchTabComponent implements OnInit, OnDest
|
||||
this.selection$
|
||||
.pipe(take(1))
|
||||
.subscribe((selection: SearchResult<Item>[]) => {
|
||||
const filteredPage = page.filter((pageItem) => selection.findIndex((selected) => selected.equals(pageItem)) < 0)
|
||||
const filteredPage = page.filter((pageItem) => selection.findIndex((selected) => selected.equals(pageItem)) < 0);
|
||||
this.selectObject.emit(...filteredPage);
|
||||
});
|
||||
this.selectableListService.select(this.listId, page);
|
||||
@@ -111,7 +111,7 @@ export class DsDynamicLookupRelationSearchTabComponent implements OnInit, OnDest
|
||||
this.selection$
|
||||
.pipe(take(1))
|
||||
.subscribe((selection: SearchResult<Item>[]) => {
|
||||
const filteredPage = page.filter((pageItem) => selection.findIndex((selected) => selected.equals(pageItem)) >= 0)
|
||||
const filteredPage = page.filter((pageItem) => selection.findIndex((selected) => selected.equals(pageItem)) >= 0);
|
||||
this.deselectObject.emit(...filteredPage);
|
||||
});
|
||||
this.selectableListService.deselect(this.listId, page);
|
||||
|
@@ -0,0 +1,62 @@
|
||||
import { async, ComponentFixture, TestBed } from '@angular/core/testing';
|
||||
import { TranslateModule } from '@ngx-translate/core';
|
||||
import { SearchConfigurationService } from '../../../../../../core/shared/search/search-configuration.service';
|
||||
import { RouterTestingModule } from '@angular/router/testing';
|
||||
import { NO_ERRORS_SCHEMA } from '@angular/core';
|
||||
import { VarDirective } from '../../../../../utils/var.directive';
|
||||
import { of as observableOf } from 'rxjs';
|
||||
import { PaginatedSearchOptions } from '../../../../../search/paginated-search-options.model';
|
||||
import { ItemSearchResult } from '../../../../../object-collection/shared/item-search-result.model';
|
||||
import { Item } from '../../../../../../core/shared/item.model';
|
||||
import { DsDynamicLookupRelationSelectionTabComponent } from './dynamic-lookup-relation-selection-tab.component';
|
||||
import { PaginationComponentOptions } from '../../../../../pagination/pagination-component-options.model';
|
||||
|
||||
describe('DsDynamicLookupRelationSelectionTabComponent', () => {
|
||||
let component: DsDynamicLookupRelationSelectionTabComponent;
|
||||
let fixture: ComponentFixture<DsDynamicLookupRelationSelectionTabComponent>;
|
||||
let pSearchOptions = new PaginatedSearchOptions({pagination: new PaginationComponentOptions()});
|
||||
let item1 = Object.assign(new Item(), { uuid: 'e1c51c69-896d-42dc-8221-1d5f2ad5516e' });
|
||||
let item2 = Object.assign(new Item(), { uuid: 'c8279647-1acc-41ae-b036-951d5f65649b' });
|
||||
let searchResult1 = Object.assign(new ItemSearchResult(), { indexableObject: item1 });
|
||||
let searchResult2 = Object.assign(new ItemSearchResult(), { indexableObject: item2 });
|
||||
let listID = '6b0c8221-fcb4-47a8-b483-ca32363fffb3';
|
||||
let selection$ = observableOf([searchResult1, searchResult2]);
|
||||
|
||||
function init() {
|
||||
pSearchOptions = new PaginatedSearchOptions({pagination: new PaginationComponentOptions()});
|
||||
item1 = Object.assign(new Item(), { uuid: 'e1c51c69-896d-42dc-8221-1d5f2ad5516e' });
|
||||
item2 = Object.assign(new Item(), { uuid: 'c8279647-1acc-41ae-b036-951d5f65649b' });
|
||||
searchResult1 = Object.assign(new ItemSearchResult(), { indexableObject: item1 });
|
||||
searchResult2 = Object.assign(new ItemSearchResult(), { indexableObject: item2 });
|
||||
listID = '6b0c8221-fcb4-47a8-b483-ca32363fffb3';
|
||||
selection$ = observableOf([searchResult1, searchResult2]);
|
||||
}
|
||||
beforeEach(async(() => {
|
||||
init();
|
||||
TestBed.configureTestingModule({
|
||||
declarations: [DsDynamicLookupRelationSelectionTabComponent, VarDirective],
|
||||
imports: [TranslateModule.forRoot(), RouterTestingModule.withRoutes([])],
|
||||
providers: [
|
||||
{
|
||||
provide: SearchConfigurationService, useValue: {
|
||||
paginatedSearchOptions: observableOf(pSearchOptions)
|
||||
}
|
||||
}
|
||||
],
|
||||
schemas: [NO_ERRORS_SCHEMA]
|
||||
})
|
||||
.compileComponents();
|
||||
}));
|
||||
|
||||
beforeEach(() => {
|
||||
fixture = TestBed.createComponent(DsDynamicLookupRelationSelectionTabComponent);
|
||||
component = fixture.componentInstance;
|
||||
component.selection$ = selection$;
|
||||
component.listId = listID;
|
||||
fixture.detectChanges();
|
||||
});
|
||||
|
||||
it('should create', () => {
|
||||
expect(component).toBeTruthy();
|
||||
});
|
||||
});
|
@@ -382,7 +382,6 @@ describe('FormComponent test suite', () => {
|
||||
|
||||
describe('', () => {
|
||||
beforeEach(() => {
|
||||
|
||||
formFixture = TestBed.createComponent(FormComponent);
|
||||
store = TestBed.get(Store);
|
||||
formComp = formFixture.componentInstance; // FormComponent test instance
|
||||
|
@@ -14,9 +14,11 @@ describe('InputSuggestionsComponent', () => {
|
||||
let fixture: ComponentFixture<InputSuggestionsComponent>;
|
||||
let de: DebugElement;
|
||||
let el: HTMLElement;
|
||||
const suggestions = [{displayValue: 'suggestion uno', value: 'suggestion uno'}, {displayValue: 'suggestion dos', value: 'suggestion dos'}, {displayValue: 'suggestion tres', value: 'suggestion tres'}];
|
||||
let suggestions;
|
||||
|
||||
beforeEach(async(() => {
|
||||
suggestions = [{displayValue: 'suggestion uno', value: 'suggestion uno'}, {displayValue: 'suggestion dos', value: 'suggestion dos'}, {displayValue: 'suggestion tres', value: 'suggestion tres'}];
|
||||
|
||||
TestBed.configureTestingModule({
|
||||
imports: [TranslateModule.forRoot(), RouterTestingModule.withRoutes([]), NoopAnimationsModule, FormsModule],
|
||||
declarations: [InputSuggestionsComponent],
|
||||
|
Reference in New Issue
Block a user