Added access log to server and modified mock-fts to use it
This commit is contained in:
1 parent
2490519c2b
commit
02e3d910a2
10 files changed
+389
-29
No files matched your search
@@ -1,13 +1,16 @@
|
||||
package server
|
||||
|
||||
import (
|
||||
"bytes"
|
||||
"context"
|
||||
"encoding/json"
|
||||
"log"
|
||||
"log/slog"
|
||||
"net/http"
|
||||
"net/http/cookiejar"
|
||||
"net/http/httptest"
|
||||
"strings"
|
||||
"sync"
|
||||
"testing"
|
||||
"time"
|
||||
|
||||
@@ -218,3 +221,89 @@ func TestNoLimitIfUnset(t *testing.T) {
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// With WithAccessLog, each request, including one refused by middleware, is
|
||||
// written to the access log in the Combined Log Format.
|
||||
func TestAccessLog(t *testing.T) {
|
||||
var buffer bytes.Buffer
|
||||
ts := newTestServer(t, func(conf *config.JSCServer) {
|
||||
conf.Headers.AllowedHosts = []string{"example.com"}
|
||||
}, WithAccessLog(log.New(&buffer, "", 0)))
|
||||
|
||||
req, _ := http.NewRequest("GET", ts.URL+"/api/health", nil)
|
||||
req.Host = "example.com"
|
||||
req.Header.Set("User-Agent", "test-agent")
|
||||
res, err := http.DefaultClient.Do(req)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
res.Body.Close()
|
||||
|
||||
// A Host that isn't allowed is refused by RequestChecks.
|
||||
res, err = http.Get(ts.URL + "/api/health")
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
res.Body.Close()
|
||||
|
||||
lines := strings.Split(strings.TrimSpace(buffer.String()), "\n")
|
||||
if len(lines) != 2 {
|
||||
t.Fatalf("access log has %d lines; want 2:\n%s", len(lines), &buffer)
|
||||
}
|
||||
if !strings.Contains(lines[0], `"GET /api/health HTTP/1.1" 200`) ||
|
||||
!strings.Contains(lines[0], `"test-agent"`) {
|
||||
t.Errorf("first line = %q; want a 200 with the user agent", lines[0])
|
||||
}
|
||||
if !strings.Contains(lines[1], `"GET /api/health HTTP/1.1" 421`) {
|
||||
t.Errorf("second line = %q; want the refused request's 421", lines[1])
|
||||
}
|
||||
}
|
||||
|
||||
// With WithAccessLog, a WebSocket upgrade still hijacks the connection: the
|
||||
// client gets its welcome, and the upgrade is logged with 101.
|
||||
func TestAccessLogWebSocket(t *testing.T) {
|
||||
var buffer syncBuffer
|
||||
ts := newTestServer(t, nil, WithAccessLog(log.New(&buffer, "", 0)))
|
||||
ctx, cancel := context.WithTimeout(context.Background(), 2*time.Second)
|
||||
defer cancel()
|
||||
|
||||
wsURL := "ws" + strings.TrimPrefix(ts.URL, "http") + "/ws"
|
||||
conn, _, err := websocket.Dial(ctx, wsURL, nil)
|
||||
if err != nil {
|
||||
t.Fatal(err)
|
||||
}
|
||||
var welcome ws.Envelope
|
||||
err = wsjson.Read(ctx, conn, &welcome)
|
||||
if err != nil || welcome.Type != ws.TypeWelcome {
|
||||
t.Fatalf("want welcome, got %+v, %v", welcome, err)
|
||||
}
|
||||
conn.Close(websocket.StatusNormalClosure, "")
|
||||
|
||||
// The line is written when the connection's handler returns.
|
||||
deadline := time.Now().Add(time.Second)
|
||||
for !strings.Contains(buffer.String(), `"GET /ws HTTP/1.1" 101`) {
|
||||
if time.Now().After(deadline) {
|
||||
t.Fatalf("upgrade not logged with 101: %q", buffer.String())
|
||||
}
|
||||
time.Sleep(5 * time.Millisecond)
|
||||
}
|
||||
}
|
||||
|
||||
// syncBuffer is a bytes.Buffer safe to write from one goroutine while
|
||||
// another reads it.
|
||||
type syncBuffer struct {
|
||||
mu sync.Mutex
|
||||
buffer bytes.Buffer
|
||||
}
|
||||
|
||||
func (b *syncBuffer) Write(data []byte) (int, error) {
|
||||
b.mu.Lock()
|
||||
defer b.mu.Unlock()
|
||||
return b.buffer.Write(data)
|
||||
}
|
||||
|
||||
func (b *syncBuffer) String() string {
|
||||
b.mu.Lock()
|
||||
defer b.mu.Unlock()
|
||||
return b.buffer.String()
|
||||
}
|
||||
Reference in new issue
Block a user