apache/beam · error · RuntimeError
f'Failed to create MonitoringInfo for urn
Error message
f'Failed to create MonitoringInfo for urn {urn} type {type_urn} labels {labels} and payload {payload}' What it means
create_monitoring_info builds a metrics_pb2.MonitoringInfo protobuf. If the arguments (urn, type_urn, labels, payload) have types the protobuf constructor rejects, it raises TypeError, which is re-raised as a RuntimeError with the full argument values included for debugging. The library does this so callers get a descriptive message instead of a bare protobuf TypeError.
Solutions
- Ensure all label keys and values are str (cast with str() or decode bytes) before calling the metric helpers.
- Ensure payload is bytes (payload.encode() for str, or the serialized proto bytes).
- Inspect the chained exception ('from e') message from protobuf to see exactly which field type was rejected.
- Ensure labels is a dict or None, not a list of tuples; use dict(labels) if converting.
Example fix
# before
metrics = Metrics.get_namespace(step).counter(label_id, labels={"step": 3})
# after
metrics = Metrics.get_namespace(step).counter(label_id, labels={"step": "3"}) Defensive patterns
Strategy: try-catch
Validate before calling
assert isinstance(labels, (dict, type(None))) and all(isinstance(k, str) and isinstance(v, str) for k, v in (labels or {}).items())
assert isinstance(payload, (bytes, bytearray, str, type(None))) Type guard
def valid_labels(labels): return labels is None or (isinstance(labels, dict) and all(isinstance(k, str) and isinstance(v, str) for k, v in labels.items()))
Try / catch
try:
mi = create_monitoring_info(urn, type_urn, labels, payload)
except RuntimeError as e:
logger.error("bad monitoring info args: %s", e); labels = {k: str(v) for k, v in labels.items()}; mi = create_monitoring_info(urn, type_urn, labels, payload) Prevention
- Coerce all label values to str at metric-creation sites
- Serialize payloads to bytes explicitly
- Wrap dynamic label construction in a helper that validates types
When it happens
Trigger: Calling int64_counter/int64_distribution/int64_gauge (or their _user_ variants) with non-string labels keys/values, labels that are not a dict, a payload that is not bytes/str, or passing a labels dict containing non-primitive values into create_monitoring_info.
Common situations: Metric labels built from dynamic data (e.g. f-strings with None, ints, or bytes instead of str); a payload passed as a dict instead of a serialized bytes string; SDK-internal callers after a Beam version changed the MonitoringInfo proto field types.
Understand the failure class
Background: "Must be a positive integer", "Invalid value", "Unsupported": the invalid-argument-value error family, when a library rejects the value you pass — this error's family across 35 libraries.
Related errors
- Unknown namespace type
- A cluster_identifier should be Optional[Union[str…
- Can not query metrics. Job id is unknown.
- Cannot convert from nanoseconds to microseconds because…
- Cannot convert from a JSON value.
AI-assisted analysis of apache/beam@12126d8942 (2026-09-13).
Data as JSON: /api/errors/a568a48244a9f9c5.
Report an issue: GitHub.
Appendix: source
Thrown at sdks/python/apache_beam/metrics/monitoring_infos.py:399
labels)
def create_monitoring_info(
urn, type_urn, payload, labels=None) -> metrics_pb2.MonitoringInfo:
"""Return the monitoring info for the URN, type, metric and labels.
Args:
urn: The URN of the monitoring info/metric.
type_urn: The URN of the type of the monitoring info/metric.
i.e. beam:metrics:sum_int_64, beam:metrics:latest_int_64.
payload: The payload field to use in the monitoring info.
labels: The label dictionary to use in the MonitoringInfo.
"""
try:
return metrics_pb2.MonitoringInfo(
urn=urn, type=type_urn, labels=labels or {}, payload=payload)
except TypeError as e:
raise RuntimeError(
f'Failed to create MonitoringInfo for urn {urn} type {type_urn} '
f'labels {labels} and payload {payload}') from e
def is_counter(monitoring_info_proto):
"""Returns true if the monitoring info is a coutner metric."""
return monitoring_info_proto.type in COUNTER_TYPES
def is_gauge(monitoring_info_proto):
"""Returns true if the monitoring info is a gauge metric."""
return monitoring_info_proto.type in GAUGE_TYPES
def is_distribution(monitoring_info_proto):
"""Returns true if the monitoring info is a distrbution metric."""
return monitoring_info_proto.type in DISTRIBUTION_TYPES
View on GitHub (pinned to 12126d8942)