gzippool.go 999 B

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970
  1. package main
  2. import (
  3. "compress/gzip"
  4. "fmt"
  5. "io"
  6. "io/ioutil"
  7. "sync"
  8. )
  9. type gzipPool struct {
  10. mutex sync.Mutex
  11. top *gzipPoolEntry
  12. }
  13. type gzipPoolEntry struct {
  14. gz *gzip.Writer
  15. next *gzipPoolEntry
  16. }
  17. func newGzipPool(n int) (*gzipPool, error) {
  18. pool := new(gzipPool)
  19. for i := 0; i < n; i++ {
  20. if err := pool.grow(); err != nil {
  21. return nil, err
  22. }
  23. }
  24. return pool, nil
  25. }
  26. func (p *gzipPool) grow() error {
  27. gz, err := gzip.NewWriterLevel(ioutil.Discard, conf.GZipCompression)
  28. if err != nil {
  29. return fmt.Errorf("Can't init GZip compression: %s", err)
  30. }
  31. p.top = &gzipPoolEntry{
  32. gz: gz,
  33. next: p.top,
  34. }
  35. return nil
  36. }
  37. func (p *gzipPool) Get(w io.Writer) *gzip.Writer {
  38. p.mutex.Lock()
  39. defer p.mutex.Unlock()
  40. if p.top == nil {
  41. p.grow()
  42. }
  43. gz := p.top.gz
  44. gz.Reset(w)
  45. p.top = p.top.next
  46. return gz
  47. }
  48. func (p *gzipPool) Put(gz *gzip.Writer) {
  49. p.mutex.Lock()
  50. defer p.mutex.Unlock()
  51. gz.Reset(ioutil.Discard)
  52. p.top = &gzipPoolEntry{gz: gz, next: p.top}
  53. }