Merge pull request #1586 from davidzchen/python

Bazel build: Keep generated sources and Python runtime in the same directory
This commit is contained in:
Jisi Liu 2016-05-25 22:41:02 -04:00
commit ed87c1fe2c
2 changed files with 76 additions and 14 deletions

45
BUILD
View File

@ -32,6 +32,7 @@ load(
"protobuf", "protobuf",
"cc_proto_library", "cc_proto_library",
"py_proto_library", "py_proto_library",
"internal_copied_filegroup",
"internal_gen_well_known_protos_java", "internal_gen_well_known_protos_java",
"internal_protobuf_py_tests", "internal_protobuf_py_tests",
) )
@ -560,6 +561,8 @@ py_library(
"python/google/protobuf/**/*.py", "python/google/protobuf/**/*.py",
], ],
exclude = [ exclude = [
"python/google/protobuf/__init__.py",
"python/google/protobuf/**/__init__.py",
"python/google/protobuf/internal/*_test.py", "python/google/protobuf/internal/*_test.py",
"python/google/protobuf/internal/test_util.py", "python/google/protobuf/internal/test_util.py",
], ],
@ -622,10 +625,26 @@ config_setting(
}, },
) )
# Copy the builtin proto files from src/google/protobuf to
# python/google/protobuf. This way, the generated Python sources will be in the
# same directory as the Python runtime sources. This is necessary for the
# modules to be imported correctly since they are all part of the same Python
# package.
internal_copied_filegroup(
name = "protos_python",
srcs = WELL_KNOWN_PROTOS,
strip_prefix = "src",
dest = "python",
)
# TODO(dzc): Remove this once py_proto_library can have labels in srcs, in
# which case we can simply add :protos_python in srcs.
COPIED_WELL_KNOWN_PROTOS = ["python/" + s for s in RELATIVE_WELL_KNOWN_PROTOS]
py_proto_library( py_proto_library(
name = "protobuf_python", name = "protobuf_python",
srcs = WELL_KNOWN_PROTOS, srcs = COPIED_WELL_KNOWN_PROTOS,
include = "src", include = "python",
data = select({ data = select({
"//conditions:default": [], "//conditions:default": [],
":use_fast_cpp_protos": [ ":use_fast_cpp_protos": [
@ -643,10 +662,27 @@ py_proto_library(
visibility = ["//visibility:public"], visibility = ["//visibility:public"],
) )
# Copy the test proto files from src/google/protobuf to
# python/google/protobuf. This way, the generated Python sources will be in the
# same directory as the Python runtime sources. This is necessary for the
# modules to be imported correctly by the tests since they are all part of the
# same Python package.
internal_copied_filegroup(
name = "protos_python_test",
srcs = LITE_TEST_PROTOS + TEST_PROTOS,
strip_prefix = "src",
dest = "python",
)
# TODO(dzc): Remove this once py_proto_library can have labels in srcs, in
# which case we can simply add :protos_python_test in srcs.
COPIED_LITE_TEST_PROTOS = ["python/" + s for s in RELATIVE_LITE_TEST_PROTOS]
COPIED_TEST_PROTOS = ["python/" + s for s in RELATIVE_TEST_PROTOS]
py_proto_library( py_proto_library(
name = "python_common_test_protos", name = "python_common_test_protos",
srcs = LITE_TEST_PROTOS + TEST_PROTOS, srcs = COPIED_LITE_TEST_PROTOS + COPIED_TEST_PROTOS,
include = "src", include = "python",
default_runtime = "", default_runtime = "",
protoc = ":protoc", protoc = ":protoc",
srcs_version = "PY2AND3", srcs_version = "PY2AND3",
@ -672,6 +708,7 @@ py_library(
[ [
"python/google/protobuf/internal/*_test.py", "python/google/protobuf/internal/*_test.py",
"python/google/protobuf/internal/test_util.py", "python/google/protobuf/internal/test_util.py",
"python/google/protobuf/internal/import_test_package/__init__.py",
], ],
), ),
imports = ["python"], imports = ["python"],

View File

@ -26,7 +26,7 @@ def _CcOuts(srcs, use_grpc_plugin=False):
def _PyOuts(srcs): def _PyOuts(srcs):
return [s[:-len(".proto")] + "_pb2.py" for s in srcs] return [s[:-len(".proto")] + "_pb2.py" for s in srcs]
def _RelativeOutputPath(path, include): def _RelativeOutputPath(path, include, dest=""):
if include == None: if include == None:
return path return path
@ -35,16 +35,11 @@ def _RelativeOutputPath(path, include):
if include and include[-1] != '/': if include and include[-1] != '/':
include = include + '/' include = include + '/'
if dest and dest[-1] != '/':
dest = dest + '/'
path = path[len(include):] path = path[len(include):]
return dest + path
if not path.startswith(PACKAGE_NAME):
fail("The package %s is not within the path %s" % (PACKAGE_NAME, path))
if not PACKAGE_NAME:
return path
return path[len(PACKAGE_NAME)+1:]
def _proto_gen_impl(ctx): def _proto_gen_impl(ctx):
"""General implementation for generating protos""" """General implementation for generating protos"""
@ -53,7 +48,7 @@ def _proto_gen_impl(ctx):
deps += ctx.files.srcs deps += ctx.files.srcs
gen_dir = _GenDir(ctx) gen_dir = _GenDir(ctx)
if gen_dir: if gen_dir:
import_flags = ["-I" + gen_dir] import_flags = ["-I" + gen_dir, "-I" + ctx.var["GENDIR"] + "/" + gen_dir]
else: else:
import_flags = ["-I."] import_flags = ["-I."]
@ -224,6 +219,36 @@ def internal_gen_well_known_protos_java(srcs):
) )
def internal_copied_filegroup(name, srcs, strip_prefix, dest, **kwargs):
"""Macro to copy files to a different directory and then create a filegroup.
This is used by the //:protobuf_python py_proto_library target to work around
an issue caused by Python source files that are part of the same Python
package being in separate directories.
Args:
srcs: The source files to copy and add to the filegroup.
strip_prefix: Path to the root of the files to copy.
dest: The directory to copy the source files into.
**kwargs: extra arguments that will be passesd to the filegroup.
"""
outs = [_RelativeOutputPath(s, strip_prefix, dest) for s in srcs]
native.genrule(
name = name + "_genrule",
srcs = srcs,
outs = outs,
cmd = " && ".join(
["cp $(location %s) $(location %s)" %
(s, _RelativeOutputPath(s, strip_prefix, dest)) for s in srcs]),
)
native.filegroup(
name = name,
srcs = outs,
**kwargs)
def py_proto_library( def py_proto_library(
name, name,
srcs=[], srcs=[],