diff --git a/MODULE.bazel b/MODULE.bazel index 7cbcfdc9c..480c2c018 100644 --- a/MODULE.bazel +++ b/MODULE.bazel @@ -189,6 +189,9 @@ npm.npm_translate_lock( # other direct dependencies in the `examples/npm_deps/package.json`. "ms@2.1.3": ["examples/npm_deps"], }, + replace_packages = { + "chalk@5.0.1": "@chalk_501//:pkg", + }, update_pnpm_lock = True, verify_node_modules_ignored = "//:.bazelignore", verify_patches = "//examples/npm_deps/patches:patches", diff --git a/WORKSPACE b/WORKSPACE index dd9a9be9a..9a4cf5d0c 100644 --- a/WORKSPACE +++ b/WORKSPACE @@ -160,6 +160,9 @@ npm_translate_lock( # other direct dependencies in the `examples/npm_deps/package.json`. "ms@2.1.3": ["examples/npm_deps"], }, + replace_packages = { + "chalk@5.0.1": "@chalk_501//:pkg", + }, update_pnpm_lock = True, verify_node_modules_ignored = "//:.bazelignore", verify_patches = "//examples/npm_deps/patches:patches", diff --git a/WORKSPACE.bzlmod b/WORKSPACE.bzlmod index bfe7c27f4..03e4a2764 100644 --- a/WORKSPACE.bzlmod +++ b/WORKSPACE.bzlmod @@ -8,3 +8,13 @@ load( fetch_shfmt() fetch_terraform() + +# dev dependency +load("@bazel_tools//tools/build_defs/repo:http.bzl", "http_archive") + +http_archive( + name = "chalk_501", + build_file = "//npm/private/test:vendored/chalk-5.0.1.BUILD", + integrity = "sha256-/nD5GSp77HDNFDwIL68S5PbS+8gefWkube2iIr80/x4=", + url = "https://registry.npmjs.org/chalk/-/chalk-5.0.1.tgz", +) diff --git a/docs/npm_import.md b/docs/npm_import.md index 60f736694..8c4e2a27f 100644 --- a/docs/npm_import.md +++ b/docs/npm_import.md @@ -26,10 +26,11 @@ for a given lockfile.
npm_import(name, package, version, deps, extra_build_content, transitive_closure, root_package, link_workspace, link_packages, lifecycle_hooks, lifecycle_hooks_execution_requirements, - lifecycle_hooks_env, integrity, url, commit, package_visibility, patch_args, patches, - custom_postinstall, npm_auth, npm_auth_basic, npm_auth_username, npm_auth_password, bins, - dev, register_copy_directory_toolchains, register_copy_to_directory_toolchains, - run_lifecycle_hooks, lifecycle_hooks_no_sandbox, kwargs) + lifecycle_hooks_env, integrity, url, commit, replace_package, package_visibility, + patch_args, patches, custom_postinstall, npm_auth, npm_auth_basic, npm_auth_username, + npm_auth_password, bins, dev, register_copy_directory_toolchains, + register_copy_to_directory_toolchains, run_lifecycle_hooks, lifecycle_hooks_no_sandbox, + kwargs)Import a single npm package into Bazel. @@ -149,6 +150,7 @@ Read more about the downloader config: <https://blog.aspect.dev/configuring-b | integrity | Expected checksum of the file downloaded, in Subresource Integrity format. This must match the checksum of the file downloaded.
""
|
| url | Optional url for this package. If unset, a default npm registry url is generated from the package name and version.git+ssh://
or git+https://
to indicate a git repository. For example, git+ssh://git@github.com/org/repo.git
""
|
| commit | Specific commit to be checked out if url is a git repository. | ""
|
+| replace_package | Use the specified npm_package target when linking instead of the fetched sources for this npm package.package.json
file, which is used to determine the generated bin entries for the package.lifecycle_hooks
attribute. | None
|
| package_visibility | Visibility of generated node_module link targets. | ["//visibility:public"]
|
| patch_args | Arguments to pass to the patch tool.-p1
will usually be needed for patches generated by git. | ["-p0"]
|
| patches | Patch files to apply onto the downloaded npm package. | []
|
diff --git a/docs/npm_translate_lock.md b/docs/npm_translate_lock.md
index 559c7313e..e861f3cb7 100644
--- a/docs/npm_translate_lock.md
+++ b/docs/npm_translate_lock.md
@@ -63,8 +63,8 @@ npm_translate_lock(name, patches, patch_args, custom_postinstalls, package_visibility, prod,
public_hoist_packages, dev, no_optional, run_lifecycle_hooks, lifecycle_hooks,
lifecycle_hooks_envs, lifecycle_hooks_exclude,
- lifecycle_hooks_execution_requirements, lifecycle_hooks_no_sandbox, bins,
- verify_node_modules_ignored, verify_patches, quiet,
+ lifecycle_hooks_execution_requirements, lifecycle_hooks_no_sandbox,
+ replace_packages, bins, verify_node_modules_ignored, verify_patches, quiet,
external_repository_action_cache, link_workspace, pnpm_version,
register_copy_directory_toolchains, register_copy_to_directory_toolchains,
register_yq_toolchains, npm_package_target_name, use_starlark_yaml_parser,
@@ -122,6 +122,7 @@ For more about how to use npm_translate_lock, read [pnpm and rules_js](/docs/pnp
| lifecycle_hooks_exclude | A list of package names or package names with their version (e.g., "my-package" or "my-package@v1.2.3") to not run any lifecycle hooks on.<value>: []
to lifecycle_hooks
.[]
|
| lifecycle_hooks_execution_requirements | Execution requirements applied to the preinstall, install and postinstall lifecycle hooks on npm packages.{}
|
| lifecycle_hooks_no_sandbox | If True, a "no-sandbox" execution requirement is added to all lifecycle hooks unless overridden by lifecycle_hooks_execution_requirements
."*": ["no-sandbox"]
to lifecycle_hooks_execution_requirements
.True
|
+| replace_packages | A dict of package names to npm_package targets to link instead of the sources specified in the pnpm lock file for the corresponding packages.package.json
files, which are used to determine the generated bin entries for packages.lifecycle_hooks
attribute. | {}
|
| bins | Binary files to create in node_modules/.bin
for packages in this lock file. bins = { "@foo/bar": { "foo": "./foo.js", "bar": "./bar.js" }, }
bins = { "@foo/bar": [ "foo=./foo.js", "bar=./bar.js" ], }
| {}
|
| verify_node_modules_ignored | node_modules folders in the source tree should be ignored by Bazel..bazelignore
file to verify that all nested node_modules directories pnpm will create are listed.None
|
| verify_patches | Label to a patch list file.list_patches
macro to guarantee that all patches in a patch folder are included in the patches
attribute. verify_patches = "//patches:patches.list",
load("@aspect_rules_js//npm:repositories.bzl", "list_patches")
list_patches( name = "patches", out = "patches.list", )
patches.list
file before generating the first list. You can do this by running touch patches/patches.list
bazel run //patches:patches_update
.list_patches
documentation for further info. NOTE: if you would like to customize the patches directory location, you can set a flag in the .npmrc
. Here is an example of what this might look like # Set the directory for pnpm when patching # https://github.com/pnpm/pnpm/issues/6508#issuecomment-1537242124 patches-dir=bazel/js/patches
If you do this, you will have to update the verify_patches
path to be this path instead of //patches
like above. | None
|
diff --git a/js/dev_repositories.bzl b/js/dev_repositories.bzl
index f5e6e60b5..ea4a647ff 100644
--- a/js/dev_repositories.bzl
+++ b/js/dev_repositories.bzl
@@ -52,3 +52,10 @@ def rules_js_dev_dependencies():
strip_prefix = "rules_lint-0.7.0",
url = "https://github.com/aspect-build/rules_lint/releases/download/v0.7.0/rules_lint-v0.7.0.tar.gz",
)
+
+ http_archive(
+ name = "chalk_501",
+ integrity = "sha256-/nD5GSp77HDNFDwIL68S5PbS+8gefWkube2iIr80/x4=",
+ url = "https://registry.npmjs.org/chalk/-/chalk-5.0.1.tgz",
+ build_file = "//npm/private/test:vendored/chalk-5.0.1.BUILD",
+ )
diff --git a/npm/extensions.bzl b/npm/extensions.bzl
index 8a8d98b2d..9eca2c114 100644
--- a/npm/extensions.bzl
+++ b/npm/extensions.bzl
@@ -47,6 +47,7 @@ def _extension_impl(module_ctx):
register_copy_directory_toolchains = False, # this registration is handled elsewhere with bzlmod
register_copy_to_directory_toolchains = False, # this registration is handled elsewhere with bzlmod
register_yq_toolchains = False, # this registration is handled elsewhere with bzlmod
+ replace_packages = attr.replace_packages,
root_package = attr.root_package,
run_lifecycle_hooks = attr.run_lifecycle_hooks,
update_pnpm_lock = attr.update_pnpm_lock,
@@ -160,6 +161,7 @@ WARNING: Cannot determine home directory in order to load home `.npmrc` file in
package = i.package,
patch_args = i.patch_args,
patches = i.patches,
+ replace_package = i.replace_package,
root_package = i.root_package,
transitive_closure = i.transitive_closure,
url = i.url,
@@ -191,6 +193,7 @@ WARNING: Cannot determine home directory in order to load home `.npmrc` file in
package = i.package,
patch_args = i.patch_args,
patches = i.patches,
+ replace_package = i.replace_package,
root_package = i.root_package,
run_lifecycle_hooks = i.run_lifecycle_hooks,
transitive_closure = i.transitive_closure,
diff --git a/npm/private/npm_import.bzl b/npm/private/npm_import.bzl
index f9e81f000..2a66d54fa 100644
--- a/npm/private/npm_import.bzl
+++ b/npm/private/npm_import.bzl
@@ -718,7 +718,9 @@ def _impl_links(rctx):
if npm_import_sources_repo_name.startswith("aspect_rules_js.npm."):
npm_import_sources_repo_name = npm_import_sources_repo_name[len("aspect_rules_js.npm."):]
- if rctx.attr.npm_translate_lock_repo:
+ if rctx.attr.replace_package:
+ npm_package_target = rctx.attr.replace_package
+ elif rctx.attr.npm_translate_lock_repo:
npm_package_target = "@{}//:{}_source_directory".format(
rctx.attr.npm_translate_lock_repo,
npm_import_sources_repo_name,
@@ -828,6 +830,7 @@ _ATTRS_LINKS = dicts.add(_COMMON_ATTRS, {
"npm_translate_lock_repo": attr.string(),
"transitive_closure": attr.string_list_dict(),
"package_visibility": attr.string_list(),
+ "replace_package": attr.string(),
})
_ATTRS = dicts.add(_COMMON_ATTRS, {
@@ -899,6 +902,7 @@ def npm_import(
integrity = "",
url = "",
commit = "",
+ replace_package = None,
package_visibility = ["//visibility:public"],
patch_args = ["-p0"],
patches = [],
@@ -1090,6 +1094,19 @@ def npm_import(
commit: Specific commit to be checked out if url is a git repository.
+ replace_package: Use the specified npm_package target when linking instead of the fetched sources for this npm package.
+
+ The injected npm_package target may optionally contribute transitive npm package dependencies on top
+ of the transitive dependencies specified in the pnpm lock file for the same package, however, these
+ transitive dependencies must not collide with pnpm lock specified transitive dependencies.
+
+ Any patches specified for this package will be not applied to the injected npm_package target. They
+ will be applied, however, to the fetches sources so they can still be useful for patching the fetched
+ `package.json` file, which is used to determine the generated bin entries for the package.
+
+ NB: lifecycle hooks and custom_postinstall scripts, if implicitly or explicitly enabled, will be run on
+ the injected npm_package. These may be disabled explicitly using the `lifecycle_hooks` attribute.
+
package_visibility: Visibility of generated node_module link targets.
patch_args: Arguments to pass to the patch tool.
@@ -1218,4 +1235,5 @@ def npm_import(
bins = bins,
npm_translate_lock_repo = npm_translate_lock_repo,
package_visibility = package_visibility,
+ replace_package = replace_package,
)
diff --git a/npm/private/npm_translate_lock.bzl b/npm/private/npm_translate_lock.bzl
index 52b5bc7cb..5a00bd70d 100644
--- a/npm/private/npm_translate_lock.bzl
+++ b/npm/private/npm_translate_lock.bzl
@@ -53,6 +53,7 @@ _ATTRS = {
"dev": attr.bool(),
"external_repository_action_cache": attr.string(default = utils.default_external_repository_action_cache()),
"generate_bzl_library_targets": attr.bool(),
+ "replace_packages": attr.string_dict(),
"lifecycle_hooks_envs": attr.string_list_dict(),
"lifecycle_hooks_execution_requirements": attr.string_list_dict(),
"lifecycle_hooks": attr.string_list_dict(),
@@ -173,6 +174,7 @@ def npm_translate_lock(
lifecycle_hooks_exclude = [],
lifecycle_hooks_execution_requirements = {},
lifecycle_hooks_no_sandbox = True,
+ replace_packages = {},
bins = {},
verify_node_modules_ignored = None,
verify_patches = None,
@@ -382,6 +384,19 @@ def npm_translate_lock(
Read more: [lifecycles](/docs/pnpm.md#lifecycles)
+ replace_packages: A dict of package names to npm_package targets to link instead of the sources specified in the pnpm lock file for the corresponding packages.
+
+ The injected npm_package targets may optionally contribute transitive npm package dependencies on top
+ of the transitive dependencies specified in the pnpm lock file for their respective packages, however, these
+ transitive dependencies must not collide with pnpm lock specified transitive dependencies.
+
+ Any patches specified for the packages will be not applied to the injected npm_package targets. They
+ will be applied, however, to the fetches sources for their respecitve packages so they can still be useful
+ for patching the fetched `package.json` files, which are used to determine the generated bin entries for packages.
+
+ NB: lifecycle hooks and custom_postinstall scripts, if implicitly or explicitly enabled, will be run on
+ the injected npm_package targets. These may be disabled explicitly using the `lifecycle_hooks` attribute.
+
bins: Binary files to create in `node_modules/.bin` for packages in this lock file.
For a given package, this is typically derived from the "bin" attribute in
@@ -616,6 +631,7 @@ WARNING: `package_json` attribute in `npm_translate_lock(name = "{name}")` is de
lifecycle_hooks = lifecycle_hooks,
lifecycle_hooks_envs = lifecycle_hooks_envs,
lifecycle_hooks_execution_requirements = lifecycle_hooks_execution_requirements,
+ replace_packages = replace_packages,
bins = bins_string_list_dict,
verify_node_modules_ignored = verify_node_modules_ignored,
verify_patches = verify_patches,
diff --git a/npm/private/npm_translate_lock_generate.bzl b/npm/private/npm_translate_lock_generate.bzl
index 688b50b37..41925f126 100644
--- a/npm/private/npm_translate_lock_generate.bzl
+++ b/npm/private/npm_translate_lock_generate.bzl
@@ -17,7 +17,7 @@ _NPM_IMPORT_TMPL = \
version = "{version}",
url = "{url}",
package_visibility = {package_visibility},
- npm_translate_lock_repo = "{npm_translate_lock_repo}",{maybe_dev}{maybe_commit}{maybe_generate_bzl_library_targets}{maybe_integrity}{maybe_deps}{maybe_transitive_closure}{maybe_patches}{maybe_patch_args}{maybe_lifecycle_hooks}{maybe_custom_postinstall}{maybe_lifecycle_hooks_env}{maybe_lifecycle_hooks_execution_requirements}{maybe_bins}{maybe_npm_auth}{maybe_npm_auth_basic}{maybe_npm_auth_username}{maybe_npm_auth_password}
+ npm_translate_lock_repo = "{npm_translate_lock_repo}",{maybe_dev}{maybe_commit}{maybe_generate_bzl_library_targets}{maybe_integrity}{maybe_deps}{maybe_transitive_closure}{maybe_patches}{maybe_patch_args}{maybe_lifecycle_hooks}{maybe_custom_postinstall}{maybe_lifecycle_hooks_env}{maybe_lifecycle_hooks_execution_requirements}{maybe_bins}{maybe_npm_auth}{maybe_npm_auth_basic}{maybe_npm_auth_username}{maybe_npm_auth_password}{maybe_replace_package}
)
"""
@@ -287,8 +287,8 @@ def npm_link_all_packages(name = "node_modules", imported_links = []):
links_bzl = {}
links_targets_bzl = {}
for (i, _import) in enumerate(npm_imports):
- maybe_integrity = """
- integrity = "%s",""" % _import.integrity if _import.integrity else ""
+ maybe_integrity = ("""
+ integrity = "%s",""" % _import.integrity) if _import.integrity else ""
maybe_deps = ("""
deps = %s,""" % starlark_codegen_utils.to_dict_attr(_import.deps, 2)) if len(_import.deps) > 0 else ""
maybe_transitive_closure = ("""
@@ -309,8 +309,8 @@ def npm_link_all_packages(name = "node_modules", imported_links = []):
bins = %s,""" % starlark_codegen_utils.to_dict_attr(_import.bins, 2)) if len(_import.bins) > 0 else ""
maybe_generate_bzl_library_targets = ("""
generate_bzl_library_targets = True,""") if rctx.attr.generate_bzl_library_targets else ""
- maybe_commit = """
- commit = "%s",""" % _import.commit if _import.commit else ""
+ maybe_commit = ("""
+ commit = "%s",""" % _import.commit) if _import.commit else ""
maybe_npm_auth = ("""
npm_auth = "%s",""" % _import.npm_auth) if _import.npm_auth else ""
maybe_npm_auth_basic = ("""
@@ -321,6 +321,8 @@ def npm_link_all_packages(name = "node_modules", imported_links = []):
npm_auth_password = "%s",""" % _import.npm_auth_password) if _import.npm_auth_password else ""
maybe_dev = ("""
dev = True,""") if _import.dev else ""
+ maybe_replace_package = ("""
+ replace_package = "%s",""" % _import.replace_package) if _import.replace_package else ""
repositories_bzl.append(_NPM_IMPORT_TMPL.format(
link_packages = starlark_codegen_utils.to_dict_attr(_import.link_packages, 2, quote_value = False),
@@ -341,6 +343,7 @@ def npm_link_all_packages(name = "node_modules", imported_links = []):
maybe_npm_auth_username = maybe_npm_auth_username,
maybe_patch_args = maybe_patch_args,
maybe_patches = maybe_patches,
+ maybe_replace_package = maybe_replace_package,
maybe_transitive_closure = maybe_transitive_closure,
name = helpers.to_apparent_repo_name(_import.name),
npm_translate_lock_repo = helpers.to_apparent_repo_name(rctx.name),
diff --git a/npm/private/npm_translate_lock_helpers.bzl b/npm/private/npm_translate_lock_helpers.bzl
index 94244d777..20c054fdb 100644
--- a/npm/private/npm_translate_lock_helpers.bzl
+++ b/npm/private/npm_translate_lock_helpers.bzl
@@ -360,6 +360,13 @@ ERROR: patch_args for package {package} contains a strip prefix that is incompat
patches_used.extend(patches_keys)
+ # gather replace packages
+ replace_packages, _ = _gather_values_from_matching_names(True, attr.replace_packages, name, friendly_name, unfriendly_name)
+ if len(replace_packages) > 1:
+ msg = "Multiple package replacements found for package {}".format(name)
+ fail(msg)
+ replace_package = replace_packages[0] if replace_packages else None
+
# gather custom postinstalls
custom_postinstalls, _ = _gather_values_from_matching_names(True, attr.custom_postinstalls, name, friendly_name, unfriendly_name)
custom_postinstall = " && ".join([c for c in custom_postinstalls if c])
@@ -453,6 +460,7 @@ ERROR: patch_args for package {package} contains a strip prefix that is incompat
bins = bins,
package_info = package_info,
dev = dev,
+ replace_package = replace_package,
))
# Check that all patches files specified were used; this is a defense-in-depth since it is too
diff --git a/npm/private/test/BUILD.bazel b/npm/private/test/BUILD.bazel
index 498816071..287c2fcff 100644
--- a/npm/private/test/BUILD.bazel
+++ b/npm/private/test/BUILD.bazel
@@ -39,6 +39,7 @@ write_source_files(
files = {
"npm_defs_checked.bzl": "@npm//:defs.bzl",
"repositories_checked.bzl": "@npm//:repositories.bzl",
+ "chalk_links_defs_checked.bzl": "@npm__chalk__5.0.1__links//:defs.bzl",
"unused_links_defs_checked.bzl": "@npm__unused__0.2.2__links//:defs.bzl",
"fsevents_links_defs_checked.bzl": "@npm__fsevents__2.3.2__links//:defs.bzl",
"rollup_links_defs_checked.bzl": "@npm__rollup__2.70.2__links//:defs.bzl",
diff --git a/npm/private/test/chalk_links_defs_checked.bzl b/npm/private/test/chalk_links_defs_checked.bzl
new file mode 100644
index 000000000..aa228d57b
--- /dev/null
+++ b/npm/private/test/chalk_links_defs_checked.bzl
@@ -0,0 +1,176 @@
+"@generated by @aspect_rules_js//npm/private:npm_import.bzl for npm package chalk@5.0.1"
+
+load("@aspect_rules_js//npm/private:npm_package_store_internal.bzl", _npm_package_store = "npm_package_store_internal")
+load("@aspect_rules_js//npm/private:npm_link_package_store.bzl", _npm_link_package_store = "npm_link_package_store")
+load("@aspect_rules_js//npm/private:utils.bzl", _utils = "utils")
+
+# Generated npm_package_store targets for npm package chalk@5.0.1
+# buildifier: disable=function-docstring
+def npm_imported_package_store(name):
+ root_package = ""
+ is_root = native.package_name() == root_package
+ if not is_root:
+ msg = "No store links in bazel package '%s' for npm package npm package chalk@5.0.1. This is neither the root package nor a link package of this package." % native.package_name()
+ fail(msg)
+ if not name.endswith("/chalk"):
+ msg = "name must end with one of '/chalk' when linking the store in package 'chalk'; recommended value is 'node_modules/chalk'"
+ fail(msg)
+ link_root_name = name[:-len("/chalk")]
+
+ deps = {
+ ":.aspect_rules_js/{}/chalk@5.0.1/pkg".format(link_root_name): "chalk",
+ }
+ ref_deps = {}
+
+ store_target_name = ".aspect_rules_js/{}/chalk@5.0.1".format(link_root_name)
+
+ # reference target used to avoid circular deps
+ _npm_package_store(
+ name = "{}/ref".format(store_target_name),
+ package = "chalk",
+ version = "5.0.1",
+ dev = False,
+ tags = ["manual"],
+ use_declare_symlink = select({
+ "@aspect_rules_js//js:allow_unresolved_symlinks": True,
+ "//conditions:default": False,
+ }),
+ )
+
+ # post-lifecycle target with reference deps for use in terminal target with transitive closure
+ _npm_package_store(
+ name = "{}/pkg".format(store_target_name),
+ src = "{}/pkg_lc".format(store_target_name) if False else "@chalk_501//:pkg",
+ package = "chalk",
+ version = "5.0.1",
+ dev = False,
+ deps = ref_deps,
+ tags = ["manual"],
+ use_declare_symlink = select({
+ "@aspect_rules_js//js:allow_unresolved_symlinks": True,
+ "//conditions:default": False,
+ }),
+ )
+
+ # virtual store target with transitive closure of all npm package dependencies
+ _npm_package_store(
+ name = store_target_name,
+ src = None if True else "@chalk_501//:pkg",
+ package = "chalk",
+ version = "5.0.1",
+ dev = False,
+ deps = deps,
+ visibility = ["//visibility:public"],
+ tags = ["manual"],
+ use_declare_symlink = select({
+ "@aspect_rules_js//js:allow_unresolved_symlinks": True,
+ "//conditions:default": False,
+ }),
+ )
+
+ # filegroup target that provides a single file which is
+ # package directory for use in $(execpath) and $(rootpath)
+ native.filegroup(
+ name = "{}/dir".format(store_target_name),
+ srcs = [":{}".format(store_target_name)],
+ output_group = _utils.package_directory_output_group,
+ visibility = ["//visibility:public"],
+ tags = ["manual"],
+ )
+
+# Generated npm_package_store and npm_link_package_store targets for npm package chalk@5.0.1
+# buildifier: disable=function-docstring
+def npm_link_imported_package_store(name):
+ link_packages = {
+ "examples/npm_package/libs/lib_a": ["chalk"],
+ "npm/private/test/npm_package": ["chalk"],
+ }
+ if native.package_name() in link_packages:
+ link_aliases = link_packages[native.package_name()]
+ else:
+ link_aliases = ["chalk"]
+
+ link_alias = None
+ for _link_alias in link_aliases:
+ if name.endswith("/{}".format(_link_alias)):
+ # longest match wins
+ if not link_alias or len(_link_alias) > len(link_alias):
+ link_alias = _link_alias
+ if not link_alias:
+ msg = "name must end with one of '/{{ {link_aliases_comma_separated} }}' when called from package 'chalk'; recommended value(s) are 'node_modules/{{ {link_aliases_comma_separated} }}'".format(link_aliases_comma_separated = ", ".join(link_aliases))
+ fail(msg)
+
+ link_root_name = name[:-len("/{}".format(link_alias))]
+ store_target_name = ".aspect_rules_js/{}/chalk@5.0.1".format(link_root_name)
+
+ # terminal package store target to link
+ _npm_link_package_store(
+ name = name,
+ package = link_alias,
+ src = "//:{}".format(store_target_name),
+ visibility = ["//visibility:public"],
+ tags = ["manual"],
+ use_declare_symlink = select({
+ "@aspect_rules_js//js:allow_unresolved_symlinks": True,
+ "//conditions:default": False,
+ }),
+ )
+
+ # filegroup target that provides a single file which is
+ # package directory for use in $(execpath) and $(rootpath)
+ native.filegroup(
+ name = "{}/dir".format(name),
+ srcs = [":{}".format(name)],
+ output_group = _utils.package_directory_output_group,
+ visibility = ["//visibility:public"],
+ tags = ["manual"],
+ )
+
+ return [":{}".format(name)] if True else []
+
+# Generated npm_package_store and npm_link_package_store targets for npm package chalk@5.0.1
+# buildifier: disable=function-docstring
+def npm_link_imported_package(
+ name = "node_modules",
+ link = None,
+ fail_if_no_link = True):
+ root_package = ""
+ link_packages = {
+ "examples/npm_package/libs/lib_a": ["chalk"],
+ "npm/private/test/npm_package": ["chalk"],
+ }
+
+ if link_packages and link != None:
+ fail("link attribute cannot be specified when link_packages are set")
+
+ is_link = (link == True) or (link == None and native.package_name() in link_packages)
+ is_root = native.package_name() == root_package
+
+ if fail_if_no_link and not is_root and not link:
+ msg = "Nothing to link in bazel package '%s' for npm package npm package chalk@5.0.1. This is neither the root package nor a link package of this package." % native.package_name()
+ fail(msg)
+
+ link_targets = []
+ scoped_targets = {}
+
+ if is_link:
+ link_aliases = []
+ if native.package_name() in link_packages:
+ link_aliases = link_packages[native.package_name()]
+ if not link_aliases:
+ link_aliases = ["chalk"]
+ for link_alias in link_aliases:
+ link_target_name = "{}/{}".format(name, link_alias)
+ npm_link_imported_package_store(name = link_target_name)
+ if True:
+ link_targets.append(":{}".format(link_target_name))
+ if len(link_alias.split("/", 1)) > 1:
+ link_scope = link_alias.split("/", 1)[0]
+ if link_scope not in scoped_targets:
+ scoped_targets[link_scope] = []
+ scoped_targets[link_scope].append(link_target_name)
+
+ if is_root:
+ npm_imported_package_store("{}/chalk".format(name))
+
+ return (link_targets, scoped_targets)
diff --git a/npm/private/test/repositories_checked.bzl b/npm/private/test/repositories_checked.bzl
index 43b83a9a0..db437feb1 100644
--- a/npm/private/test/repositories_checked.bzl
+++ b/npm/private/test/repositories_checked.bzl
@@ -6606,6 +6606,7 @@ def npm_repositories():
transitive_closure = {
"chalk": ["5.0.1"],
},
+ replace_package = "@chalk_501//:pkg",
)
npm_import(
diff --git a/npm/private/test/vendored/chalk-5.0.1.BUILD b/npm/private/test/vendored/chalk-5.0.1.BUILD
new file mode 100644
index 000000000..80faa377e
--- /dev/null
+++ b/npm/private/test/vendored/chalk-5.0.1.BUILD
@@ -0,0 +1,11 @@
+load("@aspect_rules_js//npm:defs.bzl", "npm_package")
+
+npm_package(
+ name = "pkg",
+ srcs = glob(
+ include = ["package/**/*"],
+ ),
+ include_runfiles = False,
+ root_paths = ["package"],
+ visibility = ["//visibility:public"],
+)