Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Trait method cannot be imported from package when pulling dependency from git repository #128569

Closed
edusporto opened this issue Aug 2, 2024 · 0 comments · Fixed by #128786
Closed
Labels
A-diagnostics Area: Messages for errors, warnings, and lints D-confusing Diagnostics: Confusing error or lint that should be reworked. D-crate-version-mismatch Diagnostics: Errors or lints caused be the use of two different crate versions. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue.

Comments

@edusporto
Copy link

I'm writing code for a programming language that uses two libraries: one for a (very simple) parser, and another for a lower level byte code, which also uses the same parser library.

The parser library (TSPL) defines the Parser trait, with the byte code library (HVM) defining a CoreParser that implements that trait through a macro from TSPL.

Then, a third library does something like this, where index is a method from that trait:

use TSPL::Parser;
use hvm::ast::CoreParser;

pub fn func(parser: &mut CoreParser) {
    *parser.index() = 1;
}

This works as expected if the dependencies in Cargo.toml are defined like this:

[dependencies]
TSPL = "0.0.12"
hvm = "2.0.21"

If we change TSPL to use the version from the latest git commit like this:

[dependencies]
TSPL = { git = "https://github.com/HigherOrderCO/TSPL.git" }
hvm = "2.0.21"

Then the code does not compile anymore, even though the version in the main branch in git has the exact same code as the published version 0.0.12. We get an error and a warning:

warning: unused import: `TSPL::Parser`
 --> src/lib.rs:1:5
  |
1 | use TSPL::Parser;
  |     ^^^^^^^^^^^^
  |
  = note: `#[warn(unused_imports)]` on by default

error[E0599]: no method named `index` found for mutable reference `&mut CoreParser<'_>` in the current scope
 --> src/lib.rs:5:13
  |
5 |     *parser.index() = 1;
  |             ^^^^^ private field, not a method
  |
  = help: items from traits can only be used if the trait is in scope
help: trait `Parser` which provides `index` is implemented but not in scope; perhaps you want to import it
  |
1 + use TSPL::Parser;

Notice that the compiler error tells us the function index has been found from the TSPL package, and we do as the error message tells us (use TSPL::Parser), but the compiler does not recognize the trait is being used even so.

While writing this issue, I figured out the problem: hvm uses the version from crates-io and our library doesn't and, even though they have the exact same code, the two versions of TSPL clash and the compiler does not compile. If we do something like this it works as expected:

[dependencies]
TSPL = "0.0.12"
hvm = "2.0.21"

[patch.crates-io]
TSPL = { git = "https://github.com/HigherOrderCO/TSPL.git" }

I still want to open this issue because I believe the error message could be more descriptive: in other cases where dependencies have clashing versions of other dependencies, usually Rust specifies it as such. The current error message is not very descriptive - the solution it gives to the problem does not work at all and may push users into the wrong direction.

Meta

rustc --version --verbose:

rustc 1.80.0 (051478957 2024-07-21)
binary: rustc
commit-hash: 051478957371ee0084a7c0913941d2a8c4757bb9
commit-date: 2024-07-21
host: aarch64-apple-darwin
release: 1.80.0
LLVM version: 18.1.7
Backtrace

error[E0599]: no method named `index` found for mutable reference `&mut CoreParser<'_>` in the current scope
 --> src/lib.rs:5:13
  |
5 |     *parser.index() = 1;
  |             ^^^^^ private field, not a method
  |
  = help: items from traits can only be used if the trait is in scope
help: trait `Parser` which provides `index` is implemented but not in scope; perhaps you want to import it
  |
1 + use TSPL::Parser;
  |

warning: unused import: `TSPL::Parser`
 --> src/lib.rs:1:5
  |
1 | use TSPL::Parser;
  |     ^^^^^^^^^^^^
  |
  = note: `#[warn(unused_imports)]` on by default

For more information about this error, try `rustc --explain E0599`.

