smartfuzzy/test/test.objectsorter.ts

87 lines
2.8 KiB
TypeScript

import { expect, tap } from '@push.rocks/tapbundle';
import * as smartfuzzy from '../ts/index.js';
class Car {
constructor(public brand: string, public model?: string, public year?: number) {}
}
const testCars = [
new Car('BMW', 'X5', 2022),
new Car('Mercedes Benz', 'S-Class', 2021),
new Car('Volvo', 'XC90', 2023),
new Car('Volkswagen', 'Golf', 2020),
new Car('Audi', 'A4', 2022),
];
let objectSorter: smartfuzzy.ObjectSorter<Car>;
tap.test('should create an instance of ObjectSorter', async () => {
objectSorter = new smartfuzzy.ObjectSorter<Car>(testCars);
expect(objectSorter).toBeInstanceOf(smartfuzzy.ObjectSorter);
expect(objectSorter.objectDictionary).toEqual(testCars);
// Test empty constructor
const emptyObjectSorter = new smartfuzzy.ObjectSorter<Car>();
expect(emptyObjectSorter.objectDictionary).toEqual([]);
});
tap.test('should sort objects by exact brand match', async () => {
const result = objectSorter.sort('Volvo', ['brand']);
// Should return an array of results
expect(result).toBeArray();
expect(result.length).toBeGreaterThan(0);
// First result should be the Volvo
expect(result[0].item.brand).toEqual('Volvo');
// Should have expected result structure
expect(result[0]).toHaveProperty('item');
expect(result[0]).toHaveProperty('refIndex');
expect(result[0].refIndex).toBeTypeofNumber();
// Reference index should match the original array position
expect(result[0].refIndex).toEqual(2); // Volvo is at index 2
});
tap.test('should sort objects by fuzzy brand match', async () => {
// "Wolvo" should fuzzy match to "Volvo"
const result = objectSorter.sort('Wolvo', ['brand']);
expect(result.length).toBeGreaterThan(0);
expect(result[0].item.brand).toEqual('Volvo');
});
tap.test('should sort objects by multiple field search', async () => {
// Add a car with similar model name but different brand
objectSorter = new smartfuzzy.ObjectSorter<Car>([
...testCars,
new Car('Toyota', 'X5 Replica', 2020),
]);
// Search across both brand and model
const result = objectSorter.sort('BMW X5', ['brand', 'model']);
expect(result.length).toBeGreaterThan(0);
// BMW X5 should be first result
expect(result[0].item.brand).toEqual('BMW');
expect(result[0].item.model).toEqual('X5');
// Toyota X5 Replica may be in results depending on threshold
// But we shouldn't expect it specifically since results depend on the
// fuzzy matching algorithm's threshold setting
// BMW should be the first result
const bmwIndex = result.findIndex(r => r.item.brand === 'BMW');
expect(bmwIndex).toEqual(0);
// If Toyota is in results, it should be ranked lower than BMW
const toyotaIndex = result.findIndex(r => r.item.brand === 'Toyota');
if (toyotaIndex !== -1) {
expect(bmwIndex).toBeLessThan(toyotaIndex);
}
});
export default tap.start();