背景
Bazelで依存関係を管理している環境で、celライブラリを導入したところ次のようなエラーが発生しました。
'@com_github_google_cel_go//cel:cel': target 'cel' not declared in package 'cel' defined by /external/com_github_google_cel_go/cel/BUILD.bazel and referenced by '@com_github_bufbuild_protovalidate_go//internal/celext:celext' '@com_github_google_cel_go//common/overloads:overloads': target 'overloads' not declared in package 'common/overloads' defined by /external/com_github_google_cel_go/common/overloads/BUILD.bazel and referenced by '@com_github_bufbuild_protovalidate_go//internal/celext:celext' '@com_github_google_cel_go//common/types:types': target 'types' not declared in package 'common/types' defined by /external/com_github_google_cel_go/common/types/BUILD.bazel and referenced by '@com_github_bufbuild_protovalidate_go//internal/celext:celext' '@com_github_google_cel_go//common/types/ref:ref': target 'ref' not declared in package 'common/types/ref' defined by /external/com_github_google_cel_go/common/types/ref/BUILD.bazel and referenced by '@com_github_bufbuild_protovalidate_go//internal/celext:celext' '@com_github_google_cel_go//common/types/traits:traits': target 'traits' not declared in package 'common/types/traits' defined by /external/com_github_google_cel_go/common/types/traits/BUILD.bazel and referenced by '@com_github_bufbuild_protovalidate_go//internal/celext:celext' '@com_github_google_cel_go//ext:ext': target 'ext' not declared in package 'ext' defined by /external/com_github_google_cel_go/ext/BUILD.bazel and referenced by '@com_github_bufbuild_protovalidate_go//internal/celext:celext' '@com_github_google_cel_go//cel:cel': target 'cel' not declared in package 'cel' defined by /external/com_github_google_cel_go/cel/BUILD.bazel and referenced by '@com_github_bufbuild_protovalidate_go//internal/expression:expression' '@com_github_google_cel_go//interpreter:interpreter': target 'interpreter' not declared in package 'interpreter' defined by /external/com_github_google_cel_go/interpreter/BUILD.bazel and referenced by '@com_github_bufbuild_protovalidate_go//internal/expression:expression' '@com_github_google_cel_go//cel:cel': target 'cel' not declared in package 'cel' defined by /external/com_github_google_cel_go/cel/BUILD.bazel and referenced by '@com_github_bufbuild_protovalidate_go//internal/constraints:constraints' '@com_github_google_cel_go//cel:cel': target 'cel' not declared in package 'cel' defined by /external/com_github_google_cel_go/cel/BUILD.bazel and referenced by '@com_github_bufbuild_protovalidate_go//internal/evaluator:evaluator'
これはcel-goに依存していた場合のBazelのターゲットの記述が本来は
go_library(
...
deps = [
...
"@com_github_google_cel_go//cel:go_default_library",
...
],
)
であるべきが、gazelleを使ったところ
go_library(
...
deps = [
...
"@com_github_google_cel_go//cel",
...
],
)
となってターゲットの記述が不適切になってしまったせいです。
今回はこの回避策方法について説明します。
環境
- Bazel v6.5.0
- bazel-gazelle v0.35.0
原因詳細
cel-goはBazelを使っており、中でBUILD.bazel
を持っています。
go_library( name = "go_default_library", srcs = [ "cel.go", "decls.go", "env.go", "folding.go", "io.go", "inlining.go", "library.go", "macro.go", "optimizer.go", "options.go", "program.go", "validator.go", ], importpath = "github.com/google/cel-go/cel", ...
従ってこれに依存する場合、Bazelのターゲット名はgithub.com/google/cel-go/cel:go_default_library
となります。
しかしGoの一般的なライブラリはBazelを使っておらず、gazelleがそれを考慮してくれないため
"@com_github_google_cel_go//cel", "@com_github_google_uuid//:uuid",
のように処理してしまうのが原因です。
対応方法
2つの方法を紹介します。
方法1:手動でターゲット名を設定してkeepを付ける
gazelleは# keep
があればそこを変更しないので、
go_library( .... deps = [ ... "@com_github_google_cel_go//cel:go_default_library", # keep ... ], )
や
# keep go_library( .... deps = [ ... "@com_github_google_cel_go//cel:go_default_library", ... ], )
といった記述にすることでターゲット名であるgo_default_library
が削られるのを防げます。
しかしこれは
- 前者であればcel-goの別pkgが必要となったときに都度対応が必要になる
- 後者であれば他の依存ライブラリがgazelleで更新されなくなる
といった課題がありあまりよくありません。
方法2:deps.bzl
を編集する
cel-goのdeps.bzl
は次のようになっていますが、
go_repository( name = "com_github_google_cel_go", build_file_proto_mode = "disable_global", importpath = "github.com/google/cel-go", sum = "h1:nDx9r8S3L4pE61eDdt8igGj8rf5kjYR3ILxWIpWNi84=", version = "v0.20.1", )
これにbuild_naming_convention
を付けます。
go_repository( name = "com_github_google_cel_go", build_file_proto_mode = "disable_global", build_naming_convention = "go_default_library", # ここ importpath = "github.com/google/cel-go", sum = "h1:nDx9r8S3L4pE61eDdt8igGj8rf5kjYR3ILxWIpWNi84=", version = "v0.20.1", )
こうするとgazelleが解釈してくれて、BUILD.bazel
も"@com_github_google_cel_go//cel:go_default_library"
となってくれます。
まとめ
Bazelを使っているライブラリに依存していた場合、ターゲット名がうまく解釈されない場合の対応方法を紹介しました。