2021-02-15 17:20:37 -07:00
|
|
|
package gemini
|
|
|
|
|
|
|
|
import (
|
|
|
|
"io"
|
2021-02-24 00:52:23 -07:00
|
|
|
"io/ioutil"
|
2021-02-15 17:20:37 -07:00
|
|
|
"strings"
|
|
|
|
"testing"
|
|
|
|
)
|
|
|
|
|
2021-02-17 22:07:43 -07:00
|
|
|
func TestReadWriteResponse(t *testing.T) {
|
2021-02-15 17:20:37 -07:00
|
|
|
tests := []struct {
|
2021-02-17 22:07:43 -07:00
|
|
|
Raw string
|
2021-02-20 14:15:26 -07:00
|
|
|
Status Status
|
2021-02-17 22:07:43 -07:00
|
|
|
Meta string
|
|
|
|
Body string
|
|
|
|
Err error
|
|
|
|
SkipWrite bool
|
2021-02-15 17:20:37 -07:00
|
|
|
}{
|
|
|
|
{
|
|
|
|
Raw: "20 text/gemini\r\nHello, world!\nWelcome to my capsule.",
|
|
|
|
Status: 20,
|
|
|
|
Meta: "text/gemini",
|
|
|
|
Body: "Hello, world!\nWelcome to my capsule.",
|
|
|
|
},
|
|
|
|
{
|
|
|
|
Raw: "10 Search query\r\n",
|
|
|
|
Status: 10,
|
|
|
|
Meta: "Search query",
|
|
|
|
},
|
|
|
|
{
|
|
|
|
Raw: "30 /redirect\r\n",
|
|
|
|
Status: 30,
|
|
|
|
Meta: "/redirect",
|
|
|
|
},
|
|
|
|
{
|
2021-02-17 22:07:43 -07:00
|
|
|
Raw: "31 /redirect\r\nThis body is ignored.",
|
|
|
|
Status: 31,
|
|
|
|
Meta: "/redirect",
|
|
|
|
SkipWrite: true, // skip write test since result won't match Raw
|
2021-02-15 17:20:37 -07:00
|
|
|
},
|
|
|
|
{
|
|
|
|
Raw: "99 Unknown status code\r\n",
|
|
|
|
Status: 99,
|
|
|
|
Meta: "Unknown status code",
|
|
|
|
},
|
|
|
|
{
|
|
|
|
Raw: "\r\n",
|
|
|
|
Err: ErrInvalidResponse,
|
|
|
|
},
|
|
|
|
{
|
|
|
|
Raw: "\n",
|
|
|
|
Err: ErrInvalidResponse,
|
|
|
|
},
|
|
|
|
{
|
|
|
|
Raw: "1 Bad response\r\n",
|
|
|
|
Err: ErrInvalidResponse,
|
|
|
|
},
|
|
|
|
{
|
|
|
|
Raw: "",
|
|
|
|
Err: io.EOF,
|
|
|
|
},
|
|
|
|
{
|
|
|
|
Raw: "10 Search query",
|
|
|
|
Err: io.EOF,
|
|
|
|
},
|
|
|
|
{
|
|
|
|
Raw: "20 text/gemini\nHello, world!",
|
|
|
|
Err: io.EOF,
|
|
|
|
},
|
|
|
|
{
|
|
|
|
Raw: "20 text/gemini\rHello, world!",
|
|
|
|
Err: ErrInvalidResponse,
|
|
|
|
},
|
|
|
|
{
|
|
|
|
Raw: "20 text/gemini\r",
|
|
|
|
Err: io.EOF,
|
|
|
|
},
|
|
|
|
{
|
|
|
|
Raw: "abcdefghijklmnopqrstuvwxyz",
|
|
|
|
Err: ErrInvalidResponse,
|
|
|
|
},
|
|
|
|
}
|
|
|
|
|
|
|
|
for _, test := range tests {
|
|
|
|
t.Logf("%#v", test.Raw)
|
2021-02-24 00:52:23 -07:00
|
|
|
resp, err := ReadResponse(ioutil.NopCloser(strings.NewReader(test.Raw)))
|
2021-02-15 17:20:37 -07:00
|
|
|
if err != test.Err {
|
|
|
|
t.Errorf("expected err = %v, got %v", test.Err, err)
|
|
|
|
}
|
|
|
|
if test.Err != nil {
|
|
|
|
// No response
|
|
|
|
continue
|
|
|
|
}
|
2021-02-24 06:43:57 -07:00
|
|
|
if resp.status != test.Status {
|
|
|
|
t.Errorf("expected status = %d, got %d", test.Status, resp.status)
|
2021-02-15 17:20:37 -07:00
|
|
|
}
|
2021-02-24 06:43:57 -07:00
|
|
|
if resp.meta != test.Meta {
|
|
|
|
t.Errorf("expected meta = %s, got %s", test.Meta, resp.meta)
|
2021-02-15 17:20:37 -07:00
|
|
|
}
|
2021-02-24 00:52:23 -07:00
|
|
|
b, _ := ioutil.ReadAll(resp.body)
|
2021-02-15 17:20:37 -07:00
|
|
|
body := string(b)
|
|
|
|
if body != test.Body {
|
|
|
|
t.Errorf("expected body = %#v, got %#v", test.Body, body)
|
|
|
|
}
|
|
|
|
}
|
2021-02-17 22:07:43 -07:00
|
|
|
|
|
|
|
for _, test := range tests {
|
|
|
|
if test.Err != nil || test.SkipWrite {
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
|
|
|
|
var b strings.Builder
|
2021-02-23 20:02:45 -07:00
|
|
|
w := newResponseWriter(nopCloser{&b})
|
2021-02-23 15:50:47 -07:00
|
|
|
w.WriteHeader(test.Status, test.Meta)
|
|
|
|
io.Copy(w, strings.NewReader(test.Body))
|
|
|
|
if err := w.Flush(); err != nil {
|
2021-02-17 22:07:43 -07:00
|
|
|
t.Error(err)
|
|
|
|
continue
|
|
|
|
}
|
|
|
|
|
|
|
|
got := b.String()
|
|
|
|
if got != test.Raw {
|
|
|
|
t.Errorf("expected %#v, got %#v", test.Raw, got)
|
|
|
|
}
|
|
|
|
}
|
2021-02-15 17:20:37 -07:00
|
|
|
}
|