bp2build support for python_test(_host)
There was a request for using b with python tests. bp2build python
tests exactly the same way as python binaries so that they can be
used with `b`.
Bug: None
Test: go test
Change-Id: Id68a6a73572745a4885b3e5bb1b8452e36baa982
diff --git a/android/allowlists/allowlists.go b/android/allowlists/allowlists.go
index 892e218..14c713f 100644
--- a/android/allowlists/allowlists.go
+++ b/android/allowlists/allowlists.go
@@ -806,6 +806,7 @@
// go deps:
"analyze_bcpf", // depends on bpmodify a blueprint_go_binary.
+ "analyze_bcpf_test", // depends on bpmodify a blueprint_go_binary.
"host_bionic_linker_asm", // depends on extract_linker, a go binary.
"host_bionic_linker_script", // depends on extract_linker, a go binary.
@@ -816,13 +817,15 @@
"libtombstoned_client_rust_bridge_code", "libtombstoned_client_wrapper", // rust conversions are not supported
// unconverted deps
- "CarHTMLViewer", // depends on unconverted modules android.car-stubs, car-ui-lib
+ "apexer_with_DCLA_preprocessing_test", // depends on unconverted modules: apexer_test_host_tools, com.android.example.apex
"adb", // depends on unconverted modules: AdbWinApi, libandroidfw, libopenscreen-discovery, libopenscreen-platform-impl, libusb, bin2c_fastdeployagent, AdbWinUsbApi
"android_icu4j_srcgen", // depends on unconverted modules: currysrc
"android_icu4j_srcgen_binary", // depends on unconverted modules: android_icu4j_srcgen, currysrc
+ "apex_compression_test", // depends on unconverted modules: soong_zip, com.android.example.apex
"apex_manifest_proto_java", // b/210751803, depends on libprotobuf-java-full
"art-script", // depends on unconverted modules: dalvikvm, dex2oat
"bin2c_fastdeployagent", // depends on unconverted modules: deployagent
+ "CarHTMLViewer", // depends on unconverted modules android.car-stubs, car-ui-lib
"com.android.runtime", // depends on unconverted modules: bionic-linker-config, linkerconfig
"currysrc", // depends on unconverted modules: currysrc_org.eclipse, guavalib, jopt-simple-4.9
"dex2oat-script", // depends on unconverted modules: dex2oat
@@ -852,6 +855,7 @@
"linker_reloc_bench_main", // depends on unconverted modules: liblinker_reloc_bench_*
"malloc-rss-benchmark", // depends on unconverted modules: libmeminfo
"pbtombstone", "crash_dump", // depends on libdebuggerd, libunwindstack
+ "releasetools_test", // depends on unconverted modules: com.android.apex.compressed.v1
"robolectric-sqlite4java-0.282", // depends on unconverted modules: robolectric-sqlite4java-import, robolectric-sqlite4java-native
"static_crasher", // depends on unconverted modules: libdebuggerd_handler
"test_fips", // depends on unconverted modules: adb
@@ -1397,6 +1401,16 @@
// TODO(b/266459895): depends on libunwindstack
"libutils_test",
+ // Has dependencies on other tools like ziptool, bp2build'd data properties don't work with these tests atm
+ "ziparchive_tests_large",
+ "mkbootimg_test",
+ "certify_bootimg_test",
+
+ // Despite being _host module types, these require devices to run
+ "logd_integration_test",
+ "mobly-hello-world-test",
+ "mobly-multidevice-test",
+
// TODO(b/274805756): Support core_platform and current java APIs
"fake-framework",
diff --git a/bp2build/Android.bp b/bp2build/Android.bp
index 598ca32..b6635c4 100644
--- a/bp2build/Android.bp
+++ b/bp2build/Android.bp
@@ -76,6 +76,7 @@
"prebuilt_etc_conversion_test.go",
"python_binary_conversion_test.go",
"python_library_conversion_test.go",
+ "python_test_conversion_test.go",
"sh_conversion_test.go",
"soong_config_module_type_conversion_test.go",
],
diff --git a/bp2build/python_test_conversion_test.go b/bp2build/python_test_conversion_test.go
new file mode 100644
index 0000000..4ff1fa1
--- /dev/null
+++ b/bp2build/python_test_conversion_test.go
@@ -0,0 +1,66 @@
+// Copyright 2023 Google Inc. All rights reserved.
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+// http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+
+package bp2build
+
+import (
+ "android/soong/python"
+ "testing"
+)
+
+func TestPythonTestHostSimple(t *testing.T) {
+ runBp2BuildTestCaseWithPythonLibraries(t, Bp2buildTestCase{
+ Description: "simple python_test_host converts to a native py_test",
+ ModuleTypeUnderTest: "python_test_host",
+ ModuleTypeUnderTestFactory: python.PythonTestHostFactory,
+ Filesystem: map[string]string{
+ "a.py": "",
+ "b/c.py": "",
+ "b/d.py": "",
+ "b/e.py": "",
+ "files/data.txt": "",
+ },
+ Blueprint: `python_test_host {
+ name: "foo",
+ main: "a.py",
+ srcs: ["**/*.py"],
+ exclude_srcs: ["b/e.py"],
+ data: ["files/data.txt",],
+ libs: ["bar"],
+ bazel_module: { bp2build_available: true },
+}
+ python_library_host {
+ name: "bar",
+ srcs: ["b/e.py"],
+ bazel_module: { bp2build_available: false },
+ }`,
+ ExpectedBazelTargets: []string{
+ MakeBazelTarget("py_test", "foo", AttrNameToString{
+ "data": `["files/data.txt"]`,
+ "deps": `[":bar"]`,
+ "main": `"a.py"`,
+ "imports": `["."]`,
+ "srcs": `[
+ "a.py",
+ "b/c.py",
+ "b/d.py",
+ ]`,
+ "target_compatible_with": `select({
+ "//build/bazel/platforms/os:android": ["@platforms//:incompatible"],
+ "//conditions:default": [],
+ })`,
+ }),
+ },
+ })
+}
diff --git a/python/binary.go b/python/binary.go
index 75135f3..a5db2f6 100644
--- a/python/binary.go
+++ b/python/binary.go
@@ -37,7 +37,7 @@
// this file must also be listed in srcs.
// If left unspecified, module name is used instead.
// If name doesn’t match any filename in srcs, main must be specified.
- Main *string `android:"arch_variant"`
+ Main *string
// set the name of the output binary.
Stem *string `android:"arch_variant"`
diff --git a/python/bp2build.go b/python/bp2build.go
index bdac2dc..cd3f2a1 100644
--- a/python/bp2build.go
+++ b/python/bp2build.go
@@ -15,7 +15,6 @@
package python
import (
- "fmt"
"path/filepath"
"strings"
@@ -118,42 +117,19 @@
return attrs
}
-func pythonLibBp2Build(ctx android.TopDownMutatorContext, m *PythonLibraryModule) {
- // TODO(b/182306917): this doesn't fully handle all nested props versioned
- // by the python version, which would have been handled by the version split
- // mutator. This is sufficient for very simple python_library modules under
- // Bionic.
+func (m *PythonLibraryModule) bp2buildPythonVersion(ctx android.TopDownMutatorContext) *string {
py3Enabled := proptools.BoolDefault(m.properties.Version.Py3.Enabled, true)
py2Enabled := proptools.BoolDefault(m.properties.Version.Py2.Enabled, false)
- var python_version *string
if py2Enabled && !py3Enabled {
- python_version = &pyVersion2
+ return &pyVersion2
} else if !py2Enabled && py3Enabled {
- python_version = &pyVersion3
+ return &pyVersion3
} else if !py2Enabled && !py3Enabled {
ctx.ModuleErrorf("bp2build converter doesn't understand having neither py2 nor py3 enabled")
+ return &pyVersion3
} else {
- // do nothing, since python_version defaults to PY2ANDPY3
+ return &pyVersion2And3
}
-
- baseAttrs := m.makeArchVariantBaseAttributes(ctx)
-
- attrs := &bazelPythonLibraryAttributes{
- Srcs: baseAttrs.Srcs,
- Deps: baseAttrs.Deps,
- Srcs_version: python_version,
- Imports: baseAttrs.Imports,
- }
-
- props := bazel.BazelTargetModuleProperties{
- // Use the native py_library rule.
- Rule_class: "py_library",
- }
-
- ctx.CreateBazelTargetModule(props, android.CommonAttributes{
- Name: m.Name(),
- Data: baseAttrs.Data,
- }, attrs)
}
type bazelPythonBinaryAttributes struct {
@@ -164,43 +140,71 @@
Imports bazel.StringListAttribute
}
-func pythonBinaryBp2Build(ctx android.TopDownMutatorContext, m *PythonBinaryModule) {
+func (p *PythonLibraryModule) ConvertWithBp2build(ctx android.TopDownMutatorContext) {
+ // TODO(b/182306917): this doesn't fully handle all nested props versioned
+ // by the python version, which would have been handled by the version split
+ // mutator. This is sufficient for very simple python_library modules under
+ // Bionic.
+ baseAttrs := p.makeArchVariantBaseAttributes(ctx)
+ pyVersion := p.bp2buildPythonVersion(ctx)
+ if *pyVersion == pyVersion2And3 {
+ // Libraries default to python 2 and 3
+ pyVersion = nil
+ }
+
+ attrs := &bazelPythonLibraryAttributes{
+ Srcs: baseAttrs.Srcs,
+ Deps: baseAttrs.Deps,
+ Srcs_version: pyVersion,
+ Imports: baseAttrs.Imports,
+ }
+
+ props := bazel.BazelTargetModuleProperties{
+ // Use the native py_library rule.
+ Rule_class: "py_library",
+ }
+
+ ctx.CreateBazelTargetModule(props, android.CommonAttributes{
+ Name: p.Name(),
+ Data: baseAttrs.Data,
+ }, attrs)
+}
+
+func (p *PythonBinaryModule) bp2buildBinaryProperties(ctx android.TopDownMutatorContext) (*bazelPythonBinaryAttributes, bazel.LabelListAttribute) {
// TODO(b/182306917): this doesn't fully handle all nested props versioned
// by the python version, which would have been handled by the version split
// mutator. This is sufficient for very simple python_binary_host modules
// under Bionic.
- py3Enabled := proptools.BoolDefault(m.properties.Version.Py3.Enabled, false)
- py2Enabled := proptools.BoolDefault(m.properties.Version.Py2.Enabled, false)
- var python_version *string
- if py3Enabled && py2Enabled {
- panic(fmt.Errorf(
- "error for '%s' module: bp2build's python_binary_host converter does not support "+
- "converting a module that is enabled for both Python 2 and 3 at the same time.", m.Name()))
- } else if py2Enabled {
- python_version = &pyVersion2
- } else {
- // do nothing, since python_version defaults to PY3.
+
+ baseAttrs := p.makeArchVariantBaseAttributes(ctx)
+ pyVersion := p.bp2buildPythonVersion(ctx)
+ if *pyVersion == pyVersion3 {
+ // Binaries default to python 3
+ pyVersion = nil
+ } else if *pyVersion == pyVersion2And3 {
+ ctx.ModuleErrorf("error for '%s' module: bp2build's python_binary_host converter "+
+ "does not support converting a module that is enabled for both Python 2 and 3 at the "+
+ "same time.", p.Name())
}
- baseAttrs := m.makeArchVariantBaseAttributes(ctx)
attrs := &bazelPythonBinaryAttributes{
Main: nil,
Srcs: baseAttrs.Srcs,
Deps: baseAttrs.Deps,
- Python_version: python_version,
+ Python_version: pyVersion,
Imports: baseAttrs.Imports,
}
- for _, propIntf := range m.GetProperties() {
- if props, ok := propIntf.(*BinaryProperties); ok {
- // main is optional.
- if props.Main != nil {
- main := android.BazelLabelForModuleSrcSingle(ctx, *props.Main)
- attrs.Main = &main
- break
- }
- }
+ // main is optional.
+ if p.binaryProperties.Main != nil {
+ main := android.BazelLabelForModuleSrcSingle(ctx, *p.binaryProperties.Main)
+ attrs.Main = &main
}
+ return attrs, baseAttrs.Data
+}
+
+func (p *PythonBinaryModule) ConvertWithBp2build(ctx android.TopDownMutatorContext) {
+ attrs, data := p.bp2buildBinaryProperties(ctx)
props := bazel.BazelTargetModuleProperties{
// Use the native py_binary rule.
@@ -208,19 +212,22 @@
}
ctx.CreateBazelTargetModule(props, android.CommonAttributes{
- Name: m.Name(),
- Data: baseAttrs.Data,
+ Name: p.Name(),
+ Data: data,
}, attrs)
}
-func (p *PythonLibraryModule) ConvertWithBp2build(ctx android.TopDownMutatorContext) {
- pythonLibBp2Build(ctx, p)
-}
+func (p *PythonTestModule) ConvertWithBp2build(ctx android.TopDownMutatorContext) {
+ // Python tests are currently exactly the same as binaries, but with a different module type
+ attrs, data := p.bp2buildBinaryProperties(ctx)
-func (p *PythonBinaryModule) ConvertWithBp2build(ctx android.TopDownMutatorContext) {
- pythonBinaryBp2Build(ctx, p)
-}
+ props := bazel.BazelTargetModuleProperties{
+ // Use the native py_binary rule.
+ Rule_class: "py_test",
+ }
-func (p *PythonTestModule) ConvertWithBp2build(_ android.TopDownMutatorContext) {
- // Tests are currently unsupported
+ ctx.CreateBazelTargetModule(props, android.CommonAttributes{
+ Name: p.Name(),
+ Data: data,
+ }, attrs)
}
diff --git a/python/python.go b/python/python.go
index c7c523d..1a12973 100644
--- a/python/python.go
+++ b/python/python.go
@@ -239,6 +239,7 @@
protoExt = ".proto"
pyVersion2 = "PY2"
pyVersion3 = "PY3"
+ pyVersion2And3 = "PY2ANDPY3"
internalPath = "internal"
)