After some research, I solved my own problem.
sample:
package reflect
import (
"fmt"
protoOld "github.com/golang/protobuf/proto"
"github.com/zhaochuninhefei/myproto-go/owner"
"google.golang.org/protobuf/proto"
"reflect"
)
func doReflect() {
owner1 := &owner.Owner{
OwnerId: 1,
OwnerName: "owner1",
OwnerDesc: "just test",
}
fmt.Printf("owner1: %s\n", owner1)
oldReflect(owner1)
newReflect(owner1)
}
func oldReflect(msg protoOld.Message) {
pmVal := reflect.ValueOf(msg)
if pmVal.Kind() != reflect.Ptr {
fmt.Println("error in oldReflect 1")
return
}
if pmVal.IsNil() {
fmt.Println("error in oldReflect 2")
return
}
mVal := pmVal.Elem()
if mVal.Kind() != reflect.Struct {
fmt.Println("error in oldReflect 3")
return
}
protoProps := protoOld.GetProperties(mVal.Type())
fmt.Println("----- oldReflect:")
for _, prop := range protoProps.Prop {
fmt.Println(prop)
}
}
func newReflect(msg proto.Message) {
m := msg.ProtoReflect()
fds := m.Descriptor().Fields()
fmt.Println("----- newReflect:")
for k := 0; k < fds.Len(); k++ {
fd := fds.Get(k)
fmt.Println(fd)
}
}
"protoOld.GetProperties" in oldReflect is deprecated.
And we can use "msg.ProtoReflect().Descriptor().Fields()" in newReflect instead.
Execution results of the test cases of the sample code (doReflect) is:
/usr/golang/go_1.17.5/bin/go tool test2json -t /tmp/GoLand/___Test_doReflect_in_github_com_zhaochuninhefei_myproto_test_reflect.test -test.v -test.paniconexit0 -test.run ^\QTest_doReflect\E$
=== RUN Test_doReflect
owner1: owner_id:1 owner_name:"owner1" owner_desc:"just test"
----- oldReflect:
,0,name=XXX_state
,0,name=XXX_sizeCache
,0,name=XXX_unknownFields
varint,1,opt,name=owner_id,json=ownerId,proto3
bytes,2,opt,name=owner_name,json=ownerName,proto3
bytes,16,opt,name=owner_desc,json=ownerDesc,proto3
----- newReflect:
FieldDescriptor{Syntax: proto3, FullName: owner.Owner.owner_id, Number: 1, Cardinality: optional, Kind: int64, HasJSONName: true, JSONName: "ownerId"}
FieldDescriptor{Syntax: proto3, FullName: owner.Owner.owner_name, Number: 2, Cardinality: optional, Kind: string, HasJSONName: true, JSONName: "ownerName"}
FieldDescriptor{Syntax: proto3, FullName: owner.Owner.owner_desc, Number: 16, Cardinality: optional, Kind: string, HasJSONName: true, JSONName: "ownerDesc"}
--- PASS: Test_doReflect (0.00s)
PASS
Process finished with the exit code 0
Note how they differ, especially the fields starting with "XXX_".