gbytes.Buffer implements io.Reader

Signed-off-by: Alex Suraci <asuraci@pivotal.io>
diff --git a/gbytes/buffer.go b/gbytes/buffer.go
index 7e42334..8775b86 100644
--- a/gbytes/buffer.go
+++ b/gbytes/buffer.go
@@ -14,6 +14,7 @@
 import (
 	"errors"
 	"fmt"
+	"io"
 	"regexp"
 	"sync"
 	"time"
@@ -67,6 +68,30 @@
 }
 
 /*
+Read implements the io.Reader interface. It advances the
+cursor as it reads.
+
+Returns an error if called after Close.
+*/
+func (b *Buffer) Read(d []byte) (int, error) {
+	b.lock.Lock()
+	defer b.lock.Unlock()
+
+	if b.closed {
+		return 0, errors.New("attempt to read from closed buffer")
+	}
+
+	if uint64(len(b.contents)) <= b.readCursor {
+		return 0, io.EOF
+	}
+
+	n := copy(d, b.contents[b.readCursor:])
+	b.readCursor += uint64(n)
+
+	return n, nil
+}
+
+/*
 Close signifies that the buffer will no longer be written to
 */
 func (b *Buffer) Close() error {
diff --git a/gbytes/buffer_test.go b/gbytes/buffer_test.go
index 9aa2937..b111138 100644
--- a/gbytes/buffer_test.go
+++ b/gbytes/buffer_test.go
@@ -1,7 +1,9 @@
 package gbytes_test
 
 import (
+	"io"
 	"time"
+
 	. "github.com/onsi/gomega/gbytes"
 
 	. "github.com/onsi/ginkgo"
@@ -36,6 +38,41 @@
 		})
 	})
 
+	Describe("reading from a buffer", func() {
+		It("should read the current contents of the buffer", func() {
+			buffer := BufferWithBytes([]byte("abcde"))
+
+			dest := make([]byte, 3)
+			n, err := buffer.Read(dest)
+			Ω(err).ShouldNot(HaveOccurred())
+			Ω(n).Should(Equal(3))
+			Ω(string(dest)).Should(Equal("abc"))
+
+			dest = make([]byte, 3)
+			n, err = buffer.Read(dest)
+			Ω(err).ShouldNot(HaveOccurred())
+			Ω(n).Should(Equal(2))
+			Ω(string(dest[:n])).Should(Equal("de"))
+
+			n, err = buffer.Read(dest)
+			Ω(err).Should(Equal(io.EOF))
+			Ω(n).Should(Equal(0))
+		})
+
+		Context("after the buffer has been closed", func() {
+			It("returns an error", func() {
+				buffer := BufferWithBytes([]byte("abcde"))
+
+				buffer.Close()
+
+				dest := make([]byte, 3)
+				n, err := buffer.Read(dest)
+				Ω(err).Should(HaveOccurred())
+				Ω(n).Should(Equal(0))
+			})
+		})
+	})
+
 	Describe("detecting regular expressions", func() {
 		It("should fire the appropriate channel when the passed in pattern matches, then close it", func(done Done) {
 			go func() {