Skip to content

Bug: _dict_int_op raises ValueError for float values in UsageMetadata during streaming aggregation #36015

@nevanwang

Description

@nevanwang

Checked other resources

  • I added a very descriptive title to this issue.
  • I searched the LangChain documentation with the integrated search.
  • I used the GitHub search to find a similar question and didn't find it.
  • I am sure that this is a bug in LangChain rather than my code.

Example Code

import operator
from langchain_core.utils.usage import _dict_int_op
from langchain_core.messages.ai import add_usage, UsageMetadata

# int values work fine
_dict_int_op({"a": 1}, {"a": 2}, operator.add)  # ✅ {"a": 3}

# float values crash
_dict_int_op({"tokens": 10, "cost": 0.05}, {"tokens": 20, "cost": 0.03}, operator.add)
# ❌ ValueError: Unknown value types: [<class 'float'>]. Only dict and int values are supported.

# Real-world scenario: UsageMetadata with float total_cost
left = UsageMetadata(input_tokens=100, output_tokens=50, total_tokens=150)
left["total_cost"] = 0.005
right = UsageMetadata(input_tokens=200, output_tokens=100, total_tokens=300)
right["total_cost"] = 0.010
add_usage(left, right)  # ❌ ValueError

Error Message and Stack Trace

ValueError: Unknown value types: [<class 'float'>]. Only dict and int values are supported.

Description

_dict_int_op() in libs/core/langchain_core/utils/usage.py only handles int and dict types but not float. When two dictionaries contain the same key with float values, the function raises a ValueError.

This affects streaming scenarios where LLM providers include float fields in UsageMetadata (e.g., total_cost, pricing fields, or any custom float metric). During chunk aggregation via add_usage()_dict_int_op(), these float fields cause the aggregation to crash.

This is the same class of bug as #36011 (merge_dicts missing float support), but in a different function. The _dict_int_op function was designed to handle numeric operations on dictionaries but only checked for int, missing float.

All 4 float scenarios crash:

  • Direct float values in dicts
  • UsageMetadata with float total_cost on both sides
  • Float field present on only one side (default=0 is int, other side is float)
  • Mixed int (from cache init total_cost=0) + float (from provider total_cost=0.005)

Root Cause

In usage.py, the type check is:

if isinstance(left.get(k, default), int) and isinstance(right.get(k, default), int):

This should be:

if isinstance(left.get(k, default), (int, float)) and isinstance(right.get(k, default), (int, float)):

Proposed Fix

  1. Change isinstance(..., int) to isinstance(..., (int, float)) in _dict_int_op()
  2. Update docstring and error message to reflect float support
  3. Add regression tests for float values

System Info

langchain-core: 0.3.x (latest main)
Python: 3.10+
OS: macOS / Linux

Metadata

Metadata

Assignees

No one assigned

    Labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions