@fin.cx/skr 1.3.0 → 2.0.0
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.
- package/.smartconfig.json +33 -6
- package/dist_ts/00_commitinfo_data.js +1 -1
- package/dist_ts/core/core.accountpolicy.d.ts +67 -0
- package/dist_ts/core/core.accountpolicy.js +91 -0
- package/dist_ts/core/core.bukeys.d.ts +38 -0
- package/dist_ts/core/core.bukeys.js +117 -0
- package/dist_ts/core/core.datev.captions.d.ts +7 -0
- package/dist_ts/core/core.datev.captions.js +134 -0
- package/dist_ts/core/core.datev.d.ts +47 -0
- package/dist_ts/core/core.datev.js +129 -0
- package/dist_ts/core/core.hash.d.ts +27 -0
- package/dist_ts/core/core.hash.js +72 -0
- package/dist_ts/core/core.plugins.d.ts +3 -0
- package/dist_ts/core/core.plugins.js +9 -0
- package/dist_ts/core/core.recipes.d.ts +118 -0
- package/dist_ts/core/core.recipes.js +504 -0
- package/dist_ts/core/core.taxscenario.d.ts +27 -0
- package/dist_ts/core/core.taxscenario.js +85 -0
- package/dist_ts/core/core.types.d.ts +48 -0
- package/dist_ts/core/core.types.js +2 -0
- package/dist_ts/core/core.validate.d.ts +17 -0
- package/dist_ts/core/core.validate.js +89 -0
- package/dist_ts/core/index.d.ts +15 -0
- package/dist_ts/core/index.js +16 -0
- package/dist_ts/index.d.ts +15 -0
- package/dist_ts/index.js +10 -1
- package/dist_ts/plugins.d.ts +2 -1
- package/dist_ts/plugins.js +4 -2
- package/dist_ts/skr.api.d.ts +91 -22
- package/dist_ts/skr.api.js +357 -42
- package/dist_ts/skr.balances.d.ts +28 -0
- package/dist_ts/skr.balances.js +96 -0
- package/dist_ts/skr.classes.journalentry.d.ts +19 -3
- package/dist_ts/skr.classes.journalentry.js +67 -4
- package/dist_ts/skr.classes.reports.js +49 -102
- package/dist_ts/skr.database.d.ts +2 -0
- package/dist_ts/skr.database.js +1 -1
- package/dist_ts/skr.errors.d.ts +18 -0
- package/dist_ts/skr.errors.js +34 -0
- package/dist_ts/skr.export.js +4 -7
- package/dist_ts/skr.invoice.adapter.d.ts +15 -1
- package/dist_ts/skr.invoice.adapter.js +253 -41
- package/dist_ts/skr.invoice.booking.js +14 -28
- package/dist_ts/skr.migrate.d.ts +20 -0
- package/dist_ts/skr.migrate.js +223 -0
- package/dist_ts/skr.period.d.ts +47 -0
- package/dist_ts/skr.period.js +95 -0
- package/dist_ts/skr.posting.d.ts +74 -0
- package/dist_ts/skr.posting.js +209 -0
- package/dist_ts/skr.security.d.ts +6 -9
- package/dist_ts/skr.security.js +16 -89
- package/dist_ts/skr.sequence.d.ts +32 -0
- package/dist_ts/skr.sequence.js +51 -0
- package/dist_ts/skr.txview.d.ts +46 -0
- package/dist_ts/skr.txview.js +235 -0
- package/dist_ts/skr.types.d.ts +35 -1
- package/dist_ts/skr.verify.d.ts +13 -0
- package/dist_ts/skr.verify.js +84 -0
- package/package.json +21 -24
- package/readme.hints.md +37 -0
- package/readme.md +94 -1
- package/readme.plan.md +180 -243
- package/ts/00_commitinfo_data.ts +1 -1
- package/ts/core/core.accountpolicy.ts +154 -0
- package/ts/core/core.bukeys.ts +146 -0
- package/ts/core/core.datev.captions.ts +133 -0
- package/ts/core/core.datev.ts +174 -0
- package/ts/core/core.hash.ts +76 -0
- package/ts/core/core.plugins.ts +9 -0
- package/ts/core/core.recipes.ts +659 -0
- package/ts/core/core.taxscenario.ts +156 -0
- package/ts/core/core.types.ts +74 -0
- package/ts/core/core.validate.ts +119 -0
- package/ts/core/index.ts +15 -0
- package/ts/index.ts +31 -0
- package/ts/plugins.ts +4 -0
- package/ts/skr.api.ts +432 -46
- package/ts/skr.balances.ts +127 -0
- package/ts/skr.classes.journalentry.ts +54 -5
- package/ts/skr.classes.reports.ts +54 -126
- package/ts/skr.database.ts +3 -0
- package/ts/skr.errors.ts +44 -0
- package/ts/skr.export.ts +3 -6
- package/ts/skr.invoice.adapter.ts +291 -45
- package/ts/skr.invoice.booking.ts +22 -34
- package/ts/skr.migrate.ts +268 -0
- package/ts/skr.period.ts +139 -0
- package/ts/skr.posting.ts +273 -0
- package/ts/skr.security.ts +18 -93
- package/ts/skr.sequence.ts +89 -0
- package/ts/skr.txview.ts +268 -0
- package/ts/skr.types.ts +37 -1
- package/ts/skr.verify.ts +99 -0
- /package/{license.md → license} +0 -0
|
@@ -0,0 +1,74 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* JournalPoster — the atomic v2 posting path.
|
|
3
|
+
*
|
|
4
|
+
* Flow per posting: pure pre-flight validation (stateless core) → one MongoDB
|
|
5
|
+
* transaction containing period-lock re-check, gapless sequence allocation,
|
|
6
|
+
* hash computation, entry save, and a compare-and-swap on the chain head.
|
|
7
|
+
* The driver's withTransaction() retries transient conflicts; an abort rolls
|
|
8
|
+
* the sequence $inc back, so numbering stays gapless.
|
|
9
|
+
*
|
|
10
|
+
* JournalEntry (schemaVersion 2) is the single source of truth — no
|
|
11
|
+
* Transaction-pair explosion. Balances are aggregations (skr.balances.ts).
|
|
12
|
+
*/
|
|
13
|
+
import * as core from './core/index.js';
|
|
14
|
+
import { JournalEntry } from './skr.classes.journalentry.js';
|
|
15
|
+
export interface IPostDraftOptions {
|
|
16
|
+
policy?: core.IAccountPolicy;
|
|
17
|
+
postedAt?: Date;
|
|
18
|
+
createdBy?: string;
|
|
19
|
+
}
|
|
20
|
+
/**
|
|
21
|
+
* The exact structure whose canonical form is hashed into the chain.
|
|
22
|
+
* Built identically by the poster (from the draft) and the verifier (from the
|
|
23
|
+
* persisted document) — every optional is normalized so both sides match.
|
|
24
|
+
*/
|
|
25
|
+
export declare function buildHashPayload(entry: {
|
|
26
|
+
sequenceNumber: number;
|
|
27
|
+
skrType: string;
|
|
28
|
+
fiscalYear: number;
|
|
29
|
+
date: Date;
|
|
30
|
+
postedAt: Date;
|
|
31
|
+
description: string;
|
|
32
|
+
reference?: string | null;
|
|
33
|
+
taxScenario?: string | null;
|
|
34
|
+
currency?: string | null;
|
|
35
|
+
reversalOf?: string | null;
|
|
36
|
+
lines: Array<{
|
|
37
|
+
accountNumber: string;
|
|
38
|
+
counterAccount?: string | null;
|
|
39
|
+
side?: string | null;
|
|
40
|
+
amountCents?: number | null;
|
|
41
|
+
buKey?: string | null;
|
|
42
|
+
buchungstext?: string | null;
|
|
43
|
+
belegfeld1?: string | null;
|
|
44
|
+
costCenter1?: string | null;
|
|
45
|
+
docLink?: string | null;
|
|
46
|
+
vatAmountCents?: number | null;
|
|
47
|
+
}>;
|
|
48
|
+
}): Record<string, unknown>;
|
|
49
|
+
export declare class JournalPoster {
|
|
50
|
+
/**
|
|
51
|
+
* Create the indexes the v2 posting path relies on. Idempotent.
|
|
52
|
+
*/
|
|
53
|
+
ensureIndexes(): Promise<void>;
|
|
54
|
+
/**
|
|
55
|
+
* Probe transaction support with a no-op transaction. Fails hard —
|
|
56
|
+
* filing-grade posting has no non-transactional fallback.
|
|
57
|
+
*/
|
|
58
|
+
assertTransactionSupport(): Promise<void>;
|
|
59
|
+
/**
|
|
60
|
+
* Validate and atomically post a journal draft. Returns the persisted,
|
|
61
|
+
* hashed, immutable JournalEntry.
|
|
62
|
+
*/
|
|
63
|
+
postDraft(draft: core.IJournalDraft, options?: IPostDraftOptions): Promise<JournalEntry>;
|
|
64
|
+
/**
|
|
65
|
+
* Storno: post a reversal entry for a hashed entry WITHOUT mutating the
|
|
66
|
+
* original (GoBD). The reversal references the original via belegfeld1 and
|
|
67
|
+
* reference; reversal state is derived by querying, never stored on the
|
|
68
|
+
* original.
|
|
69
|
+
*/
|
|
70
|
+
postStorno(original: JournalEntry, options?: IPostDraftOptions & {
|
|
71
|
+
date?: Date;
|
|
72
|
+
description?: string;
|
|
73
|
+
}): Promise<JournalEntry>;
|
|
74
|
+
}
|
|
@@ -0,0 +1,209 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* JournalPoster — the atomic v2 posting path.
|
|
3
|
+
*
|
|
4
|
+
* Flow per posting: pure pre-flight validation (stateless core) → one MongoDB
|
|
5
|
+
* transaction containing period-lock re-check, gapless sequence allocation,
|
|
6
|
+
* hash computation, entry save, and a compare-and-swap on the chain head.
|
|
7
|
+
* The driver's withTransaction() retries transient conflicts; an abort rolls
|
|
8
|
+
* the sequence $inc back, so numbering stays gapless.
|
|
9
|
+
*
|
|
10
|
+
* JournalEntry (schemaVersion 2) is the single source of truth — no
|
|
11
|
+
* Transaction-pair explosion. Balances are aggregations (skr.balances.ts).
|
|
12
|
+
*/
|
|
13
|
+
import * as core from './core/index.js';
|
|
14
|
+
import { getDbSync } from './skr.database.js';
|
|
15
|
+
import { JournalEntry } from './skr.classes.journalentry.js';
|
|
16
|
+
import { allocateSequence, advanceHead, ensureSequenceIndexes } from './skr.sequence.js';
|
|
17
|
+
import { assertPeriodOpen, ensurePeriodIndexes, fiscalYearOf, periodOf, JOURNAL_ENTRY_COLLECTION, } from './skr.period.js';
|
|
18
|
+
import { PeriodLockedError, TransactionsUnsupportedError } from './skr.errors.js';
|
|
19
|
+
/**
|
|
20
|
+
* The exact structure whose canonical form is hashed into the chain.
|
|
21
|
+
* Built identically by the poster (from the draft) and the verifier (from the
|
|
22
|
+
* persisted document) — every optional is normalized so both sides match.
|
|
23
|
+
*/
|
|
24
|
+
export function buildHashPayload(entry) {
|
|
25
|
+
return {
|
|
26
|
+
sequenceNumber: entry.sequenceNumber,
|
|
27
|
+
skrType: entry.skrType,
|
|
28
|
+
fiscalYear: entry.fiscalYear,
|
|
29
|
+
date: entry.date,
|
|
30
|
+
postedAt: entry.postedAt,
|
|
31
|
+
description: entry.description ?? '',
|
|
32
|
+
reference: entry.reference ?? '',
|
|
33
|
+
taxScenario: entry.taxScenario ?? '',
|
|
34
|
+
currency: entry.currency ?? 'EUR',
|
|
35
|
+
reversalOf: entry.reversalOf ?? '',
|
|
36
|
+
lines: entry.lines.map((line) => ({
|
|
37
|
+
accountNumber: line.accountNumber,
|
|
38
|
+
counterAccount: line.counterAccount ?? '',
|
|
39
|
+
side: line.side ?? '',
|
|
40
|
+
amountCents: line.amountCents ?? 0,
|
|
41
|
+
buKey: line.buKey ?? '',
|
|
42
|
+
buchungstext: line.buchungstext ?? '',
|
|
43
|
+
belegfeld1: line.belegfeld1 ?? '',
|
|
44
|
+
costCenter1: line.costCenter1 ?? '',
|
|
45
|
+
docLink: line.docLink ?? '',
|
|
46
|
+
vatAmountCents: line.vatAmountCents ?? 0,
|
|
47
|
+
})),
|
|
48
|
+
};
|
|
49
|
+
}
|
|
50
|
+
export class JournalPoster {
|
|
51
|
+
/**
|
|
52
|
+
* Create the indexes the v2 posting path relies on. Idempotent.
|
|
53
|
+
*/
|
|
54
|
+
async ensureIndexes() {
|
|
55
|
+
await ensureSequenceIndexes();
|
|
56
|
+
await ensurePeriodIndexes();
|
|
57
|
+
await getDbSync()
|
|
58
|
+
.mongoDb.collection(JOURNAL_ENTRY_COLLECTION)
|
|
59
|
+
.createIndex({ skrType: 1, fiscalYear: 1, sequenceNumber: 1 }, {
|
|
60
|
+
unique: true,
|
|
61
|
+
// only chained entries — migration inserts docs before sequencing
|
|
62
|
+
partialFilterExpression: {
|
|
63
|
+
schemaVersion: 2,
|
|
64
|
+
sequenceNumber: { $exists: true },
|
|
65
|
+
},
|
|
66
|
+
});
|
|
67
|
+
}
|
|
68
|
+
/**
|
|
69
|
+
* Probe transaction support with a no-op transaction. Fails hard —
|
|
70
|
+
* filing-grade posting has no non-transactional fallback.
|
|
71
|
+
*/
|
|
72
|
+
async assertTransactionSupport() {
|
|
73
|
+
const db = getDbSync();
|
|
74
|
+
const session = db.startSession();
|
|
75
|
+
try {
|
|
76
|
+
await session.withTransaction(async () => {
|
|
77
|
+
await db.mongoDb
|
|
78
|
+
.collection(JOURNAL_ENTRY_COLLECTION)
|
|
79
|
+
.findOne({ _id: 'txn-probe' }, { session });
|
|
80
|
+
});
|
|
81
|
+
}
|
|
82
|
+
catch (error) {
|
|
83
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
84
|
+
throw new TransactionsUnsupportedError(message);
|
|
85
|
+
}
|
|
86
|
+
finally {
|
|
87
|
+
await session.endSession();
|
|
88
|
+
}
|
|
89
|
+
}
|
|
90
|
+
/**
|
|
91
|
+
* Validate and atomically post a journal draft. Returns the persisted,
|
|
92
|
+
* hashed, immutable JournalEntry.
|
|
93
|
+
*/
|
|
94
|
+
async postDraft(draft, options) {
|
|
95
|
+
const validation = core.validateJournalDraft(draft, options?.policy);
|
|
96
|
+
if (!validation.valid) {
|
|
97
|
+
throw new Error(`Journal draft invalid: ${validation.errors.join('; ')}`);
|
|
98
|
+
}
|
|
99
|
+
const normalized = validation.normalized;
|
|
100
|
+
const period = periodOf(normalized.date);
|
|
101
|
+
const fiscalYear = fiscalYearOf(normalized.date);
|
|
102
|
+
const postedAt = options?.postedAt ?? new Date();
|
|
103
|
+
const db = getDbSync();
|
|
104
|
+
const session = db.startSession();
|
|
105
|
+
try {
|
|
106
|
+
let posted = null;
|
|
107
|
+
await session.withTransaction(async () => {
|
|
108
|
+
await assertPeriodOpen(normalized.skrType, period, session);
|
|
109
|
+
const { sequenceNumber, prevHash } = await allocateSequence(normalized.skrType, fiscalYear, session);
|
|
110
|
+
const lines = normalized.lines.map((line) => ({
|
|
111
|
+
accountNumber: line.accountNumber,
|
|
112
|
+
// legacy float mirrors keep v1 reports readable during migration
|
|
113
|
+
debit: line.side === 'debit' ? line.amountCents / 100 : 0,
|
|
114
|
+
credit: line.side === 'credit' ? line.amountCents / 100 : 0,
|
|
115
|
+
description: line.buchungstext,
|
|
116
|
+
side: line.side,
|
|
117
|
+
amountCents: line.amountCents,
|
|
118
|
+
counterAccount: line.counterAccount,
|
|
119
|
+
buKey: line.buKey,
|
|
120
|
+
buchungstext: line.buchungstext,
|
|
121
|
+
belegfeld1: line.belegfeld1,
|
|
122
|
+
costCenter1: line.costCenter1,
|
|
123
|
+
docLink: line.docLink,
|
|
124
|
+
vatAmountCents: line.vatAmountCents,
|
|
125
|
+
}));
|
|
126
|
+
const entry = new JournalEntry({
|
|
127
|
+
date: normalized.date,
|
|
128
|
+
description: normalized.description,
|
|
129
|
+
reference: normalized.reference,
|
|
130
|
+
skrType: normalized.skrType,
|
|
131
|
+
lines,
|
|
132
|
+
});
|
|
133
|
+
entry.schemaVersion = 2;
|
|
134
|
+
entry.sequenceNumber = sequenceNumber;
|
|
135
|
+
entry.prevHash = prevHash;
|
|
136
|
+
entry.taxScenario = normalized.taxScenario;
|
|
137
|
+
entry.currency = normalized.currency;
|
|
138
|
+
entry.reversalOf = normalized.reversalOf;
|
|
139
|
+
entry.status = 'posted';
|
|
140
|
+
entry.postedAt = postedAt;
|
|
141
|
+
entry.finalizedAt = null;
|
|
142
|
+
entry.createdBy = options?.createdBy ?? 'system';
|
|
143
|
+
// period/fiscalYear are UTC-derived here; the constructor derives them
|
|
144
|
+
// from local time, so overwrite for determinism
|
|
145
|
+
entry.period = period;
|
|
146
|
+
entry.fiscalYear = fiscalYear;
|
|
147
|
+
entry.entryHash = core.entryHash(prevHash, buildHashPayload({
|
|
148
|
+
sequenceNumber,
|
|
149
|
+
skrType: normalized.skrType,
|
|
150
|
+
fiscalYear,
|
|
151
|
+
date: normalized.date,
|
|
152
|
+
postedAt,
|
|
153
|
+
description: normalized.description,
|
|
154
|
+
reference: normalized.reference,
|
|
155
|
+
taxScenario: normalized.taxScenario,
|
|
156
|
+
currency: normalized.currency,
|
|
157
|
+
reversalOf: normalized.reversalOf,
|
|
158
|
+
lines,
|
|
159
|
+
}));
|
|
160
|
+
await entry.save({ session });
|
|
161
|
+
await advanceHead(normalized.skrType, fiscalYear, prevHash, entry.entryHash, session);
|
|
162
|
+
posted = entry;
|
|
163
|
+
});
|
|
164
|
+
if (!posted) {
|
|
165
|
+
throw new Error('Posting transaction did not complete');
|
|
166
|
+
}
|
|
167
|
+
return posted;
|
|
168
|
+
}
|
|
169
|
+
catch (error) {
|
|
170
|
+
if (error instanceof PeriodLockedError)
|
|
171
|
+
throw error;
|
|
172
|
+
throw error;
|
|
173
|
+
}
|
|
174
|
+
finally {
|
|
175
|
+
await session.endSession();
|
|
176
|
+
}
|
|
177
|
+
}
|
|
178
|
+
/**
|
|
179
|
+
* Storno: post a reversal entry for a hashed entry WITHOUT mutating the
|
|
180
|
+
* original (GoBD). The reversal references the original via belegfeld1 and
|
|
181
|
+
* reference; reversal state is derived by querying, never stored on the
|
|
182
|
+
* original.
|
|
183
|
+
*/
|
|
184
|
+
async postStorno(original, options) {
|
|
185
|
+
if (original.schemaVersion !== 2 || !original.entryHash) {
|
|
186
|
+
throw new Error('postStorno only reverses schemaVersion-2 (hashed) entries');
|
|
187
|
+
}
|
|
188
|
+
const draft = {
|
|
189
|
+
date: options?.date ?? new Date(),
|
|
190
|
+
description: options?.description ?? `Storno ${original.journalNumber}: ${original.description}`,
|
|
191
|
+
reference: `STORNO-${original.journalNumber}`,
|
|
192
|
+
skrType: original.skrType,
|
|
193
|
+
reversalOf: original.id,
|
|
194
|
+
currency: original.currency ?? 'EUR',
|
|
195
|
+
taxScenario: original.taxScenario,
|
|
196
|
+
lines: original.lines.map((line) => ({
|
|
197
|
+
accountNumber: line.accountNumber,
|
|
198
|
+
counterAccount: line.counterAccount ?? '',
|
|
199
|
+
side: line.side === 'debit' ? 'credit' : 'debit',
|
|
200
|
+
amountCents: line.amountCents ?? 0,
|
|
201
|
+
buKey: (line.buKey ?? ''),
|
|
202
|
+
buchungstext: `Storno: ${line.buchungstext ?? ''}`,
|
|
203
|
+
belegfeld1: original.journalNumber,
|
|
204
|
+
})),
|
|
205
|
+
};
|
|
206
|
+
return this.postDraft(draft, options);
|
|
207
|
+
}
|
|
208
|
+
}
|
|
209
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoic2tyLnBvc3RpbmcuanMiLCJzb3VyY2VSb290IjoiIiwic291cmNlcyI6WyIuLi90cy9za3IucG9zdGluZy50cyJdLCJuYW1lcyI6W10sIm1hcHBpbmdzIjoiQUFBQTs7Ozs7Ozs7Ozs7R0FXRztBQUNILE9BQU8sS0FBSyxJQUFJLE1BQU0saUJBQWlCLENBQUM7QUFDeEMsT0FBTyxFQUFFLFNBQVMsRUFBRSxNQUFNLG1CQUFtQixDQUFDO0FBQzlDLE9BQU8sRUFBRSxZQUFZLEVBQUUsTUFBTSwrQkFBK0IsQ0FBQztBQUM3RCxPQUFPLEVBQUUsZ0JBQWdCLEVBQUUsV0FBVyxFQUFFLHFCQUFxQixFQUFFLE1BQU0sbUJBQW1CLENBQUM7QUFDekYsT0FBTyxFQUNMLGdCQUFnQixFQUNoQixtQkFBbUIsRUFDbkIsWUFBWSxFQUNaLFFBQVEsRUFDUix3QkFBd0IsR0FDekIsTUFBTSxpQkFBaUIsQ0FBQztBQUN6QixPQUFPLEVBQUUsaUJBQWlCLEVBQUUsNEJBQTRCLEVBQUUsTUFBTSxpQkFBaUIsQ0FBQztBQVNsRjs7OztHQUlHO0FBQ0gsTUFBTSxVQUFVLGdCQUFnQixDQUFDLEtBdUJoQztJQUNDLE9BQU87UUFDTCxjQUFjLEVBQUUsS0FBSyxDQUFDLGNBQWM7UUFDcEMsT0FBTyxFQUFFLEtBQUssQ0FBQyxPQUFPO1FBQ3RCLFVBQVUsRUFBRSxLQUFLLENBQUMsVUFBVTtRQUM1QixJQUFJLEVBQUUsS0FBSyxDQUFDLElBQUk7UUFDaEIsUUFBUSxFQUFFLEtBQUssQ0FBQyxRQUFRO1FBQ3hCLFdBQVcsRUFBRSxLQUFLLENBQUMsV0FBVyxJQUFJLEVBQUU7UUFDcEMsU0FBUyxFQUFFLEtBQUssQ0FBQyxTQUFTLElBQUksRUFBRTtRQUNoQyxXQUFXLEVBQUUsS0FBSyxDQUFDLFdBQVcsSUFBSSxFQUFFO1FBQ3BDLFFBQVEsRUFBRSxLQUFLLENBQUMsUUFBUSxJQUFJLEtBQUs7UUFDakMsVUFBVSxFQUFFLEtBQUssQ0FBQyxVQUFVLElBQUksRUFBRTtRQUNsQyxLQUFLLEVB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
|
|
@@ -28,17 +28,14 @@ export declare class SecurityManager {
|
|
|
28
28
|
*/
|
|
29
29
|
createCadesSignature(data: Buffer | string, certificatePem?: string, privateKeyPem?: string): Promise<ISignatureResult>;
|
|
30
30
|
/**
|
|
31
|
-
*
|
|
31
|
+
* RFC 3161 timestamping — NOT implemented.
|
|
32
|
+
*
|
|
33
|
+
* The previous implementation posted a JSON blob pretending to be an ASN.1
|
|
34
|
+
* TimeStampReq — every real TSA rejects that, and failures were silently
|
|
35
|
+
* swallowed (fake CAdES-T). Until a real RFC 3161 client (DER-encoded TSQ)
|
|
36
|
+
* exists, this fails loudly; use CAdES-B (includeTimestamp: false).
|
|
32
37
|
*/
|
|
33
38
|
requestTimestamp(dataHash: string | Buffer): Promise<ITimestampResponse>;
|
|
34
|
-
/**
|
|
35
|
-
* Creates a timestamp request (simplified version)
|
|
36
|
-
*/
|
|
37
|
-
private createTimestampRequest;
|
|
38
|
-
/**
|
|
39
|
-
* Sends timestamp request to TSA server
|
|
40
|
-
*/
|
|
41
|
-
private sendTimestampRequest;
|
|
42
39
|
/**
|
|
43
40
|
* Verifies a CAdES signature
|
|
44
41
|
*/
|
package/dist_ts/skr.security.js
CHANGED
|
@@ -1,8 +1,8 @@
|
|
|
1
1
|
import * as plugins from './plugins.js';
|
|
2
2
|
import * as path from 'path';
|
|
3
3
|
import * as crypto from 'crypto';
|
|
4
|
-
import * as https from 'https';
|
|
5
4
|
import * as nodeForge from 'node-forge';
|
|
5
|
+
import { NotImplementedError } from './skr.errors.js';
|
|
6
6
|
export class SecurityManager {
|
|
7
7
|
options;
|
|
8
8
|
logger;
|
|
@@ -74,17 +74,13 @@ export class SecurityManager {
|
|
|
74
74
|
signingTime: new Date().toISOString(),
|
|
75
75
|
certificateChain: [cert]
|
|
76
76
|
};
|
|
77
|
-
// Add timestamp if requested
|
|
77
|
+
// Add timestamp if requested — no silent downgrade: if a timestamp was
|
|
78
|
+
// asked for and cannot be produced, the signing call fails loudly.
|
|
78
79
|
if (this.options.includeTimestamp && this.options.timestampServerUrl) {
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
result.signatureFormat = 'CAdES-T';
|
|
84
|
-
}
|
|
85
|
-
catch (error) {
|
|
86
|
-
this.logger.log('warn', `Failed to obtain timestamp: ${error}`);
|
|
87
|
-
}
|
|
80
|
+
const timestampResponse = await this.requestTimestamp(signature);
|
|
81
|
+
result.timestampToken = timestampResponse.token;
|
|
82
|
+
result.timestampTime = timestampResponse.time;
|
|
83
|
+
result.signatureFormat = 'CAdES-T';
|
|
88
84
|
}
|
|
89
85
|
return result;
|
|
90
86
|
}
|
|
@@ -93,85 +89,16 @@ export class SecurityManager {
|
|
|
93
89
|
}
|
|
94
90
|
}
|
|
95
91
|
/**
|
|
96
|
-
*
|
|
92
|
+
* RFC 3161 timestamping — NOT implemented.
|
|
93
|
+
*
|
|
94
|
+
* The previous implementation posted a JSON blob pretending to be an ASN.1
|
|
95
|
+
* TimeStampReq — every real TSA rejects that, and failures were silently
|
|
96
|
+
* swallowed (fake CAdES-T). Until a real RFC 3161 client (DER-encoded TSQ)
|
|
97
|
+
* exists, this fails loudly; use CAdES-B (includeTimestamp: false).
|
|
97
98
|
*/
|
|
98
99
|
async requestTimestamp(dataHash) {
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
let hash;
|
|
102
|
-
if (typeof dataHash === 'string') {
|
|
103
|
-
hash = crypto.createHash('sha256').update(dataHash).digest();
|
|
104
|
-
}
|
|
105
|
-
else {
|
|
106
|
-
hash = crypto.createHash('sha256').update(dataHash).digest();
|
|
107
|
-
}
|
|
108
|
-
// Create timestamp request (simplified - in production use proper ASN.1 encoding)
|
|
109
|
-
const tsRequest = this.createTimestampRequest(hash);
|
|
110
|
-
// Send request to TSA
|
|
111
|
-
const response = await this.sendTimestampRequest(tsRequest);
|
|
112
|
-
return {
|
|
113
|
-
token: response.toString('base64'),
|
|
114
|
-
time: new Date().toISOString(),
|
|
115
|
-
serverUrl: this.options.timestampServerUrl,
|
|
116
|
-
hashAlgorithm: 'sha256'
|
|
117
|
-
};
|
|
118
|
-
}
|
|
119
|
-
catch (error) {
|
|
120
|
-
throw new Error(`Failed to obtain timestamp: ${error}`);
|
|
121
|
-
}
|
|
122
|
-
}
|
|
123
|
-
/**
|
|
124
|
-
* Creates a timestamp request (simplified version)
|
|
125
|
-
*/
|
|
126
|
-
createTimestampRequest(hash) {
|
|
127
|
-
// In production, use proper ASN.1 encoding library
|
|
128
|
-
// This is a simplified placeholder
|
|
129
|
-
const request = {
|
|
130
|
-
version: 1,
|
|
131
|
-
messageImprint: {
|
|
132
|
-
hashAlgorithm: { algorithm: '2.16.840.1.101.3.4.2.1' }, // SHA-256 OID
|
|
133
|
-
hashedMessage: hash
|
|
134
|
-
},
|
|
135
|
-
reqPolicy: null,
|
|
136
|
-
nonce: crypto.randomBytes(8),
|
|
137
|
-
certReq: true
|
|
138
|
-
};
|
|
139
|
-
// Convert to DER-encoded ASN.1 (simplified)
|
|
140
|
-
return Buffer.from(JSON.stringify(request));
|
|
141
|
-
}
|
|
142
|
-
/**
|
|
143
|
-
* Sends timestamp request to TSA server
|
|
144
|
-
*/
|
|
145
|
-
async sendTimestampRequest(request) {
|
|
146
|
-
return new Promise((resolve, reject) => {
|
|
147
|
-
const url = new URL(this.options.timestampServerUrl);
|
|
148
|
-
const options = {
|
|
149
|
-
hostname: url.hostname,
|
|
150
|
-
port: url.port || 443,
|
|
151
|
-
path: url.pathname,
|
|
152
|
-
method: 'POST',
|
|
153
|
-
headers: {
|
|
154
|
-
'Content-Type': 'application/timestamp-query',
|
|
155
|
-
'Content-Length': request.length
|
|
156
|
-
}
|
|
157
|
-
};
|
|
158
|
-
const req = https.request(options, (res) => {
|
|
159
|
-
const chunks = [];
|
|
160
|
-
res.on('data', (chunk) => chunks.push(chunk));
|
|
161
|
-
res.on('end', () => {
|
|
162
|
-
const response = Buffer.concat(chunks);
|
|
163
|
-
if (res.statusCode === 200) {
|
|
164
|
-
resolve(response);
|
|
165
|
-
}
|
|
166
|
-
else {
|
|
167
|
-
reject(new Error(`TSA server returned status ${res.statusCode}`));
|
|
168
|
-
}
|
|
169
|
-
});
|
|
170
|
-
});
|
|
171
|
-
req.on('error', reject);
|
|
172
|
-
req.write(request);
|
|
173
|
-
req.end();
|
|
174
|
-
});
|
|
100
|
+
void dataHash;
|
|
101
|
+
throw new NotImplementedError('RFC 3161 timestamping is not implemented — CAdES-T/LT unavailable, use CAdES-B (includeTimestamp: false)');
|
|
175
102
|
}
|
|
176
103
|
/**
|
|
177
104
|
* Verifies a CAdES signature
|
|
@@ -319,4 +246,4 @@ export class SecurityManager {
|
|
|
319
246
|
return ltv;
|
|
320
247
|
}
|
|
321
248
|
}
|
|
322
|
-
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoic2tyLnNlY3VyaXR5LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vdHMvc2tyLnNlY3VyaXR5LnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sS0FBSyxPQUFPLE1BQU0sY0FBYyxDQUFDO0FBQ3hDLE9BQU8sS0FBSyxJQUFJLE1BQU0sTUFBTSxDQUFDO0FBQzdCLE9BQU8sS0FBSyxNQUFNLE1BQU0sUUFBUSxDQUFDO0FBQ2pDLE9BQU8sS0FBSyxLQUFLLE1BQU0sT0FBTyxDQUFDO0FBQy9CLE9BQU8sS0FBSyxTQUFTLE1BQU0sWUFBWSxDQUFDO0FBMEJ4QyxNQUFNLE9BQU8sZUFBZTtJQUNsQixPQUFPLENBQWtCO0lBQ3pCLE1BQU0sQ0FBOEI7SUFFNUMsWUFBWSxVQUEyQixFQUFFO1FBQ3ZDLElBQUksQ0FBQyxPQUFPLEdBQUc7WUFDYixrQkFBa0IsRUFBRSxPQUFPLENBQUMsa0JBQWtCLElBQUksK0JBQStCO1lBQ2pGLGdCQUFnQixFQUFFLE9BQU8sQ0FBQyxnQkFBZ0IsS0FBSyxLQUFLO1lBQ3BELEdBQUcsT0FBTztTQUNYLENBQUM7UUFDRixJQUFJLENBQUMsTUFBTSxHQUFHLElBQUksT0FBTyxDQUFDLFFBQVEsQ0FBQyxVQUFVLEVBQUUsQ0FBQztJQUNsRCxDQUFDO0lBRUQ7O09BRUc7SUFDSSxLQUFLLENBQUMsb0JBQW9CLENBQy9CLElBQXFCLEVBQ3JCLGNBQXVCLEVBQ3ZCLGFBQXNCO1FBRXRCLE1BQU0sSUFBSSxHQUFHLGNBQWMsSUFBSSxJQUFJLENBQUMsT0FBTyxDQUFDLGNBQWMsQ0FBQztRQUMzRCxNQUFNLEdBQUcsR0FBRyxhQUFhLElBQUksSUFBSSxDQUFDLE9BQU8sQ0FBQyxhQUFhLENBQUM7UUFFeEQsSUFBSSxDQUFDLElBQUksSUFBSSxDQUFDLEdBQUcsRUFBRSxDQUFDO1lBQ2xCLE1BQU0sSUFBSSxLQUFLLENBQUMsc0RBQXNELENBQUMsQ0FBQztRQUMxRSxDQUFDO1FBRUQsSUFBSSxDQUFDO1lBQ0gs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
|
|
249
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoic2tyLnNlY3VyaXR5LmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vdHMvc2tyLnNlY3VyaXR5LnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBLE9BQU8sS0FBSyxPQUFPLE1BQU0sY0FBYyxDQUFDO0FBQ3hDLE9BQU8sS0FBSyxJQUFJLE1BQU0sTUFBTSxDQUFDO0FBQzdCLE9BQU8sS0FBSyxNQUFNLE1BQU0sUUFBUSxDQUFDO0FBRWpDLE9BQU8sS0FBSyxTQUFTLE1BQU0sWUFBWSxDQUFDO0FBQ3hDLE9BQU8sRUFBRSxtQkFBbUIsRUFBRSxNQUFNLGlCQUFpQixDQUFDO0FBMEJ0RCxNQUFNLE9BQU8sZUFBZTtJQUNsQixPQUFPLENBQWtCO0lBQ3pCLE1BQU0sQ0FBOEI7SUFFNUMsWUFBWSxVQUEyQixFQUFFO1FBQ3ZDLElBQUksQ0FBQyxPQUFPLEdBQUc7WUFDYixrQkFBa0IsRUFBRSxPQUFPLENBQUMsa0JBQWtCLElBQUksK0JBQStCO1lBQ2pGLGdCQUFnQixFQUFFLE9BQU8sQ0FBQyxnQkFBZ0IsS0FBSyxLQUFLO1lBQ3BELEdBQUcsT0FBTztTQUNYLENBQUM7UUFDRixJQUFJLENBQUMsTUFBTSxHQUFHLElBQUksT0FBTyxDQUFDLFFBQVEsQ0FBQyxVQUFVLEVBQUUsQ0FBQztJQUNsRCxDQUFDO0lBRUQ7O09BRUc7SUFDSSxLQUFLLENBQUMsb0JBQW9CLENBQy9CLElBQXFCLEVBQ3JCLGNBQXVCLEVBQ3ZCLGFBQXNCO1FBRXRCLE1BQU0sSUFBSSxHQUFHLGNBQWMsSUFBSSxJQUFJLENBQUMsT0FBTyxDQUFDLGNBQWMsQ0FBQztRQUMzRCxNQUFNLEdBQUcsR0FBRyxhQUFhLElBQUksSUFBSSxDQUFDLE9BQU8sQ0FBQyxhQUFhLENBQUM7UUFFeEQsSUFBSSxDQUFDLElBQUksSUFBSSxDQUFDLEdBQUcsRUFBRSxDQUFDO1lBQ2xCLE1BQU0sSUFBSSxLQUFLLENBQUMsc0RBQXNELENBQUMsQ0FBQztRQUMxRSxDQUFDO1FBRUQsSUFBSSxD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
|
|
@@ -0,0 +1,32 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Gapless ledger sequences + hash-chain heads, one document per
|
|
3
|
+
* (skrType, fiscalYear). This is the only module that touches the raw
|
|
4
|
+
* MongoDB driver for sequence allocation — everything runs inside the
|
|
5
|
+
* caller's transaction session, so an aborted posting rolls the $inc back
|
|
6
|
+
* and gaplessness holds.
|
|
7
|
+
*/
|
|
8
|
+
import { type TDbSession } from './skr.database.js';
|
|
9
|
+
import type { TSKRType } from './skr.types.js';
|
|
10
|
+
export declare const LEDGER_SEQUENCE_COLLECTION = "LedgerSequence";
|
|
11
|
+
export interface ILedgerSequenceAllocation {
|
|
12
|
+
sequenceNumber: number;
|
|
13
|
+
prevHash: string;
|
|
14
|
+
}
|
|
15
|
+
export interface ILedgerSequenceState {
|
|
16
|
+
skrType: TSKRType;
|
|
17
|
+
fiscalYear: number;
|
|
18
|
+
value: number;
|
|
19
|
+
headHash: string;
|
|
20
|
+
}
|
|
21
|
+
export declare function ensureSequenceIndexes(): Promise<void>;
|
|
22
|
+
/**
|
|
23
|
+
* Allocate the next sequence number and return the current chain head.
|
|
24
|
+
* Must run inside a transaction — the $inc participates in the rollback.
|
|
25
|
+
*/
|
|
26
|
+
export declare function allocateSequence(skrType: TSKRType, fiscalYear: number, session: TDbSession): Promise<ILedgerSequenceAllocation>;
|
|
27
|
+
/**
|
|
28
|
+
* Compare-and-swap the chain head. The filter on the old head serializes
|
|
29
|
+
* concurrent posters — a lost race aborts the surrounding transaction.
|
|
30
|
+
*/
|
|
31
|
+
export declare function advanceHead(skrType: TSKRType, fiscalYear: number, prevHash: string, newHash: string, session: TDbSession): Promise<void>;
|
|
32
|
+
export declare function getSequenceState(skrType: TSKRType, fiscalYear: number): Promise<ILedgerSequenceState | null>;
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Gapless ledger sequences + hash-chain heads, one document per
|
|
3
|
+
* (skrType, fiscalYear). This is the only module that touches the raw
|
|
4
|
+
* MongoDB driver for sequence allocation — everything runs inside the
|
|
5
|
+
* caller's transaction session, so an aborted posting rolls the $inc back
|
|
6
|
+
* and gaplessness holds.
|
|
7
|
+
*/
|
|
8
|
+
import { getDbSync } from './skr.database.js';
|
|
9
|
+
import { genesisHash } from './core/core.hash.js';
|
|
10
|
+
import { SequenceConflictError } from './skr.errors.js';
|
|
11
|
+
export const LEDGER_SEQUENCE_COLLECTION = 'LedgerSequence';
|
|
12
|
+
function sequenceCollection() {
|
|
13
|
+
return getDbSync().mongoDb.collection(LEDGER_SEQUENCE_COLLECTION);
|
|
14
|
+
}
|
|
15
|
+
export async function ensureSequenceIndexes() {
|
|
16
|
+
await sequenceCollection().createIndex({ skrType: 1, fiscalYear: 1 }, { unique: true });
|
|
17
|
+
}
|
|
18
|
+
/**
|
|
19
|
+
* Allocate the next sequence number and return the current chain head.
|
|
20
|
+
* Must run inside a transaction — the $inc participates in the rollback.
|
|
21
|
+
*/
|
|
22
|
+
export async function allocateSequence(skrType, fiscalYear, session) {
|
|
23
|
+
const genesis = genesisHash(skrType, fiscalYear);
|
|
24
|
+
const doc = await sequenceCollection().findOneAndUpdate({ skrType, fiscalYear }, { $inc: { value: 1 }, $setOnInsert: { headHash: genesis } }, { upsert: true, returnDocument: 'after', session });
|
|
25
|
+
if (!doc) {
|
|
26
|
+
throw new Error(`Sequence allocation failed for ${skrType}/${fiscalYear}`);
|
|
27
|
+
}
|
|
28
|
+
return { sequenceNumber: doc.value, prevHash: doc.headHash };
|
|
29
|
+
}
|
|
30
|
+
/**
|
|
31
|
+
* Compare-and-swap the chain head. The filter on the old head serializes
|
|
32
|
+
* concurrent posters — a lost race aborts the surrounding transaction.
|
|
33
|
+
*/
|
|
34
|
+
export async function advanceHead(skrType, fiscalYear, prevHash, newHash, session) {
|
|
35
|
+
const result = await sequenceCollection().updateOne({ skrType, fiscalYear, headHash: prevHash }, { $set: { headHash: newHash } }, { session });
|
|
36
|
+
if (result.matchedCount !== 1) {
|
|
37
|
+
throw new SequenceConflictError(skrType, fiscalYear);
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
export async function getSequenceState(skrType, fiscalYear) {
|
|
41
|
+
const doc = await sequenceCollection().findOne({ skrType, fiscalYear });
|
|
42
|
+
if (!doc)
|
|
43
|
+
return null;
|
|
44
|
+
return {
|
|
45
|
+
skrType,
|
|
46
|
+
fiscalYear,
|
|
47
|
+
value: doc.value,
|
|
48
|
+
headHash: doc.headHash,
|
|
49
|
+
};
|
|
50
|
+
}
|
|
51
|
+
//# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoic2tyLnNlcXVlbmNlLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vdHMvc2tyLnNlcXVlbmNlLnRzIl0sIm5hbWVzIjpbXSwibWFwcGluZ3MiOiJBQUFBOzs7Ozs7R0FNRztBQUNILE9BQU8sRUFBRSxTQUFTLEVBQW1CLE1BQU0sbUJBQW1CLENBQUM7QUFDL0QsT0FBTyxFQUFFLFdBQVcsRUFBRSxNQUFNLHFCQUFxQixDQUFDO0FBQ2xELE9BQU8sRUFBRSxxQkFBcUIsRUFBRSxNQUFNLGlCQUFpQixDQUFDO0FBR3hELE1BQU0sQ0FBQyxNQUFNLDBCQUEwQixHQUFHLGdCQUFnQixDQUFDO0FBYzNELFNBQVMsa0JBQWtCO0lBQ3pCLE9BQU8sU0FBUyxFQUFFLENBQUMsT0FBTyxDQUFDLFVBQVUsQ0FBQywwQkFBMEIsQ0FBQyxDQUFDO0FBQ3BFLENBQUM7QUFFRCxNQUFNLENBQUMsS0FBSyxVQUFVLHFCQUFxQjtJQUN6QyxNQUFNLGtCQUFrQixFQUFFLENBQUMsV0FBVyxDQUFDLEVBQUUsT0FBTyxFQUFFLENBQUMsRUFBRSxVQUFVLEVBQUUsQ0FBQyxFQUFFLEVBQUUsRUFBRSxNQUFNLEVBQUUsSUFBSSxFQUFFLENBQUMsQ0FBQztBQUMxRixDQUFDO0FBRUQ7OztHQUdHO0FBQ0gsTUFBTSxDQUFDLEtBQUssVUFBVSxnQkFBZ0IsQ0FDcEMsT0FBaUIsRUFDakIsVUFBa0IsRUFDbEIsT0FBbUI7SUFFbkIsTUFBTSxPQUFPLEdBQUcsV0FBVyxDQUFDLE9BQU8sRUFBRSxVQUFVLENBQUMsQ0FBQztJQUNqRCxNQUFNLEdBQUcsR0FBRyxNQUFNLGtCQUFrQixFQUFFLENBQUMsZ0JBQWdCLENBQ3JELEVBQUUsT0FBTyxFQUFFLFVBQVUsRUFBRSxFQUN2QixFQUFFLElBQUksRUFBRSxFQUFFLEtBQUssRUFBRSxDQUFDLEVBQUUsRUFBRSxZQUFZLEVBQUUsRUFBRSxRQUFRLEVBQUUsT0FBTyxFQUFFLEVBQUUsRUFDM0QsRUFBRSxNQUFNLEVBQUUsSUFBSSxFQUFFLGNBQWMsRUFBRSxPQUFPLEVBQUUsT0FBTyxFQUFFLENBQ25ELENBQUM7SUFDRixJQUFJLENBQUMsR0FBRyxFQUFFLENBQUM7UUFDVCxNQUFNLElBQUksS0FBSyxDQUFDLGtDQUFrQyxPQUFPLElBQUksVUFBVSxFQUFFLENBQUMsQ0FBQztJQUM3RSxDQUFDO0lBQ0QsT0FBTyxFQUFFLGNBQWMsRUFBRSxHQUFHLENBQUMsS0FBZSxFQUFFLFFBQVEsRUFBRSxHQUFHLENBQUMsUUFBa0IsRUFBRSxDQUFDO0FBQ25GLENBQUM7QUFFRDs7O0dBR0c7QUFDSCxNQUFNLENBQUMsS0FBSyxVQUFVLFdBQVcsQ0FDL0IsT0FBaUIsRUFDakIsVUFBa0IsRUFDbEIsUUFBZ0IsRUFDaEIsT0FBZSxFQUNmLE9BQW1CO0lBRW5CLE1BQU0sTUFBTSxHQUFHLE1BQU0sa0JBQWtCLEVBQUUsQ0FBQyxTQUFTLENBQ2pELEVBQUUsT0FBTyxFQUFFLFVBQVUsRUFBRSxRQUFRLEVBQUUsUUFBUSxFQUFFLEVBQzNDLEVBQUUsSUFBSSxFQUFFLEVBQUUsUUFBUSxFQUFFLE9BQU8sRUFBRSxFQUFFLEVBQy9CLEVBQUUsT0FBTyxFQUFFLENBQ1osQ0FBQztJQUNGLElBQUksTUFBTSxDQUFDLFlBQVksS0FBSyxDQUFDLEVBQUUsQ0FBQztRQUM5QixNQUFNLElBQUkscUJBQXFCLENBQUMsT0FBTyxFQUFFLFVBQVUsQ0FBQyxDQUFDO0lBQ3ZELENBQUM7QUFDSCxDQUFDO0FBRUQsTUFBTSxDQUFDLEtBQUssVUFBVSxnQkFBZ0IsQ0FDcEMsT0FBaUIsRUFDakIsVUFBa0I7SUFFbEIsTUFBTSxHQUFHLEdBQUcsTUFBTSxrQkFBa0IsRUFBRSxDQUFDLE9BQU8sQ0FBQyxFQUFFLE9BQU8sRUFBRSxVQUFVLEVBQUUsQ0FBQyxDQUFDO0lBQ3hFLElBQUksQ0FBQyxHQUFHO1FBQUUsT0FBTyxJQUFJLENBQUM7SUFDdEIsT0FBTztRQUNMLE9BQU87UUFDUCxVQUFVO1FBQ1YsS0FBSyxFQUFFLEdBQUcsQ0FBQyxLQUFlO1FBQzFCLFFBQVEsRUFBRSxHQUFHLENBQUMsUUFBa0I7S0FDakMsQ0FBQztBQUNKLENBQUMifQ==
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
import * as core from './core/index.js';
|
|
2
|
+
import type { IJournalEntry, IJournalEntryLine, ITransactionData, ITransactionView, IReportParams, TSKRType } from './skr.types.js';
|
|
3
|
+
export declare function mapNumericPostingKey(postingKey?: number): core.TBuKey;
|
|
4
|
+
/**
|
|
5
|
+
* v1 postTransaction input -> two-line v2 draft. The amount is NOT split into
|
|
6
|
+
* net/VAT (v1 semantics: vatAmount was informational) so ledger figures stay
|
|
7
|
+
* identical across the migration.
|
|
8
|
+
*/
|
|
9
|
+
export declare function transactionDataToDraft(data: ITransactionData): core.IJournalDraft;
|
|
10
|
+
/**
|
|
11
|
+
* v1 postJournalEntry input -> v2 draft. Gegenkonto derivation: when one side
|
|
12
|
+
* of the entry has exactly one line, it is the counter account for every line
|
|
13
|
+
* of the other side (the dominant v1 usage); otherwise the first line of the
|
|
14
|
+
* opposite side is used (documented heuristic — v1 stored no Gegenkonto).
|
|
15
|
+
*/
|
|
16
|
+
export declare function journalInputToDraft(entry: IJournalEntry): core.IJournalDraft;
|
|
17
|
+
interface IEntryDocLike {
|
|
18
|
+
id: string;
|
|
19
|
+
journalNumber?: string;
|
|
20
|
+
date: Date;
|
|
21
|
+
description: string;
|
|
22
|
+
reference?: string;
|
|
23
|
+
skrType: TSKRType;
|
|
24
|
+
status: string;
|
|
25
|
+
period?: string;
|
|
26
|
+
fiscalYear?: number;
|
|
27
|
+
postedAt?: Date | null;
|
|
28
|
+
reversalOf?: string;
|
|
29
|
+
lines: IJournalEntryLine[];
|
|
30
|
+
}
|
|
31
|
+
/**
|
|
32
|
+
* Project a two-line v2 entry back into the classic transaction shape.
|
|
33
|
+
* Returns null for entries with more than two lines (journal-only view).
|
|
34
|
+
*/
|
|
35
|
+
export declare function entryToTransactionView(entry: IEntryDocLike): ITransactionView | null;
|
|
36
|
+
/**
|
|
37
|
+
* Load v2 entries of a date range as core drafts (for DATEV export).
|
|
38
|
+
*/
|
|
39
|
+
export declare function loadDraftsForExport(skrType: TSKRType, dateFrom: Date, dateTo: Date): Promise<core.IJournalDraft[]>;
|
|
40
|
+
/**
|
|
41
|
+
* Per-account activity as transaction-shaped line views from v2 entries —
|
|
42
|
+
* the data source for reports (trial balance, general ledger, cash flow).
|
|
43
|
+
* Each view carries the line's own side and its Gegenkonto.
|
|
44
|
+
*/
|
|
45
|
+
export declare function accountLineViews(accountNumber: string, skrType: TSKRType, params?: IReportParams): Promise<ITransactionView[]>;
|
|
46
|
+
export {};
|