stream.go 1.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354
  1. package fasthttp
  2. import (
  3. "bufio"
  4. "io"
  5. "sync"
  6. "github.com/valyala/fasthttp/fasthttputil"
  7. )
  8. // StreamWriter must write data to w.
  9. //
  10. // Usually StreamWriter writes data to w in a loop (aka 'data streaming').
  11. //
  12. // StreamWriter must return immediately if w returns error.
  13. //
  14. // Since the written data is buffered, do not forget calling w.Flush
  15. // when the data must be propagated to reader.
  16. type StreamWriter func(w *bufio.Writer)
  17. // NewStreamReader returns a reader, which replays all the data generated by sw.
  18. //
  19. // The returned reader may be passed to Response.SetBodyStream.
  20. //
  21. // Close must be called on the returned reader after all the required data
  22. // has been read. Otherwise goroutine leak may occur.
  23. //
  24. // See also Response.SetBodyStreamWriter.
  25. func NewStreamReader(sw StreamWriter) io.ReadCloser {
  26. pc := fasthttputil.NewPipeConns()
  27. pw := pc.Conn1()
  28. pr := pc.Conn2()
  29. var bw *bufio.Writer
  30. v := streamWriterBufPool.Get()
  31. if v == nil {
  32. bw = bufio.NewWriter(pw)
  33. } else {
  34. bw = v.(*bufio.Writer)
  35. bw.Reset(pw)
  36. }
  37. go func() {
  38. sw(bw)
  39. bw.Flush()
  40. pw.Close()
  41. streamWriterBufPool.Put(bw)
  42. }()
  43. return pr
  44. }
  45. var streamWriterBufPool sync.Pool