Bump google.golang.org/api

This commit is contained in:
Andrea Spacca
2019-03-17 20:19:56 +01:00
parent 8e39b7fa01
commit ec086b4eb3
5432 changed files with 2486664 additions and 231553 deletions

View File

@@ -0,0 +1,92 @@
// Copyright 2015 Google Inc. 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 querystring
import (
"encoding/json"
"github.com/google/martian"
"github.com/google/martian/filter"
"github.com/google/martian/parse"
)
var noop = martian.Noop("querystring.Filter")
func init() {
parse.Register("querystring.Filter", filterFromJSON)
}
// Filter runs modifiers iff the request query parameter for name matches value.
type Filter struct {
*filter.Filter
}
type filterJSON struct {
Name string `json:"name"`
Value string `json:"value"`
Modifier json.RawMessage `json:"modifier"`
ElseModifier json.RawMessage `json:"else"`
Scope []parse.ModifierType `json:"scope"`
}
// NewFilter builds a querystring.Filter that filters on name and optionally
// value.
func NewFilter(name, value string) *Filter {
m := NewMatcher(name, value)
f := filter.New()
f.SetRequestCondition(m)
f.SetResponseCondition(m)
return &Filter{f}
}
// filterFromJSON takes a JSON message and returns a querystring.Filter.
//
// Example JSON:
// {
// "name": "param",
// "value": "example",
// "scope": ["request", "response"],
// "modifier": { ... }
// }
func filterFromJSON(b []byte) (*parse.Result, error) {
msg := &filterJSON{}
if err := json.Unmarshal(b, msg); err != nil {
return nil, err
}
f := NewFilter(msg.Name, msg.Value)
r, err := parse.FromJSON(msg.Modifier)
if err != nil {
return nil, err
}
f.RequestWhenTrue(r.RequestModifier())
f.ResponseWhenTrue(r.ResponseModifier())
if len(msg.ElseModifier) > 0 {
em, err := parse.FromJSON(msg.ElseModifier)
if err != nil {
return nil, err
}
if em != nil {
f.RequestWhenFalse(em.RequestModifier())
f.ResponseWhenFalse(em.ResponseModifier())
}
}
return parse.NewResult(f, msg.Scope)
}

View File

