From 5673b8ae2bb6977ed807ca89b11b85f0770c7b1b Mon Sep 17 00:00:00 2001 From: Luis Padron Date: Wed, 30 Oct 2024 10:42:33 -0400 Subject: [PATCH] feat: support non-string attrs in swift_package_tool (#1316) Sort of missed doing this in #1307 but it provides a nicer interface for users and will support the `dict` attr for the upcoming Swift Package Registry support. --- docs/bzlmod_extensions_overview.md | 4 +- examples/interesting_deps/MODULE.bazel | 4 +- swiftpkg/internal/swift_package_tool.bzl | 14 +++---- swiftpkg/internal/swift_package_tool_repo.bzl | 39 ++++++++++++------- 4 files changed, 35 insertions(+), 26 deletions(-) diff --git a/docs/bzlmod_extensions_overview.md b/docs/bzlmod_extensions_overview.md index 4565644d6..d6632c87c 100755 --- a/docs/bzlmod_extensions_overview.md +++ b/docs/bzlmod_extensions_overview.md @@ -56,9 +56,9 @@ Used to configure the flags used when running the `swift package` binary. | :------------- | :------------- | :------------- | :------------- | :------------- | | build_path | The relative path within the runfiles tree for the Swift Package Manager build directory. | String | optional | `".build"` | | cache_path | The relative path within the runfiles tree for the shared Swift Package Manager cache directory. | String | optional | `".cache"` | -| dependency_caching | Whether to enable the dependency cache. | String | optional | `"true"` | +| dependency_caching | Whether to enable the dependency cache. | Boolean | optional | `True` | | manifest_cache | Caching mode of Package.swift manifests (shared: shared cache, local: package's build directory, none: disabled) | String | optional | `"shared"` | -| manifest_caching | Whether to enable build manifest caching. | String | optional | `"true"` | +| manifest_caching | Whether to enable build manifest caching. | Boolean | optional | `True` | diff --git a/examples/interesting_deps/MODULE.bazel b/examples/interesting_deps/MODULE.bazel index 6bcf1e8f4..f765e1775 100644 --- a/examples/interesting_deps/MODULE.bazel +++ b/examples/interesting_deps/MODULE.bazel @@ -58,9 +58,9 @@ swift_deps.from_package( swift_deps.configure_swift_package( build_path = "spm-build", cache_path = "spm-cache", - dependency_caching = "false", + dependency_caching = False, manifest_cache = "none", - manifest_caching = "false", + manifest_caching = False, ) use_repo( swift_deps, diff --git a/swiftpkg/internal/swift_package_tool.bzl b/swiftpkg/internal/swift_package_tool.bzl index c5d8896da..1f2ea1f74 100644 --- a/swiftpkg/internal/swift_package_tool.bzl +++ b/swiftpkg/internal/swift_package_tool.bzl @@ -24,8 +24,8 @@ def _swift_package_tool_impl(ctx): template_dict.add("%(package_path)s", package_path) template_dict.add("%(build_path)s", build_path) template_dict.add("%(cache_path)s", cache_path) - template_dict.add("%(enable_build_manifest_caching)s", ctx.attr.manifest_caching) - template_dict.add("%(enable_dependency_cache)s", ctx.attr.dependency_caching) + template_dict.add("%(enable_build_manifest_caching)s", "true" if ctx.attr.manifest_caching else "false") + template_dict.add("%(enable_dependency_cache)s", "true" if ctx.attr.dependency_caching else "false") template_dict.add("%(manifest_cache)s", ctx.attr.manifest_cache) ctx.actions.expand_template( @@ -52,10 +52,9 @@ SWIFT_PACKAGE_CONFIG_ATTRS = { doc = "The relative path within the runfiles tree for the shared Swift Package Manager cache directory.", default = ".cache", ), - "dependency_caching": attr.string( + "dependency_caching": attr.bool( doc = "Whether to enable the dependency cache.", - default = "true", - values = ["true", "false"], + default = True, ), "manifest_cache": attr.string( doc = """Caching mode of Package.swift manifests \ @@ -64,10 +63,9 @@ SWIFT_PACKAGE_CONFIG_ATTRS = { default = "shared", values = ["shared", "local", "none"], ), - "manifest_caching": attr.string( + "manifest_caching": attr.bool( doc = "Whether to enable build manifest caching.", - default = "true", - values = ["true", "false"], + default = True, ), } diff --git a/swiftpkg/internal/swift_package_tool_repo.bzl b/swiftpkg/internal/swift_package_tool_repo.bzl index 54403dcd9..037fe7bd1 100644 --- a/swiftpkg/internal/swift_package_tool_repo.bzl +++ b/swiftpkg/internal/swift_package_tool_repo.bzl @@ -1,23 +1,34 @@ """Defines the `swift_package_tool_repo` repository rule that creates `swift_package_tool` targets.""" load("@bazel_skylib//lib:dicts.bzl", "dicts") +load("@bazel_skylib//lib:types.bzl", "types") load("//swiftpkg/internal:repository_utils.bzl", "repository_utils") load("//swiftpkg/internal:swift_package_tool.bzl", "SWIFT_PACKAGE_CONFIG_ATTRS") -def _swift_package_tool_repo_impl(repository_ctx): - package_path = repository_ctx.attr.package - - # Construct the list of keyword arguments for the `swift_package_tool` rule. - # String should be "key = \"value\"" - # NOTE: only supports string typed values as they are all quoted +def _package_config_attrs_to_content(attrs): + """Returns a BUILD file compatible string representation of the keyword arguments""" kwargs = repository_utils.struct_to_kwargs( - struct = repository_ctx.attr, + struct = attrs, keys = SWIFT_PACKAGE_CONFIG_ATTRS, ) - kwarg_content = ",\n".join([ - " {key} = \"{value}\"".format(key = k, value = v) - for k, v in kwargs.items() - ]) + + kwarg_lines = [] + for k, v in kwargs.items(): + if types.is_string(v): + kwarg_lines.append(" {key} = \"{value}\"".format(key = k, value = v)) + elif types.is_bool(v): + kwarg_lines.append(" {key} = {value}".format(key = k, value = "True" if v else "False")) + elif types.is_dict(v): + json_str = json.encode(v) + kwarg_lines.append(" {key} = {value}".format(key = k, value = json_str)) + else: + fail("Unsupported value type for attribute {key}: {value}".format(key = k, value = v)) + + return ",\n".join(kwarg_lines) + +def _swift_package_tool_repo_impl(repository_ctx): + attrs_content = _package_config_attrs_to_content(repository_ctx.attr) + package_path = repository_ctx.attr.package repository_ctx.file( "BUILD.bazel", @@ -28,18 +39,18 @@ swift_package_tool( name = "update", cmd = "update", package = "{package}", -{kwarg_content} +{attrs_content} ) swift_package_tool( name = "resolve", cmd = "resolve", package = "{package}", -{kwarg_content} +{attrs_content} ) """.format( package = package_path, - kwarg_content = kwarg_content, + attrs_content = attrs_content, ), )