Skip to content

Commit

Permalink
Kotlin protos bazel (#290)
Browse files Browse the repository at this point in the history
* kt_jvm_proto_library proof of concept

* Document kt_jvm_proto_library

* Apply Bazel Kotlin proto rules to all examples
  • Loading branch information
aragos committed Oct 7, 2021
1 parent 1cde5bc commit 23c167a
Show file tree
Hide file tree
Showing 12 changed files with 210 additions and 24 deletions.
10 changes: 3 additions & 7 deletions WORKSPACE
Expand Up @@ -34,6 +34,7 @@ maven_install(
artifacts = [
"com.google.jimfs:jimfs:1.1",
"com.google.truth.extensions:truth-proto-extension:1.0.1",
"com.google.protobuf:protobuf-kotlin:3.18.0",
] + IO_GRPC_GRPC_KOTLIN_ARTIFACTS + IO_GRPC_GRPC_JAVA_ARTIFACTS,
generate_compat_repositories = True,
override_targets = dict(
Expand All @@ -56,16 +57,11 @@ grpc_java_repositories()

# Protocol Buffers
load("@com_google_protobuf//:protobuf_deps.bzl", "protobuf_deps")

protobuf_deps()

# Kotlin
load(
"@io_bazel_rules_kotlin//kotlin:kotlin.bzl",
"kotlin_repositories",
"kt_register_toolchains",
)

load("@io_bazel_rules_kotlin//kotlin:repositories.bzl", "kotlin_repositories")
kotlin_repositories()

load("@io_bazel_rules_kotlin//kotlin:core.bzl", "kt_register_toolchains")
kt_register_toolchains()
Expand Up @@ -10,6 +10,7 @@ kt_jvm_binary(
main_class = "io.grpc.examples.animals.AnimalsClientKt",
deps = [
"//examples/protos/src/main/proto/io/grpc/examples/animals:animals_kt_grpc",
"//examples/protos/src/main/proto/io/grpc/examples/animals:animals_kt_proto",
"@com_google_protobuf//:protobuf_java_util",
"@io_grpc_grpc_java//netty",
],
Expand Down
Expand Up @@ -10,6 +10,7 @@ kt_jvm_binary(
main_class = "io.grpc.examples.helloworld.HelloWorldClientKt",
deps = [
"//examples/protos/src/main/proto/io/grpc/examples/helloworld:hello_world_kt_grpc",
"//examples/protos/src/main/proto/io/grpc/examples/helloworld:hello_world_kt_proto",
"@io_grpc_grpc_java//netty",
],
)
Expand Up @@ -11,6 +11,7 @@ kt_jvm_binary(
resources = ["//examples/stub/src/main/resources/io/grpc/examples/routeguide:route_guide_db"],
deps = [
"//examples/protos/src/main/proto/io/grpc/examples/routeguide:route_guide_kt_grpc",
"//examples/protos/src/main/proto/io/grpc/examples/routeguide:route_guide_kt_proto",
"//examples/stub/src/main/kotlin/io/grpc/examples/routeguide:route_guide_stub",
"@com_google_protobuf//:protobuf_java_util",
"@io_grpc_grpc_java//netty",
Expand Down
@@ -1,6 +1,6 @@
load("@rules_proto//proto:defs.bzl", "proto_library")
load("@io_grpc_grpc_java//:java_grpc_library.bzl", "java_grpc_library")
load("//:kt_jvm_grpc.bzl", "kt_jvm_grpc_library")
load("//:kt_jvm_grpc.bzl", "kt_jvm_grpc_library", "kt_jvm_proto_library")

licenses(["notice"])

Expand All @@ -25,6 +25,11 @@ java_lite_proto_library(
deps = [":animals_proto"],
)

kt_jvm_proto_library(
name = "animals_kt_proto",
deps = [":animals_proto"],
)

kt_jvm_grpc_library(
name = "animals_kt_grpc",
srcs = [":animals_proto"],
Expand Down
@@ -1,6 +1,6 @@
load("@rules_proto//proto:defs.bzl", "proto_library")
load("@io_grpc_grpc_java//:java_grpc_library.bzl", "java_grpc_library")
load("//:kt_jvm_grpc.bzl", "kt_jvm_grpc_library")
load("//:kt_jvm_grpc.bzl", "kt_jvm_grpc_library", "kt_jvm_proto_library")

licenses(["notice"])

Expand All @@ -11,20 +11,20 @@ proto_library(
srcs = ["hello_world.proto"],
)

java_proto_library(
name = "hello_world_java_proto",
java_lite_proto_library(
name = "hello_world_java_proto_lite",
deps = [":hello_world_proto"],
)

java_lite_proto_library(
name = "hello_world_java_proto_lite",
kt_jvm_proto_library(
name = "hello_world_kt_proto",
deps = [":hello_world_proto"],
)

kt_jvm_grpc_library(
name = "hello_world_kt_grpc",
srcs = [":hello_world_proto"],
deps = [":hello_world_java_proto"],
deps = [":hello_world_kt_proto"],
)

kt_jvm_grpc_library(
Expand Down
@@ -1,6 +1,6 @@
load("@rules_proto//proto:defs.bzl", "proto_library")
load("@io_grpc_grpc_java//:java_grpc_library.bzl", "java_grpc_library")
load("//:kt_jvm_grpc.bzl", "kt_jvm_grpc_library")
load("//:kt_jvm_grpc.bzl", "kt_jvm_grpc_library", "kt_jvm_proto_library")

licenses(["notice"])

Expand All @@ -22,6 +22,11 @@ java_lite_proto_library(
deps = [":route_guide_proto"],
)

kt_jvm_proto_library(
name = "route_guide_kt_proto",
deps = [":route_guide_proto"],
)

kt_jvm_grpc_library(
name = "route_guide_kt_grpc",
srcs = [":route_guide_proto"],
Expand Down
Expand Up @@ -10,6 +10,7 @@ kt_jvm_binary(
main_class = "io.grpc.examples.animals.AnimalsServerKt",
deps = [
"//examples/protos/src/main/proto/io/grpc/examples/animals:animals_kt_grpc",
"//examples/protos/src/main/proto/io/grpc/examples/animals:animals_kt_proto",
"@com_google_protobuf//:protobuf_java_util",
"@io_grpc_grpc_java//netty",
],
Expand Down
Expand Up @@ -10,6 +10,7 @@ kt_jvm_binary(
main_class = "io.grpc.examples.helloworld.HelloWorldServerKt",
deps = [
"//examples/protos/src/main/proto/io/grpc/examples/helloworld:hello_world_kt_grpc",
"//examples/protos/src/main/proto/io/grpc/examples/helloworld:hello_world_kt_proto",
"@io_grpc_grpc_java//netty",
],
)
Expand Up @@ -10,8 +10,8 @@ kt_jvm_binary(
main_class = "io.grpc.examples.routeguide.RouteGuideServerKt",
resources = ["//examples/stub/src/main/resources/io/grpc/examples/routeguide:route_guide_db"],
deps = [
"//examples/protos/src/main/proto/io/grpc/examples/routeguide:route_guide_java_proto",
"//examples/protos/src/main/proto/io/grpc/examples/routeguide:route_guide_kt_grpc",
"//examples/protos/src/main/proto/io/grpc/examples/routeguide:route_guide_kt_proto",
"//examples/stub/src/main/kotlin/io/grpc/examples/routeguide:route_guide_stub",
"@com_google_protobuf//:protobuf_java_util",
"@io_grpc_grpc_java//netty",
Expand Down
173 changes: 173 additions & 0 deletions kt_jvm_grpc.bzl
Expand Up @@ -159,3 +159,176 @@ def kt_jvm_grpc_library(
deprecation = deprecation,
features = features,
)

def _get_real_short_path(file):
"""Returns the correct short path file name to be used by protoc."""
short_path = file.short_path
if short_path.startswith("../"):
second_slash = short_path.index("/", 3)
short_path = short_path[second_slash + 1:]

virtual_imports = "_virtual_imports/"
if virtual_imports in short_path:
short_path = short_path.split(virtual_imports)[1].split("/", 1)[1]
return short_path

def _kt_jvm_proto_library_helper_impl(ctx):
transitive_set = depset(
transitive =
[dep[ProtoInfo].transitive_descriptor_sets for dep in ctx.attr.proto_deps],
)
proto_sources = []
for dep in ctx.attr.proto_deps:
for file in dep[ProtoInfo].direct_sources:
proto_sources.append(_get_real_short_path(file))

gen_src_dir = ctx.actions.declare_directory(ctx.label.name + "/ktproto")

protoc_args = ctx.actions.args()
protoc_args.set_param_file_format("multiline")
protoc_args.use_param_file("@%s")
protoc_args.add("--kotlin_out=" + gen_src_dir.path)
protoc_args.add_joined(
transitive_set,
join_with = ctx.configuration.host_path_separator,
format_joined = "--descriptor_set_in=%s",
)
protoc_args.add_all(proto_sources)

ctx.actions.run(
inputs = depset(transitive = [transitive_set]),
outputs = [gen_src_dir],
executable = ctx.executable._protoc,
arguments = [protoc_args],
progress_message = "Generating kotlin proto extensions for " +
", ".join([
str(dep.label)
for dep in ctx.attr.proto_deps
]),
)

# Because protoc outputs an unknown number of files we need to zip them into a srcjar.
args = ctx.actions.args()
args.add("c")
args.add(ctx.outputs.srcjar)
args.add_all([gen_src_dir])
ctx.actions.run(
arguments = [args],
executable = ctx.executable._zip,
inputs = [gen_src_dir],
outputs = [ctx.outputs.srcjar],
)


_kt_jvm_proto_library_helper = rule(
attrs = dict(
proto_deps = attr.label_list(
providers = [ProtoInfo]
),
deps = attr.label_list(
providers = [JavaInfo],
),
exports = attr.label_list(
allow_rules = ["java_proto_library"],
),
_protoc = attr.label(
default = Label("@com_google_protobuf//:protoc"),
cfg = "host",
executable = True,
),
_zip = attr.label(
default = Label("@bazel_tools//tools/zip:zipper"),
cfg = "host",
executable=True
),
),
implementation = _kt_jvm_proto_library_helper_impl,
outputs = dict(
srcjar = "%{name}.srcjar",
)
)


def kt_jvm_proto_library(
name,
deps = None,
tags = None,
testonly = None,
compatible_with = None,
restricted_to = None,
visibility = None,
deprecation = None,
features = []):
"""
This rule accepts any number of proto_library targets in "deps", translates them to Kotlin and
returns the compiled Kotlin.
See also https://developers.google.com/protocol-buffers/docs/kotlintutorial for how to interact
with the generated Kotlin representation.
Note that the rule will also export the java version of the same protos as Kotlin protos depend
on the java version under the hood.
For standard attributes, see:
https://docs.bazel.build/versions/master/be/common-definitions.html#common-attributes
Args:
name: A name for the target
deps: One or more proto_library targets to turn into Kotlin.
tags: Standard attribute
testonly: Standard attribute
compatible_with: Standard attribute
restricted_to: Standard attribute
visibility: Standard attribute
deprecation: Standard attribute
features: Standard attribute
"""
java_proto_target = ":%s_DO_NOT_DEPEND_java_proto" % name
helper_target = ":%s_DO_NOT_DEPEND_kt_proto" % name

native.java_proto_library(
name = java_proto_target[1:],
deps = deps,
testonly = testonly,
compatible_with = compatible_with,
visibility = ["//visibility:private"],
restricted_to = restricted_to,
tags = tags,
deprecation = deprecation,
features = features,
)

_kt_jvm_proto_library_helper(
name = helper_target[1:],
proto_deps = deps,
deps = [
java_proto_target,
],
testonly = testonly,
compatible_with = compatible_with,
visibility = ["//visibility:private"],
restricted_to = restricted_to,
tags = tags,
deprecation = deprecation,
features = features,
)

kt_jvm_library(
name = name,
srcs = [helper_target + ".srcjar"],
deps = [
"@com_google_protobuf_protobuf_kotlin//jar",
java_proto_target
],
exports = [
java_proto_target
],
testonly = testonly,
compatible_with = compatible_with,
visibility = visibility,
restricted_to = restricted_to,
tags = tags,
deprecation = deprecation,
features = features,
)

18 changes: 10 additions & 8 deletions repositories.bzl
Expand Up @@ -35,21 +35,23 @@ def grpc_kt_repositories():
io_grpc_grpc_java()

def io_bazel_rules_kotlin():
rules_kotlin_version = "b40d920c5a5e044c541513f0d5e9260d0a4579c0"
rules_kotlin_version = "v1.5.0-beta-3"
rules_kotlin_sha = "58edd86f0f3c5b959c54e656b8e7eb0b0becabd412465c37a2078693c2571f7f"
http_archive(
name = "io_bazel_rules_kotlin",
urls = ["https://github.com/bazelbuild/rules_kotlin/archive/%s.zip" % rules_kotlin_version],
sha256 = "3dadd0ad7272be6b1ed1274f62cadd4a1293c89990bcd7b4af32637a70ada63e",
type = "zip",
strip_prefix = "rules_kotlin-%s" % rules_kotlin_version,
urls = ["https://github.com/bazelbuild/rules_kotlin/releases/download/%s/rules_kotlin_release.tgz" % rules_kotlin_version],
sha256 = rules_kotlin_sha,
)

def com_google_protobuf():
protobuf_version = "3.17.3"
protobuf_sha = "77ad26d3f65222fd96ccc18b055632b0bfedf295cb748b712a98ba1ac0b704b2"

http_archive(
name = "com_google_protobuf",
sha256 = "b37e96e81842af659605908a421960a5dc809acbc888f6b947bc320f8628e5b1",
strip_prefix = "protobuf-3.12.0",
urls = ["https://github.com/protocolbuffers/protobuf/archive/v3.12.0.zip"],
sha256 = protobuf_sha,
strip_prefix = "protobuf-%s" % protobuf_version,
urls = ["https://github.com/protocolbuffers/protobuf/releases/download/v%s/protobuf-all-%s.tar.gz" % (protobuf_version, protobuf_version)],
)

def io_grpc_grpc_java():
Expand Down

0 comments on commit 23c167a

Please sign in to comment.