5

我是 Go 和 Protobufs 的新手,因此这可能是一个非常菜鸟的问题。对此感到抱歉。

我的 go 项目中有几个包,我想创建一个单独的包,其中包含我所有的 .proto(也是 .pb.go)文件,然后我可以将这些 proto 文件导入任何其他包中,以更好地管理我的所有 proto 文件。

但是当我将我的 proto 文件移动到一个名为“prototemps”的单独包中并将“prototemps”导入另一个名为“reader”的包中时。在 reader.go 中,我这样做:

    sensorData := &prototemps.Sensor{}
    err := proto.Unmarshal(msg.Payload(), sensorData) 

它产生这个错误

var sensorData *prototemps.Sensor
cannot use sensorData (variable of type *prototemps.Sensor) as protoreflect.ProtoMessage value in argument to proto.Unmarshal: missing method ProtoReflect

这是我的项目结构的样子:

ProjectFolder/
 /prototemps/<all .proto and .pb.go exist here>  (Package "prototemps")
 /reader/reader.go which fails when tries to do proto.Unmarshall (Package "reader")

这是我的 .proto 的样子

syntax="proto3";
package prototemps;

import "google/protobuf/timestamp.proto";

message sensor {
      string Name = 1;
      int32 ID = 2;
      string Type = 3;
      orientation Ori = 4;
      IO IO = 5;
      google.protobuf.Timestamp ts = 6;
}

message orientation {
      int32 X = 1;
      int32 Y = 2;
      int32 Z = 3;
}

message IO {
      int32 Reads = 1;
      int32 Writes = 2;
}

这是我使用 * protoc --go_out= 生成的 .pb.go。.proto

// Code generated by protoc-gen-go. DO NOT EDIT.
// source: sensorData.proto

package prototemps

import (
    fmt "fmt"
    proto "github.com/golang/protobuf/proto"
    timestamppb "google.golang.org/protobuf/types/known/timestamppb"
    math "math"
)

// Reference imports to suppress errors if they are not otherwise used.
var _ = proto.Marshal
var _ = fmt.Errorf
var _ = math.Inf

// This is a compile-time assertion to ensure that this generated file
// is compatible with the proto package it is being compiled against.
// A compilation error at this line likely means your copy of the
// proto package needs to be updated.
const _ = proto.ProtoPackageIsVersion3 // please upgrade the proto package

type Sensor struct {
    Name                 string                 `protobuf:"bytes,1,opt,name=Name,proto3" json:"Name,omitempty"`
    ID                   int32                  `protobuf:"varint,2,opt,name=ID,proto3" json:"ID,omitempty"`
    Type                 string                 `protobuf:"bytes,3,opt,name=Type,proto3" json:"Type,omitempty"`
    Ori                  *Orientation           `protobuf:"bytes,4,opt,name=Ori,proto3" json:"Ori,omitempty"`
    IO                   *IO                    `protobuf:"bytes,5,opt,name=IO,proto3" json:"IO,omitempty"`
    Ts                   *timestamppb.Timestamp `protobuf:"bytes,6,opt,name=ts,proto3" json:"ts,omitempty"`
    XXX_NoUnkeyedLiteral struct{}               `json:"-"`
    XXX_unrecognized     []byte                 `json:"-"`
    XXX_sizecache        int32                  `json:"-"`
}

func (m *Sensor) Reset()         { *m = Sensor{} }
func (m *Sensor) String() string { return proto.CompactTextString(m) }
func (*Sensor) ProtoMessage()    {}
func (*Sensor) Descriptor() ([]byte, []int) {
    return fileDescriptor_a3adf506f94bdd26, []int{0}
}

func (m *Sensor) XXX_Unmarshal(b []byte) error {
    return xxx_messageInfo_Sensor.Unmarshal(m, b)
}
func (m *Sensor) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
    return xxx_messageInfo_Sensor.Marshal(b, m, deterministic)
}
func (m *Sensor) XXX_Merge(src proto.Message) {
    xxx_messageInfo_Sensor.Merge(m, src)
}
func (m *Sensor) XXX_Size() int {
    return xxx_messageInfo_Sensor.Size(m)
}
func (m *Sensor) XXX_DiscardUnknown() {
    xxx_messageInfo_Sensor.DiscardUnknown(m)
}

var xxx_messageInfo_Sensor proto.InternalMessageInfo

func (m *Sensor) GetName() string {
    if m != nil {
        return m.Name
    }
    return ""
}

func (m *Sensor) GetID() int32 {
    if m != nil {
        return m.ID
    }
    return 0
}

func (m *Sensor) GetType() string {
    if m != nil {
        return m.Type
    }
    return ""
}

