I'm trying to write the unit testing for the file upload method in the angular 7. Getting the below error in the testing window. I'm new for angular unit testing. Could someone help, How to add mock files to get the full code coverage?
TypeError: Cannot set property 'value' of undefined
Here is my unit test code (spec file),
describe('ImportComponent', () => {
let component: ImportComponent;
let fixture: ComponentFixture<ImportComponent>;
let element;
beforeEach(
async(() => {
TestBed.configureTestingModule({
imports: [ HttpClientModule, RouterTestingModule ],
declarations: [ ImportComponent ]
}).compileComponents();
})
);
beforeEach(() => {
fixture = TestBed.createComponent(ImportComponent);
component = fixture.componentInstance;
element = fixture.nativeElement;
fixture.detectChanges();
});
it('should create', () => {
expect(component).toBeTruthy();
});
it('should upload the file', () => {
component.importFile();
const inputEl = element.querySelector('#postal_file');
const fileList = { 0: { name: 'foo', size: 500001 } };
inputEl.value = {
target: {
files: fileList
}
};
inputEl.dispatchEvent(new Event('change'));
});
});
Method in the component
importFile() {
const inputEl: HTMLInputElement = this.el.nativeElement.querySelector('#postal_file');
const fileCount: number = inputEl.files.length;
const formData = new FormData();
if (fileCount > 0) {
formData.append(this.postalFileName, inputEl.files.item(0));
this.postalService.importPostalCodes(formData).subscribe((data) => {
this.result = data;
});
}
}
and the HTML,
<div class="file-import">
<form action="" method="post" encType="multipart/form-data">
<label for="postal_file">Choose File</label>
<input type="file" name="postal_file" id="postal_file">
<button type="button" (click)="importFile()">Import</button>
</form>
</div>
The unit test is not covered all the code as shown in the below image, please help , how to ge the 100% code coverage.
Code coverage image
For file upload related testing we need to Mock HTTPContext, HTTPContext. Server and HttpPostedFileBase. These classes handle the file uploading and saving.
A simple way to test file upload and check model value set.
.html
<input (change)="onFileSelected()" #fileInput type="file" id="file">
.ts
uploadedFile : any
onFileSelected() {
const inputNode: any = document.querySelector('#file');
this.uploadedFile = inputNode.files[0];
}
spec.ts
it('should detect file input change and set uploadedFile model', () => {
const dataTransfer = new DataTransfer()
dataTransfer.items.add(new File([''], 'test-file.pdf'))
const inputDebugEl = fixture.debugElement.query(By.css('input[type=file]'));
inputDebugEl.nativeElement.files = dataTransfer.files;
inputDebugEl.nativeElement.dispatchEvent(new InputEvent('change'));
fixture.detectChanges();
expect(component.uploadedFile).toBeTruthy()
expect(component.uploadedFile).toBe('test-file.pdf')
});
it('file change event should arrive in handler', () => {
const element = fixture.nativeElement;
const input = element.querySelector('#file');
spyOn(component, 'onFileSelected');
input.dispatchEvent(new Event('change'));
fixture.detectChanges();
expect(component.onFileSelected).toHaveBeenCalled();
});
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With