diff --git a/crates/ruff_graph/src/resolver.rs b/crates/ruff_graph/src/resolver.rs index f1f1589958..e70b07847a 100644 --- a/crates/ruff_graph/src/resolver.rs +++ b/crates/ruff_graph/src/resolver.rs @@ -1,5 +1,5 @@ use ruff_db::files::FilePath; -use ty_python_semantic::{ModuleName, resolve_module, resolve_real_module}; +use ty_python_semantic::{ModuleName, resolve_module_old, resolve_real_module_old}; use crate::ModuleDb; use crate::collector::CollectedImport; @@ -70,13 +70,13 @@ impl<'a> Resolver<'a> { /// Resolves a module name to a module. pub(crate) fn resolve_module(&self, module_name: &ModuleName) -> Option<&'a FilePath> { - let module = resolve_module(self.db, module_name)?; + let module = resolve_module_old(self.db, module_name)?; Some(module.file(self.db)?.path(self.db)) } /// Resolves a module name to a module (stubs not allowed). fn resolve_real_module(&self, module_name: &ModuleName) -> Option<&'a FilePath> { - let module = resolve_real_module(self.db, module_name)?; + let module = resolve_real_module_old(self.db, module_name)?; Some(module.file(self.db)?.path(self.db)) } } diff --git a/crates/ty/tests/file_watching.rs b/crates/ty/tests/file_watching.rs index 5a738b5fd5..3be4155694 100644 --- a/crates/ty/tests/file_watching.rs +++ b/crates/ty/tests/file_watching.rs @@ -15,7 +15,7 @@ use ty_project::metadata::pyproject::{PyProject, Tool}; use ty_project::metadata::value::{RangedValue, RelativePathBuf}; use ty_project::watch::{ChangeEvent, ProjectWatcher, directory_watcher}; use ty_project::{Db, ProjectDatabase, ProjectMetadata}; -use ty_python_semantic::{Module, ModuleName, PythonPlatform, resolve_module}; +use ty_python_semantic::{Module, ModuleName, PythonPlatform, resolve_module_old}; struct TestCase { db: ProjectDatabase, @@ -232,7 +232,8 @@ impl TestCase { } fn module<'c>(&'c self, name: &str) -> Module<'c> { - resolve_module(self.db(), &ModuleName::new(name).unwrap()).expect("module to be present") + resolve_module_old(self.db(), &ModuleName::new(name).unwrap()) + .expect("module to be present") } fn sorted_submodule_names(&self, parent_module_name: &str) -> Vec { @@ -811,7 +812,7 @@ fn directory_moved_to_project() -> anyhow::Result<()> { .with_context(|| "Failed to create __init__.py")?; std::fs::write(a_original_path.as_std_path(), "").with_context(|| "Failed to create a.py")?; - let sub_a_module = resolve_module(case.db(), &ModuleName::new_static("sub.a").unwrap()); + let sub_a_module = resolve_module_old(case.db(), &ModuleName::new_static("sub.a").unwrap()); assert_eq!(sub_a_module, None); case.assert_indexed_project_files([bar]); @@ -832,7 +833,7 @@ fn directory_moved_to_project() -> anyhow::Result<()> { .expect("a.py to exist"); // `import sub.a` should now resolve - assert!(resolve_module(case.db(), &ModuleName::new_static("sub.a").unwrap()).is_some()); + assert!(resolve_module_old(case.db(), &ModuleName::new_static("sub.a").unwrap()).is_some()); case.assert_indexed_project_files([bar, init_file, a_file]); @@ -848,7 +849,7 @@ fn directory_moved_to_trash() -> anyhow::Result<()> { ])?; let bar = case.system_file(case.project_path("bar.py")).unwrap(); - assert!(resolve_module(case.db(), &ModuleName::new_static("sub.a").unwrap()).is_some()); + assert!(resolve_module_old(case.db(), &ModuleName::new_static("sub.a").unwrap()).is_some()); let sub_path = case.project_path("sub"); let init_file = case @@ -870,7 +871,7 @@ fn directory_moved_to_trash() -> anyhow::Result<()> { case.apply_changes(changes, None); // `import sub.a` should no longer resolve - assert!(resolve_module(case.db(), &ModuleName::new_static("sub.a").unwrap()).is_none()); + assert!(resolve_module_old(case.db(), &ModuleName::new_static("sub.a").unwrap()).is_none()); assert!(!init_file.exists(case.db())); assert!(!a_file.exists(case.db())); @@ -890,8 +891,8 @@ fn directory_renamed() -> anyhow::Result<()> { let bar = case.system_file(case.project_path("bar.py")).unwrap(); - assert!(resolve_module(case.db(), &ModuleName::new_static("sub.a").unwrap()).is_some()); - assert!(resolve_module(case.db(), &ModuleName::new_static("foo.baz").unwrap()).is_none()); + assert!(resolve_module_old(case.db(), &ModuleName::new_static("sub.a").unwrap()).is_some()); + assert!(resolve_module_old(case.db(), &ModuleName::new_static("foo.baz").unwrap()).is_none()); let sub_path = case.project_path("sub"); let sub_init = case @@ -915,9 +916,9 @@ fn directory_renamed() -> anyhow::Result<()> { case.apply_changes(changes, None); // `import sub.a` should no longer resolve - assert!(resolve_module(case.db(), &ModuleName::new_static("sub.a").unwrap()).is_none()); + assert!(resolve_module_old(case.db(), &ModuleName::new_static("sub.a").unwrap()).is_none()); // `import foo.baz` should now resolve - assert!(resolve_module(case.db(), &ModuleName::new_static("foo.baz").unwrap()).is_some()); + assert!(resolve_module_old(case.db(), &ModuleName::new_static("foo.baz").unwrap()).is_some()); // The old paths are no longer tracked assert!(!sub_init.exists(case.db())); @@ -950,7 +951,7 @@ fn directory_deleted() -> anyhow::Result<()> { let bar = case.system_file(case.project_path("bar.py")).unwrap(); - assert!(resolve_module(case.db(), &ModuleName::new_static("sub.a").unwrap()).is_some()); + assert!(resolve_module_old(case.db(), &ModuleName::new_static("sub.a").unwrap()).is_some()); let sub_path = case.project_path("sub"); @@ -970,7 +971,7 @@ fn directory_deleted() -> anyhow::Result<()> { case.apply_changes(changes, None); // `import sub.a` should no longer resolve - assert!(resolve_module(case.db(), &ModuleName::new_static("sub.a").unwrap()).is_none()); + assert!(resolve_module_old(case.db(), &ModuleName::new_static("sub.a").unwrap()).is_none()); assert!(!init_file.exists(case.db())); assert!(!a_file.exists(case.db())); @@ -999,7 +1000,7 @@ fn search_path() -> anyhow::Result<()> { let site_packages = case.root_path().join("site_packages"); assert_eq!( - resolve_module(case.db(), &ModuleName::new("a").unwrap()), + resolve_module_old(case.db(), &ModuleName::new("a").unwrap()), None ); @@ -1009,7 +1010,7 @@ fn search_path() -> anyhow::Result<()> { case.apply_changes(changes, None); - assert!(resolve_module(case.db(), &ModuleName::new_static("a").unwrap()).is_some()); + assert!(resolve_module_old(case.db(), &ModuleName::new_static("a").unwrap()).is_some()); case.assert_indexed_project_files([case.system_file(case.project_path("bar.py")).unwrap()]); Ok(()) @@ -1022,7 +1023,7 @@ fn add_search_path() -> anyhow::Result<()> { let site_packages = case.project_path("site_packages"); std::fs::create_dir_all(site_packages.as_std_path())?; - assert!(resolve_module(case.db(), &ModuleName::new_static("a").unwrap()).is_none()); + assert!(resolve_module_old(case.db(), &ModuleName::new_static("a").unwrap()).is_none()); // Register site-packages as a search path. case.update_options(Options { @@ -1040,7 +1041,7 @@ fn add_search_path() -> anyhow::Result<()> { case.apply_changes(changes, None); - assert!(resolve_module(case.db(), &ModuleName::new_static("a").unwrap()).is_some()); + assert!(resolve_module_old(case.db(), &ModuleName::new_static("a").unwrap()).is_some()); Ok(()) } @@ -1172,7 +1173,7 @@ fn changed_versions_file() -> anyhow::Result<()> { // Unset the custom typeshed directory. assert_eq!( - resolve_module(case.db(), &ModuleName::new("os").unwrap()), + resolve_module_old(case.db(), &ModuleName::new("os").unwrap()), None ); @@ -1187,7 +1188,7 @@ fn changed_versions_file() -> anyhow::Result<()> { case.apply_changes(changes, None); - assert!(resolve_module(case.db(), &ModuleName::new("os").unwrap()).is_some()); + assert!(resolve_module_old(case.db(), &ModuleName::new("os").unwrap()).is_some()); Ok(()) } @@ -1410,7 +1411,7 @@ mod unix { Ok(()) })?; - let baz = resolve_module(case.db(), &ModuleName::new_static("bar.baz").unwrap()) + let baz = resolve_module_old(case.db(), &ModuleName::new_static("bar.baz").unwrap()) .expect("Expected bar.baz to exist in site-packages."); let baz_project = case.project_path("bar/baz.py"); let baz_file = baz.file(case.db()).unwrap(); @@ -1486,7 +1487,7 @@ mod unix { Ok(()) })?; - let baz = resolve_module(case.db(), &ModuleName::new_static("bar.baz").unwrap()) + let baz = resolve_module_old(case.db(), &ModuleName::new_static("bar.baz").unwrap()) .expect("Expected bar.baz to exist in site-packages."); let baz_file = baz.file(case.db()).unwrap(); let bar_baz = case.project_path("bar/baz.py"); @@ -1591,7 +1592,7 @@ mod unix { Ok(()) })?; - let baz = resolve_module(case.db(), &ModuleName::new_static("bar.baz").unwrap()) + let baz = resolve_module_old(case.db(), &ModuleName::new_static("bar.baz").unwrap()) .expect("Expected bar.baz to exist in site-packages."); let baz_site_packages_path = case.project_path(".venv/lib/python3.12/site-packages/bar/baz.py"); @@ -1854,11 +1855,11 @@ fn rename_files_casing_only() -> anyhow::Result<()> { let mut case = setup([("lib.py", "class Foo: ...")])?; assert!( - resolve_module(case.db(), &ModuleName::new("lib").unwrap()).is_some(), + resolve_module_old(case.db(), &ModuleName::new("lib").unwrap()).is_some(), "Expected `lib` module to exist." ); assert_eq!( - resolve_module(case.db(), &ModuleName::new("Lib").unwrap()), + resolve_module_old(case.db(), &ModuleName::new("Lib").unwrap()), None, "Expected `Lib` module not to exist" ); @@ -1891,13 +1892,13 @@ fn rename_files_casing_only() -> anyhow::Result<()> { // Resolving `lib` should now fail but `Lib` should now succeed assert_eq!( - resolve_module(case.db(), &ModuleName::new("lib").unwrap()), + resolve_module_old(case.db(), &ModuleName::new("lib").unwrap()), None, "Expected `lib` module to no longer exist." ); assert!( - resolve_module(case.db(), &ModuleName::new("Lib").unwrap()).is_some(), + resolve_module_old(case.db(), &ModuleName::new("Lib").unwrap()).is_some(), "Expected `Lib` module to exist" ); diff --git a/crates/ty_python_semantic/src/dunder_all.rs b/crates/ty_python_semantic/src/dunder_all.rs index 17f1706b7e..1803037d6d 100644 --- a/crates/ty_python_semantic/src/dunder_all.rs +++ b/crates/ty_python_semantic/src/dunder_all.rs @@ -166,7 +166,7 @@ impl<'db> DunderAllNamesCollector<'db> { ) -> Option<&'db FxHashSet> { let module_name = ModuleName::from_import_statement(self.db, self.file, import_from).ok()?; - let module = resolve_module(self.db, &module_name)?; + let module = resolve_module(self.db, self.file, &module_name)?; dunder_all_names(self.db, module.file(self.db)?) } diff --git a/crates/ty_python_semantic/src/lib.rs b/crates/ty_python_semantic/src/lib.rs index 84f755416f..af12a0f9a3 100644 --- a/crates/ty_python_semantic/src/lib.rs +++ b/crates/ty_python_semantic/src/lib.rs @@ -13,7 +13,8 @@ pub use diagnostic::add_inferred_python_version_hint_to_diagnostic; pub use module_name::{ModuleName, ModuleNameResolutionError}; pub use module_resolver::{ KnownModule, Module, SearchPath, SearchPathValidationError, SearchPaths, all_modules, - list_modules, resolve_module, resolve_real_module, system_module_search_paths, + list_modules, resolve_module, resolve_module_old, resolve_real_module, resolve_real_module_old, + system_module_search_paths, }; pub use program::{ Program, ProgramSettings, PythonVersionFileSource, PythonVersionSource, diff --git a/crates/ty_python_semantic/src/module_resolver/mod.rs b/crates/ty_python_semantic/src/module_resolver/mod.rs index 11d03cf7b5..cd17b0c166 100644 --- a/crates/ty_python_semantic/src/module_resolver/mod.rs +++ b/crates/ty_python_semantic/src/module_resolver/mod.rs @@ -6,7 +6,9 @@ pub use module::Module; pub use path::{SearchPath, SearchPathValidationError}; pub use resolver::SearchPaths; pub(crate) use resolver::file_to_module; -pub use resolver::{resolve_module, resolve_real_module}; +pub use resolver::{ + resolve_module, resolve_module_old, resolve_real_module, resolve_real_module_old, +}; use ruff_db::system::SystemPath; use crate::Db; diff --git a/crates/ty_python_semantic/src/module_resolver/resolver.rs b/crates/ty_python_semantic/src/module_resolver/resolver.rs index 349d685862..7fc007ffe6 100644 --- a/crates/ty_python_semantic/src/module_resolver/resolver.rs +++ b/crates/ty_python_semantic/src/module_resolver/resolver.rs @@ -33,14 +33,40 @@ use super::module::{Module, ModuleKind}; use super::path::{ModulePath, SearchPath, SearchPathValidationError, SystemOrVendoredPathRef}; /// Resolves a module name to a module. -pub fn resolve_module<'db>(db: &'db dyn Db, module_name: &ModuleName) -> Option> { +pub fn resolve_module<'db>( + db: &'db dyn Db, + importing_file: File, + module_name: &ModuleName, +) -> Option> { + let interned_name = ModuleNameIngredient::new(db, module_name, ModuleResolveMode::StubsAllowed); + + resolve_module_query(db, interned_name) + .or_else(|| desperately_resolve_module(db, importing_file, interned_name)) +} + +pub fn resolve_module_old<'db>(db: &'db dyn Db, module_name: &ModuleName) -> Option> { let interned_name = ModuleNameIngredient::new(db, module_name, ModuleResolveMode::StubsAllowed); resolve_module_query(db, interned_name) } /// Resolves a module name to a module (stubs not allowed). -pub fn resolve_real_module<'db>(db: &'db dyn Db, module_name: &ModuleName) -> Option> { +pub fn resolve_real_module<'db>( + db: &'db dyn Db, + importing_file: File, + module_name: &ModuleName, +) -> Option> { + let interned_name = + ModuleNameIngredient::new(db, module_name, ModuleResolveMode::StubsNotAllowed); + + resolve_module_query(db, interned_name) + .or_else(|| desperately_resolve_module(db, importing_file, interned_name)) +} + +pub fn resolve_real_module_old<'db>( + db: &'db dyn Db, + module_name: &ModuleName, +) -> Option> { let interned_name = ModuleNameIngredient::new(db, module_name, ModuleResolveMode::StubsNotAllowed); @@ -116,6 +142,43 @@ fn resolve_module_query<'db>( Some(module) } +fn desperately_resolve_module<'db>( + db: &'db dyn Db, + importing_file: File, + module_name: ModuleNameIngredient<'db>, +) -> Option> { + let name = module_name.name(db); + let mode = module_name.mode(db); + let _span = tracing::trace_span!("desperately_resolve_module", %name).entered(); + + let Some(resolved) = desperately_resolve_name(db, importing_file, name, mode) else { + tracing::debug!("Module `{name}` not found while looking in parent dirs"); + return None; + }; + + let module = match resolved { + ResolvedName::FileModule(module) => { + tracing::trace!( + "Resolved module `{name}` to `{path}`", + path = module.file.path(db) + ); + Module::file_module( + db, + name.clone(), + module.kind, + module.search_path, + module.file, + ) + } + ResolvedName::NamespacePackage => { + tracing::trace!("Module `{name}` is a namespace package"); + Module::namespace_package(db, name.clone()) + } + }; + + Some(module) +} + /// Resolves the module for the given path. /// /// Returns `None` if the path is not a module locatable via any of the known search paths. @@ -154,7 +217,7 @@ pub(crate) fn file_to_module(db: &dyn Db, file: File) -> Option> { // If it doesn't, then that means that multiple modules have the same name in different // root paths, but that the module corresponding to `path` is in a lower priority search path, // in which case we ignore it. - let module = resolve_module(db, &module_name)?; + let module = resolve_module(db, file, &module_name)?; let module_file = module.file(db)?; if file.path(db) == module_file.path(db) { @@ -162,10 +225,10 @@ pub(crate) fn file_to_module(db: &dyn Db, file: File) -> Option> { } else if file.source_type(db) == PySourceType::Python && module_file.source_type(db) == PySourceType::Stub { - // If a .py and .pyi are both defined, the .pyi will be the one returned by `resolve_module().file`, + // If a .py and .pyi are both defined, the .pyi will be the one returned by `resolve_module_old().file`, // which would make us erroneously believe the `.py` is *not* also this module (breaking things // like relative imports). So here we try `resolve_real_module().file` to cover both cases. - let module = resolve_real_module(db, &module_name)?; + let module = resolve_real_module(db, file, &module_name)?; let module_file = module.file(db)?; if file.path(db) == module_file.path(db) { return Some(module); @@ -808,6 +871,35 @@ fn resolve_name(db: &dyn Db, name: &ModuleName, mode: ModuleResolveMode) -> Opti None } +fn desperately_resolve_name( + db: &dyn Db, + importing_file: File, + name: &ModuleName, + mode: ModuleResolveMode, +) -> Option { + let program = Program::get(db); + let python_version = program.python_version(db); + let resolver_state = ResolverContext::new(db, python_version, mode); + let name = RelaxedModuleName::new(name); + + let system = db.system(); + let importing_path = importing_file.path(db).as_system_path()?; + for dir in importing_path.ancestors() { + let pyproject = dir.join("pyproject.toml"); + if system.path_exists(&pyproject) { + let search_path = SearchPath::extra(system, dir.to_owned()).ok()?; + return match resolve_name_in_search_path(&resolver_state, &name, &search_path) { + Ok((_, _, ResolvedName::FileModule(module))) => { + Some(ResolvedName::FileModule(module)) + } + Ok((_, _, ResolvedName::NamespacePackage)) => Some(ResolvedName::NamespacePackage), + Err(_) => None, + }; + } + } + None +} + #[derive(Debug)] enum ResolvedName { /// A module that resolves to a file. @@ -1354,11 +1446,11 @@ mod tests { .build(); let foo_module_name = ModuleName::new_static("foo").unwrap(); - let foo_module = resolve_module(&db, &foo_module_name).unwrap(); + let foo_module = resolve_module_old(&db, &foo_module_name).unwrap(); assert_eq!( Some(&foo_module), - resolve_module(&db, &foo_module_name).as_ref() + resolve_module_old(&db, &foo_module_name).as_ref() ); assert_eq!("foo", foo_module.name(&db)); @@ -1380,11 +1472,11 @@ mod tests { .build(); let foo_module_name = ModuleName::new_static("foo").unwrap(); - let foo_module = resolve_module(&db, &foo_module_name).unwrap(); + let foo_module = resolve_module_old(&db, &foo_module_name).unwrap(); assert_eq!( Some(&foo_module), - resolve_module(&db, &foo_module_name).as_ref() + resolve_module_old(&db, &foo_module_name).as_ref() ); assert_eq!("foo", foo_module.name(&db)); @@ -1412,11 +1504,11 @@ mod tests { .build(); let foo_module_name = ModuleName::new_static("foo").unwrap(); - let foo_module = resolve_module(&db, &foo_module_name).unwrap(); + let foo_module = resolve_module_old(&db, &foo_module_name).unwrap(); assert_eq!( Some(&foo_module), - resolve_module(&db, &foo_module_name).as_ref() + resolve_module_old(&db, &foo_module_name).as_ref() ); assert_eq!("foo", foo_module.name(&db)); @@ -1439,7 +1531,7 @@ mod tests { .build(); let builtins_module_name = ModuleName::new_static("builtins").unwrap(); - let builtins = resolve_module(&db, &builtins_module_name).expect("builtins to resolve"); + let builtins = resolve_module_old(&db, &builtins_module_name).expect("builtins to resolve"); assert_eq!( builtins.file(&db).unwrap().path(&db), @@ -1463,7 +1555,7 @@ mod tests { .build(); let builtins_module_name = ModuleName::new_static("builtins").unwrap(); - let builtins = resolve_module(&db, &builtins_module_name).expect("builtins to resolve"); + let builtins = resolve_module_old(&db, &builtins_module_name).expect("builtins to resolve"); assert_eq!( builtins.file(&db).unwrap().path(&db), @@ -1484,11 +1576,11 @@ mod tests { .build(); let functools_module_name = ModuleName::new_static("functools").unwrap(); - let functools_module = resolve_module(&db, &functools_module_name).unwrap(); + let functools_module = resolve_module_old(&db, &functools_module_name).unwrap(); assert_eq!( Some(&functools_module), - resolve_module(&db, &functools_module_name).as_ref() + resolve_module_old(&db, &functools_module_name).as_ref() ); assert_eq!(&stdlib, functools_module.search_path(&db).unwrap()); @@ -1541,7 +1633,7 @@ mod tests { let existing_modules = create_module_names(&["asyncio", "functools", "xml.etree"]); for module_name in existing_modules { - let resolved_module = resolve_module(&db, &module_name).unwrap_or_else(|| { + let resolved_module = resolve_module_old(&db, &module_name).unwrap_or_else(|| { panic!("Expected module {module_name} to exist in the mock stdlib") }); let search_path = resolved_module.search_path(&db).unwrap(); @@ -1594,7 +1686,7 @@ mod tests { for module_name in nonexisting_modules { assert!( - resolve_module(&db, &module_name).is_none(), + resolve_module_old(&db, &module_name).is_none(), "Unexpectedly resolved a module for {module_name}" ); } @@ -1637,7 +1729,7 @@ mod tests { ]); for module_name in existing_modules { - let resolved_module = resolve_module(&db, &module_name).unwrap_or_else(|| { + let resolved_module = resolve_module_old(&db, &module_name).unwrap_or_else(|| { panic!("Expected module {module_name} to exist in the mock stdlib") }); let search_path = resolved_module.search_path(&db).unwrap(); @@ -1673,7 +1765,7 @@ mod tests { let nonexisting_modules = create_module_names(&["importlib", "xml", "xml.etree"]); for module_name in nonexisting_modules { assert!( - resolve_module(&db, &module_name).is_none(), + resolve_module_old(&db, &module_name).is_none(), "Unexpectedly resolved a module for {module_name}" ); } @@ -1695,11 +1787,11 @@ mod tests { .build(); let functools_module_name = ModuleName::new_static("functools").unwrap(); - let functools_module = resolve_module(&db, &functools_module_name).unwrap(); + let functools_module = resolve_module_old(&db, &functools_module_name).unwrap(); assert_eq!( Some(&functools_module), - resolve_module(&db, &functools_module_name).as_ref() + resolve_module_old(&db, &functools_module_name).as_ref() ); assert_eq!(&src, functools_module.search_path(&db).unwrap()); assert_eq!(ModuleKind::Module, functools_module.kind(&db)); @@ -1722,7 +1814,7 @@ mod tests { .build(); let pydoc_data_topics_name = ModuleName::new_static("pydoc_data.topics").unwrap(); - let pydoc_data_topics = resolve_module(&db, &pydoc_data_topics_name).unwrap(); + let pydoc_data_topics = resolve_module_old(&db, &pydoc_data_topics_name).unwrap(); assert_eq!("pydoc_data.topics", pydoc_data_topics.name(&db)); assert_eq!(pydoc_data_topics.search_path(&db).unwrap(), &stdlib); @@ -1739,7 +1831,7 @@ mod tests { .build(); let foo_path = src.join("foo/__init__.py"); - let foo_module = resolve_module(&db, &ModuleName::new_static("foo").unwrap()).unwrap(); + let foo_module = resolve_module_old(&db, &ModuleName::new_static("foo").unwrap()).unwrap(); assert_eq!("foo", foo_module.name(&db)); assert_eq!(&src, foo_module.search_path(&db).unwrap()); @@ -1766,7 +1858,7 @@ mod tests { let TestCase { db, src, .. } = TestCaseBuilder::new().with_src_files(SRC).build(); - let foo_module = resolve_module(&db, &ModuleName::new_static("foo").unwrap()).unwrap(); + let foo_module = resolve_module_old(&db, &ModuleName::new_static("foo").unwrap()).unwrap(); let foo_init_path = src.join("foo/__init__.py"); assert_eq!(&src, foo_module.search_path(&db).unwrap()); @@ -1789,8 +1881,9 @@ mod tests { let TestCase { db, src, .. } = TestCaseBuilder::new().with_src_files(SRC).build(); - let foo = resolve_module(&db, &ModuleName::new_static("foo").unwrap()).unwrap(); - let foo_real = resolve_real_module(&db, &ModuleName::new_static("foo").unwrap()).unwrap(); + let foo = resolve_module_old(&db, &ModuleName::new_static("foo").unwrap()).unwrap(); + let foo_real = + resolve_real_module_old(&db, &ModuleName::new_static("foo").unwrap()).unwrap(); let foo_stub = src.join("foo.pyi"); assert_eq!(&src, foo.search_path(&db).unwrap()); @@ -1815,7 +1908,7 @@ mod tests { let TestCase { db, src, .. } = TestCaseBuilder::new().with_src_files(SRC).build(); let baz_module = - resolve_module(&db, &ModuleName::new_static("foo.bar.baz").unwrap()).unwrap(); + resolve_module_old(&db, &ModuleName::new_static("foo.bar.baz").unwrap()).unwrap(); let baz_path = src.join("foo/bar/baz.py"); assert_eq!(&src, baz_module.search_path(&db).unwrap()); @@ -1839,7 +1932,7 @@ mod tests { .with_site_packages_files(&[("foo.py", "")]) .build(); - let foo_module = resolve_module(&db, &ModuleName::new_static("foo").unwrap()).unwrap(); + let foo_module = resolve_module_old(&db, &ModuleName::new_static("foo").unwrap()).unwrap(); let foo_src_path = src.join("foo.py"); assert_eq!(&src, foo_module.search_path(&db).unwrap()); @@ -1910,8 +2003,8 @@ mod tests { }, ); - let foo_module = resolve_module(&db, &ModuleName::new_static("foo").unwrap()).unwrap(); - let bar_module = resolve_module(&db, &ModuleName::new_static("bar").unwrap()).unwrap(); + let foo_module = resolve_module_old(&db, &ModuleName::new_static("foo").unwrap()).unwrap(); + let bar_module = resolve_module_old(&db, &ModuleName::new_static("bar").unwrap()).unwrap(); assert_ne!(foo_module, bar_module); @@ -1946,7 +2039,7 @@ mod tests { .build(); let foo_module_name = ModuleName::new_static("foo").unwrap(); - let foo_module = resolve_module(&db, &foo_module_name).unwrap(); + let foo_module = resolve_module_old(&db, &foo_module_name).unwrap(); let foo_pieces = ( foo_module.name(&db).clone(), foo_module.file(&db), @@ -1967,7 +2060,7 @@ mod tests { // Re-query the foo module. The foo module should still be cached // because `bar.py` isn't relevant for resolving `foo`. - let foo_module2 = resolve_module(&db, &foo_module_name); + let foo_module2 = resolve_module_old(&db, &foo_module_name); let foo_pieces2 = foo_module2.map(|foo_module2| { ( foo_module2.name(&db).clone(), @@ -1994,14 +2087,14 @@ mod tests { let foo_path = src.join("foo.py"); let foo_module_name = ModuleName::new_static("foo").unwrap(); - assert_eq!(resolve_module(&db, &foo_module_name), None); + assert_eq!(resolve_module_old(&db, &foo_module_name), None); // Now write the foo file db.write_file(&foo_path, "x = 1")?; let foo_file = system_path_to_file(&db, &foo_path).expect("foo.py to exist"); - let foo_module = resolve_module(&db, &foo_module_name).expect("Foo module to resolve"); + let foo_module = resolve_module_old(&db, &foo_module_name).expect("Foo module to resolve"); assert_eq!(foo_file, foo_module.file(&db).unwrap()); Ok(()) @@ -2015,7 +2108,7 @@ mod tests { let TestCase { mut db, src, .. } = TestCaseBuilder::new().with_src_files(SRC).build(); let foo_module_name = ModuleName::new_static("foo").unwrap(); - let foo_module = resolve_module(&db, &foo_module_name).expect("foo module to exist"); + let foo_module = resolve_module_old(&db, &foo_module_name).expect("foo module to exist"); let foo_init_path = src.join("foo/__init__.py"); assert_eq!(&foo_init_path, foo_module.file(&db).unwrap().path(&db)); @@ -2027,7 +2120,7 @@ mod tests { File::sync_path(&mut db, &foo_init_path); File::sync_path(&mut db, foo_init_path.parent().unwrap()); - let foo_module = resolve_module(&db, &foo_module_name).expect("Foo module to resolve"); + let foo_module = resolve_module_old(&db, &foo_module_name).expect("Foo module to resolve"); assert_eq!(&src.join("foo.py"), foo_module.file(&db).unwrap().path(&db)); Ok(()) @@ -2053,7 +2146,7 @@ mod tests { let functools_module_name = ModuleName::new_static("functools").unwrap(); let stdlib_functools_path = stdlib.join("functools.pyi"); - let functools_module = resolve_module(&db, &functools_module_name).unwrap(); + let functools_module = resolve_module_old(&db, &functools_module_name).unwrap(); assert_eq!(functools_module.search_path(&db).unwrap(), &stdlib); assert_eq!( Ok(functools_module.file(&db).unwrap()), @@ -2066,7 +2159,7 @@ mod tests { let site_packages_functools_path = site_packages.join("functools.py"); db.write_file(&site_packages_functools_path, "f: int") .unwrap(); - let functools_module = resolve_module(&db, &functools_module_name).unwrap(); + let functools_module = resolve_module_old(&db, &functools_module_name).unwrap(); let functools_file = functools_module.file(&db).unwrap(); let functools_search_path = functools_module.search_path(&db).unwrap().clone(); let events = db.take_salsa_events(); @@ -2101,7 +2194,7 @@ mod tests { .build(); let functools_module_name = ModuleName::new_static("functools").unwrap(); - let functools_module = resolve_module(&db, &functools_module_name).unwrap(); + let functools_module = resolve_module_old(&db, &functools_module_name).unwrap(); assert_eq!(functools_module.search_path(&db).unwrap(), &stdlib); assert_eq!( Ok(functools_module.file(&db).unwrap()), @@ -2112,7 +2205,7 @@ mod tests { // since first-party files take higher priority in module resolution: let src_functools_path = src.join("functools.py"); db.write_file(&src_functools_path, "FOO: int").unwrap(); - let functools_module = resolve_module(&db, &functools_module_name).unwrap(); + let functools_module = resolve_module_old(&db, &functools_module_name).unwrap(); assert_eq!(functools_module.search_path(&db).unwrap(), &src); assert_eq!( Ok(functools_module.file(&db).unwrap()), @@ -2143,7 +2236,7 @@ mod tests { let functools_module_name = ModuleName::new_static("functools").unwrap(); let src_functools_path = src.join("functools.py"); - let functools_module = resolve_module(&db, &functools_module_name).unwrap(); + let functools_module = resolve_module_old(&db, &functools_module_name).unwrap(); assert_eq!(functools_module.search_path(&db).unwrap(), &src); assert_eq!( Ok(functools_module.file(&db).unwrap()), @@ -2156,7 +2249,7 @@ mod tests { .remove_file(&src_functools_path) .unwrap(); File::sync_path(&mut db, &src_functools_path); - let functools_module = resolve_module(&db, &functools_module_name).unwrap(); + let functools_module = resolve_module_old(&db, &functools_module_name).unwrap(); assert_eq!(functools_module.search_path(&db).unwrap(), &stdlib); assert_eq!( Ok(functools_module.file(&db).unwrap()), @@ -2178,8 +2271,8 @@ mod tests { let foo_module_name = ModuleName::new_static("foo").unwrap(); let foo_bar_module_name = ModuleName::new_static("foo.bar").unwrap(); - let foo_module = resolve_module(&db, &foo_module_name).unwrap(); - let foo_bar_module = resolve_module(&db, &foo_bar_module_name).unwrap(); + let foo_module = resolve_module_old(&db, &foo_module_name).unwrap(); + let foo_bar_module = resolve_module_old(&db, &foo_bar_module_name).unwrap(); assert_eq!( foo_module.file(&db).unwrap().path(&db), @@ -2207,11 +2300,11 @@ mod tests { // Lines with leading whitespace in `.pth` files do not parse: let foo_module_name = ModuleName::new_static("foo").unwrap(); - assert_eq!(resolve_module(&db, &foo_module_name), None); + assert_eq!(resolve_module_old(&db, &foo_module_name), None); // Lines with trailing whitespace in `.pth` files do: let bar_module_name = ModuleName::new_static("bar").unwrap(); - let bar_module = resolve_module(&db, &bar_module_name).unwrap(); + let bar_module = resolve_module_old(&db, &bar_module_name).unwrap(); assert_eq!( bar_module.file(&db).unwrap().path(&db), &FilePath::system("/y/src/bar.py") @@ -2230,7 +2323,7 @@ mod tests { .build(); let foo_module_name = ModuleName::new_static("foo").unwrap(); - let foo_module = resolve_module(&db, &foo_module_name).unwrap(); + let foo_module = resolve_module_old(&db, &foo_module_name).unwrap(); assert_eq!( foo_module.file(&db).unwrap().path(&db), @@ -2278,10 +2371,10 @@ not_a_directory let b_module_name = ModuleName::new_static("b").unwrap(); let spam_module_name = ModuleName::new_static("spam").unwrap(); - let foo_module = resolve_module(&db, &foo_module_name).unwrap(); - let a_module = resolve_module(&db, &a_module_name).unwrap(); - let b_module = resolve_module(&db, &b_module_name).unwrap(); - let spam_module = resolve_module(&db, &spam_module_name).unwrap(); + let foo_module = resolve_module_old(&db, &foo_module_name).unwrap(); + let a_module = resolve_module_old(&db, &a_module_name).unwrap(); + let b_module = resolve_module_old(&db, &b_module_name).unwrap(); + let spam_module = resolve_module_old(&db, &spam_module_name).unwrap(); assert_eq!( foo_module.file(&db).unwrap().path(&db), @@ -2315,14 +2408,14 @@ not_a_directory let foo_module_name = ModuleName::new_static("foo").unwrap(); let bar_module_name = ModuleName::new_static("bar").unwrap(); - let foo_module = resolve_module(&db, &foo_module_name).unwrap(); + let foo_module = resolve_module_old(&db, &foo_module_name).unwrap(); assert_eq!( foo_module.file(&db).unwrap().path(&db), &FilePath::system("/x/src/foo.py") ); db.clear_salsa_events(); - let bar_module = resolve_module(&db, &bar_module_name).unwrap(); + let bar_module = resolve_module_old(&db, &bar_module_name).unwrap(); assert_eq!( bar_module.file(&db).unwrap().path(&db), &FilePath::system("/y/src/bar.py") @@ -2352,7 +2445,7 @@ not_a_directory db.write_files(x_directory).unwrap(); let foo_module_name = ModuleName::new_static("foo").unwrap(); - let foo_module = resolve_module(&db, &foo_module_name).unwrap(); + let foo_module = resolve_module_old(&db, &foo_module_name).unwrap(); assert_eq!( foo_module.file(&db).unwrap().path(&db), &FilePath::system("/x/src/foo.py") @@ -2364,7 +2457,7 @@ not_a_directory File::sync_path(&mut db, &site_packages.join("_foo.pth")); - assert_eq!(resolve_module(&db, &foo_module_name), None); + assert_eq!(resolve_module_old(&db, &foo_module_name), None); } #[test] @@ -2379,7 +2472,7 @@ not_a_directory db.write_files(x_directory).unwrap(); let foo_module_name = ModuleName::new_static("foo").unwrap(); - let foo_module = resolve_module(&db, &foo_module_name).unwrap(); + let foo_module = resolve_module_old(&db, &foo_module_name).unwrap(); let src_path = SystemPathBuf::from("/x/src"); assert_eq!( foo_module.file(&db).unwrap().path(&db), @@ -2392,7 +2485,7 @@ not_a_directory db.memory_file_system().remove_directory(&src_path).unwrap(); File::sync_path(&mut db, &src_path.join("foo.py")); File::sync_path(&mut db, &src_path); - assert_eq!(resolve_module(&db, &foo_module_name), None); + assert_eq!(resolve_module_old(&db, &foo_module_name), None); } #[test] @@ -2452,7 +2545,7 @@ not_a_directory // The editable installs discovered from the `.pth` file in the first `site-packages` directory // take precedence over the second `site-packages` directory... let a_module_name = ModuleName::new_static("a").unwrap(); - let a_module = resolve_module(&db, &a_module_name).unwrap(); + let a_module = resolve_module_old(&db, &a_module_name).unwrap(); assert_eq!( a_module.file(&db).unwrap().path(&db), &editable_install_location @@ -2466,7 +2559,7 @@ not_a_directory // ...But now that the `.pth` file in the first `site-packages` directory has been deleted, // the editable install no longer exists, so the module now resolves to the file in the // second `site-packages` directory - let a_module = resolve_module(&db, &a_module_name).unwrap(); + let a_module = resolve_module_old(&db, &a_module_name).unwrap(); assert_eq!( a_module.file(&db).unwrap().path(&db), &system_site_packages_location @@ -2524,12 +2617,12 @@ not_a_directory // Now try to resolve the module `A` (note the capital `A` instead of `a`). let a_module_name = ModuleName::new_static("A").unwrap(); - assert_eq!(resolve_module(&db, &a_module_name), None); + assert_eq!(resolve_module_old(&db, &a_module_name), None); // Now lookup the same module using the lowercase `a` and it should // resolve to the file in the system site-packages let a_module_name = ModuleName::new_static("a").unwrap(); - let a_module = resolve_module(&db, &a_module_name).expect("a.py to resolve"); + let a_module = resolve_module_old(&db, &a_module_name).expect("a.py to resolve"); assert!( a_module .file(&db) diff --git a/crates/ty_python_semantic/src/place.rs b/crates/ty_python_semantic/src/place.rs index 6e46819b14..5d7f0335b8 100644 --- a/crates/ty_python_semantic/src/place.rs +++ b/crates/ty_python_semantic/src/place.rs @@ -1,7 +1,7 @@ use ruff_db::files::File; use crate::dunder_all::dunder_all_names; -use crate::module_resolver::{KnownModule, file_to_module}; +use crate::module_resolver::{KnownModule, file_to_module, resolve_module_old}; use crate::semantic_index::definition::{Definition, DefinitionState}; use crate::semantic_index::place::{PlaceExprRef, ScopedPlaceId}; use crate::semantic_index::scope::ScopeId; @@ -14,7 +14,7 @@ use crate::types::{ Truthiness, Type, TypeAndQualifiers, TypeQualifiers, UnionBuilder, UnionType, binding_type, declaration_type, todo_type, }; -use crate::{Db, FxOrderSet, Program, resolve_module}; +use crate::{Db, FxOrderSet, Program}; pub(crate) use implicit_globals::{ module_type_implicit_global_declaration, module_type_implicit_global_symbol, @@ -379,7 +379,7 @@ pub(crate) fn imported_symbol<'db>( /// and should not be used when a symbol is being explicitly imported from the `builtins` module /// (e.g. `from builtins import int`). pub(crate) fn builtins_symbol<'db>(db: &'db dyn Db, symbol: &str) -> PlaceAndQualifiers<'db> { - resolve_module(db, &KnownModule::Builtins.name()) + resolve_module_old(db, &KnownModule::Builtins.name()) .and_then(|module| { let file = module.file(db)?; Some( @@ -409,7 +409,7 @@ pub(crate) fn known_module_symbol<'db>( known_module: KnownModule, symbol: &str, ) -> PlaceAndQualifiers<'db> { - resolve_module(db, &known_module.name()) + resolve_module_old(db, &known_module.name()) .and_then(|module| { let file = module.file(db)?; Some(imported_symbol(db, file, symbol, None)) @@ -448,7 +448,7 @@ pub(crate) fn builtins_module_scope(db: &dyn Db) -> Option> { /// /// Can return `None` if a custom typeshed is used that is missing the core module in question. fn core_module_scope(db: &dyn Db, core_module: KnownModule) -> Option> { - let module = resolve_module(db, &core_module.name())?; + let module = resolve_module_old(db, &core_module.name())?; Some(global_scope(db, module.file(db)?)) } diff --git a/crates/ty_python_semantic/src/semantic_index/builder.rs b/crates/ty_python_semantic/src/semantic_index/builder.rs index f7b6da1a0f..9630a7b8d2 100644 --- a/crates/ty_python_semantic/src/semantic_index/builder.rs +++ b/crates/ty_python_semantic/src/semantic_index/builder.rs @@ -1580,7 +1580,7 @@ impl<'ast> Visitor<'ast> for SemanticIndexBuilder<'_, 'ast> { continue; }; - let Some(module) = resolve_module(self.db, &module_name) else { + let Some(module) = resolve_module(self.db, self.file, &module_name) else { continue; }; diff --git a/crates/ty_python_semantic/src/semantic_index/re_exports.rs b/crates/ty_python_semantic/src/semantic_index/re_exports.rs index 22389fc549..693c0f3437 100644 --- a/crates/ty_python_semantic/src/semantic_index/re_exports.rs +++ b/crates/ty_python_semantic/src/semantic_index/re_exports.rs @@ -250,7 +250,9 @@ impl<'db> Visitor<'db> for ExportFinder<'db> { for export in ModuleName::from_import_statement(self.db, self.file, node) .ok() - .and_then(|module_name| resolve_module(self.db, &module_name)) + .and_then(|module_name| { + resolve_module(self.db, self.file, &module_name) + }) .iter() .flat_map(|module| { module diff --git a/crates/ty_python_semantic/src/semantic_model.rs b/crates/ty_python_semantic/src/semantic_model.rs index 3f2a377c20..f9ed952d1f 100644 --- a/crates/ty_python_semantic/src/semantic_model.rs +++ b/crates/ty_python_semantic/src/semantic_model.rs @@ -100,7 +100,7 @@ impl<'db> SemanticModel<'db> { pub fn resolve_module(&self, module: Option<&str>, level: u32) -> Option> { let module_name = ModuleName::from_identifier_parts(self.db, self.file, module, level).ok()?; - resolve_module(self.db, &module_name) + resolve_module(self.db, self.file, &module_name) } /// Returns completions for symbols available in a `import ` context. @@ -140,7 +140,7 @@ impl<'db> SemanticModel<'db> { &self, module_name: &ModuleName, ) -> Vec> { - let Some(module) = resolve_module(self.db, module_name) else { + let Some(module) = resolve_module(self.db, self.file, module_name) else { tracing::debug!("Could not resolve module from `{module_name:?}`"); return vec![]; }; @@ -150,7 +150,7 @@ impl<'db> SemanticModel<'db> { /// Returns completions for symbols available in the given module as if /// it were imported by this model's `File`. fn module_completions(&self, module_name: &ModuleName) -> Vec> { - let Some(module) = resolve_module(self.db, module_name) else { + let Some(module) = resolve_module(self.db, self.file, module_name) else { tracing::debug!("Could not resolve module from `{module_name:?}`"); return vec![]; }; diff --git a/crates/ty_python_semantic/src/types.rs b/crates/ty_python_semantic/src/types.rs index 3c701de557..001868165a 100644 --- a/crates/ty_python_semantic/src/types.rs +++ b/crates/ty_python_semantic/src/types.rs @@ -12618,7 +12618,7 @@ impl<'db> ModuleLiteralType<'db> { let relative_submodule_name = ModuleName::new(name)?; let mut absolute_submodule_name = self.module(db).name(db).clone(); absolute_submodule_name.extend(&relative_submodule_name); - let submodule = resolve_module(db, &absolute_submodule_name)?; + let submodule = resolve_module(db, importing_file, &absolute_submodule_name)?; Some(Type::module_literal(db, importing_file, submodule)) } diff --git a/crates/ty_python_semantic/src/types/class.rs b/crates/ty_python_semantic/src/types/class.rs index 1f613fa568..cb8d0e87a7 100644 --- a/crates/ty_python_semantic/src/types/class.rs +++ b/crates/ty_python_semantic/src/types/class.rs @@ -5809,7 +5809,7 @@ impl SlotsKind { mod tests { use super::*; use crate::db::tests::setup_db; - use crate::module_resolver::resolve_module; + use crate::module_resolver::resolve_module_old; use crate::{PythonVersionSource, PythonVersionWithSource}; use salsa::Setter; use strum::IntoEnumIterator; @@ -5825,7 +5825,8 @@ mod tests { }); for class in KnownClass::iter() { let class_name = class.name(&db); - let class_module = resolve_module(&db, &class.canonical_module(&db).name()).unwrap(); + let class_module = + resolve_module_old(&db, &class.canonical_module(&db).name()).unwrap(); assert_eq!( KnownClass::try_from_file_and_name( diff --git a/crates/ty_python_semantic/src/types/function.rs b/crates/ty_python_semantic/src/types/function.rs index 7c07a86af1..9a98a1acb1 100644 --- a/crates/ty_python_semantic/src/types/function.rs +++ b/crates/ty_python_semantic/src/types/function.rs @@ -1887,7 +1887,7 @@ impl KnownFunction { let Some(module_name) = ModuleName::new(module_name) else { return; }; - let Some(module) = resolve_module(db, &module_name) else { + let Some(module) = resolve_module(db, file, &module_name) else { return; }; diff --git a/crates/ty_python_semantic/src/types/ide_support.rs b/crates/ty_python_semantic/src/types/ide_support.rs index 74eab52e72..9be805a615 100644 --- a/crates/ty_python_semantic/src/types/ide_support.rs +++ b/crates/ty_python_semantic/src/types/ide_support.rs @@ -1342,7 +1342,7 @@ mod resolve_definition { use crate::semantic_index::definition::{Definition, DefinitionKind, module_docstring}; use crate::semantic_index::scope::{NodeWithScopeKind, ScopeId}; use crate::semantic_index::{global_scope, place_table, semantic_index, use_def_map}; - use crate::{Db, ModuleName, resolve_module, resolve_real_module}; + use crate::{Db, ModuleName, resolve_module, resolve_real_module_old}; /// Represents the result of resolving an import to either a specific definition or /// a specific range within a file. @@ -1440,7 +1440,7 @@ mod resolve_definition { }; // Resolve the module to its file - let Some(resolved_module) = resolve_module(db, &module_name) else { + let Some(resolved_module) = resolve_module(db, file, &module_name) else { return Vec::new(); // Module not found, return empty list }; @@ -1527,7 +1527,7 @@ mod resolve_definition { else { return Vec::new(); }; - let Some(resolved_module) = resolve_module(db, &module_name) else { + let Some(resolved_module) = resolve_module(db, file, &module_name) else { return Vec::new(); }; resolved_module.file(db) @@ -1636,7 +1636,7 @@ mod resolve_definition { // It's definitely a stub, so now rerun module resolution but with stubs disabled. let stub_module = file_to_module(db, stub_file_for_module_lookup)?; trace!("Found stub module: {}", stub_module.name(db)); - let real_module = resolve_real_module(db, stub_module.name(db))?; + let real_module = resolve_real_module_old(db, stub_module.name(db))?; trace!("Found real module: {}", real_module.name(db)); let real_file = real_module.file(db)?; trace!("Found real file: {}", real_file.path(db)); diff --git a/crates/ty_python_semantic/src/types/infer/builder.rs b/crates/ty_python_semantic/src/types/infer/builder.rs index df165921fe..48d56d7f56 100644 --- a/crates/ty_python_semantic/src/types/infer/builder.rs +++ b/crates/ty_python_semantic/src/types/infer/builder.rs @@ -22,7 +22,8 @@ use super::{ use crate::diagnostic::format_enumeration; use crate::module_name::{ModuleName, ModuleNameResolutionError}; use crate::module_resolver::{ - KnownModule, ModuleResolveMode, file_to_module, resolve_module, search_paths, + KnownModule, ModuleResolveMode, file_to_module, resolve_module, resolve_module_old, + search_paths, }; use crate::node_key::NodeKey; use crate::place::{ @@ -5922,7 +5923,7 @@ impl<'db, 'ast> TypeInferenceBuilder<'db, 'ast> { ) else { return false; }; - resolve_module(self.db(), &module_name).is_some() + resolve_module(self.db(), self.file(), &module_name).is_some() }) { diagnostic .help("The module can be resolved if the number of leading dots is reduced"); @@ -6159,7 +6160,7 @@ impl<'db, 'ast> TypeInferenceBuilder<'db, 'ast> { } }; - if resolve_module(self.db(), &module_name).is_none() { + if resolve_module(self.db(), self.file(), &module_name).is_none() { self.report_unresolved_import(import_from.into(), module_ref.range(), *level, module); } } @@ -6177,7 +6178,7 @@ impl<'db, 'ast> TypeInferenceBuilder<'db, 'ast> { return; }; - let Some(module) = resolve_module(self.db(), &module_name) else { + let Some(module) = resolve_module(self.db(), self.file(), &module_name) else { self.add_unknown_declaration_with_binding(alias.into(), definition); return; }; @@ -6362,7 +6363,7 @@ impl<'db, 'ast> TypeInferenceBuilder<'db, 'ast> { self.add_binding(import_from.into(), definition, |_, _| Type::unknown()); return; }; - let Some(module) = resolve_module(self.db(), &thispackage_name) else { + let Some(module) = resolve_module(self.db(), self.file(), &thispackage_name) else { self.add_binding(import_from.into(), definition, |_, _| Type::unknown()); return; }; @@ -6593,7 +6594,7 @@ impl<'db, 'ast> TypeInferenceBuilder<'db, 'ast> { } fn module_type_from_name(&self, module_name: &ModuleName) -> Option> { - resolve_module(self.db(), module_name) + resolve_module(self.db(), self.file(), module_name) .map(|module| Type::module_literal(self.db(), self.file(), module)) } @@ -9172,7 +9173,7 @@ impl<'db, 'ast> TypeInferenceBuilder<'db, 'ast> { { let mut maybe_submodule_name = module_name.clone(); maybe_submodule_name.extend(&relative_submodule); - if resolve_module(db, &maybe_submodule_name).is_some() { + if resolve_module_old(db, &maybe_submodule_name).is_some() { if let Some(builder) = self .context .report_lint(&POSSIBLY_MISSING_ATTRIBUTE, attribute) diff --git a/crates/ty_python_semantic/src/types/special_form.rs b/crates/ty_python_semantic/src/types/special_form.rs index 423e1196bd..0fa10fbb45 100644 --- a/crates/ty_python_semantic/src/types/special_form.rs +++ b/crates/ty_python_semantic/src/types/special_form.rs @@ -3,8 +3,7 @@ use super::{ClassType, Type, class::KnownClass}; use crate::db::Db; -use crate::module_resolver::{KnownModule, file_to_module}; -use crate::resolve_module; +use crate::module_resolver::{KnownModule, file_to_module, resolve_module_old}; use crate::semantic_index::place::ScopedPlaceId; use crate::semantic_index::{FileScopeId, place_table, use_def_map}; use crate::types::TypeDefinition; @@ -544,7 +543,7 @@ impl SpecialFormType { self.definition_modules() .iter() .find_map(|module| { - let file = resolve_module(db, &module.name())?.file(db)?; + let file = resolve_module_old(db, &module.name())?.file(db)?; let scope = FileScopeId::global().to_scope_id(db, file); let symbol_id = place_table(db, scope).symbol_id(self.name())?; diff --git a/crates/ty_test/src/lib.rs b/crates/ty_test/src/lib.rs index ad4e7ebe4e..80b4337ab1 100644 --- a/crates/ty_test/src/lib.rs +++ b/crates/ty_test/src/lib.rs @@ -21,7 +21,7 @@ use ty_python_semantic::types::{UNDEFINED_REVEAL, check_types}; use ty_python_semantic::{ Module, Program, ProgramSettings, PythonEnvironment, PythonPlatform, PythonVersionSource, PythonVersionWithSource, SearchPath, SearchPathSettings, SysPrefixPathOrigin, list_modules, - resolve_module, + resolve_module_old, }; mod assertion; @@ -566,7 +566,7 @@ struct ModuleInconsistency<'db> { fn run_module_resolution_consistency_test(db: &db::Db) -> Result<(), Vec>> { let mut errs = vec![]; for from_list in list_modules(db) { - errs.push(match resolve_module(db, from_list.name(db)) { + errs.push(match resolve_module_old(db, from_list.name(db)) { None => ModuleInconsistency { db, from_list,