This commit is contained in:
@@ -8,16 +8,40 @@ import (
|
|||||||
)
|
)
|
||||||
|
|
||||||
func CheckResults(testCase *TestCase) (bool, error) {
|
func CheckResults(testCase *TestCase) (bool, error) {
|
||||||
|
var result bool = true
|
||||||
|
|
||||||
// Check headers
|
// Check headers
|
||||||
result, err := HeaderContains(testCase)
|
headerContains, err := HeaderContains(testCase)
|
||||||
|
if err != nil {
|
||||||
|
return result, err
|
||||||
|
}
|
||||||
|
result = result && headerContains
|
||||||
|
|
||||||
|
headerEquals, err := HeaderEquals(testCase)
|
||||||
|
if err != nil {
|
||||||
|
return result, err
|
||||||
|
}
|
||||||
|
result = result && headerEquals
|
||||||
|
|
||||||
|
// Check body
|
||||||
|
bodyContains, err := BodyContains(testCase)
|
||||||
|
if err != nil {
|
||||||
|
return result, err
|
||||||
|
}
|
||||||
|
result = result && bodyContains
|
||||||
|
|
||||||
|
bodyHasKeys, err := BodyHasKeys(testCase)
|
||||||
|
if err != nil {
|
||||||
|
return result, err
|
||||||
|
}
|
||||||
|
result = result && bodyHasKeys
|
||||||
|
|
||||||
return result, err
|
return result, err
|
||||||
}
|
}
|
||||||
|
|
||||||
func HeaderContains(testCase *TestCase) (bool, error) {
|
func HeaderContains(testCase *TestCase) (bool, error) {
|
||||||
for k, v := range testCase.Expect.Header.Contains {
|
for k, v := range testCase.Expect.Header.Contains {
|
||||||
fmt.Printf("Header contains check '%s'='%s'\n", k, v)
|
//fmt.Printf("Header contains check '%s'='%s'\n", k, v)
|
||||||
|
|
||||||
if k == "http_status" { // http status is a special case
|
if k == "http_status" { // http status is a special case
|
||||||
statusCode, err := strconv.Atoi(v)
|
statusCode, err := strconv.Atoi(v)
|
||||||
@@ -52,3 +76,56 @@ func HeaderContains(testCase *TestCase) (bool, error) {
|
|||||||
|
|
||||||
return true, nil
|
return true, nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func HeaderEquals(testCase *TestCase) (bool, error) {
|
||||||
|
|
||||||
|
for k, v := range testCase.Expect.Header.Equals {
|
||||||
|
fmt.Printf("Header equals check '%s'='%s'\n", k, v)
|
||||||
|
|
||||||
|
// TODO
|
||||||
|
}
|
||||||
|
|
||||||
|
return true, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func BodyContains(testCase *TestCase) (bool, error) {
|
||||||
|
for k, v := range testCase.Expect.Body.Contains {
|
||||||
|
//fmt.Printf("Body contains check '%s'='%s'\n", k, v)
|
||||||
|
|
||||||
|
// If the body response was json then we stored it already when running the test
|
||||||
|
if val, ok := testCase.ResultBodyMap[k]; ok {
|
||||||
|
// TODO handle values other than string using a switch
|
||||||
|
//fmt.Printf("Found key in body with response '%s'\n", val)
|
||||||
|
|
||||||
|
// Check that the value matched
|
||||||
|
if strings.Contains(val.(string), v) {
|
||||||
|
fmt.Printf("Key matches, success\n")
|
||||||
|
} else {
|
||||||
|
fmt.Printf("Body Contains check failed on key '%s'. Expected value '%s' but found '%s'\n", k, v, val)
|
||||||
|
return false, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
} else {
|
||||||
|
// body did not contain the key we were looking for so return false
|
||||||
|
return false, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO
|
||||||
|
}
|
||||||
|
|
||||||
|
return true, nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func BodyHasKeys(testCase *TestCase) (bool, error) {
|
||||||
|
for _, key := range testCase.Expect.Body.HasKeys {
|
||||||
|
// If the body response was json then we stored it already when running the test
|
||||||
|
if _, ok := testCase.ResultBodyMap[key]; ok {
|
||||||
|
fmt.Printf("Confirmed body has key '%s'\n", key)
|
||||||
|
} else {
|
||||||
|
fmt.Printf("Body HasKeys test failed, expected key '%s' not found\n", key)
|
||||||
|
return false, nil
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return true, nil
|
||||||
|
}
|
||||||
|
@@ -3,6 +3,7 @@ package main
|
|||||||
import (
|
import (
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
"fmt"
|
"fmt"
|
||||||
|
"reflect"
|
||||||
|
|
||||||
"github.com/iancoleman/orderedmap"
|
"github.com/iancoleman/orderedmap"
|
||||||
)
|
)
|
||||||
@@ -229,13 +230,18 @@ func ReadHeaderTestCases(input orderedmap.OrderedMap, result *HeaderTests) {
|
|||||||
func ReadBodyTestCases(input orderedmap.OrderedMap, result *BodyTests) {
|
func ReadBodyTestCases(input orderedmap.OrderedMap, result *BodyTests) {
|
||||||
result.Contains = make(map[string]string)
|
result.Contains = make(map[string]string)
|
||||||
result.Equals = make(map[string]string)
|
result.Equals = make(map[string]string)
|
||||||
result.HasKeys = make(map[string]string)
|
|
||||||
|
|
||||||
// TODO : Use tags in struct rather than hard coding all the different check types
|
// TODO : Use tags in struct rather than hard coding all the different check types
|
||||||
// using https://stackoverflow.com/a/23840419 as an idea
|
// using https://stackoverflow.com/a/23840419 as an idea
|
||||||
|
|
||||||
// Contains check
|
// Contains check
|
||||||
if val, ok := input.Get("contains"); ok {
|
if val, ok := input.Get("contains"); ok {
|
||||||
|
// Confirm this is an ordered map
|
||||||
|
if _, ok := val.(orderedmap.OrderedMap); !ok {
|
||||||
|
error := fmt.Sprintf("Unexpected json definition for Body Contains check. Type is '%v' but expected Object.\n", reflect.TypeOf(val))
|
||||||
|
panic(error)
|
||||||
|
}
|
||||||
|
|
||||||
containsMap := val.(orderedmap.OrderedMap)
|
containsMap := val.(orderedmap.OrderedMap)
|
||||||
result.Contains = OrderedToStringMap(containsMap)
|
result.Contains = OrderedToStringMap(containsMap)
|
||||||
}
|
}
|
||||||
@@ -247,9 +253,14 @@ func ReadBodyTestCases(input orderedmap.OrderedMap, result *BodyTests) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Has Keys check
|
// Has Keys check
|
||||||
if val, ok := input.Get("haskeys"); ok {
|
if val, ok := input.Get("hasKeys"); ok {
|
||||||
equalsMap := val.(orderedmap.OrderedMap)
|
// This is an array not a map
|
||||||
result.HasKeys = OrderedToStringMap(equalsMap)
|
|
||||||
|
hasKeysArray := val.([]interface{})
|
||||||
|
result.HasKeys = OrderedToStringSlice(hasKeysArray)
|
||||||
|
|
||||||
|
//equalsMap := val.(orderedmap.OrderedMap)
|
||||||
|
//result.HasKeys = OrderedToStringMap(equalsMap)
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO : remaining tests
|
// TODO : remaining tests
|
||||||
|
28
main.go
28
main.go
@@ -89,3 +89,31 @@ func OrderedToStringMap(input orderedmap.OrderedMap) map[string]string {
|
|||||||
|
|
||||||
return result
|
return result
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func OrderedToStringSlice(input []interface{}) []string {
|
||||||
|
result := []string{}
|
||||||
|
//vs := testsInterface.([]interface{})
|
||||||
|
//fmt.Printf("Listing %d test definitions\n", len(vs))
|
||||||
|
|
||||||
|
for i := range input {
|
||||||
|
//fmt.Printf("Reading '%s'\n", input[i])
|
||||||
|
|
||||||
|
switch vType := input[i].(type) {
|
||||||
|
case string:
|
||||||
|
result = append(result, input[i].(string))
|
||||||
|
default:
|
||||||
|
fmt.Printf("OrderedToStringSlice received unexpected value type, %T\n", vType)
|
||||||
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
v := vInterface.(orderedmap.OrderedMap)
|
||||||
|
keys := v.Keys()
|
||||||
|
fmt.Printf("Test %d\n", i)
|
||||||
|
for j := range keys {
|
||||||
|
fmt.Printf("[%d] : %s\n", j, keys[j])
|
||||||
|
}
|
||||||
|
*/
|
||||||
|
}
|
||||||
|
|
||||||
|
return result
|
||||||
|
}
|
||||||
|
15
run_tests.go
15
run_tests.go
@@ -18,7 +18,7 @@ func RunTest(testCase *TestCase) error {
|
|||||||
var requestUrl string
|
var requestUrl string
|
||||||
var requestType string
|
var requestType string
|
||||||
var req *http.Request
|
var req *http.Request
|
||||||
var bodyMap map[string]interface{}
|
//var bodyMap map[string]interface{}
|
||||||
|
|
||||||
tr := &http.Transport{
|
tr := &http.Transport{
|
||||||
TLSClientConfig: &tls.Config{InsecureSkipVerify: testDefinitions.Insecure},
|
TLSClientConfig: &tls.Config{InsecureSkipVerify: testDefinitions.Insecure},
|
||||||
@@ -110,21 +110,14 @@ func RunTest(testCase *TestCase) error {
|
|||||||
testCase.ResultBody = string(body)
|
testCase.ResultBody = string(body)
|
||||||
fmt.Printf("Body response:\n%s\n", testCase.ResultBody)
|
fmt.Printf("Body response:\n%s\n", testCase.ResultBody)
|
||||||
|
|
||||||
/*
|
|
||||||
// Something to store results in
|
|
||||||
ResultStatusCode int
|
|
||||||
ResultHeaders map[string]string
|
|
||||||
ResultBody string
|
|
||||||
*/
|
|
||||||
|
|
||||||
// We have no idea what the response will look like so use an interface and unmarshal manually as needed
|
// We have no idea what the response will look like so use an interface and unmarshal manually as needed
|
||||||
if len(body) > 0 {
|
if len(body) > 0 {
|
||||||
var b interface{}
|
var b interface{}
|
||||||
json.Unmarshal(body, &b)
|
json.Unmarshal(body, &b)
|
||||||
if b != nil {
|
if b != nil {
|
||||||
bodyMap = b.(map[string]interface{})
|
testCase.ResultBodyMap = b.(map[string]interface{})
|
||||||
|
//bodyMap = b.(map[string]interface{})
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Iterate through testDefinitions.CaptureCases and see if there are any that match this test
|
// Iterate through testDefinitions.CaptureCases and see if there are any that match this test
|
||||||
@@ -136,7 +129,7 @@ func RunTest(testCase *TestCase) error {
|
|||||||
for k, v := range captureData.Body.Data {
|
for k, v := range captureData.Body.Data {
|
||||||
//fmt.Printf("Body capture %s = %s\n", k, v)
|
//fmt.Printf("Body capture %s = %s\n", k, v)
|
||||||
|
|
||||||
if val, ok := bodyMap[k]; ok {
|
if val, ok := testCase.ResultBodyMap[k]; ok {
|
||||||
// TODO handle values other than string using a switch
|
// TODO handle values other than string using a switch
|
||||||
//fmt.Printf("Found matching capture in body with value : '%v', storing replacement with key '%s'\n", val, v)
|
//fmt.Printf("Found matching capture in body with value : '%v', storing replacement with key '%s'\n", val, v)
|
||||||
captureValues.Data[v] = val.(string)
|
captureValues.Data[v] = val.(string)
|
||||||
|
@@ -24,6 +24,7 @@ type TestCase struct {
|
|||||||
ResultStatusCode int
|
ResultStatusCode int
|
||||||
ResultHeaders map[string][]string
|
ResultHeaders map[string][]string
|
||||||
ResultBody string
|
ResultBody string
|
||||||
|
ResultBodyMap map[string]interface{}
|
||||||
}
|
}
|
||||||
|
|
||||||
type CaptureCase struct {
|
type CaptureCase struct {
|
||||||
@@ -62,7 +63,7 @@ type HeaderTests struct {
|
|||||||
type BodyTests struct {
|
type BodyTests struct {
|
||||||
Contains map[string]string
|
Contains map[string]string
|
||||||
Equals map[string]string
|
Equals map[string]string
|
||||||
HasKeys map[string]string
|
HasKeys []string
|
||||||
PathEquals string
|
PathEquals string
|
||||||
PathContains map[string]string
|
PathContains map[string]string
|
||||||
}
|
}
|
||||||
|
@@ -17,9 +17,7 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
"body": {
|
"body": {
|
||||||
"contains": {
|
"hasKeys": ["access_token"]
|
||||||
"access_token":"*"
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
Reference in New Issue
Block a user