Autodetect OFX version during import

This commit is contained in:
RunasSudo 2025-01-27 23:30:09 +11:00
parent b8223aef05
commit b8845e9b77
Signed by: RunasSudo
GPG Key ID: 7234E476BF21C61A
4 changed files with 41 additions and 14 deletions

31
src/importers/ofx.ts Normal file
View File

@ -0,0 +1,31 @@
/*
DrCr: Web-based double-entry bookkeeping framework
Copyright (C) 20222025 Lee Yingtong Li (RunasSudo)
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU Affero General Public License as published by
the Free Software Foundation, either version 3 of the License, or
(at your option) any later version.
This program 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 Affero General Public License for more details.
You should have received a copy of the GNU Affero General Public License
along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
import importOfx1 from './ofx1.ts';
import importOfx2 from './ofx2.ts';
import { StatementLine } from '../db.ts';
export default function importOfxAutodetectVersion(sourceAccount: string, content: string): StatementLine[] {
if (content.startsWith('<?')) {
// XML-style: OFX2
return importOfx2(sourceAccount, content);
} else {
// Assume SGML style: OFX1
return importOfx1(sourceAccount, content);
}
}

View File

@ -1,6 +1,6 @@
/*
DrCr: Web-based double-entry bookkeeping framework
Copyright (C) 20222024 Lee Yingtong Li (RunasSudo)
Copyright (C) 20222025 Lee Yingtong Li (RunasSudo)
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU Affero General Public License as published by
@ -20,7 +20,7 @@ import dayjs from 'dayjs';
import { DT_FORMAT, StatementLine, db } from '../db.ts';
export default function import_ofx1(sourceAccount: string, content: string): StatementLine[] {
export default function importOfx1(sourceAccount: string, content: string): StatementLine[] {
// Import an OFX1 SGML file
// Strip OFX header and parse

View File

@ -1,6 +1,6 @@
/*
DrCr: Web-based double-entry bookkeeping framework
Copyright (C) 20222024 Lee Yingtong Li (RunasSudo)
Copyright (C) 20222025 Lee Yingtong Li (RunasSudo)
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU Affero General Public License as published by
@ -20,7 +20,7 @@ import dayjs from 'dayjs';
import { DT_FORMAT, StatementLine, db } from '../db.ts';
export default function import_ofx2(sourceAccount: string, content: string): StatementLine[] {
export default function importOfx2(sourceAccount: string, content: string): StatementLine[] {
// Import an OFX2 XML file
// Convert OFX header to XML and parse

View File

@ -1,6 +1,6 @@
<!--
DrCr: Web-based double-entry bookkeeping framework
Copyright (C) 20222024 Lee Yingtong Li (RunasSudo)
Copyright (C) 20222025 Lee Yingtong Li (RunasSudo)
This program is free software: you can redistribute it and/or modify
it under the terms of the GNU Affero General Public License as published by
@ -25,8 +25,7 @@
<label for="format" class="block text-gray-900 pr-4">File type</label>
<div>
<select class="bordered-field" id="format" v-model="format">
<option value="ofx2">OFX 2.x</option>
<option value="ofx1">OFX 1.x</option>
<option value="ofx">OFX (1.x/2.x)</option>
</select>
</div>
<label for="account" class="block text-gray-900 pr-4">Source account</label>
@ -86,12 +85,11 @@
import ComboBoxAccounts from '../components/ComboBoxAccounts.vue';
import { ppWithCommodity } from '../display.ts';
import import_ofx1 from '../importers/ofx1.ts';
import import_ofx2 from '../importers/ofx2.ts';
import importOfxAutodetectVersion from '../importers/ofx.ts';
const fileInput = useTemplateRef('file');
const format = ref('ofx2');
const format = ref('ofx');
const selectedFilename = ref('');
const sourceAccount = ref('');
@ -115,10 +113,8 @@
const content = await file.text();
if (format.value === 'ofx2') {
statementLines.value = import_ofx2(sourceAccount.value, content);
} else if (format.value === 'ofx1') {
statementLines.value = import_ofx1(sourceAccount.value, content);
if (format.value === 'ofx') {
statementLines.value = importOfxAutodetectVersion(sourceAccount.value, content);
} else {
throw new Error('Unexpected import format');
}