Applique .gitattributes sur tous les fichiers existants. Élimine les différences fantômes entre WSL et Windows. Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
118 lines
3.4 KiB
TypeScript
Executable File
118 lines
3.4 KiB
TypeScript
Executable File
import { describe, it, expect } from 'vitest';
|
|
|
|
/**
|
|
* Tests de validation structurelle des imports.
|
|
* Vérifie que les données importées sont conformes au schéma attendu.
|
|
*/
|
|
|
|
// Réplique de la logique de validation de ParametresView
|
|
function validateEnclosData(data: any): boolean {
|
|
if (!data || typeof data !== 'object' || data === null) return false;
|
|
if (!Array.isArray(data.enclos)) return false;
|
|
return data.enclos.every((enc: any) =>
|
|
enc && typeof enc === 'object' &&
|
|
typeof enc.id === 'number' &&
|
|
typeof enc.name === 'string' &&
|
|
Array.isArray(enc.dragodindes) &&
|
|
enc.gaugeLevels && typeof enc.gaugeLevels === 'object' &&
|
|
enc.timer && typeof enc.timer === 'object',
|
|
);
|
|
}
|
|
|
|
describe('Validation import — validateEnclosData', () => {
|
|
it('accepte un state valide', () => {
|
|
const data = {
|
|
enclos: [{
|
|
id: 1, name: 'Enclos 1',
|
|
dragodindes: [],
|
|
gaugeLevels: { baffeur: 0 },
|
|
timer: { running: false },
|
|
}],
|
|
};
|
|
expect(validateEnclosData(data)).toBe(true);
|
|
});
|
|
|
|
it('accepte un state avec plusieurs enclos', () => {
|
|
const data = {
|
|
enclos: [
|
|
{ id: 1, name: 'A', dragodindes: [], gaugeLevels: {}, timer: {} },
|
|
{ id: 2, name: 'B', dragodindes: [{ id: 1 }], gaugeLevels: {}, timer: {} },
|
|
],
|
|
};
|
|
expect(validateEnclosData(data)).toBe(true);
|
|
});
|
|
|
|
it('rejette null', () => {
|
|
expect(validateEnclosData(null)).toBe(false);
|
|
});
|
|
|
|
it('rejette undefined', () => {
|
|
expect(validateEnclosData(undefined)).toBe(false);
|
|
});
|
|
|
|
it('rejette une chaîne', () => {
|
|
expect(validateEnclosData('hello')).toBe(false);
|
|
});
|
|
|
|
it('rejette un objet sans enclos', () => {
|
|
expect(validateEnclosData({ foo: 'bar' })).toBe(false);
|
|
});
|
|
|
|
it('rejette enclos non-array', () => {
|
|
expect(validateEnclosData({ enclos: 'not array' })).toBe(false);
|
|
});
|
|
|
|
it('rejette enclos avec id manquant', () => {
|
|
const data = {
|
|
enclos: [{ name: 'A', dragodindes: [], gaugeLevels: {}, timer: {} }],
|
|
};
|
|
expect(validateEnclosData(data)).toBe(false);
|
|
});
|
|
|
|
it('rejette enclos avec name non-string', () => {
|
|
const data = {
|
|
enclos: [{ id: 1, name: 123, dragodindes: [], gaugeLevels: {}, timer: {} }],
|
|
};
|
|
expect(validateEnclosData(data)).toBe(false);
|
|
});
|
|
|
|
it('rejette enclos sans dragodindes', () => {
|
|
const data = {
|
|
enclos: [{ id: 1, name: 'A', gaugeLevels: {}, timer: {} }],
|
|
};
|
|
expect(validateEnclosData(data)).toBe(false);
|
|
});
|
|
|
|
it('rejette enclos sans gaugeLevels', () => {
|
|
const data = {
|
|
enclos: [{ id: 1, name: 'A', dragodindes: [], timer: {} }],
|
|
};
|
|
expect(validateEnclosData(data)).toBe(false);
|
|
});
|
|
|
|
it('rejette enclos sans timer', () => {
|
|
const data = {
|
|
enclos: [{ id: 1, name: 'A', dragodindes: [], gaugeLevels: {} }],
|
|
};
|
|
expect(validateEnclosData(data)).toBe(false);
|
|
});
|
|
|
|
it('rejette si un seul enclos est invalide dans le tableau', () => {
|
|
const data = {
|
|
enclos: [
|
|
{ id: 1, name: 'A', dragodindes: [], gaugeLevels: {}, timer: {} },
|
|
{ id: 'bad' }, // invalide
|
|
],
|
|
};
|
|
expect(validateEnclosData(data)).toBe(false);
|
|
});
|
|
|
|
it('accepte un tableau enclos vide', () => {
|
|
expect(validateEnclosData({ enclos: [] })).toBe(true);
|
|
});
|
|
|
|
it('rejette un objet backup avec data: null', () => {
|
|
expect(validateEnclosData({ app: 'obsidienne', data: null })).toBe(false);
|
|
});
|
|
});
|