Skip to content

Commit

Permalink
Allow apps to depend on SDK archives.
Browse files Browse the repository at this point in the history
This changes the android_binary_with_sandboxed_sdks macro to also accept
archived SDKs.

PiperOrigin-RevId: 567555240
Change-Id: If963f6d07bd7497ab977ef3837a274a0926b6a0a
  • Loading branch information
lucasvtenorio authored and copybara-github committed Sep 22, 2023
1 parent 5170a29 commit 1997412
Show file tree
Hide file tree
Showing 2 changed files with 73 additions and 10 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -14,32 +14,38 @@

"""Bazel rule for defining an Android binary that depends on sandboxed SDKs."""

load(":providers.bzl", "AndroidSandboxedSdkBundleInfo")
load("//rules:acls.bzl", "acls")
load("//rules:bundletool.bzl", _bundletool = "bundletool")
load("//rules:common.bzl", _common = "common")
load(
"//rules:utils.bzl",
_get_android_toolchain = "get_android_toolchain",
)
load("//rules:java.bzl", _java = "java")
load(
"//rules:sandboxed_sdk_toolbox.bzl",
_sandboxed_sdk_toolbox = "sandboxed_sdk_toolbox",
)
load(
"//rules:utils.bzl",
"utils",
_get_android_toolchain = "get_android_toolchain",
)
load(":providers.bzl", "AndroidArchivedSandboxedSdkInfo", "AndroidSandboxedSdkBundleInfo")

def _gen_sdk_dependencies_manifest_impl(ctx):
manifest = ctx.actions.declare_file(ctx.label.name + "_sdk_dep_manifest.xml")
module_configs = [
bundle[AndroidSandboxedSdkBundleInfo].sdk_info.sdk_module_config
for bundle in ctx.attr.sdk_bundles
]
sdk_archives = [
archive[AndroidArchivedSandboxedSdkInfo].asar
for archive in ctx.attr.sdk_archives
]