@@ -0,0 +1,339 @@
// Copyright 2015 Google Inc. 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 querystring
import (
"errors"
"net/http"
"strings"
"testing"
"github.com/google/martian"
"github.com/google/martian/martiantest"
"github.com/google/martian/parse"
"github.com/google/martian/proxyutil"
"github.com/google/martian/verify"
// Import to register header.Modifier with JSON parser.
_ "github.com/google/martian/header"
)
func TestNoModifiers(t *testing.T) {
f := NewFilter("", "")
f.SetRequestModifier(nil)
f.SetResponseModifier(nil)
req, err := http.NewRequest("GET", "http://example.com", nil)
if err != nil {
t.Fatalf("http.NewRequest(): got %v, want no error", err)
}
if err := f.ModifyRequest(req); err != nil {
t.Errorf("ModifyRequest(): got %v, want no error", err)
}
res := proxyutil.NewResponse(200, nil, req)
if err := f.ModifyResponse(res); err != nil {
t.Errorf("ModifyResponse(): got %v, want no error", err)
}
}
func TestQueryStringFilterWithQuery(t *testing.T) {
// Name only, no value.
f := NewFilter("match", "")
tm := martiantest.NewModifier()
f.SetRequestModifier(tm)
f.SetResponseModifier(tm)
req, err := http.NewRequest("GET", "http://martian.local?match=any", nil)
if err != nil {
t.Fatalf("http.NewRequest(): got %v, want no error", err)
}
if err := f.ModifyRequest(req); err != nil {
t.Errorf("ModifyRequest(): got %v, want no error", err)
}
if !tm.RequestModified() {
t.Error("tm.RequestModified(): got false, want true")
}
res := proxyutil.NewResponse(200, nil, req)
if err := f.ModifyResponse(res); err != nil {
t.Errorf("ModifyResponse(): got %v, want no error", err)
}
if !tm.ResponseModified() {
t.Error("tm.ResponseModified(): got false, want true")
}
tm.Reset()
req, err = http.NewRequest("GET", "http://martian.local?nomatch", nil)
if err != nil {
t.Fatalf("http.NewRequest(): got %v, want no error", err)
}
if err := f.ModifyRequest(req); err != nil {
t.Errorf("ModifyRequest(): got %v, want no error", err)
}
res = proxyutil.NewResponse(200, nil, req)
if err := f.ModifyResponse(res); err != nil {
t.Errorf("ModifyResponse(): got %v, want no error", err)
}
if tm.RequestModified() {
t.Error("tm.RequestModified(): got true, want false")
}
if tm.ResponseModified() {
t.Error("tm.ResponseModified(): got true, want false")
}
tm.Reset()
// Name and value.
f = NewFilter("match", "value")
f.SetRequestModifier(tm)
f.SetResponseModifier(tm)
req, err = http.NewRequest("GET", "http://martian.local?match=value", nil)
if err != nil {
t.Fatalf("http.NewRequest(): got %v, want no error", err)
}
if err := f.ModifyRequest(req); err != nil {
t.Errorf("ModifyRequest(): got %v, want no error", err)
}
res = proxyutil.NewResponse(200, nil, req)
if err := f.ModifyResponse(res); err != nil {
t.Errorf("ModifyResponse(): got %v, want no error", err)
}
if !tm.RequestModified() {
t.Error("tm.RequestModified(): got false, want true")
}
if !tm.ResponseModified() {
t.Error("tm.ResponseModified(): got false, want true")
}
tm.Reset()
req, err = http.NewRequest("GET", "http://martian.local?match=notvalue", nil)
if err != nil {
t.Fatalf("http.NewRequest(): got %v, want no error", err)
}
if err := f.ModifyRequest(req); err != nil {
t.Errorf("ModifyRequest(): got %v, want no error", err)
}
res = proxyutil.NewResponse(200, nil, req)
if err := f.ModifyResponse(res); err != nil {
t.Errorf("ModifyResponse(): got %v, want no error", err)
}
if tm.RequestModified() {
t.Error("tm.RequestModified(): got true, want false")
}
if tm.ResponseModified() {
t.Error("tm.ResponseModified(): got true, want false")
}
tm.Reset()
// Explicitly do not match POST data.
req, err = http.NewRequest("GET", "http://martian.local", strings.NewReader("match=value"))
if err != nil {
t.Fatalf("http.NewRequest(): got %v, want no error", err)
}
if err := f.ModifyRequest(req); err != nil {
t.Errorf("ModifyRequest(): got %v, want no error", err)
}
res = proxyutil.NewResponse(200, nil, req)
if err := f.ModifyResponse(res); err != nil {
t.Errorf("ModifyResponse(): got %v, want no error", err)
}
if tm.RequestModified() {
t.Error("tm.RequestModified(): got true, want false")
}
if tm.ResponseModified() {
t.Error("tm.ResponseModified(): got true, want false")
}
tm.Reset()
}
func TestFilterFromJSON(t *testing.T) {
msg := []byte(`{
"querystring.Filter": {
"scope": ["request", "response"],
"name": "param",
"value": "true",
"modifier": {
"header.Modifier": {
"scope": ["request", "response"],
"name": "Martian-Modified",
"value": "true"
}
}
}
}`)
r, err := parse.FromJSON(msg)
if err != nil {
t.Fatalf("parse.FromJSON(): got %v, want no error", err)
}
reqmod := r.RequestModifier()
if reqmod == nil {
t.Fatal("reqmod: got nil, want not nil")
}
req, err := http.NewRequest("GET", "https://martian.test?param=true", nil)
if err != nil {
t.Fatalf("http.NewRequest(): got %v, want no error", err)
}
if err := reqmod.ModifyRequest(req); err != nil {
t.Fatalf("reqmod.ModifyRequest(): got %v, want no error", err)
}
if got, want := req.Header.Get("Martian-Modified"), "true"; got != want {
t.Errorf("req.Header.Get(%q): got %q, want %q", "Martian-Modified", got, want)
}
resmod := r.ResponseModifier()
if resmod == nil {
t.Fatalf("resmod: got nil, want not nil")
}
res := proxyutil.NewResponse(200, nil, req)
if err := resmod.ModifyResponse(res); err != nil {
t.Fatalf("resmod.ModifyResponse(): got %v, want no error", err)
}
if got, want := res.Header.Get("Martian-Modified"), "true"; got != want {
t.Errorf("res.Header.Get(%q): got %q, want %q", "Martian-Modified", got, want)
}
}
func TestElseCondition(t *testing.T) {
msg := []byte(`{
"querystring.Filter": {
"scope": ["request", "response"],
"name": "param",
"value": "true",
"modifier": {
"header.Modifier": {
"scope": ["request", "response"],
"name": "Martian-Modified",
"value": "true"
}
},
"else": {
"header.Modifier": {
"scope": ["request", "response"],
"name": "Martian-Modified",
"value": "false"
}
}
}
}`)
r, err := parse.FromJSON(msg)
if err != nil {
t.Fatalf("parse.FromJSON(): got %v, want no error", err)
}
reqmod := r.RequestModifier()
if reqmod == nil {
t.Fatal("reqmod: got nil, want not nil")
}
req, err := http.NewRequest("GET", "https://martian.test?param=false", nil)
if err != nil {
t.Fatalf("http.NewRequest(): got %v, want no error", err)
}
if err := reqmod.ModifyRequest(req); err != nil {
t.Fatalf("reqmod.ModifyRequest(): got %v, want no error", err)
}
if got, want := req.Header.Get("Martian-Modified"), "false"; got != want {
t.Errorf("req.Header.Get(%q): got %q, want %q", "Martian-Modified", got, want)
}
resmod := r.ResponseModifier()
if resmod == nil {
t.Fatalf("resmod: got nil, want not nil")
}
res := proxyutil.NewResponse(200, nil, req)
if err := resmod.ModifyResponse(res); err != nil {
t.Fatalf("resmod.ModifyResponse(): got %v, want no error", err)
}
if got, want := res.Header.Get("Martian-Modified"), "false"; got != want {
t.Errorf("res.Header.Get(%q): got %q, want %q", "Martian-Modified", got, want)
}
}
func TestVerifyRequests(t *testing.T) {
f := NewFilter("", "")
if err := f.VerifyRequests(); err != nil {
t.Fatalf("VerifyRequest(): got %v, want no error", err)
}
tv := &verify.TestVerifier{
RequestError: errors.New("verify request failure"),
}
f.SetRequestModifier(tv)
want := martian.NewMultiError()
want.Add(tv.RequestError)
if got := f.VerifyRequests(); got.Error() != want.Error() {
t.Fatalf("VerifyRequests(): got %v, want %v", got, want)
}
f.ResetRequestVerifications()
if err := f.VerifyRequests(); err != nil {
t.Fatalf("VerifyRequest(): got %v, want no error", err)
}
}
func TestVerifyResponses(t *testing.T) {
f := NewFilter("", "")
if err := f.VerifyResponses(); err != nil {
t.Fatalf("VerifyResponses(): got %v, want no error", err)
}
tv := &verify.TestVerifier{
ResponseError: errors.New("verify response failure"),
}
f.SetResponseModifier(tv)
want := martian.NewMultiError()
want.Add(tv.ResponseError)
if got := f.VerifyResponses(); got.Error() != want.Error() {
t.Fatalf("VerifyResponses(): got %v, want %v", got, want)
}
f.ResetResponseVerifications()
if err := f.VerifyResponses(); err != nil {
t.Fatalf("VerifyResponses(): got %v, want no error", err)
}
}

