go-parsekit/reader_test.go

135 lines
3.0 KiB
Go
Raw Blame History

package parsekit
import (
"fmt"
"io"
"strings"
"testing"
"git.makaay.nl/mauricem/go-parsekit/assert"
)
func ExampleNewReader() {
in := strings.NewReader("Hello, world!")
r := NewReader(in)
at := func(i int) rune { r, _ := r.RuneAt(i); return r }
fmt.Printf("%c", at(0))
fmt.Printf("%c", at(12))
// Output:
// H!
}
func ExampleReader_RuneAt() {
in := strings.NewReader("Hello, world!")
r := NewReader(in)
at := func(i int) rune { r, _ := r.RuneAt(i); return r }
// It is possible to go back and forth while reading the input.
fmt.Printf("%c", at(0))
fmt.Printf("%c", at(12))
fmt.Printf("%c", at(7))
fmt.Printf("%c", at(0))
// Output:
// H!wH
}
func ExampleReader_RuneAt_endOfFile() {
in := strings.NewReader("Hello, world!")
r := NewReader(in)
rn, err := r.RuneAt(13)
fmt.Printf("%q %s %t\n", rn, err, err == io.EOF)
rn, err = r.RuneAt(20)
fmt.Printf("%q %s %t\n", rn, err, err == io.EOF)
// Output:
// '<27>' EOF true
// '<27>' EOF true
}
func ExampleReader_RuneAt_invalidRune() {
in := strings.NewReader("Hello, \xcdworld!")
r := NewReader(in)
rn, err := r.RuneAt(6)
fmt.Printf("%q %t\n", rn, err == nil)
rn, err = r.RuneAt(7)
fmt.Printf("%q %t\n", rn, err == nil)
rn, err = r.RuneAt(8)
fmt.Printf("%q %t\n", rn, err == nil)
rn, err = r.RuneAt(9)
fmt.Printf("%q %t\n", rn, err == nil)
// Output:
// ' ' true
// '<27>' true
// 'w' true
// 'o' true
}
func ExampleReader_RunesAt() {
in := strings.NewReader("Hello, \xcdworld!")
r := NewReader(in)
rs, err := r.RunesAt(4, 6)
fmt.Printf("%q %t\n", string(rs), err == nil)
rs, err = r.RunesAt(4, 0)
fmt.Printf("%q %t\n", string(rs), err == nil)
rs, err = r.RunesAt(8, 100)
fmt.Printf("%q %t\n", string(rs), err == io.EOF)
// Output:
// "o, <20>wo" true
// "" true
// "world!" true
}
func TestRuneAt_SkipsBOMAtStartOfFile(t *testing.T) {
in := strings.NewReader("\uFEFFBommetje!")
r := NewReader(in)
b, _ := r.RuneAt(0)
o, _ := r.RuneAt(1)
m, _ := r.RuneAt(2)
bom := fmt.Sprintf("%c%c%c", b, o, m)
assert.Equal(t, "Bom", bom, "first three runes")
}
func ExampleReader_Flush() {
in := strings.NewReader("Hello, world!")
r := NewReader(in)
at := func(i int) rune { r, _ := r.RuneAt(i); return r }
rb := func(start int, len int) []rune { r, _ := r.RunesAt(start, len); return r }
// Fills the buffer with the first 8 runes on the input: "Hello, w"
fmt.Printf("%c\n", at(7))
// Now flush the first 4 runes from the buffer (dropping "Hell" from it)
r.Flush(4)
// Rune 0 is now pointing at what originally was rune offset 4.
// We can continue reading from there.
fmt.Printf("%s", string(rb(0, 8)))
// Output:
// w
// o, world
}
func TestGivenNumberOfRunesTooHigh_Flush_Panics(t *testing.T) {
in := strings.NewReader("Hello, world!")
r := NewReader(in)
// Fill buffer with "Hello, worl", the first 11 runes.
r.RuneAt(10)
// However, we flush 12 runes, which exceeds the buffer size.
assert.Panic(t, assert.PanicT{
Function: func() { r.Flush(12) },
Expect: "parsekit.Input.Reader.Flush(): number of runes to flush (12) exceeds size of the buffer (11)",
})
}