62 lines
2.6 KiB
TypeScript
62 lines
2.6 KiB
TypeScript
import { describe, expect, it } from 'vitest';
|
|
import { genericProfile } from '../../src/profiles/generic/generic-profile';
|
|
import { importFile } from '../../src/importers/importer';
|
|
import { ImportError } from '../../src/shared/errors';
|
|
import genericFixture from '../../fixtures/generic/findings.synthetic.csv?raw';
|
|
|
|
const options = { profiles: [genericProfile] };
|
|
|
|
describe('file importer', () => {
|
|
it('imports the persistent generic CSV fixture through the full pipeline', async () => {
|
|
const file = new File([genericFixture], 'findings.synthetic.csv', { type: 'text/csv', lastModified: 1234 });
|
|
|
|
const imported = await importFile(file, options);
|
|
|
|
expect(imported.profileId).toBe('generic');
|
|
expect(imported.scanTool).toBe('Tabular Data');
|
|
expect(imported.sheets[0].analysis.records).toHaveLength(2);
|
|
expect(imported.sheets[0].analysis.records[0].title).toBe('Synthetic weak policy');
|
|
});
|
|
|
|
it('falls back to Windows-1252 when UTF-8 decoding fails', async () => {
|
|
const prefix = new TextEncoder().encode('Title;Severity\nPr');
|
|
const suffix = new TextEncoder().encode('fung;High');
|
|
const bytes = new Uint8Array([...prefix, 0xfc, ...suffix]);
|
|
const file = new File([bytes], 'windows-1252.csv', { type: 'text/csv' });
|
|
|
|
const imported = await importFile(file, options);
|
|
|
|
expect(imported.sheets[0].rows[1][0]).toBe('Pr\u00fcfung');
|
|
});
|
|
|
|
it('rejects a file without any evaluable rows', async () => {
|
|
const file = new File(['\r\n\r\n'], 'empty.csv', { type: 'text/csv' });
|
|
|
|
await expect(importFile(file, options)).rejects.toThrow(ImportError);
|
|
await expect(importFile(file, options)).rejects.toThrow('Die Datei enth\u00e4lt keine auswertbaren Tabellen.');
|
|
});
|
|
|
|
|
|
it('imports a larger realistic CSV without losing rows', async () => {
|
|
const header = 'Title;Severity;Status;Asset';
|
|
const rows = Array.from({ length: 5000 }, (_, index) =>
|
|
`Synthetic finding ${index + 1};Medium;Open;asset-${index + 1}`
|
|
);
|
|
const file = new File([[header, ...rows].join('\n')], 'large.csv', { type: 'text/csv' });
|
|
|
|
const imported = await importFile(file, options);
|
|
|
|
expect(imported.sheets[0].analysis.records).toHaveLength(5000);
|
|
expect(imported.sheets[0].analysis.records[4999].title).toBe('Synthetic finding 5000');
|
|
});
|
|
|
|
it('rejects a truncated XLSX container', async () => {
|
|
const truncatedZip = new Uint8Array([0x50, 0x4b, 0x03, 0x04]);
|
|
const file = new File([truncatedZip], 'broken.xlsx', {
|
|
type: 'application/vnd.openxmlformats-officedocument.spreadsheetml.sheet'
|
|
});
|
|
|
|
await expect(importFile(file, options)).rejects.toThrow();
|
|
});
|
|
});
|