Repository: bevyengine/bevy
File: crates/bevy_asset/src/io/mod.rs (Rust)

Code before:
    /// let reader = match reader.seekable() {
    ///     Ok(seek) => seek,
    ///     Err(_) => {
    ///         fallback_reader = VecReader::new(Vec::new());
    ///         reader.read_to_end(&mut fallback_reader.bytes).await.unwrap();
    ///         &mut fallback_reader
    ///     }
    /// };
    /// reader.seek(SeekFrom::Start(10)).await.unwrap();
    /// # };
    /// ```
    fn seekable(&mut self) -> Result<&mut dyn SeekableReader, ReaderNotSeekableError>;
}

pub trait SeekableReader: Reader + AsyncSeek {}

impl<T: Reader + AsyncSeek> SeekableReader for T {}

#[derive(Error, Debug, Copy, Clone)]
#[error(
    "The `Reader` returned by the current `AssetReader` does not support `AsyncSeek` behavior."
)]
pub struct ReaderNotSeekableError;

impl Reader for Box<dyn Reader + '_> {
    fn read_to_end<'a>(
        &'a mut self,
        buf: &'a mut Vec<u8>,
    ) -> StackFuture<'a, std::io::Result<usize>, STACK_FUTURE_SIZE> {
        (**self).read_to_end(buf)
    }

    fn seekable(&mut self) -> Result<&mut dyn SeekableReader, ReaderNotSeekableError> {
        (**self).seekable()
    }
}

/// A future that returns a value or an [`AssetReaderError`]
pub trait AssetReaderFuture:
    ConditionalSendFuture<Output = Result<Self::Value, AssetReaderError>>
{
    type Value;
}

impl<F, T> AssetReaderFuture for F
where
    F: ConditionalSendFuture<Output = Result<T, AssetReaderError>>,
{
    type Value = T;
}


Review comment (bug):
```suggestion
/// Error returned by [`Reader::seekable`] when the reader implementation does not support [`AsyncSeek`] behavior.
#[derive(Error, Debug, Copy, Clone)]
#[error(
    "The `Reader` returned by the current `AssetReader` does not support `AsyncSeek` behavior."
)]
pub struct ReaderNotSeekableError;
```

Code after:
    /// let reader = match reader.seekable() {
    ///     Ok(seek) => seek,
    ///     Err(_) => {
    ///         fallback_reader = VecReader::new(Vec::new());
    ///         reader.read_to_end(&mut fallback_reader.bytes).await.unwrap();
    ///         &mut fallback_reader
    ///     }
    /// };
    /// reader.seek(SeekFrom::Start(10)).await.unwrap();
    /// # };
    /// ```
    fn seekable(&mut self) -> Result<&mut dyn SeekableReader, ReaderNotSeekableError>;
}

/// A [`Reader`] that also has [`AsyncSeek`] functionality.
/// See [`Reader::seekable`] for details.
pub trait SeekableReader: Reader + AsyncSeek {}

impl<T: Reader + AsyncSeek> SeekableReader for T {}

/// Error returned by [`Reader::seekable`] when the reader implementation does not support [`AsyncSeek`] behavior.
#[derive(Error, Debug, Copy, Clone)]
#[error(
    "The `Reader` returned by the current `AssetReader` does not support `AsyncSeek` behavior."
)]
pub struct ReaderNotSeekableError;

impl Reader for Box<dyn Reader + '_> {
    fn read_to_end<'a>(
        &'a mut self,
        buf: &'a mut Vec<u8>,
    ) -> StackFuture<'a, std::io::Result<usize>, STACK_FUTURE_SIZE> {
        (**self).read_to_end(buf)
    }

    fn seekable(&mut self) -> Result<&mut dyn SeekableReader, ReaderNotSeekableError> {
        (**self).seekable()
    }
}

/// A future that returns a value or an [`AssetReaderError`]
pub trait AssetReaderFuture:
    ConditionalSendFuture<Output = Result<Self::Value, AssetReaderError>>
{
    type Value;
}

impl<F, T> AssetReaderFuture for F
where
    F: ConditionalSendFuture<Output = Result<T, AssetReaderError>>,
{