29 lines
3.6 KiB
JavaScript
29 lines
3.6 KiB
JavaScript
import assert from 'node:assert/strict';
|
|
import test from 'node:test';
|
|
import fs from 'node:fs';
|
|
import {operationTreatments,newSalesOperation,evaluateSalesOperation,recordSales,saveSalesBook,salesBook,salesCurrent} from '../../resources/js/lib/iva-operations.ts';
|
|
import {createProjectDossierReport} from '../../resources/js/lib/project-dossier-report.ts';
|
|
const ids=['industrial_feed','industrial_feed_inputs','veterinary_goods','agricultural_services'];
|
|
function seed(){return JSON.parse(fs.readFileSync(new URL('./fixtures/iva-publications.json',import.meta.url),'utf8'));}
|
|
function fixture(){const draft=seed();draft.context_opportunity='opportunity:314';draft.project_title='SYNTHETIC QA — G2E social';
|
|
let book={currency:'MZN',rows:ids.map((id,i)=>({...newSalesOperation(`g2e-${i}`,'2026-06','MZN'),description:`SYNTHETIC QA ${id}`,establishment:'SYNTHETIC QA equipamento Manica',amount:'100',basis:i%2?'included':'net',treatment:id,confirmed:operationTreatments.find(t=>t.id===id).conditions.map((_,n)=>n),evidence:'SYNTHETIC QA — natureza, entidade, reconhecimento e condições cumulativas pressupostos documentados; sem certificação'})),periods:[{period:'2026-06',complete:true}]};book=recordSales(draft,book);draft.modelo_a_snapshot=saveSalesBook(draft,book);return {draft,book};}
|
|
test('G2E four branches require their own operation and eligibility conditions',()=>{
|
|
const {book}=fixture();for(const row of book.rows){const rule=operationTreatments.find(t=>t.id===row.treatment),r=evaluateSalesOperation(row,'MZN');assert.equal(r.field,row.treatment==='industrial_feed'?'05':'07');assert.equal(r.net,'100.00');assert.equal(r.vat,'0.00');assert.equal(r.gross,'100.00');assert.match(r.article,/9\((12|15)\)/);
|
|
assert.equal(rule.conditions.length,3);
|
|
for(const missing of row.confirmed)assert.equal(evaluateSalesOperation({...row,confirmed:row.confirmed.filter(n=>n!==missing)},'MZN').vat,null);
|
|
assert.equal(evaluateSalesOperation({...row,evidence:''},'MZN').vat,null); assert.equal(evaluateSalesOperation({...row,period:'2025-06'},'MZN').vat,null); assert.equal(evaluateSalesOperation(row,'USD').vat,null);
|
|
}
|
|
assert.equal(book.result.periods[0].fields['07'],'300.00');assert.equal(book.result.periods[0].fields['05'],'100.00');assert.match(book.result.rows[0].reason,/com direito/);assert.ok(book.result.rows.slice(1).every(r=>r.reason.includes('sem direito')));
|
|
});
|
|
test('new agro context round-trips and reports only its operations, preserving five accepted books without recalculation',()=>{
|
|
const {draft,book}=fixture(),original=seed();const old=JSON.parse(original.modelo_a_snapshot).salesOperations;
|
|
const recovered=JSON.parse(JSON.stringify(draft)),store=JSON.parse(recovered.modelo_a_snapshot).salesOperations;
|
|
for(const id of ['opportunity:309','opportunity:310','opportunity:311','opportunity:312','opportunity:313']){assert.deepEqual(store[id],old[id]);assert.equal(salesCurrent({...recovered,context_opportunity:id},store[id]),true);}
|
|
assert.equal(salesCurrent(recovered,salesBook(recovered)),true);
|
|
const model=JSON.stringify(createProjectDossierReport(recovered,{selectedSections:new Set(['finance'])}));
|
|
for(const token of [...ids,'300.00','opportunity:314','Manica','2026-06','MZN'])assert.ok(model.includes(token),token);
|
|
for(const token of ['financial_stamp','patient_transport','social_assistance_public','statutory_membership','author_rights'])assert.equal(model.includes(token),false);
|
|
assert.equal(book.result.rows.length,4);assert.equal(draft.currency,original.currency);assert.deepEqual(draft.selection_labels,original.selection_labels);
|
|
});
|
|
if(process.env.IVA_G2E_OUT)fs.writeFileSync(process.env.IVA_G2E_OUT,JSON.stringify(fixture().draft,null,2));
|