From: Maciej Wereski Date: Thu, 9 Nov 2017 12:54:46 +0000 (+0100) Subject: Create new package for http datatypes X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=32f4c975ec02537922c1a7ffb44551dd8abf805e;p=tools%2Fboruta.git Create new package for http datatypes Few datatypes will be shared between server and client, such as server errors and filters. Move these datatypes to separate package. Change-Id: I06f025ba8449d2e2c045fbdd84fe59fd76b065ca Signed-off-by: Maciej Wereski --- diff --git a/server/api/v1/error.go b/http/error.go similarity index 87% rename from server/api/v1/error.go rename to http/error.go index c6f1d76..4f48c85 100644 --- a/server/api/v1/error.go +++ b/http/error.go @@ -14,10 +14,10 @@ * limitations under the License */ -// File server/api/v1/errors.go provides errors that may occur when interacting -// with Boruta HTTP API. +// File http/errors.go provides errors that may occur when interacting with +// Boruta HTTP API. -package v1 +package http import ( "errors" @@ -27,8 +27,8 @@ import ( . "git.tizen.org/tools/boruta" ) -// serverError represents error that occured while creating response. -type serverError struct { +// ServerError represents error that occured while creating response. +type ServerError struct { // Err contains general error string. Err string `json:"error"` // Status contains HTTP error code that should be returned with the error. @@ -60,13 +60,13 @@ func isNotFoundError(err error) bool { return ok } -// newServerError provides pointer to initialized serverError. -func newServerError(err error, details ...string) (ret *serverError) { +// NewServerError provides pointer to initialized ServerError. +func NewServerError(err error, details ...string) (ret *ServerError) { if err == nil { return nil } - ret = new(serverError) + ret = new(ServerError) ret.Err = err.Error() if len(details) > 0 { diff --git a/http/error_test.go b/http/error_test.go new file mode 100644 index 0000000..9940831 --- /dev/null +++ b/http/error_test.go @@ -0,0 +1,65 @@ +/* + * Copyright (c) 2017-2018 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License + */ + +// File http/error_test.go provides test of Boruta HTTP server errors. + +package http + +import ( + "errors" + "io" + "net/http" + "testing" + + . "git.tizen.org/tools/boruta" + "github.com/stretchr/testify/assert" +) + +func TestNewServerError(t *testing.T) { + assert := assert.New(t) + badRequest := &ServerError{ + Err: "invalid request: foo", + Status: http.StatusBadRequest, + } + nobody := "no body provided in HTTP request" + missingBody := &ServerError{ + Err: nobody, + Status: http.StatusBadRequest, + } + notImplemented := &ServerError{ + Err: ErrNotImplemented.Error(), + Status: http.StatusNotImplemented, + } + internalErr := &ServerError{ + Err: ErrInternalServerError.Error(), + Status: http.StatusInternalServerError, + } + customErr := &ServerError{ + Err: "invalid request: more details", + Status: http.StatusBadRequest, + } + notFound := &ServerError{ + Err: NotFoundError("Fern Flower").Error(), + Status: http.StatusNotFound, + } + assert.Equal(badRequest, NewServerError(errors.New("foo"))) + assert.Equal(missingBody, NewServerError(io.EOF)) + assert.Equal(notImplemented, NewServerError(ErrNotImplemented)) + assert.Equal(internalErr, NewServerError(ErrInternalServerError)) + assert.Equal(customErr, NewServerError(ErrBadRequest, "more details")) + assert.Equal(notFound, NewServerError(NotFoundError("Fern Flower"))) + assert.Nil(NewServerError(nil)) +} diff --git a/server/api/v1/filter.go b/http/filter.go similarity index 95% rename from server/api/v1/filter.go rename to http/filter.go index e98c499..895dc39 100644 --- a/server/api/v1/filter.go +++ b/http/filter.go @@ -14,9 +14,9 @@ * limitations under the License */ -// File server/api/v1/filter.go provides implementation of ListFilter interface. +// File http/filter.go provides implementation of ListFilter interface. -package v1 +package http import ( "strconv" diff --git a/server/api/v1/filter_test.go b/http/filter_test.go similarity index 95% rename from server/api/v1/filter_test.go rename to http/filter_test.go index e7839b1..f367943 100644 --- a/server/api/v1/filter_test.go +++ b/http/filter_test.go @@ -14,9 +14,9 @@ * limitations under the License */ -// File server/api/v1/filter_test.go contains additional tests for RequestFilter. +// File http/filter_test.go contains tests for RequestFilter. -package v1 +package http import ( "strconv" diff --git a/http/http.go b/http/http.go new file mode 100644 index 0000000..4f137bb --- /dev/null +++ b/http/http.go @@ -0,0 +1,47 @@ +/* + * Copyright (c) 2017-2018 Samsung Electronics Co., Ltd All Rights Reserved + * + * Licensed under the Apache License, Version 2.0 (the "License"); + * you may not use this file except in compliance with the License. + * You may obtain a copy of the License at + * + * http://www.apache.org/licenses/LICENSE-2.0 + * + * Unless required by applicable law or agreed to in writing, software + * distributed under the License is distributed on an "AS IS" BASIS, + * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. + * See the License for the specific language governing permissions and + * limitations under the License + */ + +// Package http provides datatypes that are shared between server and client. +package http + +import ( + "net" + + . "git.tizen.org/tools/boruta" +) + +// ReqIDPack is used for JSON (un)marshaller. +type ReqIDPack struct { + ReqID +} + +// WorkerStatePack is used by JSON (un)marshaller. +type WorkerStatePack struct { + WorkerState +} + +// AccessInfo2 structure is used by HTTP instead of AccessInfo when acquiring +// worker. The only difference is that key field is in PEM format instead of +// rsa.PrivateKey. It is temporary solution - session private keys will be +// replaces with users' public keys when proper user support is added. +type AccessInfo2 struct { + // Addr is necessary information to connect to a tunnel to Dryad. + Addr net.Addr + // Key is private RSA key in PEM format. + Key string + // Username is a login name for the job session. + Username string +} diff --git a/server/api/v1/api.go b/http/server/api/v1/api.go similarity index 86% rename from server/api/v1/api.go rename to http/server/api/v1/api.go index e672d81..61be0d5 100644 --- a/server/api/v1/api.go +++ b/http/server/api/v1/api.go @@ -22,12 +22,12 @@ package v1 import ( "encoding/json" "fmt" - "net" "net/http" "regexp" "strconv" . "git.tizen.org/tools/boruta" + util "git.tizen.org/tools/boruta/http" "github.com/dimfeld/httptreemux" ) @@ -35,29 +35,6 @@ import ( // Returned values are directly converted to JSON responses. type responseData interface{} -// reqIDPack is used as input for JSON (un)marshaller. -type reqIDPack struct { - ReqID -} - -// AccessInfo2 structure is used by HTTP instead of AccessInfo when acquiring -// worker. The only difference is that key field is in PEM format instead of -// rsa.PrivateKey. It is temporary solution - session private keys will be -// replaces with users' public keys when proper user support is added. -type AccessInfo2 struct { - // Addr is necessary information to connect to a tunnel to Dryad. - Addr net.Addr - // Key is private RSA key in PEM format. - Key string - // Username is a login name for the job session. - Username string -} - -// workerStatePack is used as input for JSON (un)marshaller. -type workerStatePack struct { - WorkerState -} - // reqHandler denotes function that parses HTTP request and returns responseData. type reqHandler func(*http.Request, map[string]string) responseData @@ -77,7 +54,7 @@ func jsonMustMarshal(data responseData) []byte { res, err := json.Marshal(data) if err != nil { msg := "unable to marshal JSON:" + err.Error() - panic(newServerError(ErrInternalServerError, msg)) + panic(util.NewServerError(util.ErrInternalServerError, msg)) } return res } @@ -88,7 +65,7 @@ func panicHandler(w http.ResponseWriter, r *http.Request, err interface{}) { var reason interface{} var status = http.StatusInternalServerError switch srvErr := err.(type) { - case *serverError: + case *util.ServerError: reason = srvErr.Err status = srvErr.Status default: @@ -111,7 +88,7 @@ func routerSetHandler(grp *httptreemux.Group, path string, fn reqHandler, ps map[string]string) { status := status rdata := handle(r, ps) - if data, isErr := rdata.(*serverError); isErr && + if data, isErr := rdata.(*util.ServerError); isErr && data != nil { status = data.Status } diff --git a/server/api/v1/api_test.go b/http/server/api/v1/api_test.go similarity index 86% rename from server/api/v1/api_test.go rename to http/server/api/v1/api_test.go index 23f53f2..a1da367 100644 --- a/server/api/v1/api_test.go +++ b/http/server/api/v1/api_test.go @@ -17,9 +17,7 @@ package v1 import ( - "errors" "flag" - "io" "io/ioutil" "net/http" "net/http/httptest" @@ -29,6 +27,7 @@ import ( "testing" . "git.tizen.org/tools/boruta" + util "git.tizen.org/tools/boruta/http" "git.tizen.org/tools/boruta/mocks" "github.com/dimfeld/httptreemux" "github.com/golang/mock/gomock" @@ -227,42 +226,6 @@ func TestNewAPI(t *testing.T) { m.finish() } -func TestNewServerError(t *testing.T) { - assert := assert.New(t) - badRequest := &serverError{ - Err: "invalid request: foo", - Status: http.StatusBadRequest, - } - nobody := "no body provided in HTTP request" - missingBody := &serverError{ - Err: nobody, - Status: http.StatusBadRequest, - } - notImplemented := &serverError{ - Err: ErrNotImplemented.Error(), - Status: http.StatusNotImplemented, - } - internalErr := &serverError{ - Err: ErrInternalServerError.Error(), - Status: http.StatusInternalServerError, - } - customErr := &serverError{ - Err: "invalid request: more details", - Status: http.StatusBadRequest, - } - notFound := &serverError{ - Err: NotFoundError("Fern Flower").Error(), - Status: http.StatusNotFound, - } - assert.Equal(badRequest, newServerError(errors.New("foo"))) - assert.Equal(missingBody, newServerError(io.EOF)) - assert.Equal(notImplemented, newServerError(ErrNotImplemented)) - assert.Equal(internalErr, newServerError(ErrInternalServerError)) - assert.Equal(customErr, newServerError(ErrBadRequest, "more details")) - assert.Equal(notFound, newServerError(NotFoundError("Fern Flower"))) - assert.Nil(newServerError(nil)) -} - func TestJsonMustMarshal(t *testing.T) { assert := assert.New(t) assert.Panics(func() { jsonMustMarshal(make(chan bool)) }) @@ -281,7 +244,7 @@ func TestPanicHandler(t *testing.T) { { name: "panic-server-error", path: "/priv/api/panic/srvErr/", - err: &serverError{ + err: &util.ServerError{ Err: msg, Status: http.StatusInternalServerError, }, diff --git a/server/api/v1/handlers.go b/http/server/api/v1/handlers.go similarity index 78% rename from server/api/v1/handlers.go rename to http/server/api/v1/handlers.go index 2b92504..c534ca8 100644 --- a/server/api/v1/handlers.go +++ b/http/server/api/v1/handlers.go @@ -14,7 +14,7 @@ * limitations under the License */ -// File server/api/v1/handlers.go contains all handlers that are used in v1 API. +// File http/server/api/v1/handlers.go contain all handlers that are used in v1 API. package v1 @@ -26,6 +26,7 @@ import ( "net/http" . "git.tizen.org/tools/boruta" + util "git.tizen.org/tools/boruta/http" ) // newRequestHandler parses HTTP request for creating new Boruta request and @@ -35,17 +36,17 @@ func (api *API) newRequestHandler(r *http.Request, ps map[string]string) respons defer r.Body.Close() if err := json.NewDecoder(r.Body).Decode(&newReq); err != nil { - return newServerError(err) + return util.NewServerError(err) } //FIXME: currently UserInfo is ignored. Change when user support is added. rid, err := api.reqs.NewRequest(newReq.Caps, newReq.Priority, UserInfo{}, newReq.ValidAfter.UTC(), newReq.Deadline.UTC()) if err != nil { - return newServerError(err) + return util.NewServerError(err) } - return reqIDPack{rid} + return util.ReqIDPack{rid} } // closeRequestHandler parses HTTP request for closing existing Boruta request @@ -55,10 +56,10 @@ func (api *API) closeRequestHandler(r *http.Request, ps map[string]string) respo reqid, err := parseReqID(ps["id"]) if err != nil { - return newServerError(ErrBadID) + return util.NewServerError(util.ErrBadID) } - return newServerError(api.reqs.CloseRequest(reqid)) + return util.NewServerError(api.reqs.CloseRequest(reqid)) } // updateRequestHandler parses HTTP request for modification of existing Boruta @@ -69,22 +70,22 @@ func (api *API) updateRequestHandler(r *http.Request, ps map[string]string) resp reqid, err := parseReqID(ps["id"]) if err != nil { - return newServerError(ErrBadID) + return util.NewServerError(util.ErrBadID) } var req ReqInfo if err = json.NewDecoder(r.Body).Decode(&req); err != nil { - return newServerError(err) + return util.NewServerError(err) } if req.ID != 0 && req.ID != reqid { - return newServerError(ErrIDMismatch) + return util.NewServerError(util.ErrIDMismatch) } // When ID wasn't set in JSON (or was set to 0) then it should be set to // the value from URL. req.ID = reqid - return newServerError(api.reqs.UpdateRequest(&req)) + return util.NewServerError(api.reqs.UpdateRequest(&req)) } // getRequestInfoHandler parses HTTP request for getting information about Boruta @@ -94,12 +95,12 @@ func (api *API) getRequestInfoHandler(r *http.Request, ps map[string]string) res reqid, err := parseReqID(ps["id"]) if err != nil { - return newServerError(ErrBadID) + return util.NewServerError(util.ErrBadID) } reqinfo, err := api.reqs.GetRequestInfo(reqid) if err != nil { - return newServerError(err) + return util.NewServerError(err) } return reqinfo @@ -108,14 +109,14 @@ func (api *API) getRequestInfoHandler(r *http.Request, ps map[string]string) res // listRequestsHandler parses HTTP request for listing Boruta requests and calls // ListRequests(). func (api *API) listRequestsHandler(r *http.Request, ps map[string]string) responseData { - var filter *RequestFilter + var filter *util.RequestFilter defer r.Body.Close() if r.Method == http.MethodPost { - filter = new(RequestFilter) + filter = new(util.RequestFilter) if err := json.NewDecoder(r.Body).Decode(filter); err != nil { if err != io.EOF { - return newServerError(err) + return util.NewServerError(err) } filter = nil } @@ -123,7 +124,7 @@ func (api *API) listRequestsHandler(r *http.Request, ps map[string]string) respo reqs, err := api.reqs.ListRequests(filter) if err != nil { - return newServerError(err) + return util.NewServerError(err) } return reqs @@ -136,18 +137,18 @@ func (api *API) acquireWorkerHandler(r *http.Request, ps map[string]string) resp reqid, err := parseReqID(ps["id"]) if err != nil { - return newServerError(ErrBadID) + return util.NewServerError(util.ErrBadID) } accessInfo, err := api.reqs.AcquireWorker(reqid) if err != nil { - return newServerError(err) + return util.NewServerError(err) } key := string(pem.EncodeToMemory(&pem.Block{ Type: "RSA PRIVATE KEY", Bytes: x509.MarshalPKCS1PrivateKey(&accessInfo.Key), })) - return AccessInfo2{ + return util.AccessInfo2{ Addr: accessInfo.Addr, Key: key, Username: accessInfo.Username, @@ -161,27 +162,27 @@ func (api *API) prolongAccessHandler(r *http.Request, ps map[string]string) resp reqid, err := parseReqID(ps["id"]) if err != nil { - return newServerError(ErrBadID) + return util.NewServerError(util.ErrBadID) } - return newServerError(api.reqs.ProlongAccess(reqid)) + return util.NewServerError(api.reqs.ProlongAccess(reqid)) } // listWorkersHandler parses HTTP request for listing workers and calls ListWorkers(). func (api *API) listWorkersHandler(r *http.Request, ps map[string]string) responseData { - var filter WorkersFilter + var filter util.WorkersFilter defer r.Body.Close() if r.Method == http.MethodPost { err := json.NewDecoder(r.Body).Decode(&filter) if err != nil && err != io.EOF { - return newServerError(err) + return util.NewServerError(err) } } workers, err := api.workers.ListWorkers(filter.Groups, filter.Capabilities) if err != nil { - return newServerError(err) + return util.NewServerError(err) } return workers @@ -193,12 +194,12 @@ func (api *API) getWorkerInfoHandler(r *http.Request, ps map[string]string) resp defer r.Body.Close() if !isValidUUID(ps["id"]) { - return newServerError(ErrBadUUID) + return util.NewServerError(util.ErrBadUUID) } workerinfo, err := api.workers.GetWorkerInfo(WorkerUUID(ps["id"])) if err != nil { - return newServerError(err) + return util.NewServerError(err) } return workerinfo @@ -207,18 +208,18 @@ func (api *API) getWorkerInfoHandler(r *http.Request, ps map[string]string) resp // setWorkerStateHandler parses HTTP workers for setting worker state and calls // workers.SetState(). func (api *API) setWorkerStateHandler(r *http.Request, ps map[string]string) responseData { - var state workerStatePack + var state util.WorkerStatePack defer r.Body.Close() if !isValidUUID(ps["id"]) { - return newServerError(ErrBadUUID) + return util.NewServerError(util.ErrBadUUID) } if err := json.NewDecoder(r.Body).Decode(&state); err != nil { - return newServerError(err) + return util.NewServerError(err) } - return newServerError(api.workers.SetState(WorkerUUID(ps["id"]), + return util.NewServerError(api.workers.SetState(WorkerUUID(ps["id"]), state.WorkerState)) } @@ -229,13 +230,13 @@ func (api *API) setWorkerGroupsHandler(r *http.Request, ps map[string]string) re defer r.Body.Close() if !isValidUUID(ps["id"]) { - return newServerError(ErrBadUUID) + return util.NewServerError(util.ErrBadUUID) } if err := json.NewDecoder(r.Body).Decode(&groups); err != nil { - return newServerError(err) + return util.NewServerError(err) } - return newServerError(api.workers.SetGroups(WorkerUUID(ps["id"]), groups)) + return util.NewServerError(api.workers.SetGroups(WorkerUUID(ps["id"]), groups)) } // workerDeregister parses HTTP workers for deregistering worker state and calls @@ -244,8 +245,8 @@ func (api *API) workerDeregister(r *http.Request, ps map[string]string) response defer r.Body.Close() if !isValidUUID(ps["id"]) { - return newServerError(ErrBadUUID) + return util.NewServerError(util.ErrBadUUID) } - return newServerError(api.workers.Deregister(WorkerUUID(ps["id"]))) + return util.NewServerError(api.workers.Deregister(WorkerUUID(ps["id"]))) } diff --git a/server/api/v1/handlers_test.go b/http/server/api/v1/handlers_test.go similarity index 96% rename from server/api/v1/handlers_test.go rename to http/server/api/v1/handlers_test.go index d5cd366..fe238fc 100644 --- a/server/api/v1/handlers_test.go +++ b/http/server/api/v1/handlers_test.go @@ -27,6 +27,7 @@ import ( "time" . "git.tizen.org/tools/boruta" + util "git.tizen.org/tools/boruta/http" "git.tizen.org/tools/boruta/requests" ) @@ -242,18 +243,18 @@ func TestListRequestsHandler(t *testing.T) { filterPath := "/api/v1/reqs/list" malformedJSONTest := testFromTempl(malformedJSONTestTempl, prefix, filterPath, methods...) - validFilter := NewRequestFilter("WAIT", "") + validFilter := util.NewRequestFilter("WAIT", "") m.rq.EXPECT().ListRequests(validFilter).Return(reqs[:2], nil) - emptyFilter := NewRequestFilter("", "") + emptyFilter := util.NewRequestFilter("", "") m.rq.EXPECT().ListRequests(emptyFilter).Return(reqs, nil).Times(2) m.rq.EXPECT().ListRequests(nil).Return(reqs, nil).Times(3) - missingFilter := NewRequestFilter("INVALID", "") + missingFilter := util.NewRequestFilter("INVALID", "") m.rq.EXPECT().ListRequests(missingFilter).Return([]ReqInfo{}, nil) // Currently ListRequests doesn't return any error hence the meaningless values. - badFilter := NewRequestFilter("FAIL", "-1") + badFilter := util.NewRequestFilter("FAIL", "-1") m.rq.EXPECT().ListRequests(badFilter).Return([]ReqInfo{}, errors.New("foo bar: pizza failed")) tests := []requestTest{ @@ -419,7 +420,7 @@ func TestListWorkersHandler(t *testing.T) { filterPath := "/api/v1/workers/list" malformedJSONTest := testFromTempl(malformedJSONTestTempl, prefix, filterPath, methods...) - validFilter := WorkersFilter{ + validFilter := util.WorkersFilter{ Groups: Groups{"Lędzianie"}, Capabilities: map[string]string{"architecture": "AArch64"}, } @@ -429,13 +430,13 @@ func TestListWorkersHandler(t *testing.T) { m.wm.EXPECT().ListWorkers(Groups{}, nil).Return(workers, nil) m.wm.EXPECT().ListWorkers(nil, make(Capabilities)).Return(workers, nil) - missingFilter := WorkersFilter{ + missingFilter := util.WorkersFilter{ Groups: Groups{"Fern Flower"}, } m.wm.EXPECT().ListWorkers(missingFilter.Groups, missingFilter.Capabilities).Return([]WorkerInfo{}, nil) // Currently ListWorkers doesn't return any error hence the meaningless values. - badFilter := WorkersFilter{ + badFilter := util.WorkersFilter{ Groups: Groups{"Oops"}, } m.wm.EXPECT().ListWorkers(badFilter.Groups, badFilter.Capabilities).Return([]WorkerInfo{}, errors.New("foo bar: pizza failed")) @@ -473,7 +474,7 @@ func TestListWorkersHandler(t *testing.T) { name: prefix + "empty-filter", path: filterPath, methods: methods, - json: string(jsonMustMarshal(WorkersFilter{nil, nil})), + json: string(jsonMustMarshal(util.WorkersFilter{nil, nil})), contentType: contentTypeJSON, status: http.StatusOK, }, @@ -482,7 +483,7 @@ func TestListWorkersHandler(t *testing.T) { name: prefix + "empty2-filter", path: filterPath, methods: methods, - json: string(jsonMustMarshal(WorkersFilter{nil, make(Capabilities)})), + json: string(jsonMustMarshal(util.WorkersFilter{nil, make(Capabilities)})), contentType: contentTypeJSON, status: http.StatusOK, }, @@ -491,7 +492,7 @@ func TestListWorkersHandler(t *testing.T) { name: prefix + "empty3-filter", path: filterPath, methods: methods, - json: string(jsonMustMarshal(WorkersFilter{Groups{}, nil})), + json: string(jsonMustMarshal(util.WorkersFilter{Groups{}, nil})), contentType: contentTypeJSON, status: http.StatusOK, }, @@ -565,7 +566,7 @@ func TestSetWorkerStateHandler(t *testing.T) { methods := []string{http.MethodPost} notFoundTest := testFromTempl(notFoundTestTempl, prefix, fmt.Sprintf(path, missingUUID), methods...) - notFoundTest.json = string(jsonMustMarshal(workerStatePack{IDLE})) + notFoundTest.json = string(jsonMustMarshal(util.WorkerStatePack{IDLE})) malformedJSONTest := testFromTempl(malformedJSONTestTempl, prefix, fmt.Sprintf(path, validUUID), methods...) missingErr := NotFoundError("Worker") @@ -577,7 +578,7 @@ func TestSetWorkerStateHandler(t *testing.T) { name: prefix + "valid", path: fmt.Sprintf(path, validUUID), methods: methods, - json: string(jsonMustMarshal(workerStatePack{IDLE})), + json: string(jsonMustMarshal(util.WorkerStatePack{IDLE})), contentType: contentTypeJSON, status: http.StatusNoContent, }, @@ -585,7 +586,7 @@ func TestSetWorkerStateHandler(t *testing.T) { name: prefix + "bad-uuid", path: fmt.Sprintf(path, invalidID), methods: methods, - json: string(jsonMustMarshal(workerStatePack{IDLE})), + json: string(jsonMustMarshal(util.WorkerStatePack{IDLE})), contentType: contentTypeJSON, status: http.StatusBadRequest, }, diff --git a/server/api/v1/testdata/acquire-worker-bad-id-POST.json b/http/server/api/v1/testdata/acquire-worker-bad-id-POST.json similarity index 100% rename from server/api/v1/testdata/acquire-worker-bad-id-POST.json rename to http/server/api/v1/testdata/acquire-worker-bad-id-POST.json diff --git a/server/api/v1/testdata/acquire-worker-missing-POST.json b/http/server/api/v1/testdata/acquire-worker-missing-POST.json similarity index 100% rename from server/api/v1/testdata/acquire-worker-missing-POST.json rename to http/server/api/v1/testdata/acquire-worker-missing-POST.json diff --git a/server/api/v1/testdata/acquire-worker-valid-POST.json b/http/server/api/v1/testdata/acquire-worker-valid-POST.json similarity index 100% rename from server/api/v1/testdata/acquire-worker-valid-POST.json rename to http/server/api/v1/testdata/acquire-worker-valid-POST.json diff --git a/server/api/v1/testdata/close-req-bad-id-POST.json b/http/server/api/v1/testdata/close-req-bad-id-POST.json similarity index 100% rename from server/api/v1/testdata/close-req-bad-id-POST.json rename to http/server/api/v1/testdata/close-req-bad-id-POST.json diff --git a/server/api/v1/testdata/close-req-missing-POST.json b/http/server/api/v1/testdata/close-req-missing-POST.json similarity index 100% rename from server/api/v1/testdata/close-req-missing-POST.json rename to http/server/api/v1/testdata/close-req-missing-POST.json diff --git a/server/api/v1/testdata/close-req-valid-POST.json b/http/server/api/v1/testdata/close-req-valid-POST.json similarity index 100% rename from server/api/v1/testdata/close-req-valid-POST.json rename to http/server/api/v1/testdata/close-req-valid-POST.json diff --git a/server/api/v1/testdata/filter-reqs-bad-filter-POST.json b/http/server/api/v1/testdata/filter-reqs-bad-filter-POST.json similarity index 100% rename from server/api/v1/testdata/filter-reqs-bad-filter-POST.json rename to http/server/api/v1/testdata/filter-reqs-bad-filter-POST.json diff --git a/server/api/v1/testdata/filter-reqs-empty-POST.json b/http/server/api/v1/testdata/filter-reqs-empty-POST.json similarity index 100% rename from server/api/v1/testdata/filter-reqs-empty-POST.json rename to http/server/api/v1/testdata/filter-reqs-empty-POST.json diff --git a/server/api/v1/testdata/filter-reqs-empty-json-POST.json b/http/server/api/v1/testdata/filter-reqs-empty-json-POST.json similarity index 100% rename from server/api/v1/testdata/filter-reqs-empty-json-POST.json rename to http/server/api/v1/testdata/filter-reqs-empty-json-POST.json diff --git a/server/api/v1/testdata/filter-reqs-malformed-json-POST.json b/http/server/api/v1/testdata/filter-reqs-malformed-json-POST.json similarity index 100% rename from server/api/v1/testdata/filter-reqs-malformed-json-POST.json rename to http/server/api/v1/testdata/filter-reqs-malformed-json-POST.json diff --git a/server/api/v1/testdata/filter-reqs-nil-POST.json b/http/server/api/v1/testdata/filter-reqs-nil-POST.json similarity index 100% rename from server/api/v1/testdata/filter-reqs-nil-POST.json rename to http/server/api/v1/testdata/filter-reqs-nil-POST.json diff --git a/server/api/v1/testdata/filter-reqs-nomatch-all-POST.json b/http/server/api/v1/testdata/filter-reqs-nomatch-all-POST.json similarity index 100% rename from server/api/v1/testdata/filter-reqs-nomatch-all-POST.json rename to http/server/api/v1/testdata/filter-reqs-nomatch-all-POST.json diff --git a/server/api/v1/testdata/filter-reqs-valid-filter-POST.json b/http/server/api/v1/testdata/filter-reqs-valid-filter-POST.json similarity index 100% rename from server/api/v1/testdata/filter-reqs-valid-filter-POST.json rename to http/server/api/v1/testdata/filter-reqs-valid-filter-POST.json diff --git a/server/api/v1/testdata/filter-workers-bad-filter-POST.json b/http/server/api/v1/testdata/filter-workers-bad-filter-POST.json similarity index 100% rename from server/api/v1/testdata/filter-workers-bad-filter-POST.json rename to http/server/api/v1/testdata/filter-workers-bad-filter-POST.json diff --git a/server/api/v1/testdata/filter-workers-empty-body-POST.json b/http/server/api/v1/testdata/filter-workers-empty-body-POST.json similarity index 100% rename from server/api/v1/testdata/filter-workers-empty-body-POST.json rename to http/server/api/v1/testdata/filter-workers-empty-body-POST.json diff --git a/server/api/v1/testdata/filter-workers-empty-filter-POST.json b/http/server/api/v1/testdata/filter-workers-empty-filter-POST.json similarity index 100% rename from server/api/v1/testdata/filter-workers-empty-filter-POST.json rename to http/server/api/v1/testdata/filter-workers-empty-filter-POST.json diff --git a/server/api/v1/testdata/filter-workers-empty2-filter-POST.json b/http/server/api/v1/testdata/filter-workers-empty2-filter-POST.json similarity index 100% rename from server/api/v1/testdata/filter-workers-empty2-filter-POST.json rename to http/server/api/v1/testdata/filter-workers-empty2-filter-POST.json diff --git a/server/api/v1/testdata/filter-workers-empty3-filter-POST.json b/http/server/api/v1/testdata/filter-workers-empty3-filter-POST.json similarity index 100% rename from server/api/v1/testdata/filter-workers-empty3-filter-POST.json rename to http/server/api/v1/testdata/filter-workers-empty3-filter-POST.json diff --git a/server/api/v1/testdata/filter-workers-malformed-json-POST.json b/http/server/api/v1/testdata/filter-workers-malformed-json-POST.json similarity index 100% rename from server/api/v1/testdata/filter-workers-malformed-json-POST.json rename to http/server/api/v1/testdata/filter-workers-malformed-json-POST.json diff --git a/server/api/v1/testdata/filter-workers-nomatch-POST.json b/http/server/api/v1/testdata/filter-workers-nomatch-POST.json similarity index 100% rename from server/api/v1/testdata/filter-workers-nomatch-POST.json rename to http/server/api/v1/testdata/filter-workers-nomatch-POST.json diff --git a/server/api/v1/testdata/filter-workers-valid-filter-POST.json b/http/server/api/v1/testdata/filter-workers-valid-filter-POST.json similarity index 100% rename from server/api/v1/testdata/filter-workers-valid-filter-POST.json rename to http/server/api/v1/testdata/filter-workers-valid-filter-POST.json diff --git a/server/api/v1/testdata/list-reqs-all-GET.json b/http/server/api/v1/testdata/list-reqs-all-GET.json similarity index 100% rename from server/api/v1/testdata/list-reqs-all-GET.json rename to http/server/api/v1/testdata/list-reqs-all-GET.json diff --git a/server/api/v1/testdata/list-workers-all-GET.json b/http/server/api/v1/testdata/list-workers-all-GET.json similarity index 100% rename from server/api/v1/testdata/list-workers-all-GET.json rename to http/server/api/v1/testdata/list-workers-all-GET.json diff --git a/server/api/v1/testdata/new-req-bad-prio-POST.json b/http/server/api/v1/testdata/new-req-bad-prio-POST.json similarity index 100% rename from server/api/v1/testdata/new-req-bad-prio-POST.json rename to http/server/api/v1/testdata/new-req-bad-prio-POST.json diff --git a/server/api/v1/testdata/new-req-malformed-json-POST.json b/http/server/api/v1/testdata/new-req-malformed-json-POST.json similarity index 100% rename from server/api/v1/testdata/new-req-malformed-json-POST.json rename to http/server/api/v1/testdata/new-req-malformed-json-POST.json diff --git a/server/api/v1/testdata/new-req-valid-POST.json b/http/server/api/v1/testdata/new-req-valid-POST.json similarity index 100% rename from server/api/v1/testdata/new-req-valid-POST.json rename to http/server/api/v1/testdata/new-req-valid-POST.json diff --git a/server/api/v1/testdata/panic-other-error.txt b/http/server/api/v1/testdata/panic-other-error.txt similarity index 100% rename from server/api/v1/testdata/panic-other-error.txt rename to http/server/api/v1/testdata/panic-other-error.txt diff --git a/server/api/v1/testdata/panic-server-error.txt b/http/server/api/v1/testdata/panic-server-error.txt similarity index 100% rename from server/api/v1/testdata/panic-server-error.txt rename to http/server/api/v1/testdata/panic-server-error.txt diff --git a/server/api/v1/testdata/prolong-access-bad-id-POST.json b/http/server/api/v1/testdata/prolong-access-bad-id-POST.json similarity index 100% rename from server/api/v1/testdata/prolong-access-bad-id-POST.json rename to http/server/api/v1/testdata/prolong-access-bad-id-POST.json diff --git a/server/api/v1/testdata/prolong-access-missing-POST.json b/http/server/api/v1/testdata/prolong-access-missing-POST.json similarity index 100% rename from server/api/v1/testdata/prolong-access-missing-POST.json rename to http/server/api/v1/testdata/prolong-access-missing-POST.json diff --git a/server/api/v1/testdata/prolong-access-valid-POST.json b/http/server/api/v1/testdata/prolong-access-valid-POST.json similarity index 100% rename from server/api/v1/testdata/prolong-access-valid-POST.json rename to http/server/api/v1/testdata/prolong-access-valid-POST.json diff --git a/server/api/v1/testdata/req-info-GET.json b/http/server/api/v1/testdata/req-info-GET.json similarity index 100% rename from server/api/v1/testdata/req-info-GET.json rename to http/server/api/v1/testdata/req-info-GET.json diff --git a/server/api/v1/testdata/req-info-bad-id-GET.json b/http/server/api/v1/testdata/req-info-bad-id-GET.json similarity index 100% rename from server/api/v1/testdata/req-info-bad-id-GET.json rename to http/server/api/v1/testdata/req-info-bad-id-GET.json diff --git a/server/api/v1/testdata/req-info-missing-GET.json b/http/server/api/v1/testdata/req-info-missing-GET.json similarity index 100% rename from server/api/v1/testdata/req-info-missing-GET.json rename to http/server/api/v1/testdata/req-info-missing-GET.json diff --git a/server/api/v1/testdata/update-req-bad-id-POST.json b/http/server/api/v1/testdata/update-req-bad-id-POST.json similarity index 100% rename from server/api/v1/testdata/update-req-bad-id-POST.json rename to http/server/api/v1/testdata/update-req-bad-id-POST.json diff --git a/server/api/v1/testdata/update-req-empty-POST.json b/http/server/api/v1/testdata/update-req-empty-POST.json similarity index 100% rename from server/api/v1/testdata/update-req-empty-POST.json rename to http/server/api/v1/testdata/update-req-empty-POST.json diff --git a/server/api/v1/testdata/update-req-malformed-json-POST.json b/http/server/api/v1/testdata/update-req-malformed-json-POST.json similarity index 100% rename from server/api/v1/testdata/update-req-malformed-json-POST.json rename to http/server/api/v1/testdata/update-req-malformed-json-POST.json diff --git a/server/api/v1/testdata/update-req-mismatch-POST.json b/http/server/api/v1/testdata/update-req-mismatch-POST.json similarity index 100% rename from server/api/v1/testdata/update-req-mismatch-POST.json rename to http/server/api/v1/testdata/update-req-mismatch-POST.json diff --git a/server/api/v1/testdata/update-req-missing-POST.json b/http/server/api/v1/testdata/update-req-missing-POST.json similarity index 100% rename from server/api/v1/testdata/update-req-missing-POST.json rename to http/server/api/v1/testdata/update-req-missing-POST.json diff --git a/server/api/v1/testdata/update-req-prio-POST.json b/http/server/api/v1/testdata/update-req-prio-POST.json similarity index 100% rename from server/api/v1/testdata/update-req-prio-POST.json rename to http/server/api/v1/testdata/update-req-prio-POST.json diff --git a/server/api/v1/testdata/update-req-valid-POST.json b/http/server/api/v1/testdata/update-req-valid-POST.json similarity index 100% rename from server/api/v1/testdata/update-req-valid-POST.json rename to http/server/api/v1/testdata/update-req-valid-POST.json diff --git a/server/api/v1/testdata/worker-deregister-bad-uuid-POST.json b/http/server/api/v1/testdata/worker-deregister-bad-uuid-POST.json similarity index 100% rename from server/api/v1/testdata/worker-deregister-bad-uuid-POST.json rename to http/server/api/v1/testdata/worker-deregister-bad-uuid-POST.json diff --git a/server/api/v1/testdata/worker-deregister-missing-POST.json b/http/server/api/v1/testdata/worker-deregister-missing-POST.json similarity index 100% rename from server/api/v1/testdata/worker-deregister-missing-POST.json rename to http/server/api/v1/testdata/worker-deregister-missing-POST.json diff --git a/server/api/v1/testdata/worker-deregister-valid-POST.json b/http/server/api/v1/testdata/worker-deregister-valid-POST.json similarity index 100% rename from server/api/v1/testdata/worker-deregister-valid-POST.json rename to http/server/api/v1/testdata/worker-deregister-valid-POST.json diff --git a/server/api/v1/testdata/worker-info-bad-uuid-GET.json b/http/server/api/v1/testdata/worker-info-bad-uuid-GET.json similarity index 100% rename from server/api/v1/testdata/worker-info-bad-uuid-GET.json rename to http/server/api/v1/testdata/worker-info-bad-uuid-GET.json diff --git a/server/api/v1/testdata/worker-info-missing-GET.json b/http/server/api/v1/testdata/worker-info-missing-GET.json similarity index 100% rename from server/api/v1/testdata/worker-info-missing-GET.json rename to http/server/api/v1/testdata/worker-info-missing-GET.json diff --git a/server/api/v1/testdata/worker-info-valid-GET.json b/http/server/api/v1/testdata/worker-info-valid-GET.json similarity index 100% rename from server/api/v1/testdata/worker-info-valid-GET.json rename to http/server/api/v1/testdata/worker-info-valid-GET.json diff --git a/server/api/v1/testdata/worker-set-groups-bad-uuid-POST.json b/http/server/api/v1/testdata/worker-set-groups-bad-uuid-POST.json similarity index 100% rename from server/api/v1/testdata/worker-set-groups-bad-uuid-POST.json rename to http/server/api/v1/testdata/worker-set-groups-bad-uuid-POST.json diff --git a/server/api/v1/testdata/worker-set-groups-malformed-json-POST.json b/http/server/api/v1/testdata/worker-set-groups-malformed-json-POST.json similarity index 100% rename from server/api/v1/testdata/worker-set-groups-malformed-json-POST.json rename to http/server/api/v1/testdata/worker-set-groups-malformed-json-POST.json diff --git a/server/api/v1/testdata/worker-set-groups-missing-POST.json b/http/server/api/v1/testdata/worker-set-groups-missing-POST.json similarity index 100% rename from server/api/v1/testdata/worker-set-groups-missing-POST.json rename to http/server/api/v1/testdata/worker-set-groups-missing-POST.json diff --git a/server/api/v1/testdata/worker-set-groups-valid-POST.json b/http/server/api/v1/testdata/worker-set-groups-valid-POST.json similarity index 100% rename from server/api/v1/testdata/worker-set-groups-valid-POST.json rename to http/server/api/v1/testdata/worker-set-groups-valid-POST.json diff --git a/server/api/v1/testdata/worker-set-state-bad-uuid-POST.json b/http/server/api/v1/testdata/worker-set-state-bad-uuid-POST.json similarity index 100% rename from server/api/v1/testdata/worker-set-state-bad-uuid-POST.json rename to http/server/api/v1/testdata/worker-set-state-bad-uuid-POST.json diff --git a/server/api/v1/testdata/worker-set-state-malformed-json-POST.json b/http/server/api/v1/testdata/worker-set-state-malformed-json-POST.json similarity index 100% rename from server/api/v1/testdata/worker-set-state-malformed-json-POST.json rename to http/server/api/v1/testdata/worker-set-state-malformed-json-POST.json diff --git a/server/api/v1/testdata/worker-set-state-missing-POST.json b/http/server/api/v1/testdata/worker-set-state-missing-POST.json similarity index 100% rename from server/api/v1/testdata/worker-set-state-missing-POST.json rename to http/server/api/v1/testdata/worker-set-state-missing-POST.json diff --git a/server/api/v1/testdata/worker-set-state-valid-POST.json b/http/server/api/v1/testdata/worker-set-state-valid-POST.json similarity index 100% rename from server/api/v1/testdata/worker-set-state-valid-POST.json rename to http/server/api/v1/testdata/worker-set-state-valid-POST.json