Python
AttributeError
Google Protobuf
Debugging
Programming Error

AttributeError 'google.protobuf.pyext._message.RepeatedCompositeCo' object has no attribute 'append'

Master System Design with Codemia

Enhance your system design skills with over 120 practice problems, detailed solutions, and hands-on exercises.

Introduction

This protobuf error appears when Python code treats a repeated message field like a normal Python list. Repeated composite fields look list-like, but they are managed protobuf containers with their own mutation API, and for message types the correct operation is usually add() rather than append().

Why the Error Happens

Protocol Buffers generate specialized containers for repeated fields. There is an important distinction:

  • repeated scalar fields behave more like basic value lists
  • repeated message fields use a repeated composite container

For repeated message fields, protobuf needs tighter control because each item must be a valid message instance with the correct ownership and serialization behavior.

Suppose the .proto file looks like this:

proto
1message PhoneNumber {
2  string number = 1;
3}
4
5message Person {
6  repeated PhoneNumber phones = 1;
7}

Then in Python, person.phones is not just an ordinary list.

Use add() for Repeated Message Fields

The most common fix is this:

python
1from person_pb2 import Person
2
3person = Person()
4phone = person.phones.add()
5phone.number = "123-456"
6
7print(person)

add() creates a new child message in the container and returns it so you can populate its fields.

That is the protobuf-native pattern. It keeps the parent and child relationship consistent.

Why append() Fails

This fails for repeated composite fields:

python
person = Person()
person.phones.append({"number": "123-456"})

It fails because:

  • the container is not a normal Python list
  • the item is not a protobuf message instance
  • protobuf expects message-aware mutation methods

Even if you already created a PhoneNumber object, append() is not the method to assume.

Safe Ways to Populate Repeated Message Fields

Build with add()

python
1person = Person()
2
3phone = person.phones.add()
4phone.number = "123-456"
5
6phone = person.phones.add()
7phone.number = "999-000"

Copy from existing message objects

If you already have a populated message, use CopyFrom on a newly added element.

python
1from person_pb2 import Person, PhoneNumber
2
3person = Person()
4
5external = PhoneNumber()
6external.number = "555-111"
7
8person.phones.add().CopyFrom(external)
9print(person)

That pattern is explicit and works well when building messages in stages.

Repeated Scalar Fields Are Different

A repeated scalar field such as repeated int32 ids = 1; behaves differently from repeated message fields. Many developers learn protobuf from scalar examples and then expect the same methods to work for repeated messages.

That expectation is what usually causes this error.

If the field is composite, think in terms of "add a child message" rather than "append a list item."

Inspect the Field Type When Debugging

When unsure, inspect the container and one expected item type.

python
print(type(person.phones))

You can also inspect the message descriptor if the generated module is unfamiliar:

python
print(Person.DESCRIPTOR)

That makes it obvious whether the field is repeated scalar or repeated message.

Avoid Dictionary Shortcuts

A lot of Python code tries to construct protobuf data by passing dictionaries around. That is fine for some higher-level libraries, but generated protobuf objects are stricter.

Prefer direct message construction:

python
person = Person()
phone = person.phones.add()
phone.number = "123-456"

This is more verbose than a loose dictionary append, but it is type-safe and serialization-safe.

Version Awareness

If you find old examples online, pay attention to protobuf version differences and generated-code conventions. The safest rule is still the same: when the field is a repeated message field, start with add() and work from there.

Do not build your mental model from generic Python list methods. Build it from the protobuf message API.

Common Pitfalls

  • Treating repeated protobuf message fields like plain Python lists.
  • Trying to append() dictionaries or arbitrary objects.
  • Confusing repeated scalar fields with repeated composite fields.
  • Building child messages externally without using CopyFrom where needed.
  • Following list-based examples that were not written for protobuf containers.

Summary

  • Repeated protobuf message fields are not ordinary Python lists.
  • For repeated composite fields, use add() to create a new child message.
  • Populate the returned message directly or use CopyFrom with an existing message.
  • Do not assume list methods such as append() will exist for composite containers.
  • When debugging, inspect the generated field type and treat protobuf containers as protobuf APIs, not generic lists.

Course illustration
Course illustration

All Rights Reserved.