View File

@@ -0,0 +1,56 @@
// Copyright 2017 Google Inc. 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 querystring
import "net/http"
// Matcher is a conditonal evalutor of query string parameters
// to be used in structs that take conditions.
type Matcher struct {
name, value string
}
// NewMatcher builds a new querystring matcher
func NewMatcher(name, value string) *Matcher {
return &Matcher{name: name, value: value}
}
// MatchRequest evaluates a request and returns whether or not
// the request contains a querystring param that matches the provided name
// and value.
func (m *Matcher) MatchRequest(req *http.Request) bool {
for n, vs := range req.URL.Query() {
if m.name == n {
if m.value == "" {
return true
}
for _, v := range vs {
if m.value == v {
return true
}
}
}
}
return false
}
// MatchResponse evaluates a response and returns whether or not
// the request that resulted in that response contains a querystring param that matches the provided name
// and value.
func (m *Matcher) MatchResponse(res *http.Response) bool {
return m.MatchRequest(res.Request)
}

View File

@@ -0,0 +1,76 @@
// Copyright 2015 Google Inc. 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 querystring contains a modifier to rewrite query strings in a request.
package querystring
import (
"encoding/json"
"net/http"
"github.com/google/martian"
"github.com/google/martian/parse"
)
func init() {
parse.Register("querystring.Modifier", modifierFromJSON)
}
type modifier struct {
key, value string
}
type modifierJSON struct {
Name string `json:"name"`
Value string `json:"value"`
Scope []parse.ModifierType `json:"scope"`
}
// ModifyRequest modifies the query string of the request with the given key and value.
func (m *modifier) ModifyRequest(req *http.Request) error {
query := req.URL.Query()
query.Set(m.key, m.value)
req.URL.RawQuery = query.Encode()
return nil
}
// NewModifier returns a request modifier that will set the query string
// at key with the given value. If the query string key already exists all
// values will be overwritten.
func NewModifier(key, value string) martian.RequestModifier {
return &modifier{
key: key,
value: value,
}
}
// modifierFromJSON takes a JSON message as a byte slice and returns
// a querystring.modifier and an error.
//
// Example JSON:
// {
// "name": "param",
// "value": "true",
// "scope": ["request", "response"]
// }
func modifierFromJSON(b []byte) (*parse.Result, error) {
msg := &modifierJSON{}
if err := json.Unmarshal(b, msg); err != nil {
return nil, err
}
return parse.NewResult(NewModifier(msg.Name, msg.Value), msg.Scope)
}

