risingwavelabs/risingwave · error · ProtobufTypeError

{0}

Error message

{0}

What it means

ProtobufTypeError is an internal error in the Protobuf parser that reports a type-related problem (as the message string) when deriving RisingWave columns from Protobuf field descriptors. It is thrown during schema mapping, including cycle detection over nested/message-typed fields, when a descriptor's type cannot be converted to a supported RW type.

Source

Thrown at src/connector/codec/src/decoder/protobuf/parser.rs:53

pub fn pb_schema_to_fields(
    message_descriptor: &MessageDescriptor,
    messages_as_jsonb: &HashSet<String>,
) -> anyhow::Result<Vec<Field>> {
    let mut parse_trace: Vec<String> = vec![];
    message_descriptor
        .fields()
        .map(|field| {
            let field_type = protobuf_type_mapping(&field, &mut parse_trace, messages_as_jsonb)
                .context("failed to map protobuf type")?;
            let column = Field::new(field.name(), field_type);
            Ok(column)
        })
        .collect()
}

#[derive(Error, Debug, Macro)]
#[error("{0}")]
struct ProtobufTypeError(#[message] String);

fn detect_loop_and_push(
    trace: &mut Vec<String>,
    fd: &FieldDescriptor,
) -> std::result::Result<(), ProtobufTypeError> {
    let identifier = format!("{}({})", fd.name(), fd.full_name());
    if trace.iter().any(|s| s == identifier.as_str()) {
        bail_protobuf_type_error!(
            "circular reference detected: {}, conflict with {}, kind {:?}. Adding {:?} to {:?} may help.",
            trace.iter().format("->"),
            identifier,
            fd.kind(),
            fd.kind(),
            PROTOBUF_MESSAGES_AS_JSONB,
        );
    }
    trace.push(identifier);

View on GitHub (pinned to 6469eb736d)

Solutions

  1. Remove or restructure recursive/self-referential message types in the proto
  2. Replace unsupported protobuf types (Any, unsupported maps/wrappers) with supported ones
  3. Regenerate the descriptor file with a compatible protoc version matching your RW release
  4. Check the message text for the exact field and consult RW docs on supported proto types

Example fix

// before: message Node { Node child = 1; } // recursion
// after
// message Node { string value = 1; int32 depth = 2; }
Defensive patterns

Strategy: validation

Validate before calling

// Reject recursive or unsupported messages before creating the source
fn check(proto: &FileDescriptorSet) -> bool {
    proto.file.iter().all(|f| f.message_type.iter().all(|m| !is_self_referential(m)))
}

Try / catch

match result {
    Err(ProtobufTypeError(msg)) => {
        eprintln!("protobuf schema unsupported: {msg}");
        // fall back to a corrected descriptor or abort source creation
    }
    other => other?,
}

Prevention

When it happens

Trigger: Parsing a .pb descriptor for a protobuf-encoded source: unsupported field types (e.g. map with unsupported value, oneof edge cases, recursive message types detected by detect_loop_and_push), or unknown well-known types.

Common situations: Using a proto with recursive message definitions; protos compiled with protoc versions producing descriptors RW does not handle; using unsupported protobuf types (e.g. google.protobuf.Any) in sources.

Understand the failure class

Background: "cannot parse invalid wire-format data", "cannot unmarshal", "failed unmarshalling": protobuf unmarshal errors explained — this error's family across 10 libraries.

Related errors


AI-assisted analysis of risingwavelabs/risingwave@6469eb736d (2026-09-11). Data as JSON: /api/errors/fc52fb36d56782cb. Report an issue: GitHub.