306d18e466
Here's the squash of the following patches that enable support
for go1.18 and update our dependencies.
This diff WILL need to be backported to the release/3.14 branch.
* chore: use go1.17.8
See https://github.com/ooni/probe/issues/2067
* chore: upgrade to probe-assets@v0.8.0
See https://github.com/ooni/probe/issues/2067.
* chore: update dependencies and enable go1.18
As mentioned in 7a0d17ea91
,
the tree won't build with `go1.18` unless we say it does.
So, not only here we need to update dependencies but also we
need to explicitly say `go1.18` in the `go.mod`.
This work is part of https://github.com/ooni/probe/issues/2067.
* chore(coverage.yml): run with go1.18
This change will give us a bare minimum confidence that we're
going to build our tree using version 1.18 of golang.
See https://github.com/ooni/probe/issues/2067.
* chore: update user agent used for measuring
See https://github.com/ooni/probe/issues/2067
* chore: run `go generate ./...`
See https://github.com/ooni/probe/issues/2067
* fix(dialer_test.go): make test work with go1.17 and go1.18
1. the original test wanted the dial to fail, so ensure we're not
passing any domain name to exercise dialing not resolving;
2. match the end of the error rather than the whole error string.
Tested locally with both go1.17 and go1.18.
See https://github.com/ooni/probe-cli/pull/708#issuecomment-1096447186
900 lines
21 KiB
Go
900 lines
21 KiB
Go
// Code generated by go generate; DO NOT EDIT.
|
|
// 2022-04-12 11:16:01.247582 +0200 CEST m=+0.000156834
|
|
|
|
package ooapi
|
|
|
|
//go:generate go run ./internal/generator -file clientcall_test.go
|
|
|
|
import (
|
|
"context"
|
|
"encoding/json"
|
|
"net/http"
|
|
"net/http/httptest"
|
|
"net/url"
|
|
"sync"
|
|
"testing"
|
|
|
|
"github.com/google/go-cmp/cmp"
|
|
"github.com/ooni/probe-cli/v3/internal/kvstore"
|
|
"github.com/ooni/probe-cli/v3/internal/netxlite"
|
|
"github.com/ooni/probe-cli/v3/internal/ooapi/apimodel"
|
|
)
|
|
|
|
type handleClientCallCheckReportID struct {
|
|
accept string
|
|
body []byte
|
|
contentType string
|
|
count int32
|
|
method string
|
|
mu sync.Mutex
|
|
resp *apimodel.CheckReportIDResponse
|
|
url *url.URL
|
|
userAgent string
|
|
}
|
|
|
|
func (h *handleClientCallCheckReportID) ServeHTTP(w http.ResponseWriter, r *http.Request) {
|
|
ff := fakeFill{}
|
|
defer h.mu.Unlock()
|
|
h.mu.Lock()
|
|
if h.count > 0 {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.count++
|
|
if r.Body != nil {
|
|
data, err := netxlite.ReadAllContext(r.Context(), r.Body)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.body = data
|
|
}
|
|
h.method = r.Method
|
|
h.url = r.URL
|
|
h.accept = r.Header.Get("Accept")
|
|
h.contentType = r.Header.Get("Content-Type")
|
|
h.userAgent = r.Header.Get("User-Agent")
|
|
var out *apimodel.CheckReportIDResponse
|
|
ff.Fill(&out)
|
|
h.resp = out
|
|
data, err := json.Marshal(out)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
w.Write(data)
|
|
}
|
|
|
|
func TestCheckReportIDClientCallRoundTrip(t *testing.T) {
|
|
// setup
|
|
handler := &handleClientCallCheckReportID{}
|
|
srvr := httptest.NewServer(handler)
|
|
defer srvr.Close()
|
|
req := &apimodel.CheckReportIDRequest{}
|
|
ff := &fakeFill{}
|
|
ff.Fill(&req)
|
|
clnt := &Client{KVStore: &kvstore.Memory{}, BaseURL: srvr.URL}
|
|
ff.Fill(&clnt.UserAgent)
|
|
// issue request
|
|
ctx := context.Background()
|
|
resp, err := clnt.CheckReportID(ctx, req)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if resp == nil {
|
|
t.Fatal("expected non-nil response here")
|
|
}
|
|
// compare our response and server's one
|
|
if diff := cmp.Diff(handler.resp, resp); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
// check whether headers are OK
|
|
if handler.accept != "application/json" {
|
|
t.Fatal("invalid accept header")
|
|
}
|
|
if handler.userAgent != clnt.UserAgent {
|
|
t.Fatal("invalid user-agent header")
|
|
}
|
|
// check whether the method is OK
|
|
if handler.method != "GET" {
|
|
t.Fatal("invalid method")
|
|
}
|
|
// check the query
|
|
api := &simpleCheckReportIDAPI{BaseURL: srvr.URL}
|
|
httpReq, err := api.newRequest(context.Background(), req)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if diff := cmp.Diff(handler.url.Path, httpReq.URL.Path); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
if diff := cmp.Diff(handler.url.RawQuery, httpReq.URL.RawQuery); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
}
|
|
|
|
type handleClientCallCheckIn struct {
|
|
accept string
|
|
body []byte
|
|
contentType string
|
|
count int32
|
|
method string
|
|
mu sync.Mutex
|
|
resp *apimodel.CheckInResponse
|
|
url *url.URL
|
|
userAgent string
|
|
}
|
|
|
|
func (h *handleClientCallCheckIn) ServeHTTP(w http.ResponseWriter, r *http.Request) {
|
|
ff := fakeFill{}
|
|
defer h.mu.Unlock()
|
|
h.mu.Lock()
|
|
if h.count > 0 {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.count++
|
|
if r.Body != nil {
|
|
data, err := netxlite.ReadAllContext(r.Context(), r.Body)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.body = data
|
|
}
|
|
h.method = r.Method
|
|
h.url = r.URL
|
|
h.accept = r.Header.Get("Accept")
|
|
h.contentType = r.Header.Get("Content-Type")
|
|
h.userAgent = r.Header.Get("User-Agent")
|
|
var out *apimodel.CheckInResponse
|
|
ff.Fill(&out)
|
|
h.resp = out
|
|
data, err := json.Marshal(out)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
w.Write(data)
|
|
}
|
|
|
|
func TestCheckInClientCallRoundTrip(t *testing.T) {
|
|
// setup
|
|
handler := &handleClientCallCheckIn{}
|
|
srvr := httptest.NewServer(handler)
|
|
defer srvr.Close()
|
|
req := &apimodel.CheckInRequest{}
|
|
ff := &fakeFill{}
|
|
ff.Fill(&req)
|
|
clnt := &Client{KVStore: &kvstore.Memory{}, BaseURL: srvr.URL}
|
|
ff.Fill(&clnt.UserAgent)
|
|
// issue request
|
|
ctx := context.Background()
|
|
resp, err := clnt.CheckIn(ctx, req)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if resp == nil {
|
|
t.Fatal("expected non-nil response here")
|
|
}
|
|
// compare our response and server's one
|
|
if diff := cmp.Diff(handler.resp, resp); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
// check whether headers are OK
|
|
if handler.accept != "application/json" {
|
|
t.Fatal("invalid accept header")
|
|
}
|
|
if handler.userAgent != clnt.UserAgent {
|
|
t.Fatal("invalid user-agent header")
|
|
}
|
|
// check whether the method is OK
|
|
if handler.method != "POST" {
|
|
t.Fatal("invalid method")
|
|
}
|
|
// check the body
|
|
if handler.contentType != "application/json" {
|
|
t.Fatal("invalid content-type header")
|
|
}
|
|
got := &apimodel.CheckInRequest{}
|
|
if err := json.Unmarshal(handler.body, &got); err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if diff := cmp.Diff(req, got); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
}
|
|
|
|
type handleClientCallMeasurementMeta struct {
|
|
accept string
|
|
body []byte
|
|
contentType string
|
|
count int32
|
|
method string
|
|
mu sync.Mutex
|
|
resp *apimodel.MeasurementMetaResponse
|
|
url *url.URL
|
|
userAgent string
|
|
}
|
|
|
|
func (h *handleClientCallMeasurementMeta) ServeHTTP(w http.ResponseWriter, r *http.Request) {
|
|
ff := fakeFill{}
|
|
defer h.mu.Unlock()
|
|
h.mu.Lock()
|
|
if h.count > 0 {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.count++
|
|
if r.Body != nil {
|
|
data, err := netxlite.ReadAllContext(r.Context(), r.Body)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.body = data
|
|
}
|
|
h.method = r.Method
|
|
h.url = r.URL
|
|
h.accept = r.Header.Get("Accept")
|
|
h.contentType = r.Header.Get("Content-Type")
|
|
h.userAgent = r.Header.Get("User-Agent")
|
|
var out *apimodel.MeasurementMetaResponse
|
|
ff.Fill(&out)
|
|
h.resp = out
|
|
data, err := json.Marshal(out)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
w.Write(data)
|
|
}
|
|
|
|
func TestMeasurementMetaClientCallRoundTrip(t *testing.T) {
|
|
// setup
|
|
handler := &handleClientCallMeasurementMeta{}
|
|
srvr := httptest.NewServer(handler)
|
|
defer srvr.Close()
|
|
req := &apimodel.MeasurementMetaRequest{}
|
|
ff := &fakeFill{}
|
|
ff.Fill(&req)
|
|
clnt := &Client{KVStore: &kvstore.Memory{}, BaseURL: srvr.URL}
|
|
ff.Fill(&clnt.UserAgent)
|
|
// issue request
|
|
ctx := context.Background()
|
|
resp, err := clnt.MeasurementMeta(ctx, req)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if resp == nil {
|
|
t.Fatal("expected non-nil response here")
|
|
}
|
|
// compare our response and server's one
|
|
if diff := cmp.Diff(handler.resp, resp); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
// check whether headers are OK
|
|
if handler.accept != "application/json" {
|
|
t.Fatal("invalid accept header")
|
|
}
|
|
if handler.userAgent != clnt.UserAgent {
|
|
t.Fatal("invalid user-agent header")
|
|
}
|
|
// check whether the method is OK
|
|
if handler.method != "GET" {
|
|
t.Fatal("invalid method")
|
|
}
|
|
// check the query
|
|
api := &simpleMeasurementMetaAPI{BaseURL: srvr.URL}
|
|
httpReq, err := api.newRequest(context.Background(), req)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if diff := cmp.Diff(handler.url.Path, httpReq.URL.Path); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
if diff := cmp.Diff(handler.url.RawQuery, httpReq.URL.RawQuery); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
}
|
|
|
|
type handleClientCallTestHelpers struct {
|
|
accept string
|
|
body []byte
|
|
contentType string
|
|
count int32
|
|
method string
|
|
mu sync.Mutex
|
|
resp apimodel.TestHelpersResponse
|
|
url *url.URL
|
|
userAgent string
|
|
}
|
|
|
|
func (h *handleClientCallTestHelpers) ServeHTTP(w http.ResponseWriter, r *http.Request) {
|
|
ff := fakeFill{}
|
|
defer h.mu.Unlock()
|
|
h.mu.Lock()
|
|
if h.count > 0 {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.count++
|
|
if r.Body != nil {
|
|
data, err := netxlite.ReadAllContext(r.Context(), r.Body)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.body = data
|
|
}
|
|
h.method = r.Method
|
|
h.url = r.URL
|
|
h.accept = r.Header.Get("Accept")
|
|
h.contentType = r.Header.Get("Content-Type")
|
|
h.userAgent = r.Header.Get("User-Agent")
|
|
var out apimodel.TestHelpersResponse
|
|
ff.Fill(&out)
|
|
h.resp = out
|
|
data, err := json.Marshal(out)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
w.Write(data)
|
|
}
|
|
|
|
func TestTestHelpersClientCallRoundTrip(t *testing.T) {
|
|
// setup
|
|
handler := &handleClientCallTestHelpers{}
|
|
srvr := httptest.NewServer(handler)
|
|
defer srvr.Close()
|
|
req := &apimodel.TestHelpersRequest{}
|
|
ff := &fakeFill{}
|
|
ff.Fill(&req)
|
|
clnt := &Client{KVStore: &kvstore.Memory{}, BaseURL: srvr.URL}
|
|
ff.Fill(&clnt.UserAgent)
|
|
// issue request
|
|
ctx := context.Background()
|
|
resp, err := clnt.TestHelpers(ctx, req)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if resp == nil {
|
|
t.Fatal("expected non-nil response here")
|
|
}
|
|
// compare our response and server's one
|
|
if diff := cmp.Diff(handler.resp, resp); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
// check whether headers are OK
|
|
if handler.accept != "application/json" {
|
|
t.Fatal("invalid accept header")
|
|
}
|
|
if handler.userAgent != clnt.UserAgent {
|
|
t.Fatal("invalid user-agent header")
|
|
}
|
|
// check whether the method is OK
|
|
if handler.method != "GET" {
|
|
t.Fatal("invalid method")
|
|
}
|
|
// check the query
|
|
api := &simpleTestHelpersAPI{BaseURL: srvr.URL}
|
|
httpReq, err := api.newRequest(context.Background(), req)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if diff := cmp.Diff(handler.url.Path, httpReq.URL.Path); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
if diff := cmp.Diff(handler.url.RawQuery, httpReq.URL.RawQuery); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
}
|
|
|
|
type handleClientCallPsiphonConfig struct {
|
|
accept string
|
|
body []byte
|
|
contentType string
|
|
count int32
|
|
method string
|
|
mu sync.Mutex
|
|
resp apimodel.PsiphonConfigResponse
|
|
url *url.URL
|
|
userAgent string
|
|
}
|
|
|
|
func (h *handleClientCallPsiphonConfig) ServeHTTP(w http.ResponseWriter, r *http.Request) {
|
|
ff := fakeFill{}
|
|
if r.URL.Path == "/api/v1/register" {
|
|
var out apimodel.RegisterResponse
|
|
ff.Fill(&out)
|
|
data, err := json.Marshal(out)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
w.Write(data)
|
|
return
|
|
}
|
|
if r.URL.Path == "/api/v1/login" {
|
|
var out apimodel.LoginResponse
|
|
ff.Fill(&out)
|
|
data, err := json.Marshal(out)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
w.Write(data)
|
|
return
|
|
}
|
|
defer h.mu.Unlock()
|
|
h.mu.Lock()
|
|
if h.count > 0 {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.count++
|
|
if r.Body != nil {
|
|
data, err := netxlite.ReadAllContext(r.Context(), r.Body)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.body = data
|
|
}
|
|
h.method = r.Method
|
|
h.url = r.URL
|
|
h.accept = r.Header.Get("Accept")
|
|
h.contentType = r.Header.Get("Content-Type")
|
|
h.userAgent = r.Header.Get("User-Agent")
|
|
var out apimodel.PsiphonConfigResponse
|
|
ff.Fill(&out)
|
|
h.resp = out
|
|
data, err := json.Marshal(out)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
w.Write(data)
|
|
}
|
|
|
|
func TestPsiphonConfigClientCallRoundTrip(t *testing.T) {
|
|
// setup
|
|
handler := &handleClientCallPsiphonConfig{}
|
|
srvr := httptest.NewServer(handler)
|
|
defer srvr.Close()
|
|
req := &apimodel.PsiphonConfigRequest{}
|
|
ff := &fakeFill{}
|
|
ff.Fill(&req)
|
|
clnt := &Client{KVStore: &kvstore.Memory{}, BaseURL: srvr.URL}
|
|
ff.Fill(&clnt.UserAgent)
|
|
// issue request
|
|
ctx := context.Background()
|
|
resp, err := clnt.PsiphonConfig(ctx, req)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if resp == nil {
|
|
t.Fatal("expected non-nil response here")
|
|
}
|
|
// compare our response and server's one
|
|
if diff := cmp.Diff(handler.resp, resp); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
// check whether headers are OK
|
|
if handler.accept != "application/json" {
|
|
t.Fatal("invalid accept header")
|
|
}
|
|
if handler.userAgent != clnt.UserAgent {
|
|
t.Fatal("invalid user-agent header")
|
|
}
|
|
// check whether the method is OK
|
|
if handler.method != "GET" {
|
|
t.Fatal("invalid method")
|
|
}
|
|
// check the query
|
|
api := &simplePsiphonConfigAPI{BaseURL: srvr.URL}
|
|
httpReq, err := api.newRequest(context.Background(), req)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if diff := cmp.Diff(handler.url.Path, httpReq.URL.Path); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
if diff := cmp.Diff(handler.url.RawQuery, httpReq.URL.RawQuery); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
}
|
|
|
|
type handleClientCallTorTargets struct {
|
|
accept string
|
|
body []byte
|
|
contentType string
|
|
count int32
|
|
method string
|
|
mu sync.Mutex
|
|
resp apimodel.TorTargetsResponse
|
|
url *url.URL
|
|
userAgent string
|
|
}
|
|
|
|
func (h *handleClientCallTorTargets) ServeHTTP(w http.ResponseWriter, r *http.Request) {
|
|
ff := fakeFill{}
|
|
if r.URL.Path == "/api/v1/register" {
|
|
var out apimodel.RegisterResponse
|
|
ff.Fill(&out)
|
|
data, err := json.Marshal(out)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
w.Write(data)
|
|
return
|
|
}
|
|
if r.URL.Path == "/api/v1/login" {
|
|
var out apimodel.LoginResponse
|
|
ff.Fill(&out)
|
|
data, err := json.Marshal(out)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
w.Write(data)
|
|
return
|
|
}
|
|
defer h.mu.Unlock()
|
|
h.mu.Lock()
|
|
if h.count > 0 {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.count++
|
|
if r.Body != nil {
|
|
data, err := netxlite.ReadAllContext(r.Context(), r.Body)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.body = data
|
|
}
|
|
h.method = r.Method
|
|
h.url = r.URL
|
|
h.accept = r.Header.Get("Accept")
|
|
h.contentType = r.Header.Get("Content-Type")
|
|
h.userAgent = r.Header.Get("User-Agent")
|
|
var out apimodel.TorTargetsResponse
|
|
ff.Fill(&out)
|
|
h.resp = out
|
|
data, err := json.Marshal(out)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
w.Write(data)
|
|
}
|
|
|
|
func TestTorTargetsClientCallRoundTrip(t *testing.T) {
|
|
// setup
|
|
handler := &handleClientCallTorTargets{}
|
|
srvr := httptest.NewServer(handler)
|
|
defer srvr.Close()
|
|
req := &apimodel.TorTargetsRequest{}
|
|
ff := &fakeFill{}
|
|
ff.Fill(&req)
|
|
clnt := &Client{KVStore: &kvstore.Memory{}, BaseURL: srvr.URL}
|
|
ff.Fill(&clnt.UserAgent)
|
|
// issue request
|
|
ctx := context.Background()
|
|
resp, err := clnt.TorTargets(ctx, req)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if resp == nil {
|
|
t.Fatal("expected non-nil response here")
|
|
}
|
|
// compare our response and server's one
|
|
if diff := cmp.Diff(handler.resp, resp); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
// check whether headers are OK
|
|
if handler.accept != "application/json" {
|
|
t.Fatal("invalid accept header")
|
|
}
|
|
if handler.userAgent != clnt.UserAgent {
|
|
t.Fatal("invalid user-agent header")
|
|
}
|
|
// check whether the method is OK
|
|
if handler.method != "GET" {
|
|
t.Fatal("invalid method")
|
|
}
|
|
// check the query
|
|
api := &simpleTorTargetsAPI{BaseURL: srvr.URL}
|
|
httpReq, err := api.newRequest(context.Background(), req)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if diff := cmp.Diff(handler.url.Path, httpReq.URL.Path); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
if diff := cmp.Diff(handler.url.RawQuery, httpReq.URL.RawQuery); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
}
|
|
|
|
type handleClientCallURLs struct {
|
|
accept string
|
|
body []byte
|
|
contentType string
|
|
count int32
|
|
method string
|
|
mu sync.Mutex
|
|
resp *apimodel.URLsResponse
|
|
url *url.URL
|
|
userAgent string
|
|
}
|
|
|
|
func (h *handleClientCallURLs) ServeHTTP(w http.ResponseWriter, r *http.Request) {
|
|
ff := fakeFill{}
|
|
defer h.mu.Unlock()
|
|
h.mu.Lock()
|
|
if h.count > 0 {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.count++
|
|
if r.Body != nil {
|
|
data, err := netxlite.ReadAllContext(r.Context(), r.Body)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.body = data
|
|
}
|
|
h.method = r.Method
|
|
h.url = r.URL
|
|
h.accept = r.Header.Get("Accept")
|
|
h.contentType = r.Header.Get("Content-Type")
|
|
h.userAgent = r.Header.Get("User-Agent")
|
|
var out *apimodel.URLsResponse
|
|
ff.Fill(&out)
|
|
h.resp = out
|
|
data, err := json.Marshal(out)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
w.Write(data)
|
|
}
|
|
|
|
func TestURLsClientCallRoundTrip(t *testing.T) {
|
|
// setup
|
|
handler := &handleClientCallURLs{}
|
|
srvr := httptest.NewServer(handler)
|
|
defer srvr.Close()
|
|
req := &apimodel.URLsRequest{}
|
|
ff := &fakeFill{}
|
|
ff.Fill(&req)
|
|
clnt := &Client{KVStore: &kvstore.Memory{}, BaseURL: srvr.URL}
|
|
ff.Fill(&clnt.UserAgent)
|
|
// issue request
|
|
ctx := context.Background()
|
|
resp, err := clnt.URLs(ctx, req)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if resp == nil {
|
|
t.Fatal("expected non-nil response here")
|
|
}
|
|
// compare our response and server's one
|
|
if diff := cmp.Diff(handler.resp, resp); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
// check whether headers are OK
|
|
if handler.accept != "application/json" {
|
|
t.Fatal("invalid accept header")
|
|
}
|
|
if handler.userAgent != clnt.UserAgent {
|
|
t.Fatal("invalid user-agent header")
|
|
}
|
|
// check whether the method is OK
|
|
if handler.method != "GET" {
|
|
t.Fatal("invalid method")
|
|
}
|
|
// check the query
|
|
api := &simpleURLsAPI{BaseURL: srvr.URL}
|
|
httpReq, err := api.newRequest(context.Background(), req)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if diff := cmp.Diff(handler.url.Path, httpReq.URL.Path); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
if diff := cmp.Diff(handler.url.RawQuery, httpReq.URL.RawQuery); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
}
|
|
|
|
type handleClientCallOpenReport struct {
|
|
accept string
|
|
body []byte
|
|
contentType string
|
|
count int32
|
|
method string
|
|
mu sync.Mutex
|
|
resp *apimodel.OpenReportResponse
|
|
url *url.URL
|
|
userAgent string
|
|
}
|
|
|
|
func (h *handleClientCallOpenReport) ServeHTTP(w http.ResponseWriter, r *http.Request) {
|
|
ff := fakeFill{}
|
|
defer h.mu.Unlock()
|
|
h.mu.Lock()
|
|
if h.count > 0 {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.count++
|
|
if r.Body != nil {
|
|
data, err := netxlite.ReadAllContext(r.Context(), r.Body)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.body = data
|
|
}
|
|
h.method = r.Method
|
|
h.url = r.URL
|
|
h.accept = r.Header.Get("Accept")
|
|
h.contentType = r.Header.Get("Content-Type")
|
|
h.userAgent = r.Header.Get("User-Agent")
|
|
var out *apimodel.OpenReportResponse
|
|
ff.Fill(&out)
|
|
h.resp = out
|
|
data, err := json.Marshal(out)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
w.Write(data)
|
|
}
|
|
|
|
func TestOpenReportClientCallRoundTrip(t *testing.T) {
|
|
// setup
|
|
handler := &handleClientCallOpenReport{}
|
|
srvr := httptest.NewServer(handler)
|
|
defer srvr.Close()
|
|
req := &apimodel.OpenReportRequest{}
|
|
ff := &fakeFill{}
|
|
ff.Fill(&req)
|
|
clnt := &Client{KVStore: &kvstore.Memory{}, BaseURL: srvr.URL}
|
|
ff.Fill(&clnt.UserAgent)
|
|
// issue request
|
|
ctx := context.Background()
|
|
resp, err := clnt.OpenReport(ctx, req)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if resp == nil {
|
|
t.Fatal("expected non-nil response here")
|
|
}
|
|
// compare our response and server's one
|
|
if diff := cmp.Diff(handler.resp, resp); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
// check whether headers are OK
|
|
if handler.accept != "application/json" {
|
|
t.Fatal("invalid accept header")
|
|
}
|
|
if handler.userAgent != clnt.UserAgent {
|
|
t.Fatal("invalid user-agent header")
|
|
}
|
|
// check whether the method is OK
|
|
if handler.method != "POST" {
|
|
t.Fatal("invalid method")
|
|
}
|
|
// check the body
|
|
if handler.contentType != "application/json" {
|
|
t.Fatal("invalid content-type header")
|
|
}
|
|
got := &apimodel.OpenReportRequest{}
|
|
if err := json.Unmarshal(handler.body, &got); err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if diff := cmp.Diff(req, got); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
}
|
|
|
|
type handleClientCallSubmitMeasurement struct {
|
|
accept string
|
|
body []byte
|
|
contentType string
|
|
count int32
|
|
method string
|
|
mu sync.Mutex
|
|
resp *apimodel.SubmitMeasurementResponse
|
|
url *url.URL
|
|
userAgent string
|
|
}
|
|
|
|
func (h *handleClientCallSubmitMeasurement) ServeHTTP(w http.ResponseWriter, r *http.Request) {
|
|
ff := fakeFill{}
|
|
defer h.mu.Unlock()
|
|
h.mu.Lock()
|
|
if h.count > 0 {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.count++
|
|
if r.Body != nil {
|
|
data, err := netxlite.ReadAllContext(r.Context(), r.Body)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
h.body = data
|
|
}
|
|
h.method = r.Method
|
|
h.url = r.URL
|
|
h.accept = r.Header.Get("Accept")
|
|
h.contentType = r.Header.Get("Content-Type")
|
|
h.userAgent = r.Header.Get("User-Agent")
|
|
var out *apimodel.SubmitMeasurementResponse
|
|
ff.Fill(&out)
|
|
h.resp = out
|
|
data, err := json.Marshal(out)
|
|
if err != nil {
|
|
w.WriteHeader(400)
|
|
return
|
|
}
|
|
w.Write(data)
|
|
}
|
|
|
|
func TestSubmitMeasurementClientCallRoundTrip(t *testing.T) {
|
|
// setup
|
|
handler := &handleClientCallSubmitMeasurement{}
|
|
srvr := httptest.NewServer(handler)
|
|
defer srvr.Close()
|
|
req := &apimodel.SubmitMeasurementRequest{}
|
|
ff := &fakeFill{}
|
|
ff.Fill(&req)
|
|
clnt := &Client{KVStore: &kvstore.Memory{}, BaseURL: srvr.URL}
|
|
ff.Fill(&clnt.UserAgent)
|
|
// issue request
|
|
ctx := context.Background()
|
|
resp, err := clnt.SubmitMeasurement(ctx, req)
|
|
if err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if resp == nil {
|
|
t.Fatal("expected non-nil response here")
|
|
}
|
|
// compare our response and server's one
|
|
if diff := cmp.Diff(handler.resp, resp); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
// check whether headers are OK
|
|
if handler.accept != "application/json" {
|
|
t.Fatal("invalid accept header")
|
|
}
|
|
if handler.userAgent != clnt.UserAgent {
|
|
t.Fatal("invalid user-agent header")
|
|
}
|
|
// check whether the method is OK
|
|
if handler.method != "POST" {
|
|
t.Fatal("invalid method")
|
|
}
|
|
// check the body
|
|
if handler.contentType != "application/json" {
|
|
t.Fatal("invalid content-type header")
|
|
}
|
|
got := &apimodel.SubmitMeasurementRequest{}
|
|
if err := json.Unmarshal(handler.body, &got); err != nil {
|
|
t.Fatal(err)
|
|
}
|
|
if diff := cmp.Diff(req, got); diff != "" {
|
|
t.Fatal(diff)
|
|
}
|
|
}
|