View File

@@ -0,0 +1,108 @@
// Copyright 2015 Google Inc. 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 querystring
import (
"net/http"
"testing"
"github.com/google/martian/parse"
)
func TestNewQueryStringModifier(t *testing.T) {
mod := NewModifier("testing", "true")
req, err := http.NewRequest("GET", "/", nil)
if err != nil {
t.Fatalf("NewRequest(): got %v, want no error", err)
}
if err := mod.ModifyRequest(req); err != nil {
t.Fatalf("ModifyRequest(): got %v, want no error", err)
}
if got, want := req.URL.Query().Get("testing"), "true"; got != want {
t.Errorf("req.URL.Query().Get(%q): got %q, want %q", "testing", got, want)
}
}
func TestQueryStringModifierQueryExists(t *testing.T) {
mod := NewModifier("testing", "true")
req, err := http.NewRequest("GET", "/?testing=false", nil)
if err != nil {
t.Fatalf("NewRequest(): got %v, want no error", err)
}
if err := mod.ModifyRequest(req); err != nil {
t.Fatalf("ModifyRequest(): got %v, want no error", err)
}
if got, want := req.URL.Query().Get("testing"), "true"; got != want {
t.Errorf("req.URL.Query().Get(%q): got %q, want %q", "testing", got, want)
}
}
func TestQueryStringModifierQueryExistsMultipleKeys(t *testing.T) {
mod := NewModifier("testing", "true")
req, err := http.NewRequest("GET", "/?testing=false&testing=foo&foo=bar", nil)
if err != nil {
t.Fatalf("NewRequest(): got %v, want no error", err)
}
if err := mod.ModifyRequest(req); err != nil {
t.Fatalf("ModifyRequest(): got %v, want no error", err)
}
if got, want := req.URL.Query().Get("testing"), "true"; got != want {
t.Errorf("req.URL.Query().Get(%q): got %q, want %q", "testing", got, want)
}
if got, want := req.URL.Query().Get("foo"), "bar"; got != want {
t.Errorf("req.URL.Query().Get(%q): got %q, want %q", "testing", got, want)
}
}
func TestModifierFromJSON(t *testing.T) {
msg := []byte(`
{
"querystring.Modifier": {
"scope": ["request"],
"name": "param",
"value": "true"
}
}`)
r, err := parse.FromJSON(msg)
if err != nil {
t.Fatalf("parse.FromJSON(): got %v, want no error", err)
}
req, err := http.NewRequest("GET", "http://martian.test", nil)
if err != nil {
t.Fatalf("http.NewRequest(): got %q, want no error", err)
}
reqmod := r.RequestModifier()
if reqmod == nil {
t.Fatalf("reqmod: got nil, want not nil")
}
if err := reqmod.ModifyRequest(req); err != nil {
t.Fatalf("reqmod.ModifyRequest(): got %v, want no error", err)
}
if got, want := req.URL.Query().Get("param"), "true"; got != want {
t.Errorf("req.URL.Query().Get(%q): got %q, want %q", "param", got, want)
}
}

View File

