使用 etcd 和 grpc 遇到的版本衝突的那些事兒

xiaoma_nmg發表於2020-04-26

近來在學習etcd,拿到一份程式碼的demo.想跑起來看看效果。沒想過這竟然是個艱難的過程,記錄下來,以便大家遇到同樣的問題時,可以快速解決。

protoc –go_out=plugins=grpc:. *.proto

報錯如下:

2020/04/26 16:33:39 WARNING: Missing 'go_package' option in "hello.proto", please specify:
        option go_package = ".;protoes";
A future release of protoc-gen-go will require this be specified.
See https://developers.google.com/protocol-buffers/docs/reference/go-generated#package for more information.

這個比較好解決,按照提示把第3行改為第4行,如下圖

使用etcd和grpc遇到的版本衝突的那些事兒

go.mod目錄下執行 go mod tidy

報錯如下:

go: finding golang.org/x/time latest
go: finding github.com/golang/groupcache latest
go: etcdDemo/etcdservice imports
        go.etcd.io/etcd/clientv3 tested by
        go.etcd.io/etcd/clientv3.test imports
        github.com/coreos/etcd/auth imports
        github.com/coreos/etcd/mvcc/backend imports
        github.com/coreos/bbolt: github.com/coreos/bbolt@v1.3.4: parsing go.mod:
        module declares its path as: go.etcd.io/bbolt
                but was required as: github.com/coreos/bbolt

在go.mod中新增兩行

replace github.com/coreos/bbolt v1.3.4 => go.etcd.io/bbolt v1.3.4
replace go.etcd.io/bbolt v1.3.4 => github.com/coreos/bbolt v1.3.4

再次執行 go mod tidy, 再次報錯如下:

go: finding golang.org/x/net latest
go: finding github.com/coreos/go-systemd latest
go: finding github.com/coreos/pkg latest
go: finding golang.org/x/time latest
go: finding github.com/xiang90/probing latest
go: finding github.com/tmc/grpc-websocket-proxy latest
go: finding github.com/golang/groupcache latest
etcdDemo/etcdservice imports
        go.etcd.io/etcd/clientv3 imports
        github.com/coreos/etcd/pkg/logutil imports
        github.com/coreos/go-systemd/journal: no matching versions for query "latest"

go 1.13 的版本導致的 (go 1.14應該沒有)
解決方法:在go.mod 中新增

replace github.com/coreos/go-systemd => github.com/coreos/go-systemd/v22 v22.0.0

再次go mod tidy , 這一項暫時通過了。

執行go build

報錯如下:

D:\code\etcdDemo\server>go build
# github.com/coreos/etcd/clientv3/balancer/resolver/endpoint
E:\gocode\pkg\mod\github.com\coreos\etcd@v3.3.20+incompatible\clientv3\balancer\resolver\endpoint\endpoint.go:114:78: undefined: resolver.BuildOption
E:\gocode\pkg\mod\github.com\coreos\etcd@v3.3.20+incompatible\clientv3\balancer\resolver\endpoint\endpoint.go:182:31: undefined: resolver.ResolveNowOption
# github.com/coreos/etcd/clientv3/balancer/picker
E:\gocode\pkg\mod\github.com\coreos\etcd@v3.3.20+incompatible\clientv3\balancer\picker\err.go:37:44: undefined: balancer.PickOptions
E:\gocode\pkg\mod\github.com\coreos\etcd@v3.3.20+incompatible\clientv3\balancer\picker\roundrobin_balanced.go:55:54: undefined: balancer.PickOptions

原因etcd3.3.20的release版本要求grpc的版本是 v1.26.0 之前的。而此時go.mod裡面的 google.golang.org/grpc 是 v1.29.1
解決方法:在go.mod 裡新增一句

replace google.golang.org/grpc => google.golang.org/grpc v1.26.0

go build 接著報錯,如下:

D:\code\etcdDemo\server>go build
# etcdDemo/protoes
..\protoes\hello.pb.go:292:11: undefined: grpc.SupportPackageIsVersion6
..\protoes\hello.pb.go:303:5: undefined: grpc.ClientConnInterface
# etcdDemo/etcdservice
..\etcdservice\resolver.go:82:4: invalid case "go.etcd.io/etcd/mvcc/mvccpb".PUT in switch on ev.Type (mismatched types "go.etcd.io/etcd/mvcc/mvccpb".Event_EventType and "github.com/coreos/etcd/mvcc/mvccpb".
Event_EventType)
..\etcdservice\resolver.go:87:4: invalid case "go.etcd.io/etcd/mvcc/mvccpb".DELETE in switch on ev.Type (mismatched types "go.etcd.io/etcd/mvcc/mvccpb".Event_EventType and "github.com/coreos/etcd/mvcc/mvccp
b".Event_EventType)

原因:此時裝置上的 proto-gen-go 是v1.4.0版本,它要求 grpc的版本是 v1.27.0往後的,而剛才etcd要求 grpc 是v.1.26.0 ! 無奈了,柿子挑軟的捏吧,把proto-gen-go 降級到能夠匹配grpc v.1.26.0的版本。執行下面這條命令

go get -u -v github.com/golang/protobuf/protoc-gen-go@v1.2.0

之後千萬別忘了,重新生成proto
繼續 go build, 繼續報錯!!! (心態有點兒崩了。。。)

D:\code\etcdDemo\server>go build
go: finding google.golang.org/genproto latest
go: finding github.com/golang/protobuf v1.3.3
# etcdDemo/etcdservice
..\etcdservice\resolver.go:82:4: invalid case "go.etcd.io/etcd/mvcc/mvccpb".PUT in switch on ev.Type (mismatched types "go.etcd.io/etcd/mvcc/mvccpb".Event_EventType and "github.com/coreos/etcd/mvcc/mvccpb".
Event_EventType)
..\etcdservice\resolver.go:87:4: invalid case "go.etcd.io/etcd/mvcc/mvccpb".DELETE in switch on ev.Type (mismatched types "go.etcd.io/etcd/mvcc/mvccpb".Event_EventType and "github.com/coreos/etcd/mvcc/mvccp
b".Event_EventType)
..\etcdservice\resolver.go:82:4: invalid case "go.etcd.io/etcd/mvcc/mvccpb".PUT in switch on ev.Type (mismatched types "go.etcd.io/etcd/mvcc/mvccpb".Event_EventTyp
Event_EventType)
..\etcdservice\resolver.go:87:4: invalid case "go.etcd.io/etcd/mvcc/mvccpb".DELETE in switch on ev.Type (mismatched types "go.etcd.io/etcd/mvcc/mvccpb".Event_Event
b".Event_EventType)

緩緩。。。
仔細看了一下報錯的內容,編譯器要求 mvccpb 使用 github.com/coreos/etcd/mvcc/mvccpb 這個包,而程式碼中使用的是
go.etcd.io/etcd/mvcc/mvccpb 。去對應的程式碼檔案看了一下,果然是這樣。按照要求,把github.com/coreos/etcd/mvcc/mvccpb import 進來。
繼續 go build, 終於

使用etcd和grpc遇到的版本衝突的那些事兒
那一刻,世界彷彿清靜了許多。
對於程式設計師來說,最美好的事,莫過於no warning, no error

本作品採用《CC 協議》,轉載必須註明作者和本文連結

相關文章