_sandboxed_sdk_toolbox.generate_sdk_dependencies_manifest(
ctx,
output = manifest,
manifest_package = ctx.attr.package,
sdk_module_configs = module_configs,
sdk_archives = sdk_archives,
debug_key = ctx.file.debug_key,
sandboxed_sdk_toolbox = _get_android_toolchain(ctx).sandboxed_sdk_toolbox.files_to_run,
host_javabase = _common.get_host_javabase(ctx),
Expand All @@ -59,6 +65,11 @@ _gen_sdk_dependencies_manifest = rule(
[AndroidSandboxedSdkBundleInfo],
],
),
sdk_archives = attr.label_list(
providers = [
[AndroidArchivedSandboxedSdkInfo],
],
),
debug_key = attr.label(
allow_single_file = True,
default = Label("//tools/android:debug_keystore"),
Expand All @@ -78,8 +89,34 @@ _gen_sdk_dependencies_manifest = rule(

def _android_binary_with_sandboxed_sdks_impl(ctx):
sdk_apks = []
for idx, sdk_archive in enumerate(ctx.attr.sdk_archives):
# Bundletool is rejecting ASARs when creating APKs, but since the formats are similar enough
# for this command we can just rename the file.
# TODO b/294970460) -- Remove this extra copy once Bundletool is updated with ASAR support
# in build_sdk_apks. Their work is being tracked in b/228176834.
renamed_sdk_archive = ctx.actions.declare_file("%s/renamed_sdk_archive/%s.asb" % (
ctx.label.name,
idx,
))
utils.copy_file(ctx, sdk_archive[AndroidArchivedSandboxedSdkInfo].asar, renamed_sdk_archive)

apk_out = ctx.actions.declare_file("%s/sdk_archive_dep_apks/%s.apk" % (
ctx.label.name,
idx,
))
_bundletool.build_sdk_apks(
ctx,
out = apk_out,
aapt2 = _get_android_toolchain(ctx).aapt2.files_to_run,
sdk_bundle = renamed_sdk_archive,
debug_key = ctx.file.debug_key,
bundletool = _get_android_toolchain(ctx).bundletool.files_to_run,
host_javabase = _common.get_host_javabase(ctx),
)
sdk_apks.append(apk_out)

for idx, sdk_bundle_target in enumerate(ctx.attr.sdk_bundles):
apk_out = ctx.actions.declare_file("%s/sdk_dep_apks/%s.apk" % (
apk_out = ctx.actions.declare_file("%s/sdk_bundle_dep_apks/%s.apk" % (
ctx.label.name,
idx,
))
Expand Down Expand Up @@ -137,6 +174,11 @@ _android_binary_with_sandboxed_sdks = rule(
[AndroidSandboxedSdkBundleInfo],
],
),
sdk_archives = attr.label_list(
providers = [
[AndroidArchivedSandboxedSdkInfo],
],
),
_install_script_template = attr.label(
allow_single_file = True,
default = ":install_script.sh_template",
Expand Down Expand Up @@ -171,7 +213,8 @@ def android_binary_with_sandboxed_sdks_macro(
fail("%s is not allowed to use the android_binary_with_sandboxed_sdks macro." %
fully_qualified_name)

sdk_bundles = attrs.pop("sdk_bundles", None)
sdk_bundles = attrs.pop("sdk_bundles", [])
sdk_archives = attrs.pop("sdk_archives", [])
debug_keystore = getattr(attrs, "debug_keystore", None)

bin_package = _java.resolve_package_from_label(
Expand All @@ -185,6 +228,10 @@ def android_binary_with_sandboxed_sdks_macro(
name = sdk_dependencies_manifest_name,
package = "%s.internalsdkdependencies" % bin_package,
sdk_bundles = sdk_bundles,
sdk_archives = sdk_archives,
testonly = attrs.get("testonly", False),
tags = attrs.get("tags", []),
visibility = attrs.get("visibility", None),
)

# Use the manifest in a normal android_library. This will later be added as a dependency to the
Expand All @@ -194,6 +241,10 @@ def android_binary_with_sandboxed_sdks_macro(
name = sdk_dependencies_lib_name,
exports_manifest = 1,
manifest = ":%s" % sdk_dependencies_manifest_name,
testonly = attrs.get("testonly", False),
tags = attrs.get("tags", []),
transitive_configs = attrs.get("transitive_configs", []),
visibility = attrs.get("visibility", None),
)
deps = attrs.pop("deps", [])
deps.append(":%s" % sdk_dependencies_lib_name)
Expand All @@ -210,6 +261,10 @@ def android_binary_with_sandboxed_sdks_macro(
_android_binary_with_sandboxed_sdks(
name = name,
sdk_bundles = sdk_bundles,
sdk_archives = sdk_archives,
debug_key = debug_keystore,
internal_android_binary = bin_label,
testonly = attrs.get("testonly", False),
tags = attrs.get("tags", []),
visibility = attrs.get("visibility", None),
)
14 changes: 11 additions & 3 deletions rules/sandboxed_sdk_toolbox.bzl
Original file line number Diff line number Diff line change
Expand Up @@ -128,6 +128,7 @@ def _generate_sdk_dependencies_manifest(
output = None,
manifest_package = None,
sdk_module_configs = None,
sdk_archives = None,
debug_key = None,
sandboxed_sdk_toolbox = None,
host_javabase = None):
Expand All @@ -141,14 +142,21 @@ def _generate_sdk_dependencies_manifest(
output: File where the final manifest will be written.
manifest_package: The package used in the manifest.
sdk_module_configs: List of SDK Module config JSON files with SDK packages and versions.
debug_key: Keystore that will later be used to sign the SDK APKs. It's expected to be a
sdk_archives: List of SDK archives, as ASAR files. They will also be listed as dependencies.
debug_key: Debug keystore that will later be used to sign the SDK APKs.
sandboxed_sdk_toolbox: Toolbox executable files.
host_javabase: Javabase used to run the toolbox.
"""
inputs = [debug_key]
args = ctx.actions.args()
args.add("generate-sdk-dependencies-manifest")
args.add("--manifest-package", manifest_package)
args.add("--sdk-module-configs", ",".join([config.path for config in sdk_module_configs]))
if sdk_module_configs:
args.add("--sdk-module-configs", ",".join([config.path for config in sdk_module_configs]))
inputs.extend(sdk_module_configs)
if sdk_archives:
args.add("--sdk-archives", ",".join([archive.path for archive in sdk_archives]))
inputs.extend(sdk_archives)
args.add("--debug-keystore", debug_key)
args.add("--debug-keystore-pass", "android")
args.add("--debug-keystore-alias", "androiddebugkey")
Expand All @@ -158,7 +166,7 @@ def _generate_sdk_dependencies_manifest(
host_javabase = host_javabase,
executable = sandboxed_sdk_toolbox,
arguments = [args],
inputs = sdk_module_configs + [debug_key],
inputs = inputs,
outputs = [output],
mnemonic = "GenSdkDepManifest",
progress_message = "Generate SDK dependencies manifest %s" % output.short_path,
Expand Down

0 comments on commit 1997412

Please sign in to comment.