Cecilya
Cecilya

Reputation: 527

Test that event handler is called when file input receives data

I have an Angular 4 component that has an <input> of type file. I want to create a Jasmine test that verifies that the event handler is called when the input field receives a file.

This is the component:

<div>
    <input type="file" (change)="fileChange($event)" placeholder="Upload file" accept=".xls, .xlsx" style="padding-left: 5px">
</div>

This is the event handler:

fileChange(event) {
    let fileList: FileList = event.target.files;
    if (fileList.length > 0) {
        // save the file to the backend - this behaviour is tested in a different test
    }
}

And this is the test case I have so far, cobbled together from various answers on Stackoverflow (e.g. some of these answers) which seems to have worked in Angular 2, but not in Angular 4:

beforeEach(() => {
    fixture = TestBed.createComponent(MyComponent);
    component = fixture.componentInstance;
    fixture.detectChanges();
});

it('file change event should arrive in handler', () => {
    let input  = fixture.debugElement.query(By.css('input[type=file]')).nativeElement;
    input.value = {name: 'excel'};
    input.dispatchEvent(new Event('input'));

    // check that the event handler has been called
    spyOn(component, 'fileChange');

    expect(component.fileChange).toHaveBeenCalled();
});

The problem is that Karma displays SecurityError: The operation is insecure. for the line input.value = {name: 'excel'};. Is there another way to manually assign the value of the input field or at least get it to send an event that is handled by fileChange?

Upvotes: 8

Views: 11030

Answers (2)

Don
Don

Reputation: 1

describe("A suite is just a function", function() {
  var a;

  it("and so is a spec", function() {
    a = true;

    expect(a).toBe(true);
  });
});

Upvotes: -6

yurzui
yurzui

Reputation: 214067

Is there another way to manually assign the value of the input field

You can't assign value to input[type="file"] due to security reasons.

or at least get it to send an event that is handled by fileChange

You can fire change event after spyOn:

spyOn(component, 'fileChange');
input.dispatchEvent(new Event('change'));
expect(component.fileChange).toHaveBeenCalled();

Plunker Example

Upvotes: 11

Related Questions