@@ -0,0 +1,127 @@
// Copyright 2015 Google Inc. 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 querystring
import (
"encoding/json"
"fmt"
"net/http"
"strings"
"github.com/google/martian"
"github.com/google/martian/parse"
"github.com/google/martian/verify"
)
func init() {
parse.Register("querystring.Verifier", verifierFromJSON)
}
type verifier struct {
key, value string
err *martian.MultiError
}
type verifierJSON struct {
Name string `json:"name"`
Value string `json:"value"`
Scope []parse.ModifierType `json:"scope"`
}
// NewVerifier returns a new param verifier.
func NewVerifier(key, value string) (verify.RequestVerifier, error) {
if key == "" {
return nil, fmt.Errorf("no key provided to param verifier")
}
return &verifier{
key: key,
value: value,
err: martian.NewMultiError(),
}, nil
}
// ModifyRequest verifies that the request's URL params match the given params
// in all modified requests. If no value is provided, the verifier will only
// check if the given key is present. An error will be added to the contained
// *MultiError if the param is unmatched.
func (v *verifier) ModifyRequest(req *http.Request) error {
// skip requests to API
ctx := martian.NewContext(req)
if ctx.IsAPIRequest() {
return nil
}
if err := req.ParseForm(); err != nil {
err := fmt.Errorf("request(%v) parsing failed; could not parse query parameters", req.URL)
v.err.Add(err)
return nil
}
vals, ok := req.Form[v.key]
if !ok {
err := fmt.Errorf("request(%v) param verification error: key %v not found", req.URL, v.key)
v.err.Add(err)
return nil
}
if v.value == "" {
return nil
}
for _, val := range vals {
if v.value == val {
return nil
}
}
err := fmt.Errorf("request(%v) param verification error: got %v for key %v, want %v", req.URL, strings.Join(vals, ", "), v.key, v.value)
v.err.Add(err)
return nil
}
// VerifyRequests returns an error if verification for any request failed.
// If an error is returned it will be of type *martian.MultiError.
func (v *verifier) VerifyRequests() error {
if v.err.Empty() {
return nil
}
return v.err
}
// ResetRequestVerifications clears all failed request verifications.
func (v *verifier) ResetRequestVerifications() {
v.err = martian.NewMultiError()
}
// verifierFromJSON builds a querystring.Verifier from JSON.
//
// Example JSON:
// {
// "querystring.Verifier": {
// "scope": ["request", "response"],
// "name": "Martian-Testing",
// "value": "true"
// }
// }
func verifierFromJSON(b []byte) (*parse.Result, error) {
msg := &verifierJSON{}
if err := json.Unmarshal(b, msg); err != nil {
return nil, err
}
v, err := NewVerifier(msg.Name, msg.Value)
if err != nil {
return nil, err
}
return parse.NewResult(v, msg.Scope)
}

View File