func (m *Sensor) GetOri() *Orientation {
    if m != nil {
        return m.Ori
    }
    return nil
}

func (m *Sensor) GetIO() *IO {
    if m != nil {
        return m.IO
    }
    return nil
}

func (m *Sensor) GetTs() *timestamppb.Timestamp {
    if m != nil {
        return m.Ts
    }
    return nil
}

type Orientation struct {
    X                    int32    `protobuf:"varint,1,opt,name=X,proto3" json:"X,omitempty"`
    Y                    int32    `protobuf:"varint,2,opt,name=Y,proto3" json:"Y,omitempty"`
    Z                    int32    `protobuf:"varint,3,opt,name=Z,proto3" json:"Z,omitempty"`
    XXX_NoUnkeyedLiteral struct{} `json:"-"`
    XXX_unrecognized     []byte   `json:"-"`
    XXX_sizecache        int32    `json:"-"`
}

func (m *Orientation) Reset()         { *m = Orientation{} }
func (m *Orientation) String() string { return proto.CompactTextString(m) }
func (*Orientation) ProtoMessage()    {}
func (*Orientation) Descriptor() ([]byte, []int) {
    return fileDescriptor_a3adf506f94bdd26, []int{1}
}

func (m *Orientation) XXX_Unmarshal(b []byte) error {
    return xxx_messageInfo_Orientation.Unmarshal(m, b)
}
func (m *Orientation) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
    return xxx_messageInfo_Orientation.Marshal(b, m, deterministic)
}
func (m *Orientation) XXX_Merge(src proto.Message) {
    xxx_messageInfo_Orientation.Merge(m, src)
}
func (m *Orientation) XXX_Size() int {
    return xxx_messageInfo_Orientation.Size(m)
}
func (m *Orientation) XXX_DiscardUnknown() {
    xxx_messageInfo_Orientation.DiscardUnknown(m)
}

var xxx_messageInfo_Orientation proto.InternalMessageInfo

func (m *Orientation) GetX() int32 {
    if m != nil {
        return m.X
    }
    return 0
}

func (m *Orientation) GetY() int32 {
    if m != nil {
        return m.Y
    }
    return 0
}

func (m *Orientation) GetZ() int32 {
    if m != nil {
        return m.Z
    }
    return 0
}

type IO struct {
    Reads                int32    `protobuf:"varint,1,opt,name=Reads,proto3" json:"Reads,omitempty"`
    Writes               int32    `protobuf:"varint,2,opt,name=Writes,proto3" json:"Writes,omitempty"`
    XXX_NoUnkeyedLiteral struct{} `json:"-"`
    XXX_unrecognized     []byte   `json:"-"`
    XXX_sizecache        int32    `json:"-"`
}

func (m *IO) Reset()         { *m = IO{} }
func (m *IO) String() string { return proto.CompactTextString(m) }
func (*IO) ProtoMessage()    {}
func (*IO) Descriptor() ([]byte, []int) {
    return fileDescriptor_a3adf506f94bdd26, []int{2}
}

func (m *IO) XXX_Unmarshal(b []byte) error {
    return xxx_messageInfo_IO.Unmarshal(m, b)
}
func (m *IO) XXX_Marshal(b []byte, deterministic bool) ([]byte, error) {
    return xxx_messageInfo_IO.Marshal(b, m, deterministic)
}
func (m *IO) XXX_Merge(src proto.Message) {
    xxx_messageInfo_IO.Merge(m, src)
}
func (m *IO) XXX_Size() int {
    return xxx_messageInfo_IO.Size(m)
}
func (m *IO) XXX_DiscardUnknown() {
    xxx_messageInfo_IO.DiscardUnknown(m)
}

var xxx_messageInfo_IO proto.InternalMessageInfo

func (m *IO) GetReads() int32 {
    if m != nil {
        return m.Reads
    }
    return 0
}

func (m *IO) GetWrites() int32 {
    if m != nil {
        return m.Writes
    }
    return 0
}

func init() {
    proto.RegisterType((*Sensor)(nil), "prototemps.sensor")
    proto.RegisterType((*Orientation)(nil), "prototemps.orientation")
    proto.RegisterType((*IO)(nil), "prototemps.IO")
}

func init() {
    proto.RegisterFile("sensorData.proto", fileDescriptor_a3adf506f94bdd26)
}

