Skip to content

ValidationError: TransactionObject fails on null recurring/category fields #146

@edbyford

Description

@edbyford

Description

When fetching transactions from the Lunch Money API, the TransactionObject Pydantic model fails validation when the API returns null for certain optional fields. The fields are correctly typed as Optional[str], but the values arrive as nan (float) rather than None, causing Pydantic to reject them.

Error

ValidationError: 5 validation errors for TransactionObject
category_name
  Input should be a valid string [type=string_type, input_value=nan, input_type=float]
recurring_payee
  Input should be a valid string [type=string_type, input_value=nan, input_type=float]
recurring_cadence
  Input should be a valid string [type=string_type, input_value=nan, input_type=float]
recurring_type
  Input should be a valid string [type=string_type, input_value=nan, input_type=float]
recurring_currency
  Input should be a valid string [type=string_type, input_value=nan, input_type=float]

Steps to reproduce

  1. Have Lunch Money transactions that include uncategorised transactions or transactions without recurring fields
  2. Run lunchable plugins primelunch -f amazon_export.csv
  3. The tool successfully fetches and matches transactions, then crashes when deserialising a transaction with null fields

Environment

  • lunchable 1.4.3
  • Python 3.14.0
  • macOS

Analysis

The TransactionObject model in models/transactions.py correctly defines these fields as Optional[str] with default None. However, somewhere in the deserialisation pipeline, null JSON values are being converted to nan (float) rather than None, which Pydantic then rejects as it expects str | None.

This is similar to the previously fixed #113 (Assets validation error on null balance_as_of).

Possible fix

A Pydantic field_validator (or model_validator) could coerce nan values to None for these optional string fields, similar to how #113 was resolved.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions