Skip to content

crate_universe: aliases attr can't reference targets that are themselves rust_library wrappers (e.g. transition aliases) #4035

@ashi009

Description

@ashi009

Background

Tracking the chain so it's clear what this is downstream of:

Important to note up front: the bug here is independent of which alias rule you use. Upstream's verbatim alias_rules.bzl and the hand-rolled workaround copy are byte-identical, and either one trips this. Today the issue is mostly latent because #2832 blocks the upstream path, but once #2832 is fixed and users adopt default_alias_rule = "opt", they'd hit this immediately.

The bug

rust/private/rustc.bzl::collect_deps (0.70.0):

aliases = {k.label: v for k, v in aliases.items()}
for dep in crate_deps:
    crate_info = dep.crate_info
    ...
    if crate_info.owner in aliases:
        ...

The dict is keyed by the aliased target's own .label, but the lookup is against crate_info.owner of the dep. These differ whenever the aliased target is a rule that forwards COMMON_PROVIDERS from an underlying rust_library — which is exactly what the canonical transition_alias_opt rule does:

def _transition_alias_impl(ctx):
    return [ctx.attr.actual[0][provider] for provider in COMMON_PROVIDERS]

So crate_info.owner ends up as the wrapped rust_library's label (e.g. @crate_index__hyper-0.14.29//:hyper), but the dict key is the wrapper's label (e.g. //third_party/rust/crates:hyper1427). They don't match → the alias is silently dropped → the crate gets imported under its original name → compile error like unresolved import alias_name.

Reproducer

In a workspace where #2832 is worked around with a custom alias_rules.bzl (or, hypothetically, once #2832 is fixed, with default_alias_rule = "opt" directly):

# Cargo.toml → renders as `transition_alias_opt(name="hyper", actual="@crate_index__hyper-0.14.29//:hyper")` in crate_index

# user-facing rust_library:
rust_library(
    name = "foo",
    aliases = {"@crate_index//:hyper": "hyper1427"},
    deps = ["@crate_index//:hyper"],
    ...
)

foo's source imports the crate as hyper1427 (e.g. use hyper1427::Body;). Compile fails with unresolved import hyper1427 because the alias dict key doesn't match dep.crate_info.owner.

Proposed fix

Use the underlying library's owner when the alias key is itself a crate_info-providing target:

aliases = {
    k[rust_common.crate_info].owner if rust_common.crate_info in k else k.label: v
    for k, v in aliases.items()
}

This is what we carry as a local patch (0010-allow-using-aliased-crate-in-aliases-attr.patch) against 0.70.0. Happy to send a PR if the maintainers agree.

Versions

  • rules_rust: 0.70.0
  • bazel: 7.7.1

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions