package server import ( "io" "net/http" "net/http/httptest" "net/url" "testing" "git.netflux.io/rob/clipper/config" "git.netflux.io/rob/clipper/generated/mocks" "github.com/stretchr/testify/assert" "github.com/stretchr/testify/require" "go.uber.org/zap" ) func TestHandler(t *testing.T) { testCases := []struct { name string path string method string config config.Config wantStatus int wantBody string }{ { name: "assets disabled, file system store disabled, GET /", path: "/", method: http.MethodGet, config: config.Config{FileStore: config.S3Store}, wantStatus: http.StatusNotFound, }, { name: "assets disabled, file system store disabled, GET /foo.js", path: "/foo.js", method: http.MethodGet, config: config.Config{FileStore: config.S3Store}, wantStatus: http.StatusNotFound, }, { name: "assets enabled, file system store disabled, index.html exists, GET /", path: "/", method: http.MethodGet, config: config.Config{FileStore: config.S3Store, AssetsHTTPRoot: "testdata/http/assets"}, wantStatus: http.StatusOK, wantBody: "index", }, { name: "assets enabled, file system store disabled, index.html does not exist, GET /css/", path: "/css/", method: http.MethodGet, config: config.Config{FileStore: config.S3Store, AssetsHTTPRoot: "testdata/http/assets"}, wantStatus: http.StatusNotFound, }, { name: "assets enabled, file system store disabled, index.html does not exist, GET /css/style.css", path: "/css/style.css", method: http.MethodGet, config: config.Config{FileStore: config.S3Store, AssetsHTTPRoot: "testdata/http/assets"}, wantStatus: http.StatusOK, wantBody: "css", }, { name: "assets enabled, file system store disabled, GET /foo.js", path: "/foo.js", method: http.MethodGet, config: config.Config{FileStore: config.S3Store, AssetsHTTPRoot: "testdata/http/assets"}, wantStatus: http.StatusOK, wantBody: "foo", }, { name: "assets enabled, file system store enabled with path prefix /store/, GET /foo.js", path: "/foo.js", method: http.MethodGet, config: config.Config{FileStore: config.FileSystemStore, FileStoreHTTPBaseURL: mustParseURL(t, "/store/"), FileStoreHTTPRoot: "testdata/http/filestore", AssetsHTTPRoot: "testdata/http/assets"}, wantStatus: http.StatusOK, wantBody: "foo", }, { name: "assets enabled, file system store enabled with path prefix /store/, GET /store/bar.mp4", path: "/store/bar.mp4", method: http.MethodGet, config: config.Config{FileStore: config.FileSystemStore, FileStoreHTTPBaseURL: mustParseURL(t, "/store/"), FileStoreHTTPRoot: "testdata/http/filestore", AssetsHTTPRoot: "testdata/http/assets"}, wantStatus: http.StatusOK, wantBody: "bar", }, { name: "assets enabled, file system store enabled with path prefix /store/, GET /store/", path: "/store/", method: http.MethodGet, config: config.Config{FileStore: config.FileSystemStore, FileStoreHTTPBaseURL: mustParseURL(t, "/store/"), FileStoreHTTPRoot: "testdata/http/filestore", AssetsHTTPRoot: "testdata/http/assets"}, wantStatus: http.StatusNotFound, }, { name: "assets enabled, file system store enabled with path prefix /store/, GET /", path: "/", method: http.MethodGet, config: config.Config{FileStore: config.FileSystemStore, FileStoreHTTPBaseURL: mustParseURL(t, "/store/"), FileStoreHTTPRoot: "testdata/http/filestore", AssetsHTTPRoot: "testdata/http/assets"}, wantStatus: http.StatusOK, wantBody: "index", }, { name: "assets enabled, file system store enabled with path prefix /, GET / clobbers the assets routes", path: "/", method: http.MethodGet, config: config.Config{FileStore: config.FileSystemStore, FileStoreHTTPBaseURL: mustParseURL(t, "/"), FileStoreHTTPRoot: "testdata/http/filestore", AssetsHTTPRoot: "testdata/http/assets"}, wantStatus: http.StatusNotFound, }, } for _, tc := range testCases { t.Run(tc.name, func(t *testing.T) { var mediaSetService mocks.MediaSetService handler := newHTTPHandler(nil, &mediaSetService, tc.config, zap.NewNop().Sugar()) req := httptest.NewRequest(tc.method, tc.path, nil) w := httptest.NewRecorder() handler.ServeHTTP(w, req) resp := w.Result() assert.Equal(t, tc.wantStatus, resp.StatusCode) if tc.wantBody != "" { body, err := io.ReadAll(resp.Body) require.NoError(t, err) assert.Equal(t, tc.wantBody, string(body)) } }) } } func mustParseURL(t *testing.T, u string) *url.URL { pu, err := url.Parse(u) require.NoError(t, err) return pu }