mirror of
https://github.com/DSpace/dspace-angular.git
synced 2025-10-18 15:33:04 +00:00
71380: Fix loading/cache issue with dropping objects on page
This commit is contained in:
@@ -196,9 +196,11 @@ export class ItemBitstreamsComponent extends AbstractItemUpdateComponent impleme
|
||||
path: `/_links/bitstreams/${event.toIndex}/href`
|
||||
});
|
||||
this.bundleService.patch(bundle, [moveOperation]).pipe(take(1)).subscribe((response: RestResponse) => {
|
||||
this.displayNotifications('item.edit.bitstreams.notifications.move', [response]);
|
||||
this.requestService.removeByHrefSubstring(bundle.self);
|
||||
this.zone.run(() => event.finish());
|
||||
this.zone.run(() => {
|
||||
this.displayNotifications('item.edit.bitstreams.notifications.move', [response]);
|
||||
this.requestService.removeByHrefSubstring(bundle.self);
|
||||
event.finish();
|
||||
});
|
||||
});
|
||||
}
|
||||
});
|
||||
|
@@ -16,6 +16,7 @@ import { ResponsiveTableSizes } from '../../../../../shared/responsive-table-siz
|
||||
import { ResponsiveColumnSizes } from '../../../../../shared/responsive-table-sizes/responsive-column-sizes';
|
||||
import { createSuccessfulRemoteDataObject$ } from '../../../../../shared/remote-data.utils';
|
||||
import { createPaginatedList } from '../../../../../shared/testing/utils.test';
|
||||
import { RequestService } from '../../../../../core/data/request.service';
|
||||
|
||||
describe('PaginatedDragAndDropBitstreamListComponent', () => {
|
||||
let comp: PaginatedDragAndDropBitstreamListComponent;
|
||||
@@ -23,6 +24,7 @@ describe('PaginatedDragAndDropBitstreamListComponent', () => {
|
||||
let objectUpdatesService: ObjectUpdatesService;
|
||||
let bundleService: BundleDataService;
|
||||
let objectValuesPipe: ObjectValuesPipe;
|
||||
let requestService: RequestService;
|
||||
|
||||
const columnSizes = new ResponsiveTableSizes([
|
||||
new ResponsiveColumnSizes(2, 2, 3, 4, 4),
|
||||
@@ -98,18 +100,24 @@ describe('PaginatedDragAndDropBitstreamListComponent', () => {
|
||||
);
|
||||
|
||||
bundleService = jasmine.createSpyObj('bundleService', {
|
||||
getBitstreams: createSuccessfulRemoteDataObject$(createPaginatedList([bitstream1, bitstream2]))
|
||||
getBitstreams: createSuccessfulRemoteDataObject$(createPaginatedList([bitstream1, bitstream2])),
|
||||
getBitstreamsEndpoint: observableOf('')
|
||||
});
|
||||
|
||||
objectValuesPipe = new ObjectValuesPipe();
|
||||
|
||||
requestService = jasmine.createSpyObj('requestService', {
|
||||
hasByHrefObservable: observableOf(true)
|
||||
});
|
||||
|
||||
TestBed.configureTestingModule({
|
||||
imports: [TranslateModule.forRoot()],
|
||||
declarations: [PaginatedDragAndDropBitstreamListComponent, VarDirective],
|
||||
providers: [
|
||||
{ provide: ObjectUpdatesService, useValue: objectUpdatesService },
|
||||
{ provide: BundleDataService, useValue: bundleService },
|
||||
{ provide: ObjectValuesPipe, useValue: objectValuesPipe }
|
||||
{ provide: ObjectValuesPipe, useValue: objectValuesPipe },
|
||||
{ provide: RequestService, useValue: requestService }
|
||||
], schemas: [
|
||||
NO_ERRORS_SCHEMA
|
||||
]
|
||||
|
@@ -9,6 +9,7 @@ import { PaginatedSearchOptions } from '../../../../../shared/search/paginated-s
|
||||
import { ResponsiveTableSizes } from '../../../../../shared/responsive-table-sizes/responsive-table-sizes';
|
||||
import { followLink } from '../../../../../shared/utils/follow-link-config.model';
|
||||
import { ObjectValuesPipe } from '../../../../../shared/utils/object-values-pipe';
|
||||
import { RequestService } from '../../../../../core/data/request.service';
|
||||
|
||||
@Component({
|
||||
selector: 'ds-paginated-drag-and-drop-bitstream-list',
|
||||
@@ -35,7 +36,8 @@ export class PaginatedDragAndDropBitstreamListComponent extends AbstractPaginate
|
||||
constructor(protected objectUpdatesService: ObjectUpdatesService,
|
||||
protected elRef: ElementRef,
|
||||
protected objectValuesPipe: ObjectValuesPipe,
|
||||
protected bundleService: BundleDataService) {
|
||||
protected bundleService: BundleDataService,
|
||||
protected requestService: RequestService) {
|
||||
super(objectUpdatesService, elRef, objectValuesPipe);
|
||||
}
|
||||
|
||||
@@ -48,11 +50,17 @@ export class PaginatedDragAndDropBitstreamListComponent extends AbstractPaginate
|
||||
*/
|
||||
initializeObjectsRD(): void {
|
||||
this.objectsRD$ = this.currentPage$.pipe(
|
||||
switchMap((page: number) => this.bundleService.getBitstreams(
|
||||
this.bundle.id,
|
||||
new PaginatedSearchOptions({pagination: Object.assign({}, this.options, { currentPage: page })}),
|
||||
followLink('format')
|
||||
))
|
||||
switchMap((page: number) => {
|
||||
const paginatedOptions = new PaginatedSearchOptions({pagination: Object.assign({}, this.options, { currentPage: page })});
|
||||
return this.bundleService.getBitstreamsEndpoint(this.bundle.id, paginatedOptions).pipe(
|
||||
switchMap((href) => this.requestService.hasByHrefObservable(href)),
|
||||
switchMap(() => this.bundleService.getBitstreams(
|
||||
this.bundle.id,
|
||||
paginatedOptions,
|
||||
followLink('format')
|
||||
))
|
||||
);
|
||||
})
|
||||
);
|
||||
}
|
||||
|
||||
|
@@ -88,10 +88,12 @@ export class BundleDataService extends DataService<Bundle> {
|
||||
/**
|
||||
* Get the bitstreams endpoint for a bundle
|
||||
* @param bundleId
|
||||
* @param searchOptions
|
||||
*/
|
||||
getBitstreamsEndpoint(bundleId: string): Observable<string> {
|
||||
getBitstreamsEndpoint(bundleId: string, searchOptions?: PaginatedSearchOptions): Observable<string> {
|
||||
return this.getBrowseEndpoint().pipe(
|
||||
switchMap((href: string) => this.halService.getEndpoint(this.bitstreamsEndpoint, `${href}/${bundleId}`))
|
||||
switchMap((href: string) => this.halService.getEndpoint(this.bitstreamsEndpoint, `${href}/${bundleId}`)),
|
||||
map((href) => searchOptions ? searchOptions.toRestUrl(href) : href)
|
||||
);
|
||||
}
|
||||
|
||||
@@ -102,9 +104,8 @@ export class BundleDataService extends DataService<Bundle> {
|
||||
* @param linksToFollow The {@link FollowLinkConfig}s for the request
|
||||
*/
|
||||
getBitstreams(bundleId: string, searchOptions?: PaginatedSearchOptions, ...linksToFollow: Array<FollowLinkConfig<Bitstream>>): Observable<RemoteData<PaginatedList<Bitstream>>> {
|
||||
const hrefObs = this.getBitstreamsEndpoint(bundleId).pipe(
|
||||
map((href) => searchOptions ? searchOptions.toRestUrl(href) : href)
|
||||
);
|
||||
const hrefObs = this.getBitstreamsEndpoint(bundleId, searchOptions);
|
||||
|
||||
hrefObs.pipe(
|
||||
take(1)
|
||||
).subscribe((href) => {
|
||||
|
@@ -1,4 +1,4 @@
|
||||
import { FieldUpdate, FieldUpdates, Identifiable } from '../../core/data/object-updates/object-updates.reducer';
|
||||
import { FieldUpdate, FieldUpdates } from '../../core/data/object-updates/object-updates.reducer';
|
||||
import { Observable } from 'rxjs/internal/Observable';
|
||||
import { RemoteData } from '../../core/data/remote-data';
|
||||
import { PaginatedList } from '../../core/data/paginated-list';
|
||||
@@ -6,7 +6,7 @@ import { PaginationComponentOptions } from '../pagination/pagination-component-o
|
||||
import { BehaviorSubject } from 'rxjs/internal/BehaviorSubject';
|
||||
import { ObjectUpdatesService } from '../../core/data/object-updates/object-updates.service';
|
||||
import { distinctUntilChanged, map, switchMap, take } from 'rxjs/operators';
|
||||
import { hasValue } from '../empty.util';
|
||||
import { hasValue, isNotEmpty } from '../empty.util';
|
||||
import { paginatedListToArray } from '../../core/shared/operators';
|
||||
import { DSpaceObject } from '../../core/shared/dspace-object.model';
|
||||
import { CdkDragDrop, moveItemInArray } from '@angular/cdk/drag-drop';
|
||||
@@ -95,10 +95,19 @@ export abstract class AbstractPaginatedDragAndDropListComponent<T extends DSpace
|
||||
/**
|
||||
* Whether or not we should display a loading animation
|
||||
* This is used to display a loading page when the user drops a bitstream onto a new page. The loading animation
|
||||
* should stop once the bitstream has moved to the new page and the new page's response has loaded
|
||||
* should stop once the bitstream has moved to the new page and the new page's response has loaded and contains the
|
||||
* dropped object on top (see this.stopLoadingWhenFirstIs below)
|
||||
*/
|
||||
loading$: BehaviorSubject<boolean> = new BehaviorSubject<boolean>(false);
|
||||
|
||||
/**
|
||||
* ID of the object the page's first element needs to match in order to stop the loading animation.
|
||||
* This is to ensure the new page is fully loaded containing the latest data from the REST API whenever an object is
|
||||
* dropped on a new page. This allows the component to expect the dropped object to be present on top of the new page,
|
||||
* while displaying a loading animation until this is the case.
|
||||
*/
|
||||
stopLoadingWhenFirstIs: string;
|
||||
|
||||
/**
|
||||
* List of subscriptions
|
||||
*/
|
||||
@@ -148,7 +157,15 @@ export abstract class AbstractPaginatedDragAndDropListComponent<T extends DSpace
|
||||
distinctUntilChanged(compareArraysUsingFieldUuids())
|
||||
).subscribe((updateValues) => {
|
||||
this.customOrder = updateValues.map((fieldUpdate) => fieldUpdate.field.uuid);
|
||||
})
|
||||
// Check if stopLoadingWhenFirstIs contains a value. If it does and it equals the first value in customOrder, stop the loading animation.
|
||||
// This is to ensure the page is updated to contain the new values first, before displaying it.
|
||||
if (hasValue(this.stopLoadingWhenFirstIs) && isNotEmpty(this.customOrder) && this.customOrder[0] === this.stopLoadingWhenFirstIs) {
|
||||
this.stopLoadingWhenFirstIs = undefined;
|
||||
this.loading$.next(false);
|
||||
}
|
||||
}),
|
||||
// Disable the pagination when objects are loading
|
||||
this.loading$.subscribe((loading) => this.options.disabled = loading)
|
||||
);
|
||||
}
|
||||
|
||||
@@ -197,6 +214,7 @@ export abstract class AbstractPaginatedDragAndDropListComponent<T extends DSpace
|
||||
// Send out a drop event (and navigate to the new page) when the "from" and "to" indexes are different from each other
|
||||
if (fromIndex !== toIndex) {
|
||||
if (isNewPage) {
|
||||
this.stopLoadingWhenFirstIs = this.customOrder[dragIndex];
|
||||
this.customOrder = [];
|
||||
this.paginationComponent.doPageChange(redirectPage);
|
||||
this.loading$.next(true);
|
||||
@@ -207,7 +225,6 @@ export abstract class AbstractPaginatedDragAndDropListComponent<T extends DSpace
|
||||
finish: () => {
|
||||
if (isNewPage) {
|
||||
this.currentPage$.next(redirectPage);
|
||||
this.loading$.next(false);
|
||||
}
|
||||
}
|
||||
}));
|
||||
|
Reference in New Issue
Block a user