mirror of
https://github.com/mayswind/ezbookkeeping.git
synced 2026-05-18 00:34:28 +08:00
use the expense and revenue account names as category names if the transaction has not category when importing Firefly III transactions
This commit is contained in:
@@ -1,51 +1,77 @@
|
||||
package fireflyIII
|
||||
|
||||
import (
|
||||
"strings"
|
||||
|
||||
"github.com/mayswind/ezbookkeeping/pkg/converters/datatable"
|
||||
"github.com/mayswind/ezbookkeeping/pkg/core"
|
||||
"github.com/mayswind/ezbookkeeping/pkg/errs"
|
||||
"github.com/mayswind/ezbookkeeping/pkg/models"
|
||||
"github.com/mayswind/ezbookkeeping/pkg/utils"
|
||||
)
|
||||
|
||||
const fireflyIIITransactionTimeColumnName = "date"
|
||||
const fireflyIIITransactionTypeColumnName = "type"
|
||||
const fireflyIIITransactionCategoryColumnName = "category"
|
||||
const fireflyIIITransactionSourceAccountColumnName = "source_name"
|
||||
const fireflyIIITransactionCurrencyCodeColumnName = "currency_code"
|
||||
const fireflyIIITransactionAmountColumnName = "amount"
|
||||
const fireflyIIITransactionDestinationAccountColumnName = "destination_name"
|
||||
const fireflyIIITransactionForeignCurrencyCodeColumnName = "foreign_currency_code"
|
||||
const fireflyIIITransactionForeignAmountColumnName = "foreign_amount"
|
||||
const fireflyIIITransactionTagsColumnName = "tags"
|
||||
const fireflyIIITransactionDescriptionColumnName = "description"
|
||||
|
||||
// fireflyIIITransactionDataRowParser defines the structure of firefly III transaction data row parser
|
||||
type fireflyIIITransactionDataRowParser struct {
|
||||
}
|
||||
|
||||
// GetAddedColumns returns the added columns after converting the data row
|
||||
func (p *fireflyIIITransactionDataRowParser) GetAddedColumns() []datatable.TransactionDataTableColumn {
|
||||
return []datatable.TransactionDataTableColumn{
|
||||
datatable.TRANSACTION_DATA_TABLE_TRANSACTION_TIMEZONE,
|
||||
}
|
||||
}
|
||||
|
||||
// Parse returns the converted transaction data row
|
||||
func (p *fireflyIIITransactionDataRowParser) Parse(data map[datatable.TransactionDataTableColumn]string) (rowData map[datatable.TransactionDataTableColumn]string, rowDataValid bool, err error) {
|
||||
rowData = make(map[datatable.TransactionDataTableColumn]string, len(data))
|
||||
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_SUB_CATEGORY] = ""
|
||||
|
||||
for column, value := range data {
|
||||
rowData[column] = value
|
||||
}
|
||||
func (p *fireflyIIITransactionDataRowParser) Parse(ctx core.Context, user *models.User, dataRow datatable.CommonDataTableRow, rowId string) (rowData map[datatable.TransactionDataTableColumn]string, rowDataValid bool, err error) {
|
||||
rowData = make(map[datatable.TransactionDataTableColumn]string, len(fireflyIIITransactionSupportedColumns))
|
||||
|
||||
// parse long date time and timezone
|
||||
if rowData[datatable.TRANSACTION_DATA_TABLE_TRANSACTION_TIME] != "" {
|
||||
if strings.Index(rowData[datatable.TRANSACTION_DATA_TABLE_TRANSACTION_TIME], "T") <= 0 {
|
||||
return nil, false, errs.ErrTransactionTimeInvalid
|
||||
}
|
||||
dateTime, err := utils.ParseFromLongDateTimeWithTimezoneRFC3339Format(dataRow.GetData(fireflyIIITransactionTimeColumnName))
|
||||
|
||||
dateTime, err := utils.ParseFromLongDateTimeWithTimezone(strings.ReplaceAll(rowData[datatable.TRANSACTION_DATA_TABLE_TRANSACTION_TIME], "T", " "))
|
||||
|
||||
if err != nil {
|
||||
return nil, false, errs.ErrTransactionTimeInvalid
|
||||
}
|
||||
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_TRANSACTION_TIME] = utils.FormatUnixTimeToLongDateTime(dateTime.Unix(), dateTime.Location())
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_TRANSACTION_TIMEZONE] = utils.FormatTimezoneOffset(dateTime.Location())
|
||||
if err != nil {
|
||||
return nil, false, errs.ErrTransactionTimeInvalid
|
||||
}
|
||||
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_TRANSACTION_TIME] = utils.FormatUnixTimeToLongDateTime(dateTime.Unix(), dateTime.Location())
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_TRANSACTION_TIMEZONE] = utils.FormatTimezoneOffset(dateTime.Location())
|
||||
|
||||
// parse transaction type
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_TRANSACTION_TYPE] = dataRow.GetData(fireflyIIITransactionTypeColumnName)
|
||||
|
||||
// parse transaction category
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_SUB_CATEGORY] = dataRow.GetData(fireflyIIITransactionCategoryColumnName)
|
||||
|
||||
if rowData[datatable.TRANSACTION_DATA_TABLE_TRANSACTION_TYPE] == fireflyIIITransactionTypeNameMapping[models.TRANSACTION_TYPE_INCOME] {
|
||||
// if the category is empty, use the source account (revenue account) name as the category name
|
||||
if rowData[datatable.TRANSACTION_DATA_TABLE_SUB_CATEGORY] == "" {
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_SUB_CATEGORY] = dataRow.GetData(fireflyIIITransactionSourceAccountColumnName)
|
||||
}
|
||||
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_ACCOUNT_NAME] = dataRow.GetData(fireflyIIITransactionDestinationAccountColumnName)
|
||||
} else if rowData[datatable.TRANSACTION_DATA_TABLE_TRANSACTION_TYPE] == fireflyIIITransactionTypeNameMapping[models.TRANSACTION_TYPE_EXPENSE] {
|
||||
// if the category is empty, use the destination account (expense account) name as the category name
|
||||
if rowData[datatable.TRANSACTION_DATA_TABLE_SUB_CATEGORY] == "" {
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_SUB_CATEGORY] = dataRow.GetData(fireflyIIITransactionDestinationAccountColumnName)
|
||||
}
|
||||
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_ACCOUNT_NAME] = dataRow.GetData(fireflyIIITransactionSourceAccountColumnName)
|
||||
} else if rowData[datatable.TRANSACTION_DATA_TABLE_TRANSACTION_TYPE] == fireflyIIITransactionTypeNameMapping[models.TRANSACTION_TYPE_TRANSFER] {
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_ACCOUNT_NAME] = dataRow.GetData(fireflyIIITransactionSourceAccountColumnName)
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_RELATED_ACCOUNT_NAME] = dataRow.GetData(fireflyIIITransactionDestinationAccountColumnName)
|
||||
} else if rowData[datatable.TRANSACTION_DATA_TABLE_TRANSACTION_TYPE] == fireflyIIITransactionTypeNameMapping[models.TRANSACTION_TYPE_MODIFY_BALANCE] {
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_SUB_CATEGORY] = ""
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_ACCOUNT_NAME] = dataRow.GetData(fireflyIIITransactionDestinationAccountColumnName)
|
||||
} else {
|
||||
return nil, false, errs.ErrTransactionTypeInvalid
|
||||
}
|
||||
|
||||
// parse amount
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_AMOUNT] = dataRow.GetData(fireflyIIITransactionAmountColumnName)
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_RELATED_AMOUNT] = dataRow.GetData(fireflyIIITransactionForeignAmountColumnName)
|
||||
|
||||
// trim trailing zero in decimal
|
||||
if rowData[datatable.TRANSACTION_DATA_TABLE_AMOUNT] != "" {
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_AMOUNT] = utils.TrimTrailingZerosInDecimal(rowData[datatable.TRANSACTION_DATA_TABLE_AMOUNT])
|
||||
@@ -71,25 +97,23 @@ func (p *fireflyIIITransactionDataRowParser) Parse(data map[datatable.Transactio
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_RELATED_AMOUNT] = rowData[datatable.TRANSACTION_DATA_TABLE_AMOUNT]
|
||||
}
|
||||
|
||||
// parse account currency
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_ACCOUNT_CURRENCY] = dataRow.GetData(fireflyIIITransactionCurrencyCodeColumnName)
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_RELATED_ACCOUNT_CURRENCY] = dataRow.GetData(fireflyIIITransactionForeignCurrencyCodeColumnName)
|
||||
|
||||
// the related account currency field is foreign currency in firefly III actually
|
||||
if rowData[datatable.TRANSACTION_DATA_TABLE_RELATED_ACCOUNT_CURRENCY] == "" {
|
||||
if rowData[datatable.TRANSACTION_DATA_TABLE_RELATED_ACCOUNT_CURRENCY] == "" && rowData[datatable.TRANSACTION_DATA_TABLE_ACCOUNT_CURRENCY] != "" {
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_RELATED_ACCOUNT_CURRENCY] = rowData[datatable.TRANSACTION_DATA_TABLE_ACCOUNT_CURRENCY]
|
||||
}
|
||||
|
||||
// the destination account of modify balance transaction in firefly III is the asset account
|
||||
if rowData[datatable.TRANSACTION_DATA_TABLE_TRANSACTION_TYPE] == fireflyIIITransactionTypeNameMapping[models.TRANSACTION_TYPE_MODIFY_BALANCE] {
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_ACCOUNT_NAME] = rowData[datatable.TRANSACTION_DATA_TABLE_RELATED_ACCOUNT_NAME]
|
||||
}
|
||||
|
||||
// the destination account of income transaction in firefly III is the asset account
|
||||
if rowData[datatable.TRANSACTION_DATA_TABLE_TRANSACTION_TYPE] == fireflyIIITransactionTypeNameMapping[models.TRANSACTION_TYPE_INCOME] {
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_ACCOUNT_NAME] = rowData[datatable.TRANSACTION_DATA_TABLE_RELATED_ACCOUNT_NAME]
|
||||
}
|
||||
// parse tags / description
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_TAGS] = dataRow.GetData(fireflyIIITransactionTagsColumnName)
|
||||
rowData[datatable.TRANSACTION_DATA_TABLE_DESCRIPTION] = dataRow.GetData(fireflyIIITransactionDescriptionColumnName)
|
||||
|
||||
return rowData, true, nil
|
||||
}
|
||||
|
||||
// createFireflyIIITransactionDataRowParser returns firefly III transaction data row parser
|
||||
func createFireflyIIITransactionDataRowParser() datatable.TransactionDataRowParser {
|
||||
func createFireflyIIITransactionDataRowParser() datatable.CommonTransactionDataRowParser {
|
||||
return &fireflyIIITransactionDataRowParser{}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user