Quellcode durchsuchen

goprotobuf: Handle nils in repeated message fields in text formatting.

Previously this code would panic. A nil in a repeated message field is,
strictly speaking, invalid, but text formatting is often used for debugging,
and it's much more useful to generate "<nil>" than to panic.

LGTM=r
R=r
CC=golang-codereviews
https://codereview.appspot.com/87960043
David Symonds vor 11 Jahren
Ursprung
Commit
4b9d2e1e38
2 geänderte Dateien mit 31 neuen und 1 gelöschten Zeilen
  1. 10 1
      proto/text.go
  2. 21 0
      proto/text_test.go

+ 10 - 1
proto/text.go

@@ -232,7 +232,16 @@ func writeStruct(w *textWriter, sv reflect.Value) error {
 						return err
 					}
 				}
-				if err := writeAny(w, fv.Index(j), props); err != nil {
+				v := fv.Index(j)
+				if v.Kind() == reflect.Ptr && v.IsNil() {
+					// A nil message in a repeated field is not valid,
+					// but we can handle that more gracefully than panicking.
+					if _, err := w.Write([]byte("<nil>\n")); err != nil {
+						return err
+					}
+					continue
+				}
+				if err := writeAny(w, v, props); err != nil {
 					return err
 				}
 				if err := w.WriteByte('\n'); err != nil {

+ 21 - 0
proto/text_test.go

@@ -385,3 +385,24 @@ func TestFloats(t *testing.T) {
 		}
 	}
 }
+
+func TestRepeatedNilText(t *testing.T) {
+	m := &pb.MessageList{
+		Message: []*pb.MessageList_Message{
+			nil,
+			&pb.MessageList_Message{
+				Name: proto.String("Horse"),
+			},
+			nil,
+		},
+	}
+	want := `Message <nil>
+Message {
+  name: "Horse"
+}
+Message <nil>
+`
+	if s := proto.MarshalTextString(m); s != want {
+		t.Errorf(" got: %s\nwant: %s", s, want)
+	}
+}