[FR]: Select appropriate `node_toolchain` automatically
What is the current behavior?
Currently for multi-arch builds, one has to select on the appropriate node_toolchain on JS rules. For example:
node_toolchain = select(
{
"@platforms//cpu:arm64": "@nodejs_linux_arm64//:toolchain",
"@platforms//cpu:x86_64": "@nodejs_linux_amd64//:toolchain",
"//conditions:default": "@platforms//:incompatible",
},
),
From (my understanding of) the platform ideology, this behavior is unexpected, as the toolchain is coupled to the rule, rather than being registered elsewhere and automatically selected. Following similar rule syntax where the toolchain is not specified, one can find that their js_* targets have the wrong architecture's Node libraries bundled to them.
Describe the feature
The node toolchains should be registered so the correct toolchain for the specified platform is chosen automatically.
Hmm, i don't think this this is true, our toolchain does respect the value of --platform, perhaps you are missing a transition?
I have this problem building a js_image_layer on Darwin to run inside a Linux OCI image. Without specifying a node_toolchain in the js_binary, we get an exec format error.
Do we need to force our own transition? Maybe I misunderstand how transitions and the target platform work.
A short version of the BUILD:
js_library(
name = "deps",
...
)
js_binary(
name = "js",
data = [":deps"],
entry_point = "main.js",
# Work around aspect-build/rules_js#2135
node_toolchain = select({
"@platforms//cpu:arm64": "@nodejs_linux_arm64//:toolchain",
"@platforms//cpu:x86_64": "@nodejs_linux_amd64//:toolchain",
}),
)
js_image_layer(
name = "layer",
binary = ":js",
root = "/app",
)
oci_image(
name = "image",
base = "@node22-debian-bookworm",
cmd = ["/app/test/js/js"],
exposed_ports = [
"8080/tcp",
"9090/tcp",
],
tars = [":layer"],
visibility = ["//test:__pkg__"],
)
We run this image in a test on the GHA runners (Docker, linux/amd64) and on local Mac developer machines (linux/arm64 in the Docker Desktop).
Without the node_toolchain setting, when running on MacOS the docker image fails with an exec format error. This led me here to this bug and also #1530.
Based on https://github.com/aspect-build/rules_js/issues/2135#issuecomment-2847835902 what's forcing us to specify the transition manually, if this should have set the toolchain for the platform?
I would have expected our image to be linux/arm64 for the host platform target, which implies it should have picked the node toolchain for arm64 automatically too.