UNPKG

kokopu

Version:

A JavaScript/TypeScript library implementing the chess game rules and providing tools to read/write the standard chess file formats.

139 lines (117 loc) 5.26 kB
/*! * -------------------------------------------------------------------------- * * * * Kokopu - A JavaScript/TypeScript chess library. * * <https://www.npmjs.com/package/kokopu> * * Copyright (C) 2018-2025 Yoann Le Montagner <yo35 -at- melix.net> * * * * Kokopu is free software: you can redistribute it and/or * * modify it under the terms of the GNU Lesser General Public License * * as published by the Free Software Foundation, either version 3 of * * the License, or (at your option) any later version. * * * * Kokopu is distributed in the hope that it will be useful, * * but WITHOUT ANY WARRANTY; without even the implied warranty of * * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * * GNU Lesser General Public License for more details. * * * * You should have received a copy of the GNU Lesser General * * Public License along with this program. If not, see * * <http://www.gnu.org/licenses/>. * * * * -------------------------------------------------------------------------- */ const { exception, Game } = require('../dist/lib/index'); const dumpGame = require('./common/dumpgame'); const readCSV = require('./common/readcsv'); const readText = require('./common/readtext'); const resourceExists = require('./common/resourceexists'); const test = require('unit.js'); function testData() { return readCSV('jsons.csv', fields => { const label = fields[0].trim(); if (label.length === 0 || label.charAt(0) === '#') { return false; } return { label: label, json: readText(`jsons/${fields[0]}/game.json`), }; }); } /** * Return whether the JSON item corresponding to the given name is expected to be parsed as a valid game, * or is expected to throw an exception on a parsing attempt. */ function getItemType(jsonName) { const fileBasename = `jsons/${jsonName}/game`; const txtExist = resourceExists(fileBasename + '.txt'); const errExist = resourceExists(fileBasename + '.err'); if (txtExist && errExist) { throw 'Both .txt not .err defined for ' + fileBasename; // eslint-disable-line no-throw-literal } else if (txtExist) { return 'txt'; } else if (errExist) { return 'err'; } else { throw 'Neither .txt nor .err defined for ' + fileBasename; // eslint-disable-line no-throw-literal } } /** * Load the descriptor corresponding to a valid JSON item. */ function loadValidItemDescriptor(jsonName) { const filename = `jsons/${jsonName}/game.txt`; return readText(filename).trim(); } /** * Load the descriptor corresponding to an invalid JSON item. */ function loadErrorItemDescriptor(jsonName) { const filename = `jsons/${jsonName}/game.err`; const fields = readText(filename).split('\n'); return { fieldName: fields[0], message: fields[1].trim() }; } function itCheckJSONItem(label, jsonName, loader) { it(label, () => { // TXT type => ensure that the item is valid, and compare its dump result to the descriptor. if (getItemType(jsonName) === 'txt') { const expectedDescriptor = loadValidItemDescriptor(jsonName); test.value(dumpGame(loader()).trim()).is(expectedDescriptor); } // ERR type => ensure that an exception is thrown, and check its attributes. else { const expectedDescriptor = loadErrorItemDescriptor(jsonName); test.exception(() => loader()) .isInstanceOf(exception.InvalidPOJO) .hasProperty('fieldName', expectedDescriptor.fieldName) .hasProperty('message', expectedDescriptor.message); } }); } describe('Read JSON', () => { for (const elem of testData()) { itCheckJSONItem(`File ${elem.label}`, elem.label, () => Game.fromPOJO(JSON.parse(elem.json))); } }); describe('Read non-JSONified POJO', () => { itCheckJSONItem('Undefined fields', 'undefined-fields', () => Game.fromPOJO({ event: 'Game with undefined fields', site: undefined, white: undefined, black: { elo: undefined, }, mainVariation: [ 'e4', { notation: 'e5', variations: undefined }, 'Nf3', 'Nc6', { notation: 'd4', comment: 'I\'m a comment...', isLongComment: undefined }, { notation: 'exd4', nags: [ 1, undefined, 10 ], tags: { cal: undefined, csl: 'Gd4' } }, ], })); itCheckJSONItem('Not a POJO', 'not-a-pojo', () => Game.fromPOJO('not-a-pojo')); });