@edusporto edusporto added the C-bug Category: This is a bug. label Aug 2, 2024
@rustbot rustbot added the needs-triage This issue may need triage. Remove it if it has been sufficiently triaged. label Aug 2, 2024
@bjorn3 bjorn3 added A-diagnostics Area: Messages for errors, warnings, and lints D-confusing Diagnostics: Confusing error or lint that should be reworked. labels Aug 2, 2024
@fmease fmease added D-crate-version-mismatch Diagnostics: Errors or lints caused be the use of two different crate versions. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue. and removed C-bug Category: This is a bug. needs-triage This issue may need triage. Remove it if it has been sufficiently triaged. labels Aug 2, 2024
estebank added a commit to estebank/rust that referenced this issue Aug 7, 2024
As per the case presented in rust-lang#128569, we should be showing the extra info even if auto-deref is involved.
estebank added a commit to estebank/rust that referenced this issue Aug 10, 2024
As per the case presented in rust-lang#128569, we should be showing the extra info even if auto-deref is involved.
estebank added a commit to estebank/rust that referenced this issue Aug 12, 2024
As per the case presented in rust-lang#128569, we should be showing the extra info even if auto-deref is involved.
tgross35 added a commit to tgross35/rust that referenced this issue Aug 17, 2024
…r=fee1-dead

Detect multiple crate versions on method not found

When a type comes indirectly from one crate version but the imported trait comes from a separate crate version, the called method won't be found. We now show additional context:

```
error[E0599]: no method named `foo` found for struct `dep_2_reexport::Type` in the current scope
 --> multiple-dep-versions.rs:8:10
  |
8 |     Type.foo();
  |          ^^^ method not found in `Type`
  |
note: there are multiple different versions of crate `dependency` in the dependency graph
 --> multiple-dep-versions.rs:4:32
  |
4 | use dependency::{do_something, Trait};
  |                                ^^^^^ `dependency` imported here doesn't correspond to the right crate version
  |
 ::: ~/rust/build/x86_64-unknown-linux-gnu/test/run-make/crate-loading/rmake_out/multiple-dep-versions-1.rs:4:1
  |
4 | pub trait Trait {
  | --------------- this is the trait that was imported
  |
 ::: ~/rust/build/x86_64-unknown-linux-gnu/test/run-make/crate-loading/rmake_out/multiple-dep-versions-2.rs:4:1
  |
4 | pub trait Trait {
  | --------------- this is the trait that is needed
5 |     fn foo(&self);
  |        --- the method is available for `dep_2_reexport::Type` here
```

Fix rust-lang#128569, fix rust-lang#110926, fix rust-lang#109161, fix rust-lang#81659, fix rust-lang#51458, fix rust-lang#32611. Follow up to rust-lang#124944.
tgross35 added a commit to tgross35/rust that referenced this issue Aug 17, 2024
…r=fee1-dead

Detect multiple crate versions on method not found

When a type comes indirectly from one crate version but the imported trait comes from a separate crate version, the called method won't be found. We now show additional context:

```
error[E0599]: no method named `foo` found for struct `dep_2_reexport::Type` in the current scope
 --> multiple-dep-versions.rs:8:10
  |
8 |     Type.foo();
  |          ^^^ method not found in `Type`
  |
note: there are multiple different versions of crate `dependency` in the dependency graph
 --> multiple-dep-versions.rs:4:32
  |
4 | use dependency::{do_something, Trait};
  |                                ^^^^^ `dependency` imported here doesn't correspond to the right crate version
  |
 ::: ~/rust/build/x86_64-unknown-linux-gnu/test/run-make/crate-loading/rmake_out/multiple-dep-versions-1.rs:4:1
  |
4 | pub trait Trait {
  | --------------- this is the trait that was imported
  |
 ::: ~/rust/build/x86_64-unknown-linux-gnu/test/run-make/crate-loading/rmake_out/multiple-dep-versions-2.rs:4:1
  |
4 | pub trait Trait {
  | --------------- this is the trait that is needed
5 |     fn foo(&self);
  |        --- the method is available for `dep_2_reexport::Type` here
```

Fix rust-lang#128569, fix rust-lang#110926, fix rust-lang#109161, fix rust-lang#81659, fix rust-lang#51458, fix rust-lang#32611. Follow up to rust-lang#124944.
@bors bors closed this as completed in 9b318d2 Aug 17, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-diagnostics Area: Messages for errors, warnings, and lints D-confusing Diagnostics: Confusing error or lint that should be reworked. D-crate-version-mismatch Diagnostics: Errors or lints caused be the use of two different crate versions. T-compiler Relevant to the compiler team, which will review and decide on the PR/issue.
Projects
None yet
Development

Successfully merging a pull request may close this issue.

4 participants