From cedd2e904c7d1698c5834ab4a96696be4b179912 Mon Sep 17 00:00:00 2001 From: IWANABETHATGUY Date: Mon, 6 Nov 2023 11:19:48 +0800 Subject: [PATCH] =?UTF-8?q?chore:=20=F0=9F=A4=96=20remove=20generic=20in?= =?UTF-8?q?=20FileSystem=20trait=20(#1163)?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit generic will make the Trait non-object safe, so use a specific type instead a generic instead. ```rs // Examples of non-object safe traits. trait NotObjectSafe { const CONST: i32 = 1; // ERROR: cannot have associated const fn foo() {} // ERROR: associated function without Sized fn returns(&self) -> Self; // ERROR: Self in return type fn typed(&self, x: T) {} // ERROR: has generic type parameters fn nested(self: Rc>) {} // ERROR: nested receiver not yet supported } struct S; impl NotObjectSafe for S { fn returns(&self) -> Self { S } } let obj: Box = Box::new(S); // ERROR ``` --- crates/oxc_resolver/src/file_system.rs | 37 ++++++++++++++++------ crates/oxc_resolver/src/tests/memory_fs.rs | 12 +++---- 2 files changed, 34 insertions(+), 15 deletions(-) diff --git a/crates/oxc_resolver/src/file_system.rs b/crates/oxc_resolver/src/file_system.rs index 62a249a07..a676d8d26 100644 --- a/crates/oxc_resolver/src/file_system.rs +++ b/crates/oxc_resolver/src/file_system.rs @@ -10,28 +10,47 @@ pub trait FileSystem: Send + Sync { /// # Errors /// /// * See [std::fs::read_to_string] - fn read_to_string>(&self, path: P) -> io::Result; + /// ## Warning + /// Use `&Path` instead of a generic `P: AsRef` here, + /// because object safety requirements, it is especially useful, when + /// you want to store multiple `dyn FileSystem` in a `Vec` or use a `ResolverGeneric` in + /// napi env. + fn read_to_string(&self, path: &Path) -> io::Result; /// See [std::fs::metadata] /// /// # Errors - /// /// See [std::fs::metadata] - fn metadata>(&self, path: P) -> io::Result; + /// ## Warning + /// Use `&Path` instead of a generic `P: AsRef` here, + /// because object safety requirements, it is especially useful, when + /// you want to store multiple `dyn FileSystem` in a `Vec` or use a `ResolverGeneric` in + /// napi env. + fn metadata(&self, path: &Path) -> io::Result; /// See [std::fs::symlink_metadata] /// /// # Errors /// /// See [std::fs::symlink_metadata] - fn symlink_metadata>(&self, path: P) -> io::Result; + /// ## Warning + /// Use `&Path` instead of a generic `P: AsRef` here, + /// because object safety requirements, it is especially useful, when + /// you want to store multiple `dyn FileSystem` in a `Vec` or use a `ResolverGeneric` in + /// napi env. + fn symlink_metadata(&self, path: &Path) -> io::Result; /// See [std::fs::canonicalize] /// /// # Errors /// /// See [std::fs::read_link] - fn canonicalize>(&self, path: P) -> io::Result; + /// ## Warning + /// Use `&Path` instead of a generic `P: AsRef` here, + /// because object safety requirements, it is especially useful, when + /// you want to store multiple `dyn FileSystem` in a `Vec` or use a `ResolverGeneric` in + /// napi env. + fn canonicalize(&self, path: &Path) -> io::Result; } /// Metadata information about a file. @@ -59,19 +78,19 @@ impl From for FileMetadata { pub struct FileSystemOs; impl FileSystem for FileSystemOs { - fn read_to_string>(&self, path: P) -> io::Result { + fn read_to_string(&self, path: &Path) -> io::Result { fs::read_to_string(path) } - fn metadata>(&self, path: P) -> io::Result { + fn metadata(&self, path: &Path) -> io::Result { fs::metadata(path).map(FileMetadata::from) } - fn symlink_metadata>(&self, path: P) -> io::Result { + fn symlink_metadata(&self, path: &Path) -> io::Result { fs::symlink_metadata(path).map(FileMetadata::from) } - fn canonicalize>(&self, path: P) -> io::Result { + fn canonicalize(&self, path: &Path) -> io::Result { dunce::canonicalize(path) } } diff --git a/crates/oxc_resolver/src/tests/memory_fs.rs b/crates/oxc_resolver/src/tests/memory_fs.rs index 186327061..e25e3e856 100644 --- a/crates/oxc_resolver/src/tests/memory_fs.rs +++ b/crates/oxc_resolver/src/tests/memory_fs.rs @@ -40,33 +40,33 @@ impl MemoryFS { } impl FileSystem for MemoryFS { - fn read_to_string>(&self, path: P) -> io::Result { + fn read_to_string(&self, path: &Path) -> io::Result { use vfs::FileSystem; let mut file = self .fs - .open_file(path.as_ref().to_string_lossy().as_ref()) + .open_file(path.to_string_lossy().as_ref()) .map_err(|err| io::Error::new(io::ErrorKind::NotFound, err))?; let mut buffer = String::new(); file.read_to_string(&mut buffer).unwrap(); Ok(buffer) } - fn metadata>(&self, path: P) -> io::Result { + fn metadata(&self, path: &Path) -> io::Result { use vfs::FileSystem; let metadata = self .fs - .metadata(path.as_ref().to_string_lossy().as_ref()) + .metadata(path.to_string_lossy().as_ref()) .map_err(|err| io::Error::new(io::ErrorKind::NotFound, err))?; let is_file = metadata.file_type == vfs::VfsFileType::File; let is_dir = metadata.file_type == vfs::VfsFileType::Directory; Ok(FileMetadata::new(is_file, is_dir, false)) } - fn symlink_metadata>(&self, path: P) -> io::Result { + fn symlink_metadata(&self, path: &Path) -> io::Result { self.metadata(path) } - fn canonicalize>(&self, _path: P) -> io::Result { + fn canonicalize(&self, _path: &Path) -> io::Result { Err(io::Error::new(io::ErrorKind::NotFound, "not a symlink")) } }