Files
dobotai-platform/internal/outboundimage/stable_handler_test.go

92 lines
3.0 KiB
Go

package outboundimage
import (
"context"
"net/http"
"net/http/httptest"
"testing"
)
type fakeImageReader struct {
key string
maxBytes int64
data []byte
contentType string
err error
}
func (r *fakeImageReader) Get(_ context.Context, key string, maxBytes int64) ([]byte, string, error) {
r.key = key
r.maxBytes = maxBytes
return append([]byte(nil), r.data...), r.contentType, r.err
}
func TestStableImageHandlerReturnsImageBytesDirectly(t *testing.T) {
const id = "ca13f02b-58b6-5f8f-a80d-b41873a97425"
reader := &fakeImageReader{data: []byte("JPEG"), contentType: "image/jpeg"}
handler, err := NewStableImageHandler(reader, "dobotai/im-images", "/dingtalk/i/", 10<<20)
if err != nil {
t.Fatal(err)
}
recorder := httptest.NewRecorder()
handler.ServeHTTP(recorder, httptest.NewRequest(http.MethodGet, "/dingtalk/i/"+id, nil))
if recorder.Code != http.StatusOK {
t.Fatalf("status=%d", recorder.Code)
}
if recorder.Header().Get("Location") != "" {
t.Fatalf("stable image endpoint must not redirect: location=%q", recorder.Header().Get("Location"))
}
if recorder.Header().Get("Content-Type") != "image/jpeg" {
t.Fatalf("content-type=%q", recorder.Header().Get("Content-Type"))
}
if recorder.Body.String() != "JPEG" {
t.Fatalf("body=%q", recorder.Body.String())
}
if reader.key != "dobotai/im-images/"+id || reader.maxBytes != 10<<20 {
t.Fatalf("key=%q maxBytes=%d", reader.key, reader.maxBytes)
}
}
func TestStableImageHandlerAllowsHeadWithoutBody(t *testing.T) {
const id = "ca13f02b-58b6-5f8f-a80d-b41873a97425"
reader := &fakeImageReader{data: []byte("JPEG"), contentType: "image/jpeg"}
handler, err := NewStableImageHandler(reader, "dobotai/im-images", "/dingtalk/i/", 10<<20)
if err != nil {
t.Fatal(err)
}
recorder := httptest.NewRecorder()
handler.ServeHTTP(recorder, httptest.NewRequest(http.MethodHead, "/dingtalk/i/"+id, nil))
if recorder.Code != http.StatusOK || recorder.Body.Len() != 0 {
t.Fatalf("status=%d body=%q", recorder.Code, recorder.Body.String())
}
if recorder.Header().Get("Content-Length") != "4" {
t.Fatalf("content-length=%q", recorder.Header().Get("Content-Length"))
}
}
func TestStableImageHandlerRejectsPostAndInvalidIDsWithoutReadingOSS(t *testing.T) {
reader := &fakeImageReader{data: []byte("JPEG"), contentType: "image/jpeg"}
handler, err := NewStableImageHandler(reader, "dobotai/im-images", "/dingtalk/i/", 10<<20)
if err != nil {
t.Fatal(err)
}
post := httptest.NewRecorder()
handler.ServeHTTP(post, httptest.NewRequest(http.MethodPost, "/dingtalk/i/ca13f02b-58b6-5f8f-a80d-b41873a97425", nil))
if post.Code != http.StatusMethodNotAllowed {
t.Fatalf("post status=%d", post.Code)
}
invalid := httptest.NewRecorder()
handler.ServeHTTP(invalid, httptest.NewRequest(http.MethodGet, "/dingtalk/i/../../secret", nil))
if invalid.Code != http.StatusNotFound {
t.Fatalf("invalid status=%d", invalid.Code)
}
if reader.key != "" {
t.Fatalf("invalid requests reached OSS key=%q", reader.key)
}
}