hubcard-inspector-pro / test_engine.mjs
Hugdrigo's picture
Upload 12 files
bc4b45e verified
Raw History Blame Contribute Delete
3.72 kB
import test from 'node:test';
import assert from 'node:assert/strict';
import fs from 'node:fs';
import {RULES,auditCard,parseFrontmatter,parseRepoLine,buildRemediation,buildReport,csvReport,validateSpaceReadme,headings} from './engine.mjs';
const sample=(type)=>{
const rows={
model:`---\nlicense: mit\nlanguage:\n- en\npipeline_tag: text-classification\n---\n# Model Description\n\n## Intended Uses\n\n## Training Data\n\n## Training Procedure\n\n## Evaluation\n\n## Usage Example\n\n## Ethical Considerations\n\n## Limitations\n\n## Versions`,
dataset:`---\nlicense: mit\nlanguage: en\ntask_categories: [text-classification]\n---\n# Dataset Description\n\n## Source Data\n\n## Data Processing\n\n## Features\n\n## Dataset Splits\n\n## Intended Uses\n\n## Limitations\n\n## Examples\n\n## Privacy`,
space:`---\ntitle: An Example\nshort_description: Demo\nlicense: mit\nsdk: static\n---\n# Overview\n\n## How to Use\n\n## Example\n\n## Architecture\n\n## Limitations\n\n## Privacy\n\n## Sources\n\n## Maintenance\n\n## Responsible Use`
};return rows[type]};
for(const t of Object.keys(RULES))test(`rubric ${t} has 100 points`,()=>assert.equal(RULES[t].reduce((s,x)=>s+x[2],0),100));
for(const t of Object.keys(RULES))test(`full ${t} card scores 100`,()=>assert.equal(auditCard(t,sample(t)).score,100));
test('empty card scores zero for every type',()=>{for(const t of Object.keys(RULES))assert.equal(auditCard(t,'').score,0)});
test('YAML frontmatter correctly parses lists and fields',()=>{const m=parseFrontmatter('---\nlanguage:\n- en\n- es\nlicense: mit\n---\n');assert.deepEqual(m.language,['en','es']);assert.equal(m.license,'mit')});
test('headings only recognize Markdown headings, not inline words',()=>{assert.equal(headings('some evaluation words\n## Evaluation\n').length,1);assert.equal(auditCard('model','The evaluation was impressive.').score,0)});
test('ambiguous heading empty still scores, with disclaimer',()=>{const a=auditCard('model','## Evaluation\n');assert.ok(a.score>0);assert.ok(a.disclaimer.includes('Heuristic'))});
test('missing checks make a non-fabricated remediation template',()=>{const a=auditCard('model','## Model Description');const s=buildRemediation(a);assert.ok(s.includes('[To be completed with verified information'));assert.ok(s.includes('verified facts'))});
test('reports export valid Markdown and CSV',()=>{const result=auditCard('dataset',sample('dataset'),{},'Demo');assert.ok(buildReport([result]).includes('## Demo'));assert.equal(csvReport([result]).split('\n').length,result.checks.length+1)});
test('repo URL parsing supports 3 types and blocks invalid paths',()=>{
assert.deepEqual(parseRepoLine('https://huggingface.co/spaces/Hugdrigo/researchlens'),{type:'space',id:'Hugdrigo/researchlens'});
assert.deepEqual(parseRepoLine('dataset:org/set'),{type:'dataset',id:'org/set'});
assert.deepEqual(parseRepoLine('org/model'),{type:'model',id:'org/model'});
assert.throws(()=>parseRepoLine('invalid!'));
});
test('Hugging Face README metadata obeys Space validator and color limits',()=>{
const src=fs.readFileSync(new URL('./README.md',import.meta.url),'utf8');const v=validateSpaceReadme(src);
assert.deepEqual(v.errors,[]);assert.equal(v.metadata.sdk,'static');assert.ok(v.metadata.short_description.length<=60);
const bad=src.replace('colorTo: blue','colorTo: cyan');assert.equal(validateSpaceReadme(bad).valid,false);
});
test('fictional offline demos have different, non-perfect scores',()=>{
const demos=JSON.parse(fs.readFileSync(new URL('./demo_cards.json',import.meta.url)));
assert.equal(demos.length,3);for(const d of demos){const a=auditCard(d.type,d.readme);assert.ok(a.score>0&&a.score<100);assert.ok(d.name.includes('DEMO'))}
});