| /******************************************************************************** |
| * Copyright (c) 2020 Contributors to the Eclipse Foundation |
| * |
| * See the NOTICE file(s) distributed with this work for additional |
| * information regarding copyright ownership. |
| * |
| * This program and the accompanying materials are made available under the |
| * terms of the Eclipse Public License 2.0 which is available at |
| * http://www.eclipse.org/legal/epl-2.0 |
| * |
| * SPDX-License-Identifier: EPL-2.0 |
| ********************************************************************************/ |
| |
| import {HttpClientTestingModule, HttpTestingController} from "@angular/common/http/testing"; |
| import {TestBed} from "@angular/core/testing"; |
| import {provideMockActions} from "@ngrx/effects/testing"; |
| import {Action} from "@ngrx/store"; |
| import {EMPTY, Observable, of, Subscription} from "rxjs"; |
| import {IAPIAttachmentModel, SPA_BACKEND_ROUTE} from "../../../../core"; |
| import {createFileMock} from "../../../../test"; |
| import { |
| addAttachmentEntityAction, |
| deleteAttachmentsAction, |
| setAttachmentCacheAction, |
| submitAttachmentFormAction, |
| updateAttachmentTagsAction |
| } from "../../actions"; |
| import {IAttachmentControlValue, IAttachmentError} from "../../model"; |
| import {SubmitAttachmentsEffect} from "./submit-attachments.effect"; |
| |
| describe("SubmitAttachmentsEffect", () => { |
| |
| const statementId = 19; |
| const taskId = "1919"; |
| |
| let actions$: Observable<Action>; |
| let httpTestingController: HttpTestingController; |
| let effect: SubmitAttachmentsEffect; |
| let subscription: Subscription; |
| |
| beforeEach(async () => { |
| TestBed.configureTestingModule({ |
| imports: [ |
| HttpClientTestingModule |
| ], |
| providers: [ |
| SubmitAttachmentsEffect, |
| provideMockActions(() => actions$), |
| { |
| provide: SPA_BACKEND_ROUTE, |
| useValue: "/" |
| } |
| ] |
| }); |
| effect = TestBed.inject(SubmitAttachmentsEffect); |
| httpTestingController = TestBed.inject(HttpTestingController); |
| }); |
| |
| afterEach(() => { |
| if (subscription != null) { |
| subscription.unsubscribe(); |
| } |
| }); |
| |
| it("should call submit method on submit action", async () => { |
| const submitSpy = spyOn(effect, "submit").and.returnValue(EMPTY); |
| actions$ = of(submitAttachmentFormAction({statementId, taskId, value: {add: [], edit: []}})); |
| subscription = effect.submit$.subscribe(); |
| expect(submitSpy).toHaveBeenCalledWith(statementId, taskId, {add: [], edit: []}); |
| }); |
| |
| it("should call add and remove method on submit", async () => { |
| const addSpy = spyOn(effect, "addAttachments").and.returnValue(EMPTY); |
| const editSpy = spyOn(effect, "editAttachments").and.returnValue(EMPTY); |
| const fetchSpy = spyOn(effect.fetchAttachmentsEffect, "fetchAttachments").and.returnValue(EMPTY); |
| |
| subscription = effect.submit(statementId, taskId, {add: [], edit: []}).subscribe(); |
| expect(addSpy).toHaveBeenCalledWith(statementId, taskId, [], []); |
| expect(editSpy).toHaveBeenCalledWith(statementId, taskId, [], []); |
| expect(fetchSpy).toHaveBeenCalledWith(statementId); |
| }); |
| |
| it("should throw an error if a single request fails on submit", async () => { |
| const attachmentError: IAttachmentError = {statementId, attachment: null, error: new Error("Test")}; |
| effect.addAttachments = ( |
| _: number, |
| __: string, |
| ___: IAttachmentControlValue[], |
| errors: IAttachmentError[] = [] |
| ) => { |
| errors.push(attachmentError); |
| return EMPTY; |
| }; |
| spyOn(effect, "editAttachments").and.returnValue(EMPTY); |
| spyOn(effect.fetchAttachmentsEffect, "fetchAttachments").and.returnValue(EMPTY); |
| |
| await expectAsync(effect.submit(statementId, taskId, {add: [], edit: []}).toPromise()) |
| .toBeRejectedWith([attachmentError]); |
| }); |
| |
| it("should add attachments", async () => { |
| const errors: IAttachmentError[] = []; |
| const values: IAttachmentControlValue[] = [ |
| { |
| name: "18.pdf", |
| file: createFileMock("18.pdf"), |
| tagIds: ["tag18", "tag1818"] |
| }, |
| { |
| name: "19.pdf", |
| file: createFileMock("19.pdf"), |
| tagIds: ["tag19", "tag1919"] |
| }, |
| { |
| tagIds: [] |
| }, |
| null |
| ]; |
| const add$ = effect.addAttachments(statementId, taskId, values, errors); |
| const results: Action[] = []; |
| |
| subscription = add$.subscribe((_) => results.push(_)); |
| expectAddRequest({id: 18} as any, values[0].tagIds, true); |
| expectAddRequest({id: 19} as any, values[1].tagIds); |
| expect(results).toEqual([ |
| setAttachmentCacheAction({statementId, items: values}), |
| addAttachmentEntityAction({statementId, entity: {id: 19} as any}), |
| setAttachmentCacheAction({statementId, items: [values[0]]}) |
| ]); |
| expect(errors.length).toBe(1); |
| expect(errors[0].statementId).toBe(statementId); |
| expect(errors[0].attachment).toBe(values[0]); |
| expect(errors[0].error).toBeDefined(); |
| httpTestingController.verify(); |
| }); |
| |
| |
| it("should remove attachments", async () => { |
| const errors: IAttachmentError[] = []; |
| const values: IAttachmentControlValue[] = [ |
| { |
| id: 18, |
| name: "18.pdf", |
| tagIds: ["tag18", "tag1818"], |
| isSelected: false |
| }, |
| { |
| id: 19, |
| name: "19.pdf", |
| tagIds: ["tag19", "tag1919"], |
| isSelected: false |
| }, |
| { |
| name: "", |
| tagIds: [] |
| }, |
| null |
| ]; |
| const add$ = effect.editAttachments(statementId, taskId, values, errors); |
| const results: Action[] = []; |
| |
| subscription = add$.subscribe((_) => results.push(_)); |
| expectDeleteRequest(18, true); |
| expectDeleteRequest(19, false); |
| expect(results).toEqual([ |
| updateAttachmentTagsAction({items: values}), |
| deleteAttachmentsAction({statementId, entityIds: [19]}) |
| ]); |
| expect(errors.length).toBe(1); |
| expect(errors[0].statementId).toBe(statementId); |
| expect(errors[0].attachment).toBe(values[0]); |
| expect(errors[0].error).toBeDefined(); |
| httpTestingController.verify(); |
| }); |
| |
| it("should edit attachment tags", async () => { |
| const errors: IAttachmentError[] = []; |
| const values: IAttachmentControlValue[] = [ |
| { |
| id: 18, |
| name: "18.pdf", |
| tagIds: ["tag18", "tag1818"], |
| isSelected: true |
| }, |
| { |
| id: 19, |
| name: "19.pdf", |
| tagIds: ["tag19", "tag1919"], |
| isSelected: true |
| }, |
| { |
| tagIds: [] |
| } |
| ]; |
| const add$ = effect.editAttachments(statementId, taskId, values, errors); |
| const results: Action[] = []; |
| |
| subscription = add$.subscribe((_) => results.push(_)); |
| expectPostAttachmentTags(values[0].id, values[0].tagIds, true); |
| expectPostAttachmentTags(values[1].id, values[1].tagIds, false); |
| expect(results).toEqual([updateAttachmentTagsAction({items: values})]); |
| expect(errors.length).toBe(1); |
| expect(errors[0].statementId).toBe(statementId); |
| expect(errors[0].attachment).toBe(values[0]); |
| expect(errors[0].error).toBeDefined(); |
| httpTestingController.verify(); |
| }); |
| |
| function expectAddRequest(returnValue: IAPIAttachmentModel, tagIds: string[], error = false) { |
| const url = `/process/statements/${statementId}/task/${taskId}/attachments`; |
| const params = tagIds.reduce((_, tagId, i) => _ + (i > 0 ? "&" : "") + "tagId=" + tagId, ""); |
| const request = httpTestingController.expectOne(url + (params.length > 0 ? "?" : "") + params); |
| expect(request.request.method).toBe("POST"); |
| if (error) { |
| request.error(new ErrorEvent("test error")); |
| } else { |
| request.flush(returnValue); |
| } |
| |
| } |
| |
| function expectPostAttachmentTags(attachmentId: number, tagIds: string[], error = false) { |
| const url = `/process/statements/${statementId}/task/${taskId}/attachments/${attachmentId}/tags`; |
| const request = httpTestingController.expectOne(url); |
| expect(request.request.method).toBe("POST"); |
| expect(request.request.body).toEqual(tagIds); |
| if (error) { |
| request.error(new ErrorEvent("test error")); |
| } else { |
| request.flush("204"); |
| } |
| } |
| |
| function expectDeleteRequest(attachmentId: number, error = false) { |
| const url = `/process/statements/${statementId}/task/${taskId}/attachments/${attachmentId}`; |
| const request = httpTestingController.expectOne(url); |
| expect(request.request.method).toBe("DELETE"); |
| if (error) { |
| request.error(new ErrorEvent("test error")); |
| } else { |
| request.flush("204"); |
| } |
| } |
| |
| }); |
| |