@@ -0,0 +1,194 @@
// Copyright 2015 Google Inc. 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 querystring
import (
"net/http"
"testing"
"github.com/google/martian"
"github.com/google/martian/parse"
"github.com/google/martian/verify"
)
func TestVerifyRequestPasses(t *testing.T) {
v, err := NewVerifier("foo", "bar")
if err != nil {
t.Fatalf("NewVerifier(%q, %q): got %v, want no error", "foo", "bar", err)
}
req, err := http.NewRequest("GET", "http://www.google.com?foo=baz&foo=bar", nil)
if err != nil {
t.Fatalf("http.NewRequest(): got %v, want no error", err)
}
_, remove, err := martian.TestContext(req, nil, nil)
if err != nil {
t.Fatalf("TestContext(): got %v, want no error", err)
}
defer remove()
if err := v.ModifyRequest(req); err != nil {
t.Fatalf("ModifyRequest(): got %v, want no error", err)
}
if err := v.VerifyRequests(); err != nil {
t.Fatalf("VerifyRequests(): got %v, want no error", err)
}
}
func TestVerifyEmptyValue(t *testing.T) {
v, err := NewVerifier("foo", "")
if err != nil {
t.Fatalf("NewVerifier(%q, %q): got %v, want no error", "foo", "", err)
}
req, err := http.NewRequest("GET", "http://www.google.com?foo=bar", nil)
if err != nil {
t.Fatalf("http.NewRequest(): got %v, want no error", err)
}
_, remove, err := martian.TestContext(req, nil, nil)
if err != nil {
t.Fatalf("TestContext(): got %v, want no error", err)
}
defer remove()
if err := v.ModifyRequest(req); err != nil {
t.Fatalf("ModifyRequest(): got %v, want no error", err)
}
if err := v.VerifyRequests(); err != nil {
t.Fatalf("VerifyRequests(): got %v, want no error", err)
}
}
func TestFailureWithMissingKey(t *testing.T) {
v, err := NewVerifier("foo", "bar")
if err != nil {
t.Fatalf("NewVerifier(%q, %q): got %v, want no error", "foo", "bar", err)
}
req, err := http.NewRequest("GET", "http://www.google.com?fizz=bar", nil)
if err != nil {
t.Fatalf("http.NewRequest(): got %v, want no error", err)
}
_, remove, err := martian.TestContext(req, nil, nil)
if err != nil {
t.Fatalf("TestContext(): got %v, want no error", err)
}
defer remove()
if err := v.ModifyRequest(req); err != nil {
t.Fatalf("ModifyRequest(): got %v, want no error", err)
}
merr, ok := v.VerifyRequests().(*martian.MultiError)
if !ok {
t.Fatal("VerifyRequests(): got nil, want *verify.MultiError")
}
errs := merr.Errors()
if len(errs) != 1 {
t.Fatalf("len(merr.Errors()): got %d, want 1", len(errs))
}
expectErr := "request(http://www.google.com?fizz=bar) param verification error: key foo not found"
for i := range errs {
if got, want := errs[i].Error(), expectErr; got != want {
t.Errorf("%d. err.Error(): mismatched error output\ngot: %s\nwant: %s", i, got, want)
}
}
}
func TestFailureWithMultiFail(t *testing.T) {
v, err := NewVerifier("foo", "bar")
if err != nil {
t.Fatalf("NewVerifier(%q, %q): got %v, want no error", "foo", "bar", err)
}
req, err := http.NewRequest("GET", "http://www.google.com?foo=baz", nil)
if err != nil {
t.Fatalf("http.NewRequest(): got %v, want no error", err)
}
_, remove, err := martian.TestContext(req, nil, nil)
if err != nil {
t.Fatalf("TestContext(): got %v, want no error", err)
}
defer remove()
if err := v.ModifyRequest(req); err != nil {
t.Fatalf("ModifyRequest(): got %v, want no error", err)
}
if err := v.ModifyRequest(req); err != nil {
t.Fatalf("ModifyRequest(): got %v, want no error", err)
}
merr, ok := v.VerifyRequests().(*martian.MultiError)
if !ok {
t.Fatalf("VerifyRequests(): got nil, want *verify.MultiError")
}
errs := merr.Errors()
if len(errs) != 2 {
t.Fatalf("len(merr.Errors()): got %d, want 2", len(errs))
}
expectErr := "request(http://www.google.com?foo=baz) param verification error: got baz for key foo, want bar"
for i := range errs {
if got, want := errs[i].Error(), expectErr; got != want {
t.Errorf("%d. err.Error(): mismatched error output\ngot: %s\nwant: %s", i,
got, want)
}
}
v.ResetRequestVerifications()
if err := v.VerifyRequests(); err != nil {
t.Fatalf("VerifyRequests(): got %v, want no error", err)
}
}
func TestBadInputToConstructor(t *testing.T) {
if _, err := NewVerifier("", "bar"); err == nil {
t.Fatalf("NewVerifier(): no error returned for empty key")
}
}
func TestVerifierFromJSON(t *testing.T) {
msg := []byte(`{
"querystring.Verifier": {
"scope": ["request"],
"name": "param",
"value": "true"
}
}`)
r, err := parse.FromJSON(msg)
if err != nil {
t.Fatalf("parse.FromJSON(): got %v, want no error", err)
}
reqmod := r.RequestModifier()
if reqmod == nil {
t.Fatal("reqmod: got nil, want not nil")
}
reqv, ok := reqmod.(verify.RequestVerifier)
if !ok {
t.Fatal("reqmod.(verify.RequestVerifier): got !ok, want ok")
}
req, err := http.NewRequest("GET", "http://example.com", nil)
if err != nil {
t.Fatalf("http.NewRequest(): got %v, want no error", err)
}
_, remove, err := martian.TestContext(req, nil, nil)
if err != nil {
t.Fatalf("TestContext(): got %v, want no error", err)
}
defer remove()
if err := reqv.ModifyRequest(req); err != nil {
t.Fatalf("ModifyRequest(): got %v, want no error", err)
}
if err := reqv.VerifyRequests(); err == nil {
t.Error("VerifyRequests(): got nil, want not nil")
}
}