cry-klikvet-logic 1.0.708 → 1.0.711

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (73) hide show
  1. package/dist/index-browser.d.mts +18 -0
  2. package/dist/index-browser.d.mts.map +1 -1
  3. package/dist/index-browser.mjs +12 -0
  4. package/dist/index-browser.mjs.map +1 -1
  5. package/dist/index.d.mts +18 -0
  6. package/dist/index.d.mts.map +1 -1
  7. package/dist/index.mjs +12 -0
  8. package/dist/index.mjs.map +1 -1
  9. package/dist/izvozRacunov/db.d.mts +26 -0
  10. package/dist/izvozRacunov/db.d.mts.map +1 -0
  11. package/dist/izvozRacunov/db.mjs +6 -0
  12. package/dist/izvozRacunov/db.mjs.map +1 -0
  13. package/dist/izvozRacunov/generirajIzvoz.d.mts +48 -0
  14. package/dist/izvozRacunov/generirajIzvoz.d.mts.map +1 -0
  15. package/dist/izvozRacunov/generirajIzvoz.mjs +63 -0
  16. package/dist/izvozRacunov/generirajIzvoz.mjs.map +1 -0
  17. package/dist/izvozRacunov/izvoziRacune.d.mts +58 -0
  18. package/dist/izvozRacunov/izvoziRacune.d.mts.map +1 -0
  19. package/dist/izvozRacunov/izvoziRacune.mjs +578 -0
  20. package/dist/izvozRacunov/izvoziRacune.mjs.map +1 -0
  21. package/dist/izvozRacunov/oznake.d.mts +41 -0
  22. package/dist/izvozRacunov/oznake.d.mts.map +1 -0
  23. package/dist/izvozRacunov/oznake.mjs +88 -0
  24. package/dist/izvozRacunov/oznake.mjs.map +1 -0
  25. package/dist/izvozRacunov/schemas/izvozRacunov.schema.json +285 -0
  26. package/dist/izvozRacunov/schemas/izvozRacunov.xsd +400 -0
  27. package/dist/izvozRacunov/serializirajJson.d.mts +16 -0
  28. package/dist/izvozRacunov/serializirajJson.d.mts.map +1 -0
  29. package/dist/izvozRacunov/serializirajJson.mjs +13 -0
  30. package/dist/izvozRacunov/serializirajJson.mjs.map +1 -0
  31. package/dist/izvozRacunov/serializirajXml.d.mts +18 -0
  32. package/dist/izvozRacunov/serializirajXml.d.mts.map +1 -0
  33. package/dist/izvozRacunov/serializirajXml.mjs +309 -0
  34. package/dist/izvozRacunov/serializirajXml.mjs.map +1 -0
  35. package/dist/q-mojPromet.d.mts +1 -1
  36. package/dist/q-promet.d.mts +2 -2
  37. package/dist/q-racunovodji.d.mts +1 -1
  38. package/dist/q-zakljucek-blagajne.d.mts +2 -2
  39. package/dist/racunovodstvo/konti.d.mts +139 -0
  40. package/dist/racunovodstvo/konti.d.mts.map +1 -0
  41. package/dist/racunovodstvo/konti.mjs +135 -0
  42. package/dist/racunovodstvo/konti.mjs.map +1 -0
  43. package/dist/racunovodstvo/kontiUparitev.d.mts +127 -0
  44. package/dist/racunovodstvo/kontiUparitev.d.mts.map +1 -0
  45. package/dist/racunovodstvo/kontiUparitev.mjs +266 -0
  46. package/dist/racunovodstvo/kontiUparitev.mjs.map +1 -0
  47. package/dist/racunovodstvo/stroskovnoMesto.d.mts +56 -0
  48. package/dist/racunovodstvo/stroskovnoMesto.d.mts.map +1 -0
  49. package/dist/racunovodstvo/stroskovnoMesto.mjs +89 -0
  50. package/dist/racunovodstvo/stroskovnoMesto.mjs.map +1 -0
  51. package/dist/test/izvozRacunov.d.mts +2 -0
  52. package/dist/test/izvozRacunov.d.mts.map +1 -0
  53. package/dist/test/izvozRacunov.mjs +258 -0
  54. package/dist/test/izvozRacunov.mjs.map +1 -0
  55. package/dist/test/izvozRacunovShema.d.mts +2 -0
  56. package/dist/test/izvozRacunovShema.d.mts.map +1 -0
  57. package/dist/test/izvozRacunovShema.mjs +267 -0
  58. package/dist/test/izvozRacunovShema.mjs.map +1 -0
  59. package/dist/types/blagajna.d.mts +8 -0
  60. package/dist/types/blagajna.d.mts.map +1 -1
  61. package/dist/types/dnevnikIzvozov.d.mts +1 -0
  62. package/dist/types/dnevnikIzvozov.d.mts.map +1 -1
  63. package/dist/types/izvozRacun.d.mts +481 -0
  64. package/dist/types/izvozRacun.d.mts.map +1 -0
  65. package/dist/types/izvozRacun.mjs +53 -0
  66. package/dist/types/izvozRacun.mjs.map +1 -0
  67. package/dist/types/lokacija.d.mts +10 -0
  68. package/dist/types/lokacija.d.mts.map +1 -1
  69. package/dist/types/nastavitve.d.mts +17 -0
  70. package/dist/types/nastavitve.d.mts.map +1 -1
  71. package/dist/types/racun.d.mts +9 -1
  72. package/dist/types/racun.d.mts.map +1 -1
  73. package/package.json +4 -2
