I have several protobuf files that share some message names and for this reason I cannot have all the generated go files in one folder as I run into issues like "..re-declared in this block". I attached a minimal go project how to reproduce this issue. The structure of the project is like below:
protos/myMessages/Folder0/MyMessage0.proto
syntax = "proto2";
package myMessages.Folder0;
option go_package = "myMessages/Folder0";
message Message0 {
optional uint32 payload = 1;
}
protos/myMessages/Folder1/MyMessage1.proto
syntax = "proto2";
package myMessages.Folder1;
option go_package = "myMessages/Folder1";
message Message0 {
optional uint32 payload = 1;
}
protos/myMessages/helloworld.proto
syntax = "proto2";
package myMessages;
option go_package = "./;gen";
import "myMessages/Folder0/MyMessage0.proto";
import "myMessages/Folder1/MyMessage1.proto";
service Greeter {
rpc SayHello1 (myMessages.Folder0.Message0) returns (myMessages.Folder0.Message0) {}
rpc SayHello2 (myMessages.Folder1.Message0) returns (myMessages.Folder1.Message0) {}
}
main.go
package main
import (
"context"
"flag"
"fmt"
"log"
"net"
"google.golang.org/grpc"
pb0 "main/build/myMessages/Folder0"
pb1 "main/build/myMessages/Folder1"
pb "main/build"
)
var (
port = flag.Int("port", 50051, "The server port")
)
// server is used to implement helloworld.GreeterServer.
type server struct {
pb.UnimplementedGreeterServer
}
func (s *server) SayHello1(ctx context.Context, in *pb0.Message0) (*pb0.Message0, error) {
return &pb0.Message0{}, nil
}
func (s *server) SayHello2(ctx context.Context, in *pb1.Message0) (*pb1.Message0, error) {
return &pb1.Message0{}, nil
}
func main() {
flag.Parse()
lis, err := net.Listen("tcp", fmt.Sprintf(":%d", *port))
if err != nil {
log.Fatalf("failed to listen: %v", err)
}
s := grpc.NewServer()
pb.RegisterGreeterServer(s, &server{})
log.Printf("server listening at %v", lis.Addr())
if err := s.Serve(lis); err != nil {
log.Fatalf("failed to serve: %v", err)
}
}
Makefile
all: build protos
protos:
protoc -Iprotos --go_out=build protos/myMessages/Folder0/MyMessage0.proto
protoc -Iprotos --go_out=build protos/myMessages/Folder1/MyMessage1.proto
protoc -Iprotos --go_out=build --go-grpc_out=build protos/helloworld.proto
go build -o build/server main.go
build:
mkdir -p build
After I run the make
command, I get the error below:
mkdir -p build
protoc -Iprotos --go_out=build protos/myMessages/Folder0/MyMessage0.proto
protoc -Iprotos --go_out=build protos/myMessages/Folder1/MyMessage1.proto
protoc -Iprotos --go_out=build --go-grpc_out=build protos/helloworld.proto
go build -o build/server main.go
build/helloworld.pb.go:12:2: package myMessages/Folder0 is not in GOROOT (/home/andrei/env/gosdk/go1.17.2/src/myMessages/Folder0)
build/helloworld.pb.go:13:2: package myMessages/Folder1 is not in GOROOT (/home/andrei/env/gosdk/go1.17.2/src/myMessages/Folder1)
make: *** [Makefile:21: protos] Error 1
The generated build/helloworld.pb.go
and build/helloworld_grpc.pb.go
files have the following imports:
import (
Folder0 "myMessages/Folder0"
Folder1 "myMessages/Folder1"
)
But if I change these to the following then it works:
import (
Folder0 "main/build/myMessages/Folder0"
Folder1 "main/build/myMessages/Folder1"
)
What's the correct way to organise this code to avoid manually adding the main/build
prefix to the imports in the generated files?