///|
async test "binary pipe quick start" {
@async.with_task_group() <| root => {
let (reader, writer) = @io.pipe()
defer reader.close()
root.spawn_bg() <| () => {
defer writer.close()
writer.write(b"Hello, ")
writer.write(b"MoonBit!")
}
inspect(@utf8.decode(reader.read_all()), content="Hello, MoonBit!")
}
}///|
async test "read into caller-owned storage" {
@async.with_task_group() <| root => {
let (reader, writer) = @io.pipe()
defer reader.close()
root.spawn_bg() <| () => {
defer writer.close()
writer.write(b"hello")
}
let dst = FixedArray::make(9, b'.')
let count = reader.read_into(dst, offset=2, max_len=5)
inspect(count, content="5")
inspect(
@utf8.decode(dst.unsafe_reinterpret_as_bytes()[2:7]),
content="hello",
)
}
}///|
async test "peek then consume an exact frame" {
@async.with_task_group() <| root => {
let (reader, writer) = @io.pipe()
defer reader.close()
root.spawn_bg() <| () => {
defer writer.close()
writer.write(b"HEADbody")
}
let preview = reader.peek_exactly(4).to_owned()
inspect(@utf8.decode(preview), content="HEAD")
inspect(@utf8.decode(reader.read_exactly(4)), content="HEAD")
inspect(@utf8.decode(reader.read_all()), content="body")
}
}///|
async test "read delimiter-separated binary records" {
@async.with_task_group() <| root => {
let (reader, writer) = @io.pipe()
defer reader.close()
root.spawn_bg() <| () => {
defer writer.close()
writer.write(b"alpha|beta")
}
guard reader.read_until(b"|") is Some(first) else {
fail("missing first record")
}
inspect(@utf8.decode(first), content="alpha")
guard reader.read_until(b"|") is Some(second) else {
fail("missing final record")
}
inspect(@utf8.decode(second), content="beta")
assert_eq(reader.read_until(b"|"), None)
}
}///|
async test "write a byte view" {
@async.with_task_group() <| root => {
let (reader, writer) = @io.pipe()
defer reader.close()
root.spawn_bg() <| () => {
defer writer.close()
let packet = b"xxpayloadyy"
writer.write(packet[2:9])
}
inspect(@utf8.decode(reader.read_all()), content="payload")
}
}///|
async test "UTF-8 text adapters" {
@async.with_task_group() <| root => {
let (reader, writer) = @io.pipe()
defer reader.close()
root.spawn_bg() <| () => {
defer writer.close()
let text_writer = @io.Utf8Writer(writer)
text_writer.write("你好|MoonBit")
}
let text_reader = @io.Utf8Reader(reader)
guard text_reader.read_until("|") is Some(first) else {
fail("missing first text record")
}
inspect(first, content="你好")
inspect(text_reader.read_all(), content="MoonBit")
}
}///|
async test "callback-backed memory reader" {
let reader = @io.MemoryReader() <| writer => {
writer.write(b"generated ")
@async.sleep(10)
writer.write(b"content")
}
defer reader.close()
inspect(@utf8.decode(reader.read_all()), content="generated content")
}///|
async test "buffered writer" {
@async.with_task_group() <| root => {
let (reader, writer) = @io.pipe()
defer reader.close()
root.spawn_bg() <| () => {
defer writer.close()
let buffered = @io.BufferedWriter::new(writer, size=4)
buffered.write(b"ab")
buffered.write(b"cd")
buffered.write(b"ef")
buffered.flush()
}
inspect(@utf8.decode(reader.read_all()), content="abcdef")
}
}///|
pub(open) trait BinaryReaderImpl {
fn get_controller(Self) -> BinaryReaderController
async fn raw_read_impl(
Self,
FixedArray[Byte],
offset~ : Int32,
max_len~ : Int32,
) -> Int32
}
///|
pub(open) trait BinaryWriterImpl {
fn get_controller(Self) -> BinaryWriterController
async fn raw_write_impl(Self, Bytes, offset~ : Int32, len~ : Int32) -> Int32
}pub(open) trait BinaryReader : BinaryReaderImpl {
async fn read_into(Self, FixedArray[Byte], offset? : Int, max_len? : Int) -> Int = _
async fn read(Self) -> Bytes? = _
async fn read_at_least(Self, Int) -> Bytes = _
async fn peek(Self) -> BytesView? = _
async fn peek_at_least(Self, Int) -> BytesView = _
async fn read_exactly(Self, len : Int) -> Bytes = _
async fn drop_exactly(Self, len : Int) -> Unit = _
async fn peek_exactly(Self, len : Int) -> BytesView = _
async fn read_all(Self) -> Bytes = _
async fn drop_all(Self) -> Int64 = _
async fn read_until(Self, pattern : BytesView, include_delimiter? : Bool) -> Bytes? = _
async fn peek_until(Self, pattern : BytesView, include_delimiter? : Bool) -> BytesView? = _
}pub(open) trait BinaryReaderImpl {
fn get_controller(Self) -> BinaryReaderController
async fn raw_read_impl(Self, buf : FixedArray[Byte], offset~ : Int, max_len~ : Int) -> Int
async fn ensure_buffered(Self, Int) -> Bool = _
}pub(open) trait BinaryWriter : BinaryWriterImpl {
async fn write(Self, BytesView) -> Unit = _
async fn write_reader(Self, &BinaryReader) -> Unit = _
}pub(open) trait BinaryWriterImpl {
fn get_controller(Self) -> BinaryWriterController
async fn raw_write_impl(Self, Bytes, offset~ : Int, len~ : Int) -> Int
}pub(open) trait TextReader {
async fn read(Self) -> String?
async fn read_all(Self) -> String
async fn read_until(Self, StringView, include_delimiter? : Bool) -> String?
}pub(open) trait TextWriter {
async fn write(Self, StringView) -> Unit
async fn write_json(Self, Json) -> Unit
}type BinaryReaderControllertype BinaryWriterControllertype BufferedWriter[W]impl BinaryWriter for BufferedWriter[W]async fn[W : BinaryWriter + BinaryWriterImpl] BufferedWriter::flush(self : BufferedWriter[W]) -> Unitasync fn[W : BinaryWriter + BinaryWriterImpl] BufferedWriter::write(self : BufferedWriter[W], data : BytesView) -> Unitasync fn[W : BinaryWriter + BinaryWriterImpl] BufferedWriter::write_reader(self : BufferedWriter[W], reader : &BinaryReader) -> Unittype MemoryReaderimpl BinaryReader for MemoryReader#callsite(autofill(loc))
fn MemoryReader::MemoryReader(f : async (&BinaryWriter) -> Unit, loc~ : SourceLoc) -> MemoryReaderasync fn MemoryReader::peek_until(self : MemoryReader, pattern : BytesView, include_delimiter? : Bool) -> BytesView?async fn MemoryReader::read_into(self : MemoryReader, dst : FixedArray[Byte], offset? : Int, max_len? : Int) -> Intasync fn MemoryReader::read_until(self : MemoryReader, pattern : BytesView, include_delimiter? : Bool) -> Bytes?type PipeReadimpl BinaryReader for PipeReadtype PipeWriteimpl BinaryWriter for PipeWritetype Utf8Readerimpl TextReader for Utf8Readerasync fn Utf8Reader::read_until(self : Utf8Reader, pattern : StringView, include_delimiter? : Bool) -> String?type Utf8TextViewimpl TextReader for Utf8TextViewasync fn read_until(self : Utf8TextView, pattern : StringView, include_delimiter? : Bool) -> String?impl TextWriter for Utf8TextViewasync fn Utf8TextView::read_until(self : Utf8TextView, pattern : StringView, include_delimiter? : Bool) -> String?type Utf8Writerimpl TextWriter for Utf8WriterInstall
Installed by default