@@ -178,9 +178,9 @@ impl<W: AsyncWrite + Unpin> BufWriter<W> {
178
178
& mut self . inner
179
179
}
180
180
181
- pub fn get_pin_mut ( self : Pin < & mut Self > ) -> Pin < & mut W > {
182
- self . inner ( )
183
- }
181
+ // pub fn get_pin_mut(self: Pin<&mut Self>) -> Pin<&mut W> {
182
+ // self.inner()
183
+ // }
184
184
185
185
/// Consumes BufWriter, returning the underlying writer
186
186
///
@@ -192,9 +192,9 @@ impl<W: AsyncWrite + Unpin> BufWriter<W> {
192
192
self . inner
193
193
}
194
194
195
- pub fn poll_into_inner ( self : Pin < & mut Self > , _cx : Context < ' _ > ) -> Poll < io:: Result < usize > > {
196
- unimplemented ! ( "poll into inner method" )
197
- }
195
+ // pub fn poll_into_inner(self: Pin<&mut Self>, _cx: Context<'_>) -> Poll<io::Result<usize>> {
196
+ // unimplemented!("poll into inner method")
197
+ // }
198
198
199
199
/// Returns a reference to the internally buffered data.
200
200
///
@@ -217,7 +217,11 @@ impl<W: AsyncWrite + Unpin> BufWriter<W> {
217
217
& self . buf
218
218
}
219
219
220
-
220
+ /// Poll buffer flushing until completion
221
+ ///
222
+ /// This is used in types that wrap around BufWrite, one such example: [`LineWriter`]
223
+ ///
224
+ /// [`LineWriter`]: struct.LineWriter.html
221
225
pub fn poll_flush_buf ( self : Pin < & mut Self > , cx : & mut Context < ' _ > ) -> Poll < io:: Result < ( ) > > {
222
226
let Self {
223
227
inner,
@@ -289,6 +293,73 @@ impl<W: AsyncWrite + fmt::Debug + Unpin> fmt::Debug for BufWriter<W> {
289
293
}
290
294
}
291
295
296
+ /// Wraps a writer and buffers output to it, flushing whenever a newline
297
+ /// (`0x0a`, `'\n'`) is detected.
298
+ ///
299
+ /// The [`BufWriter`][bufwriter] struct wraps a writer and buffers its output.
300
+ /// But it only does this batched write when it goes out of scope, or when the
301
+ /// internal buffer is full. Sometimes, you'd prefer to write each line as it's
302
+ /// completed, rather than the entire buffer at once. Enter `LineWriter`. It
303
+ /// does exactly that.
304
+ ///
305
+ /// Like [`BufWriter`][bufwriter], a `LineWriter`’s buffer will also be flushed when the
306
+ /// `LineWriter` goes out of scope or when its internal buffer is full.
307
+ ///
308
+ /// [bufwriter]: struct.BufWriter.html
309
+ ///
310
+ /// If there's still a partial line in the buffer when the `LineWriter` is
311
+ /// dropped, it will flush those contents.
312
+ ///
313
+ /// This type is an async version of [`std::io::LineWriter`]
314
+ ///
315
+ /// [`std::io::LineWriter`]: https://doc.rust-lang.org/std/io/struct.LineWriter.html
316
+ ///
317
+ /// # Examples
318
+ ///
319
+ /// We can use `LineWriter` to write one line at a time, significantly
320
+ /// reducing the number of actual writes to the file.
321
+ ///
322
+ /// ```no_run
323
+ /// # #![feature(async_await)]
324
+ /// # fn main() -> std::io::Result<()> { async_std::task::block_on(async {
325
+ /// use async_std::io::{LineWriter, Write};
326
+ /// use async_std::fs::{File, self};
327
+ /// let road_not_taken = b"I shall be telling this with a sigh
328
+ /// Somewhere ages and ages hence:
329
+ /// Two roads diverged in a wood, and I -
330
+ /// I took the one less traveled by,
331
+ /// And that has made all the difference.";
332
+ ///
333
+ /// let file = File::create("poem.txt").await?;
334
+ /// let mut file = LineWriter::new(file);
335
+ ///
336
+ /// file.write_all(b"I shall be telling this with a sigh").await?;
337
+ ///
338
+ /// // No bytes are written until a newline is encountered (or
339
+ /// // the internal buffer is filled).
340
+ /// assert_eq!(fs::read_to_string("poem.txt").await?, "");
341
+ /// file.write_all(b"\n").await?;
342
+ /// assert_eq!(
343
+ /// fs::read_to_string("poem.txt").await?,
344
+ /// "I shall be telling this with a sigh\n",
345
+ /// );
346
+ ///
347
+ /// // Write the rest of the poem.
348
+ /// file.write_all(b"Somewhere ages and ages hence:
349
+ /// Two roads diverged in a wood, and I -
350
+ /// I took the one less traveled by,
351
+ /// And that has made all the difference.").await?;
352
+ ///
353
+ /// // The last line of the poem doesn't end in a newline, so
354
+ /// // we have to flush or drop the `LineWriter` to finish
355
+ /// // writing.
356
+ /// file.flush().await?;
357
+ ///
358
+ /// // Confirm the whole poem was written.
359
+ /// assert_eq!(fs::read("poem.txt").await?, &road_not_taken[..]);
360
+ /// #
361
+ /// # Ok(()) }) }
362
+ /// ```
292
363
pub struct LineWriter < W : AsyncWrite + Unpin > {
293
364
inner : BufWriter < W > ,
294
365
need_flush : bool ,
@@ -340,14 +411,57 @@ impl<W: AsyncWrite + Unpin> LineWriter<W> {
340
411
}
341
412
}
342
413
414
+ /// Gets a reference to the underlying writer.
415
+ ///
416
+ /// # Examples
417
+ ///
418
+ /// ```no_run
419
+ /// # #![feature(async_await)]
420
+ /// # #![allow(unused_mut)]
421
+ /// # fn main() -> std::io::Result<()> { async_std::task::block_on(async {
422
+ /// use async_std::io::LineWriter;
423
+ /// use async_std::fs::File;
424
+ ///
425
+ /// let file = File::create("poem.txt").await?;
426
+ /// let file = LineWriter::new(file);
427
+ ///
428
+ /// // We can use reference just like buffer
429
+ /// let reference = file.get_ref();
430
+ /// #
431
+ /// # Ok(()) }) }
432
+ /// ```
343
433
pub fn get_ref ( & self ) -> & W {
344
434
self . inner . get_ref ( )
345
435
}
346
436
437
+ /// Gets a mutable reference to the underlying writer.
438
+ ///
439
+ /// Caution must be taken when calling methods on the mutable reference
440
+ /// returned as extra writes could corrupt the output stream.
441
+ ///
442
+ /// # Examples
443
+ ///
444
+ /// ```no_run
445
+ /// # #![feature(async_await)]
446
+ /// # #![allow(unused_mut)]
447
+ /// # fn main() -> std::io::Result<()> { async_std::task::block_on(async {
448
+ /// use async_std::io::LineWriter;
449
+ /// use async_std::fs::File;
450
+ ///
451
+ /// let file = File::create("poem.txt").await?;
452
+ /// let mut file = LineWriter::new(file);
453
+ ///
454
+ /// // We can use reference just like buffer
455
+ /// let reference = file.get_mut();
456
+ /// #
457
+ /// # Ok(()) }) }
458
+ /// ```
347
459
pub fn get_mut ( & mut self ) -> & mut W {
348
460
self . inner . get_mut ( )
349
461
}
350
462
463
+ //TODO: Implement flushing before returning inner
464
+ #[ allow( missing_docs) ]
351
465
pub fn into_inner ( self ) -> W {
352
466
self . inner . into_inner ( )
353
467
}
@@ -360,7 +474,7 @@ impl<W: AsyncWrite + Unpin> AsyncWrite for LineWriter<W> {
360
474
buf : & [ u8 ] ,
361
475
) -> Poll < io:: Result < usize > > {
362
476
if self . need_flush {
363
- self . as_mut ( ) . poll_flush ( cx) ?;
477
+ let _ = self . as_mut ( ) . poll_flush ( cx) ?;
364
478
}
365
479
366
480
let i = match memchr:: memrchr ( b'\n' , buf) {
@@ -380,13 +494,13 @@ impl<W: AsyncWrite + Unpin> AsyncWrite for LineWriter<W> {
380
494
}
381
495
382
496
fn poll_flush ( mut self : Pin < & mut Self > , cx : & mut Context < ' _ > ) -> Poll < io:: Result < ( ) > > {
383
- self . as_mut ( ) . inner ( ) . poll_flush ( cx) ?;
497
+ let _ = self . as_mut ( ) . inner ( ) . poll_flush ( cx) ?;
384
498
* self . need_flush ( ) = false ;
385
499
Poll :: Ready ( Ok ( ( ) ) )
386
500
}
387
501
388
502
fn poll_close ( mut self : Pin < & mut Self > , cx : & mut Context < ' _ > ) -> Poll < io:: Result < ( ) > > {
389
- self . as_mut ( ) . inner ( ) . poll_flush ( cx) ?;
503
+ let _ = self . as_mut ( ) . inner ( ) . poll_flush ( cx) ?;
390
504
self . inner ( ) . poll_close ( cx)
391
505
}
392
506
}
0 commit comments