My library supports Bazel builds and has a dependency from Maven Central. A user of my library wants to use a newer version of a dependency that has new transitive dependencies. How can that be done?
gRPC 1.17 depends on Guava 26. However, Guava 27 added a dependency on com.google.guava:failureaccess
. Normally an application using gRPC would just make their own native.maven_jar()
with the new version and disable gRPC's call to native.maven_jar()
. This would then "upgrade" the @com_google_guava_guava
repository that is then consumed by both gRPC and the application.
But @com_google_guava_guava
does not include dependency information. That is commonly solved by having third_party java_library()
s that stitch the transitive dependencies together. However, those java_library()
s can't be changed by the application.
I believe that bind()
would solve this problem, as gRPC could depend on //external:com_google_guava_guava
which could be a java_library()
. But bind()
is discouraged.
答案 0 :(得分:1)
考虑了一段时间之后,我觉得bind()
可能是grpc-java提供此功能的最佳方法。我不知道现有的Maven转换工具中的任何功能可以简化此操作。
但是,如果用户希望在不更改grpc-java的情况下进行操作,则可以:
在WORKSPACE
中,用com_google_guava_guava
覆盖local_repository()
:
grpc_java_repositories(
omit_com_google_guava = True,
)
maven_jar(
name = "com_google_guava_guava_real",
artifact = "com.google.guava:guava:27.0.1-jre",
sha1 = "bd41a290787b5301e63929676d792c507bbc00ae",
)
maven_jar(
name = "com_google_guava_failureaccess",
artifact = "com.google.guava:failureaccess:1.0.1",
sha1 = "1dcf1de382a0bf95a3d8b0849546c88bac1292c9",
)
local_repository(
name = "com_google_guava_guava",
path = "guava_27",
)
创建一个子仓库,该子仓库显示兼容的java_library()
:
mkdir -p guava_27/jar
echo > guava_27/WORKSPACE
cat > guava_27/jar/BUILD.bazel << EOF
java_library(
name = "jar",
visibility = ["//visibility:public"],
exports = [
"@com_google_guava_failureaccess//jar",
"@com_google_guava_guava_real//jar",
],
)
EOF
答案 1 :(得分:1)
请考虑将您的库切换为使用java_import_external
而不是maven_jar
。
java_import_external
目标includes dependency information,因此允许应用程序取代目标的版本及其传递依赖项。
只需记住添加if native.existing_rule(name) == None:
在定义@com_google_guava_guava
之前,以便允许您的库用户使用更新了依赖性的较新版本的番石榴自己定义它。
答案 2 :(得分:0)
更新:rules_jvm_external
是Bazel团队的新规则集,用于可传递地获取和解决工件。
在这种情况下,WORKSPACE文件将包含以下内容:
load("@rules_jvm_external//:defs.bzl", "maven_install")
maven_install(
artifacts = [
"com.google.guava:guava:27.0.1-jre",
],
repositories = [
"https://jcenter.bintray.com",
]
)
这将自动解决并获取番石榴和failaccess工件。然后在BUILD文件中,您可以像这样直接依赖Guava:
java_library(
name = "my_jar",
srcs = # ...
deps = [
"@maven//com_google_guava_guava",
],
)