@@ -0,0 +1,89 @@
1
+ // AI created: 2026-10-02 (stroškovno mesto računa: ena veriga za izvoz in prikaz)
2
+ // AI moved: 2026-10-05 (iz klikVetApp/code/VOD/stroskovnoMesto.ts v klikvet-logic —
3
+ // uporabljata jo VOD izvoz knjižb in izvoz izdanih računov v zunanji sistem)
4
+ /**
5
+ * Stroškovno mesto za izvoz v računovodstvo — **ena sama veriga**, ki jo uporabljata
6
+ * tako izvoz knjižb (`klikVetApp/code/VOD/izvoziRacuneVOD.ts`) kot izvoz izdanih
7
+ * računov (`src/izvozRacunov`) in prikaz na strani `glavneUparitve.vue`.
8
+ *
9
+ * Zakaj ločen modul: stran v stolpcu »privzeto« obljublja tisto, kar bo izvoz
10
+ * zares vzel. Če bi verigo pisala vsaka stran svojo, bi se prikaz in datoteka
11
+ * razhajala — natanko to, čemur se pri kontih izogibamo s skupnimi funkcijami.
12
+ *
13
+ * Veriga (bolj določeno prevlada): **blagajna → lokacija → nadrejena lokacija**.
14
+ * Blagajna ve, kam gre denar tega računa; lokacija je okvir; nadrejena lokacija
15
+ * je najbolj splošna (npr. terenska enota pod matično ambulanto). Manjkajočega
16
+ * mesta **ne izmišljamo** — račun gre v izvoz brez elementa, izvoz pa opozori.
17
+ */
18
+ /**
19
+ * Največja dolžina stroškovnega mesta (10 znakov), kot jo določa VOD shema
20
+ * (`Stroskovno_mesto`, `xs:maxLength 10`).
21
+ *
22
+ * Pantheonova imena stroškovnih mest so daljša (`PE PODČETRTEK` = 13), zato v
23
+ * datoteko ne gredo — vrednost je koda (`anQId`), ime pa služi le prikazu.
24
+ */
25
+ export const NAJVEC_ZNAKOV_STROSKOVNEGA_MESTA = 10;
26
+ /** Vrednost, ki sme v `Stroskovno_mesto`: neprazna in največ 10 znakov. */
27
+ export function veljavnoStroskovnoMesto(v) {
28
+ const s = String(v !== null && v !== void 0 ? v : "").trim();
29
+ if (!s)
30
+ return undefined;
31
+ if (s.length > NAJVEC_ZNAKOV_STROSKOVNEGA_MESTA)
32
+ return undefined;
33
+ return s;
34
+ }
35
+ /** Mesta blagajn, ključena po `_id` blagajne. */
36
+ export function mestaBlagajnIz(zapisi) {
37
+ var _a, _b;
38
+ const mapa = new Map();
39
+ for (const z of zapisi) {
40
+ const id = String((_a = z === null || z === void 0 ? void 0 : z._id) !== null && _a !== void 0 ? _a : "");
41
+ if (id)
42
+ mapa.set(id, String((_b = z === null || z === void 0 ? void 0 : z.stroskovnoMesto) !== null && _b !== void 0 ? _b : ""));
43
+ }
44
+ return mapa;
45
+ }
46
+ /** Mesta lokacij, ključena po `_id` lokacije (z id-jem nadrejene lokacije). */
47
+ export function mestaLokacijIz(zapisi) {
48
+ var _a, _b, _c;
49
+ const mapa = new Map();
50
+ for (const z of zapisi) {
51
+ const id = String((_a = z === null || z === void 0 ? void 0 : z._id) !== null && _a !== void 0 ? _a : "");
52
+ if (!id)
53
+ continue;
54
+ mapa.set(id, {
55
+ mesto: String((_b = z === null || z === void 0 ? void 0 : z.stroskovnoMesto) !== null && _b !== void 0 ? _b : ""),
56
+ nadrejena: String((_c = z === null || z === void 0 ? void 0 : z.delLokacijeId) !== null && _c !== void 0 ? _c : ""),
57
+ });
58
+ }
59
+ return mapa;
60
+ }
61
+ /**
62
+ * Stroškovno mesto, ki velja za vrstico (račun, blagajno ali lokacijo).
63
+ *
64
+ * Vrne **prazen niz**, kadar ga ni nikjer v verigi — klicatelj se sam odloči,
65
+ * ali element izpusti (izvoz) ali izpiše pomišljaj (prikaz).
66
+ *
67
+ * Cikel v `delLokacijeId` (podatki so lahko tudi ročno pokvarjeni) nas ne sme
68
+ * zavrteti: vsako lokacijo obiščemo največ enkrat, veriga pa se takrat ustavi.
69
+ */
70
+ export function stroskovnoMestoZaVrstico(vrstica, mestaBlagajn, mestaLokacij) {
71
+ var _a, _b, _c;
72
+ const zBlagajne = veljavnoStroskovnoMesto(mestaBlagajn.get(String((_a = vrstica === null || vrstica === void 0 ? void 0 : vrstica.blagajna_id) !== null && _a !== void 0 ? _a : "")));
73
+ if (zBlagajne)
74
+ return zBlagajne;
75
+ const obiskane = new Set();
76
+ let id = String((_b = vrstica === null || vrstica === void 0 ? void 0 : vrstica.lokacija_id) !== null && _b !== void 0 ? _b : "");
77
+ while (id && !obiskane.has(id)) {
78
+ obiskane.add(id);
79
+ const lokacija = mestaLokacij.get(id);
80
+ if (!lokacija)
81
+ return "";
82
+ const mesto = veljavnoStroskovnoMesto(lokacija.mesto);
83
+ if (mesto)
84
+ return mesto;
85
+ id = String((_c = lokacija.nadrejena) !== null && _c !== void 0 ? _c : "");
86
+ }
87
+ return "";
88
+ }
89
+ //# sourceMappingURL=stroskovnoMesto.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"stroskovnoMesto.mjs","sourceRoot":"","sources":["../../src/racunovodstvo/stroskovnoMesto.mts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=izvozRacunov.d.mts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"izvozRacunov.d.mts","sourceRoot":"","sources":["../../src/test/izvozRacunov.mts"],"names":[],"mappings":""}
@@ -0,0 +1,258 @@
1
+ // AI created: 2026-10-05 (izvoz izdanih računov: preslikava, oznake, serializerja)
2
+ import { expect } from "chai";
3
+ import { Mongo } from "cry-db";
4
+ import { MongoMemoryServer } from "mongodb-memory-server";
5
+ import { izvoziRacune, izracunajVsote, sestaviPaket, izvozeniRacuni } from "../izvozRacunov/izvoziRacune.mjs";
6
+ import { serializirajJson } from "../izvozRacunov/serializirajJson.mjs";
7
+ import { serializirajXml } from "../izvozRacunov/serializirajXml.mjs";
8
+ // ---------------------------------------------------------------------------
9
+ // Ponarejena baza: izvoz potrebuje samo `find`, zato testi ne rabijo Mongo-ta
10
+ // ---------------------------------------------------------------------------
11
+ function ponarejenaBaza(zbirke) {
12
+ return {
13
+ async find(zbirka, _query) {
14
+ var _a;
15
+ return ((_a = zbirke[zbirka]) !== null && _a !== void 0 ? _a : []);
16
+ },
17
+ };
18
+ }
19
+ /** Minimalni zapis `Racun` z vsemi obveznimi polji. */
20
+ function racun(deli) {
21
+ return {
22
+ tenant: "test",
23
+ zapSt: 1,
24
+ odprt: new Date("2026-10-01T08:00:00.000Z"),
25
+ lokacija_id: "L1",
26
+ blagajna_id: "B1",
27
+ skladisce_id: "K1",
28
+ poslovalnica_id: "P1",
29
+ naprava_id: "N1",
30
+ stRacuna: 7,
31
+ datum: new Date("2026-10-01T09:00:00.000Z"),
32
+ datumIzdaje: new Date("2026-10-01T09:00:00.000Z"),
33
+ datumStoritve: new Date("2026-10-01T09:00:00.000Z"),
34
+ izdajNaDan: new Date("2026-10-01T09:00:00.000Z"),
35
+ izdal: "ana",
36
+ izdalDs: 3,
37
+ stKopij: 0,
38
+ postavke: [],
39
+ placila: [],
40
+ davki: [],
41
+ odprl: "ana",
42
+ mpc: 0,
43
+ prc: 0,
44
+ dav: 0,
45
+ pop: 0,
46
+ nbc: 0,
47
+ leto: 2026,
48
+ mesec: 10,
49
+ kvartal: 4,
50
+ dan: 1,
51
+ ura: 9,
52
+ danTedna: 4,
53
+ teden: 40,
54
+ stevilka: "TEST-2026-7",
55
+ krajIzdaje: "Test",
56
+ staraStevilka: "",
57
+ idIzdanegaRacuna: "",
58
+ izdajatelj: { naziv: "Vet", firma: "Vet d.o.o.", naslov: "Ulica 1", idDdv: "SI1", davcnaStevilka: "1" },
59
+ semaforPotrditve: "success",
60
+ statusIzdaje: "err",
61
+ zdruzenVOdprtega: "",
62
+ ...deli,
63
+ };
64
+ }
65
+ function postavka(deli) {
66
+ return {
67
+ opis: "Pregled",
68
+ artikel_id: "A1",
69
+ kategorija: "storitev",
70
+ kolicina: 2,
71
+ enota: "kos",
72
+ dodal: "ana",
73
+ dst: 0.22,
74
+ pop: 0,
75
+ mpc0: 12.2,
76
+ nbc: 5,
77
+ mpc: 12.2,
78
+ prc0: 10,
79
+ prc: 10,
80
+ _entered: new Date("2026-10-01T09:00:00.000Z"),
81
+ virPostavke: "račun",
82
+ ...deli,
83
+ };
84
+ }
85
+ const ZBIRKE = {
86
+ artikli: [
87
+ { _id: "A1", naziv: "Pregled", _externalId: "9001", _erpVatCode: "2B" },
88
+ { _id: "A2", naziv: "Brez šifre" },
89
+ ],
90
+ stranke: [{ _id: "S1", firma: "Stranka d.o.o.", _externalId: "100", _exportId: "S0001" }],
91
+ enote: [{ _id: "E1", enota: "kos", pomen: "Kos", _externalId: "KOS" }],
92
+ naciniPlacil: [{ _id: "NP1", nacin: "gotovina", kategorija: "gotovina", _externalId: "GOT" }],
93
+ blagajne: [{ _id: "B1", nazivZaIzpis: "Blagajna 1", _externalId: "BL1", stroskovnoMesto: "100" }],
94
+ lokacije: [{ _id: "L1", naziv: "Ambulanta", _externalId: "LOC1" }],
95
+ poslovalnice: [{ _id: "P1", naziv: "PE Test", _externalId: "PE1" }],
96
+ skladisca: [{ _id: "K1", naziv: "Glavno", _externalId: "SK1" }],
97
+ zavarovalnice: [],
98
+ konti: [
99
+ { _id: "KO1", kljuc: "terjatev", naziv: "terjatev do stranke", tip: "konto", konto: "1200", vrstniRed: 1 },
100
+ { _id: "KO2", kljuc: "prihodek", naziv: "splošni", tip: "konto", konto: "7600", vrstniRed: 2 },
101
+ { _id: "KO3", kljuc: "ddv", naziv: "splošni", tip: "konto", konto: "2600", vrstniRed: 3 },
102
+ ],
103
+ };
104
+ const META = {
105
+ izdajatelj: {
106
+ naziv: "Vet",
107
+ firma: "Vet d.o.o.",
108
+ naslov: "Ulica 1",
109
+ idDdv: "SI1",
110
+ davcnaStevilka: "1",
111
+ },
112
+ obdobjeOd: new Date("2026-10-01T00:00:00.000Z"),
113
+ obdobjeDo: new Date("2026-10-31T23:59:59.000Z"),
114
+ };
115
+ async function izvozi(racuni) {
116
+ return izvoziRacune(racuni, { db: ponarejenaBaza(ZBIRKE), ...META });
117
+ }
118
+ // ---------------------------------------------------------------------------
119
+ describe("izvoz izdanih računov", () => {
120
+ it("razreši konta, uparitve in stroškovno mesto", async () => {
121
+ var _a, _b;
122
+ const rezultat = await izvozi([
123
+ racun({
124
+ _id: "R1",
125
+ stranka: { _id: "S1", firma: "Stranka d.o.o." },
126
+ postavke: [postavka({})],
127
+ placila: [{ nacin: "gotovina", kategorija: "gotovina", vsota: 24.4 }],
128
+ }),
129
+ ]);
130
+ expect(rezultat.statusi.size).to.equal(0);
131
+ const r = rezultat.racuni[0];
132
+ expect(r.stevilka).to.equal("TEST-2026-7");
133
+ expect((_a = r.stranka) === null || _a === void 0 ? void 0 : _a.erpId).to.equal("100");
134
+ expect((_b = r.stranka) === null || _b === void 0 ? void 0 : _b.virId).to.equal("S0001");
135
+ expect(r.kontoTerjatve).to.equal("1200");
136
+ expect(r.stroskovnoMesto).to.equal("100", "blagajna prevlada in da stroškovno mesto");
137
+ const p = r.postavke[0];
138
+ expect(p.artikel.erpId).to.equal("9001");
139
+ expect(p.erpDavcnaKoda).to.equal("2B");
140
+ expect(p.enota.erpId).to.equal("KOS");
141
+ expect(p.kontoPrihodka).to.equal("7600");
142
+ expect(p.kontoDdv).to.equal("2600");
143
+ expect(p.popustOdstotek).to.equal(0);
144
+ expect(r.placila[0].konto).to.equal("1000", "gotovina gre na konto blagajne iz privzetkov");
145
+ expect(r.placila[0].erpId).to.equal("GOT");
146
+ // Model ne nosi izvedenih vrednosti — vsote izračuna prejemnik.
147
+ expect(izracunajVsote(r.postavke)).to.deep.equal({ neto: 20, davek: 4.4, bruto: 24.4 });
148
+ });
149
+ it("označi manjkajoče uparitve in ju po toleranci zavrne", async () => {
150
+ var _a, _b;
151
+ var _c;
152
+ const rezultat = await izvozi([
153
+ racun({
154
+ _id: "R2",
155
+ postavke: [postavka({ artikel_id: "A2", opis: "Brez šifre" })],
156
+ placila: [{ nacin: "gotovina", kategorija: "gotovina", vsota: 24.4 }],
157
+ }),
158
+ ]);
159
+ const status = rezultat.statusi.get("R2");
160
+ expect(status, "status računa z manjkajočimi uparitvami").to.exist;
161
+ const vrste = ((_c = status === null || status === void 0 ? void 0 : status.opozorila) !== null && _c !== void 0 ? _c : []).map((o) => o.vrsta);
162
+ expect(vrste).to.include("manjkaErpIdArtikla");
163
+ expect(vrste).to.include("manjkaErpDavcnaKodaArtikla");
164
+ const artikelOznaka = status === null || status === void 0 ? void 0 : status.opozorila.find((o) => o.vrsta === "manjkaErpIdArtikla");
165
+ expect((_b = (_a = artikelOznaka === null || artikelOznaka === void 0 ? void 0 : artikelOznaka.zapisi) === null || _a === void 0 ? void 0 : _a[0]) === null || _b === void 0 ? void 0 : _b.naziv).to.equal("Brez šifre");
166
+ // Privzeta toleranca: artikel brez šifre je napaka.
167
+ expect(izvozeniRacuni(rezultat)).to.have.length(0);
168
+ // Z ohlapno toleranco gre račun skozi.
169
+ expect(izvozeniRacuni(rezultat, { manjkaErpIdArtikla: "opozorilo", manjkaErpDavcnaKodaArtikla: "opozorilo" })).to.have.length(1);
170
+ });
171
+ it("označi račun brez postavk in neusklajena plačila", async () => {
172
+ var _a, _b;
173
+ var _c, _d;
174
+ const rezultat = await izvozi([
175
+ racun({ _id: "R3", postavke: [], placila: [] }),
176
+ racun({
177
+ _id: "R4",
178
+ postavke: [postavka({})],
179
+ placila: [{ nacin: "gotovina", kategorija: "gotovina", vsota: 10 }],
180
+ }),
181
+ ]);
182
+ const vrsteR3 = (_c = (_a = rezultat.statusi.get("R3")) === null || _a === void 0 ? void 0 : _a.opozorila.map((o) => o.vrsta)) !== null && _c !== void 0 ? _c : [];
183
+ expect(vrsteR3).to.include("racunBrezPostavk");
184
+ const vrsteR4 = (_d = (_b = rezultat.statusi.get("R4")) === null || _b === void 0 ? void 0 : _b.opozorila.map((o) => o.vrsta)) !== null && _d !== void 0 ? _d : [];
185
+ expect(vrsteR4).to.include("vsotaPlacilSeNeUjema");
186
+ });
187
+ it("zapiše paket v JSON in XML z istimi imeni polj", async () => {
188
+ const rezultat = await izvozi([
189
+ racun({
190
+ _id: "R1",
191
+ stranka: { _id: "S1", firma: "Stranka d.o.o." },
192
+ postavke: [postavka({ opis: "Pregled & <test>" })],
193
+ placila: [{ nacin: "gotovina", kategorija: "gotovina", vsota: 24.4 }],
194
+ }),
195
+ ]);
196
+ const paket = sestaviPaket(rezultat, META);
197
+ const json = JSON.parse(serializirajJson(paket));
198
+ expect(json.verzija).to.equal("1.0");
199
+ expect(json.oznakaValute).to.equal("EUR");
200
+ expect(json.racuni[0].postavke[0].kontoPrihodka).to.equal("7600");
201
+ const xml = serializirajXml(paket);
202
+ expect(xml.startsWith('<?xml version="1.0" encoding="UTF-8"?><izvozRacunov>')).to.equal(true);
203
+ expect(xml).to.contain("<verzija>1.0</verzija>");
204
+ expect(xml).to.contain("<oznakaValute>EUR</oznakaValute>");
205
+ expect(xml).to.contain("<postavke><postavka>");
206
+ expect(xml).to.contain("<kontoPrihodka>7600</kontoPrihodka>");
207
+ expect(xml).to.contain("Pregled &amp; &lt;test&gt;", "vsebina mora biti ubežana");
208
+ expect(xml).not.to.contain("<>", "vmesnih vozlišč brez imena ne sme biti");
209
+ expect(xml).not.to.contain("undefined");
210
+ });
211
+ });
212
+ // ---------------------------------------------------------------------------
213
+ // Integracijski test: `Mongo` iz `cry-db` mora ustrezati vmesniku `IzvozDb`
214
+ // ---------------------------------------------------------------------------
215
+ describe("izvoz izdanih računov (Mongo)", () => {
216
+ const tenant = "izvoz-racunov-test";
217
+ let mongoServer;
218
+ let mongo;
219
+ let prejsnjiUrl;
220
+ before(async function () {
221
+ mongoServer = await MongoMemoryServer.create();
222
+ prejsnjiUrl = process.env.MONGO_URL;
223
+ process.env.MONGO_URL = mongoServer.getUri();
224
+ mongo = new Mongo(tenant);
225
+ for (const [zbirka, zapisi] of Object.entries(ZBIRKE)) {
226
+ if (zapisi.length)
227
+ await mongo.insertMany(zbirka, zapisi);
228
+ }
229
+ await mongo.insertMany("racuni", [
230
+ racun({
231
+ _id: "RM1",
232
+ stranka: { _id: "S1", firma: "Stranka d.o.o." },
233
+ postavke: [postavka({})],
234
+ placila: [{ nacin: "gotovina", kategorija: "gotovina", vsota: 24.4 }],
235
+ }),
236
+ ]);
237
+ });
238
+ after(async function () {
239
+ await (mongo === null || mongo === void 0 ? void 0 : mongo.close());
240
+ await (mongoServer === null || mongoServer === void 0 ? void 0 : mongoServer.stop());
241
+ if (prejsnjiUrl === undefined)
242
+ delete process.env.MONGO_URL;
243
+ else
244
+ process.env.MONGO_URL = prejsnjiUrl;
245
+ });
246
+ it("prebere šifrante iz Mongo-ta in izvozi račun", async function () {
247
+ var _a;
248
+ const db = mongo;
249
+ const racuni = await mongo.find("racuni", {});
250
+ const rezultat = await izvoziRacune(racuni, { db, ...META });
251
+ expect(rezultat.racuni).to.have.length(1);
252
+ const r = rezultat.racuni[0];
253
+ expect((_a = r.stranka) === null || _a === void 0 ? void 0 : _a.erpId).to.equal("100");
254
+ expect(r.postavke[0].artikel.erpId).to.equal("9001");
255
+ expect(r.stroskovnoMesto).to.equal("100");
256
+ });
257
+ });
258
+ //# sourceMappingURL=izvozRacunov.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"izvozRacunov.mjs","sourceRoot":"","sources":["../../src/test/izvozRacunov.mts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export {};
2
+ //# sourceMappingURL=izvozRacunovShema.d.mts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"izvozRacunovShema.d.mts","sourceRoot":"","sources":["../../src/test/izvozRacunovShema.mts"],"names":[],"mappings":""}
@@ -0,0 +1,267 @@
1
+ // AI created: 2026-10-05 (shemi izvoza izdanih računov: JSON Schema + XSD, validacija izhoda)
2
+ import { expect } from "chai";
3
+ import { readFileSync, writeFileSync, mkdtempSync } from "node:fs";
4
+ import { spawnSync } from "node:child_process";
5
+ import { tmpdir } from "node:os";
6
+ import { join } from "node:path";
7
+ import Ajv2020 from "ajv/dist/2020.js";
8
+ import addFormats from "ajv-formats";
9
+ import { serializirajJson } from "../izvozRacunov/serializirajJson.mjs";
10
+ import { serializirajXml } from "../izvozRacunov/serializirajXml.mjs";
11
+ import { generirajIzvozneDatoteke, imeIzvozneDatoteke, SHEMA_JSON, SHEMA_XSD } from "../izvozRacunov/generirajIzvoz.mjs";
12
+ const POT_SHEME_JSON = "src/izvozRacunov/schemas/izvozRacunov.schema.json";
13
+ const POT_SHEME_XSD = "src/izvozRacunov/schemas/izvozRacunov.xsd";
14
+ /**
15
+ * Paket z **vsemi** polji modela.
16
+ *
17
+ * Ker sta obe shemi zaprti (`additionalProperties: false` v JSON shemi oz.
18
+ * `xs:sequence` brez `xs:any` v XSD), ta primer dokaže, da shemi pokrivata
19
+ * natanko tista polja, ki jih model pozna; vsako polje, ki bi ga pozabili
20
+ * dodati, bi validacijo podrlo.
21
+ */
22
+ const PAKET = {
23
+ verzija: "1.0",
24
+ izdajatelj: {
25
+ naziv: "Vet",
26
+ firma: "Vet d.o.o.",
27
+ naslov: "Ulica 1, 1000 Ljubljana",
28
+ idDdv: "SI12345678",
29
+ davcnaStevilka: "12345678",
30
+ },
31
+ obdobjeOd: new Date("2026-10-01T00:00:00.000Z"),
32
+ obdobjeDo: new Date("2026-10-31T23:59:59.000Z"),
33
+ oznakaValute: "EUR",
34
+ racuni: [
35
+ {
36
+ racunId: "R1",
37
+ virId: "R00001",
38
+ stevilka: "SEZ-2026-1",
39
+ zaporednaStevilka: 1,
40
+ zapSt: 42,
41
+ datumIzdaje: new Date("2026-10-01T09:00:00.000Z"),
42
+ datumStoritve: new Date("2026-10-01T08:00:00.000Z"),
43
+ datumZapadlosti: new Date("2026-10-15T00:00:00.000Z"),
44
+ datumOdprtja: new Date("2026-10-01T08:30:00.000Z"),
45
+ dodan: new Date("2026-10-01T08:31:00.000Z"),
46
+ krajIzdaje: "Sežana",
47
+ namenRacuna: "ambulanta",
48
+ opomba: "opomba",
49
+ pripis: "pripis",
50
+ navodiloStranki: "navodilo",
51
+ sklic: "SI00 1234",
52
+ pogodba: "P-1",
53
+ narocilnica: "N-1",
54
+ zbirnik: true,
55
+ strniZbirnik: true,
56
+ imeZbirnika: "Zbirnik 1",
57
+ zdruzenIzOdprtih: ["R0"],
58
+ izdajatelj: {
59
+ naziv: "Vet",
60
+ firma: "Vet d.o.o.",
61
+ naslov: "Ulica 1",
62
+ idDdv: "SI12345678",
63
+ davcnaStevilka: "12345678",
64
+ },
65
+ izdal: "ana",
66
+ odprl: "ana",
67
+ izdalDelovnoMesto: 3,
68
+ veterinar: "ana",
69
+ imeIzdajatelja: "Ana",
70
+ imeVeterinarja: "Ana",
71
+ dezurstvo: true,
72
+ stranka: {
73
+ klikvetId: "S1",
74
+ erpId: "100",
75
+ virId: "S0001",
76
+ firma: "Stranka d.o.o.",
77
+ ime: "Janez",
78
+ priimek: "Novak",
79
+ spol: "m",
80
+ naslov: {
81
+ ulica: "Ulica 2",
82
+ hisnaStevilka: "12a",
83
+ postnaStevilka: "1000",
84
+ posta: "Ljubljana",
85
+ naselje: "Center",
86
+ obcina: "Ljubljana",
87
+ drzava: "SI",
88
+ },
89
+ davcniZavezanec: true,
90
+ idDdv: "SI87654321",
91
+ maticnaStevilka: "1234567",
92
+ emso: "0101990500011",
93
+ gsm: "041123456",
94
+ telefon: "051234567",
95
+ email: "a@b.si",
96
+ trr: "SI56000000000000000",
97
+ bic: "BAKOSI2X",
98
+ },
99
+ lastnik: { klikvetId: "S2", erpId: "101" },
100
+ zaStranko: { klikvetId: "S3", erpId: "102" },
101
+ kontoTerjatve: "1200",
102
+ stroskovnoMesto: "100",
103
+ lokacija: { klikvetId: "L1", erpId: "LOC1", virId: "L0001", naziv: "Ambulanta" },
104
+ blagajna: { klikvetId: "B1", erpId: "BL1", virId: "B0001", naziv: "Blagajna 1" },
105
+ poslovalnica: { klikvetId: "P1", erpId: "PE1", virId: "P0001", naziv: "PE Test" },
106
+ skladisce: { klikvetId: "K1", erpId: "SK1", virId: "K0001", naziv: "Glavno" },
107
+ obravnavaId: "O1",
108
+ obiskId: "V1",
109
+ pacientId: "PZ1",
110
+ pacientIme: "Biki",
111
+ pacientCip: "705000123456789",
112
+ namenObravnave: "cepljenje",
113
+ diagnoza: "D1",
114
+ zival: "govedo",
115
+ vrstaRejneZivali: "krave",
116
+ gmid: "GMID1",
117
+ imaPmzPostavke: true,
118
+ IPV: true,
119
+ negotovinski: true,
120
+ zoi: "ZOI1",
121
+ eor: "EOR1",
122
+ davcnoPotrjeno: new Date("2026-10-01T09:00:05.000Z"),
123
+ neFiskaliziraj: "vsota 0",
124
+ predhodniRacun: { klikvetId: "R0", stevilka: "SEZ-2026-0", datum: new Date("2026-09-30T09:00:00.000Z") },
125
+ naslednjiRacun: {
126
+ klikvetId: "R2",
127
+ stevilka: "SEZ-2026-2",
128
+ datum: new Date("2026-10-02T09:00:00.000Z"),
129
+ izdal: "ana",
130
+ },
131
+ idIzdanegaRacuna: "SEZ-2026-0",
132
+ prestevilcen: new Date("2026-10-03T09:00:00.000Z"),
133
+ staraStevilka: "ST-1",
134
+ postavke: [
135
+ {
136
+ postavkaId: "PO1",
137
+ opis: "Pregled",
138
+ opisDodatni: "dodatni opis",
139
+ artikel: { klikvetId: "A1", erpId: "9001", virId: "A0001", naziv: "Pregled" },
140
+ kategorija: "storitev",
141
+ kolicina: 2,
142
+ enota: { klikvetId: "E1", erpId: "KOS", naziv: "kos" },
143
+ stopnjaDdv: 0.22,
144
+ erpDavcnaKoda: "2B",
145
+ popustOdstotek: 10,
146
+ netoProdajnaCenaBrezPopusta: 10,
147
+ netoProdajnaCena: 9,
148
+ brutoProdajnaCenaBrezPopusta: 12.2,
149
+ brutoProdajnaCena: 10.98,
150
+ nabavnaCenaBrezDavka: 5,
151
+ kontoPrihodka: "7600",
152
+ kontoDdv: "2600",
153
+ kodaPopusta: "K1",
154
+ zaStrankoId: "S3",
155
+ zaStrankoErpId: "102",
156
+ nazivZaStranko: "Plačnik d.o.o.",
157
+ pacientId: "PZ1",
158
+ pacientIme: "Biki",
159
+ pacientCip: "705000123456789",
160
+ lastnikId: "S1",
161
+ lastnikErpId: "100",
162
+ obravnavaId: "O1",
163
+ obiskId: "V1",
164
+ korakObravnaveId: "K1",
165
+ namenObravnave: "cepljenje",
166
+ diagnoza: "D1",
167
+ terenNamen: "kontrola",
168
+ veterinar: "ana",
169
+ poljeObravnave: "terapija",
170
+ virPostavke: "obravnava",
171
+ izPredracunaId: "PR1",
172
+ izDobavniceId: "DO1",
173
+ poDokumentu: "DO1",
174
+ dodal: "ana",
175
+ zaracunal: "ana",
176
+ vneseno: new Date("2026-10-01T08:45:00.000Z"),
177
+ zavarovanje: { naziv: "SAVA", erpId: "Z1", polica: "P-123", kritje: 0.8, soudelezba: 0.2 },
178
+ prikrijIme: true,
179
+ recept: true,
180
+ IPV: true,
181
+ stevilkaZdravila: "2*abc-03/26",
182
+ vtipkaneStevilkeZdravila: "abc-03/26",
183
+ pmzKodaZdravila: 12345,
184
+ pmzZa: "govedo",
185
+ karencaOd: new Date("2026-10-01T09:00:00.000Z"),
186
+ karencaZa: "mleko",
187
+ karence: { pot: "IM", vrsta: "Antibiotik", karence: { mleko: 3, meso: 7 } },
188
+ navodilo: "3 dni",
189
+ stevilkaZivali: "SI-1",
190
+ zaZivali: ["SI-1", "SI-2"],
191
+ rejna: true,
192
+ neRazknjiziObIzdajiRacuna: true,
193
+ razknjiziZalogoId: "A2",
194
+ vrstaRazknjizbe: "ob prodaji",
195
+ faktorRazknjizbe: 1.5,
196
+ naKg: true,
197
+ pribitekDezurstvaOdstotek: 20,
198
+ gmid: "GMID1",
199
+ },
200
+ ],
201
+ placila: [
202
+ { kategorija: "kartica", nacin: "kartica", klikvetId: "NP2", erpId: "KAR", virId: "N0002", konto: "1001", znesek: 21.96 },
203
+ ],
204
+ },
205
+ ],
206
+ };
207
+ function preberiTs() {
208
+ return readFileSync(POT_SHEME_JSON, "utf8");
209
+ }
210
+ describe("shemi izvoza izdanih računov", () => {
211
+ it("JSON izhod ustreza JSON shemi (vsa polja modela)", () => {
212
+ const ajv = new Ajv2020({ allErrors: true, strict: true });
213
+ addFormats(ajv);
214
+ const validiraj = ajv.compile(JSON.parse(preberiTs()));
215
+ const velja = validiraj(JSON.parse(serializirajJson(PAKET)));
216
+ expect(velja, JSON.stringify(validiraj.errors, null, 2)).to.equal(true);
217
+ });
218
+ it("XML izhod ustreza XSD (xmllint)", function () {
219
+ var _a;
220
+ const xmllint = spawnSync("xmllint", ["--version"]);
221
+ if (xmllint.error || xmllint.status !== 0)
222
+ this.skip();
223
+ const mapa = mkdtempSync(join(tmpdir(), "izvoz-racunov-"));
224
+ const pot = join(mapa, "izvoz.xml");
225
+ writeFileSync(pot, serializirajXml(PAKET), "utf8");
226
+ const rezultat = spawnSync("xmllint", ["--noout", "--schema", POT_SHEME_XSD, pot], { encoding: "utf8" });
227
+ expect(rezultat.status, (_a = rezultat.stderr) !== null && _a !== void 0 ? _a : "").to.equal(0);
228
+ });
229
+ it("JSON shema in XSD pokrivata ista imena polj", () => {
230
+ const shema = JSON.parse(preberiTs());
231
+ const xsd = readFileSync(POT_SHEME_XSD, "utf8");
232
+ const imenaJson = new Set();
233
+ const pobiraj = (vozlisce) => {
234
+ if (!vozlisce || typeof vozlisce !== "object")
235
+ return;
236
+ for (const [kljuc, vrednost] of Object.entries(vozlisce)) {
237
+ if (kljuc === "properties" && vrednost && typeof vrednost === "object") {
238
+ for (const ime of Object.keys(vrednost))
239
+ imenaJson.add(ime);
240
+ }
241
+ pobiraj(vrednost);
242
+ }
243
+ };
244
+ pobiraj(shema);
245
+ const imenaXsd = new Set();
246
+ for (const ujemanje of xsd.matchAll(/<xs:element name="([^"]+)"/g))
247
+ imenaXsd.add(ujemanje[1]);
248
+ // XSD pozna še koren in imena posameznih elementov seznamov, ki v JSON-u niso polja.
249
+ // `zival` je obenem polje na računu (vrsta živali) in element seznama `zaZivali`,
250
+ // zato je med polji in ne med izjemami.
251
+ const samoVXsd = [...imenaXsd].filter((i) => !imenaJson.has(i)).sort();
252
+ expect(samoVXsd).to.deep.equal(["izvozRacunov", "placilo", "postavka", "racun"]);
253
+ const samoVJson = [...imenaJson].filter((i) => !imenaXsd.has(i)).sort();
254
+ expect(samoVJson, "polja JSON sheme, ki jih XSD ne pozna").to.deep.equal([]);
255
+ });
256
+ it("generator sestavi obe datoteki z imeni shem", () => {
257
+ const datoteke = generirajIzvozneDatoteke(PAKET);
258
+ expect(datoteke.map((d) => d.format)).to.deep.equal(["json", "xml"]);
259
+ expect(datoteke.map((d) => d.shema)).to.deep.equal([SHEMA_JSON, SHEMA_XSD]);
260
+ expect(datoteke[0].ime).to.equal("izvoz-racunov_20261001-20261031.json");
261
+ expect(datoteke[1].ime).to.equal(imeIzvozneDatoteke(PAKET, "xml"));
262
+ expect(datoteke[1].vsebina.startsWith("<?xml")).to.equal(true);
263
+ expect(datoteke[1].mime).to.equal("application/xml");
264
+ expect(() => JSON.parse(datoteke[0].vsebina)).not.to.throw();
265
+ });
266
+ });
267
+ //# sourceMappingURL=izvozRacunovShema.mjs.map