var fileDescriptor_a3adf506f94bdd26 = []byte{
    // 259 bytes of a gzipped FileDescriptorProto
    0x1f, 0x8b, 0x08, 0x00, 0x00, 0x09, 0x6e, 0x88, 0x02, 0xff, 0x4c, 0x8e, 0xcf, 0x4a, 0xc3, 0x40,
    0x10, 0xc6, 0xd9, 0xb4, 0x09, 0x38, 0x95, 0x22, 0x83, 0xe8, 0xd2, 0x83, 0x4a, 0x4e, 0xea, 0x61,
    0x0b, 0xf5, 0xe0, 0x0b, 0xf4, 0xd2, 0x8b, 0x81, 0xa5, 0x60, 0xdb, 0xdb, 0x16, 0xd7, 0xb2, 0x60,
    0xb2, 0x61, 0x77, 0x3c, 0xf8, 0x64, 0xbe, 0x9e, 0xfb, 0x27, 0xc5, 0x9c, 0x32, 0xdf, 0xe4, 0x37,
    0xdf, 0xfe, 0xe0, 0xca, 0xeb, 0xce, 0x5b, 0xb7, 0x56, 0xa4, 0x44, 0xef, 0x2c, 0x59, 0x84, 0xf4,
    0x21, 0xdd, 0xf6, 0x7e, 0x71, 0x7f, 0xb2, 0xf6, 0xf4, 0xa5, 0x97, 0x69, 0x75, 0xfc, 0xfe, 0x5c,
    0x92, 0x69, 0xb5, 0x27, 0xd5, 0xf6, 0x19, 0xae, 0x7f, 0x19, 0x54, 0xb9, 0x01, 0x11, 0xa6, 0x6f,
    0xaa, 0xd5, 0x9c, 0x3d, 0xb0, 0xc7, 0x0b, 0x99, 0x66, 0x9c, 0x43, 0xb1, 0x59, 0xf3, 0x22, 0x6c,
    0x4a, 0x19, 0xa6, 0xc8, 0x6c, 0x7f, 0x7a, 0xcd, 0x27, 0x99, 0x89, 0x33, 0x3e, 0xc1, 0xa4, 0x71,
    0x86, 0x4f, 0xc3, 0x6a, 0xb6, 0xba, 0x15, 0xff, 0xaf, 0x0b, 0xeb, 0x8c, 0xee, 0x48, 0x91, 0xb1,
    0x9d, 0x8c, 0x0c, 0xde, 0x85, 0xba, 0x86, 0x97, 0x89, 0x9c, 0x8f, 0xc9, 0x4d, 0x13, 0xea, 0x1b,
    0x7c, 0x86, 0x82, 0x3c, 0xaf, 0xd2, 0xff, 0x85, 0xc8, 0xee, 0xe2, 0xec, 0x2e, 0xb6, 0x67, 0x77,
    0x19, 0xa8, 0xfa, 0x15, 0x66, 0xa3, 0x7e, 0xbc, 0x04, 0xb6, 0x4b, 0xea, 0xa5, 0x64, 0xbb, 0x98,
    0xf6, 0x83, 0x36, 0xdb, 0xc7, 0x74, 0x48, 0xca, 0x21, 0x1d, 0xea, 0x55, 0x94, 0xc0, 0x6b, 0x28,
    0xa5, 0x56, 0x1f, 0x7e, 0xb8, 0xc9, 0x01, 0x6f, 0xa0, 0x7a, 0x77, 0x86, 0xb4, 0x1f, 0x8e, 0x87,
    0x74, 0xac, 0x92, 0xc4, 0xcb, 0x5f, 0x00, 0x00, 0x00, 0xff, 0xff, 0xa3, 0x7e, 0xde, 0x40, 0x6e,
    0x01, 0x00, 0x00,
}

任何帮助将不胜感激,谢谢!

4

3 回答 3

4

如果您对 protoc-gen-go 版本感到满意,您可能只想更改调用的go导入位置。proto.Unmarshal我知道有两种选择:

  • "github.com/golang/protobuf/proto"

  • "google.golang.org/protobuf/proto"

试试你没有的那个。希望对其他人也有帮助!

于 2021-01-29T22:33:08.920 回答
3

错误消息说变量sensorData缺少方法ProtoReflect。检查生成的文件,这是正确的。类型上没有这样的方法Sensor

在我看来,您在使用不同版本的 Go protobuf 时遇到问题。确保您使用与*.pb.go用于编组/解组的文件相同的版本来生成文件。

现在 Go 世界中有不同的包不兼容,因为 API 发生了重大变化:https ://blog.golang.org/protobuf-apiv2

如果您从 protobuf 开始,我肯定会尝试使用新包。确保您遵循的任何介绍都使用您正在使用的包。

于 2021-01-04T13:46:11.217 回答
-1

检查您的 $GOPATH/bin 并查看是否有名为 proto-gen-go-grpc 的二进制文件

如果是这样,请尝试运行以下命令

protoc --go_out=. --go-grpc_out=. .proto

--go_out 仅在 go lang 中生成 protobuf,但不会生成 gGRPC 方法

于 2021-01-04T14:54:12.177 回答