Skip to content

Commit

Permalink
Include Multi namespace support
Browse files Browse the repository at this point in the history
Signed-off-by: Nitishkumar Singh <[email protected]>

refactor invoke function for multi-namespace

Signed-off-by: Nitishkumar Singh <[email protected]>

Refactored invoke_test for multi-ns

Signed-off-by: Nitishkumar Singh <[email protected]>

Refactored helpers function

Signed-off-by: Nitishkumar Singh <[email protected]>

Network field included

Signed-off-by: Nitishkumar Singh <[email protected]>

Rebased to master

Signed-off-by: Nitishkumar Singh <[email protected]>

refactored invoke code for single list

Signed-off-by: Nitishkumar Singh <[email protected]>

remvoed unwanted logging code

Signed-off-by: Nitishkumar Singh <[email protected]>

Fixed test logs

Signed-off-by: Nitishkumar Singh <[email protected]>

fixed secret crud test

Signed-off-by: Nitishkumar Singh <[email protected]>

removed unwanted variable

Signed-off-by: Nitishkumar Singh <[email protected]>
  • Loading branch information
nitishkumar71 authored and LucasRoesler committed Jun 20, 2021
1 parent 4860398 commit 82821dd
Show file tree
Hide file tree
Showing 8 changed files with 149 additions and 113 deletions.
30 changes: 6 additions & 24 deletions tests/deploy_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,13 +10,12 @@ import (
"testing"
"time"

sdk "github.com/openfaas/faas-cli/proxy"
types "github.com/openfaas/faas-provider/types"
)

var emptyQueryString = ""

type FunctionMetaSchema struct {
type FunctionTestCase struct {
name string
function types.FunctionDeployment
}
Expand Down Expand Up @@ -51,7 +50,7 @@ func Test_Deploy_MetaData(t *testing.T) {
ctx, cancel := context.WithTimeout(context.Background(), 10*time.Second)
defer cancel()

cases := []FunctionMetaSchema{
cases := []FunctionTestCase{
{
name: "Deploy without any extra metadata",
function: types.FunctionDeployment{
Expand Down Expand Up @@ -94,36 +93,19 @@ func Test_Deploy_MetaData(t *testing.T) {
}

// Add Test case, if CERTIFIER_NAMESPACES defined
if len(config.Namespaces) > 0 {
cnCases := make([]FunctionMetaSchema, len(cases))
copy(cnCases, cases)
for index := 0; index < len(cnCases); index++ {
cnCases[index].name = fmt.Sprintf("%s to %s", cnCases[index].name, config.Namespaces[0])
cnCases[index].function.Namespace = config.Namespaces[0]
}

cases = append(cases, cnCases...)
}
cases = copyNamespacesTest(cases)

for _, c := range cases {
t.Run(c.name, func(t *testing.T) {
functionRequest := &sdk.DeployFunctionSpec{
Image: c.function.Image,
FunctionName: c.function.Service,
FProcess: c.function.EnvProcess,
Annotations: *c.function.Annotations,
EnvVars: c.function.EnvVars,
Labels: *c.function.Labels,
Namespace: c.function.Namespace,
}
functionRequest := createDeploymentSpec(c)

deployStatus := deploy(t, functionRequest)
if deployStatus != http.StatusOK && deployStatus != http.StatusAccepted {
t.Fatalf("got %d, wanted %d or %d", deployStatus, http.StatusOK, http.StatusAccepted)
}

function := get(t, functionRequest.FunctionName)
list(t, http.StatusOK)
function := get(t, functionRequest.FunctionName, functionRequest.Namespace)
list(t, http.StatusOK, functionRequest.Namespace)
if err := strMapEqual("annotations", *function.Annotations, *c.function.Annotations); err != nil {
t.Fatal(err)
}
Expand Down
45 changes: 41 additions & 4 deletions tests/function_helpers_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ package tests

import (
"context"
"fmt"
"net/http"
"os"
"path"
Expand Down Expand Up @@ -34,8 +35,8 @@ func deploy(t *testing.T, createRequest *sdk.DeployFunctionSpec) int {
return statusCode
}

func list(t *testing.T, expectedStatusCode int) {
functions, err := config.Client.ListFunctions(context.Background(), defaultNamespace)
func list(t *testing.T, expectedStatusCode int, namespace string) {
functions, err := config.Client.ListFunctions(context.Background(), namespace)
if err != nil {
t.Fatal(err)
}
Expand All @@ -45,8 +46,8 @@ func list(t *testing.T, expectedStatusCode int) {
}
}

func get(t *testing.T, name string) types.FunctionStatus {
function, err := config.Client.GetFunctionInfo(context.Background(), name, defaultNamespace)
func get(t *testing.T, name string, namespace string) types.FunctionStatus {
function, err := config.Client.GetFunctionInfo(context.Background(), name, namespace)
if err != nil {
t.Fatal(err)
}
Expand Down Expand Up @@ -80,3 +81,39 @@ func scaleFunction(t *testing.T, name string, count int) {
t.Fatalf("scale got %d, wanted %d (or %d)", res.StatusCode, http.StatusAccepted, http.StatusOK)
}
}

func copyNamespacesTest(cases []FunctionTestCase) []FunctionTestCase {
// Add Test case, if CERTIFIER_NAMESPACES defined
if len(config.Namespaces) > 0 {
cnCases := make([]FunctionTestCase, len(cases))
copy(cnCases, cases)
for index := 0; index < len(cnCases); index++ {
cnCases[index].name = fmt.Sprintf("%s to %s", cnCases[index].name, config.Namespaces[0])
cnCases[index].function.Namespace = config.Namespaces[0]
}

cases = append(cases, cnCases...)
return cases
}
return make([]FunctionTestCase, 0)
}

func createDeploymentSpec(test FunctionTestCase) *sdk.DeployFunctionSpec {
functionRequest := &sdk.DeployFunctionSpec{
Image: test.function.Image,
FunctionName: test.function.Service,
FProcess: test.function.EnvProcess,
EnvVars: test.function.EnvVars,
Namespace: test.function.Namespace,
}

if test.function.Annotations != nil {
functionRequest.Annotations = *test.function.Annotations
}

if test.function.Labels != nil {
functionRequest.Labels = *test.function.Labels
}

return functionRequest
}
130 changes: 71 additions & 59 deletions tests/invoke_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,30 +8,18 @@ import (
"fmt"

sdk "github.com/openfaas/faas-cli/proxy"
types "github.com/openfaas/faas-provider/types"
)

func Test_InvokeNotFound(t *testing.T) {
_ = invoke(t, "notfound", "", "", http.StatusNotFound, http.StatusBadGateway)
}

func Test_Invoke_With_Supported_Verbs(t *testing.T) {
envVars := map[string]string{}
functionRequest := &sdk.DeployFunctionSpec{
Image: "functions/alpine:latest",
FunctionName: "env-test-verbs",
Network: "func_functions",
FProcess: "env",
EnvVars: envVars,
}

deployStatus := deploy(t, functionRequest)
if deployStatus != http.StatusOK && deployStatus != http.StatusAccepted {
t.Fatalf("got %d, wanted %d or %d", deployStatus, http.StatusOK, http.StatusAccepted)
return
Image: "notfound",
Namespace: config.DefaultNamespace,
}
_ = invoke(t, functionRequest, "", "", http.StatusNotFound, http.StatusBadGateway)
}

list(t, http.StatusOK)

func invokeWithSupportedVerbs(t *testing.T, functionRequest *sdk.DeployFunctionSpec) {
verbs := []struct {
verb string
match func(string) bool
Expand All @@ -46,7 +34,7 @@ func Test_Invoke_With_Supported_Verbs(t *testing.T) {
for _, v := range verbs {
t.Run(v.verb, func(t *testing.T) {

bytesOut, res := invokeWithVerb(t, v.verb, functionRequest.FunctionName, emptyQueryString, "", http.StatusOK)
bytesOut, res := invokeWithVerb(t, v.verb, functionRequest, emptyQueryString, "", http.StatusOK)

out := string(bytesOut)
if !v.match(out) {
Expand All @@ -66,57 +54,81 @@ func Test_Invoke_With_Supported_Verbs(t *testing.T) {
}
}

func Test_InvokePropogatesRedirectToTheCaller(t *testing.T) {
destination := "http://example.com"
functionRequest := &sdk.DeployFunctionSpec{
Image: "theaxer/redirector:latest",
FunctionName: "redirector-test",
Network: "func_functions",
FProcess: "./handler",
EnvVars: map[string]string{"destination": destination},
}

deployStatus := deploy(t, functionRequest)
if deployStatus != http.StatusOK && deployStatus != http.StatusAccepted {
t.Fatalf("got %d, wanted %d or %d", deployStatus, http.StatusOK, http.StatusAccepted)
return
}

_ = invoke(t, "redirector-test", emptyQueryString, "", http.StatusFound)
}

func Test_Invoke_With_CustomEnvVars_AndQueryString(t *testing.T) {
envVars := map[string]string{}
envVars["custom_env"] = "custom_env_value"

functionRequest := &sdk.DeployFunctionSpec{
Image: "functions/alpine:latest",
FunctionName: "env-test",
Network: "func_functions",
FProcess: "env",
EnvVars: envVars,
}

deployStatus := deploy(t, functionRequest)
if deployStatus != http.StatusOK && deployStatus != http.StatusAccepted {
t.Fatalf("got %d, wanted %d or %d", deployStatus, http.StatusOK, http.StatusAccepted)
}

list(t, http.StatusOK)

func invokeWithCustomEnvVarsAndQueryString(t *testing.T, functionRequest *sdk.DeployFunctionSpec) {
t.Run("Empty QueryString", func(t *testing.T) {
bytesOut := invoke(t, functionRequest.FunctionName, emptyQueryString, "", http.StatusOK)
bytesOut := invoke(t, functionRequest, emptyQueryString, "", http.StatusOK)
out := string(bytesOut)
if strings.Contains(out, "custom_env") == false {
t.Fatalf("want: %s, got: %s", "custom_env", out)
}
})

t.Run("Populated QueryString", func(t *testing.T) {
bytesOut := invoke(t, functionRequest.FunctionName, "testing=1", "", http.StatusOK)
bytesOut := invoke(t, functionRequest, "testing=1", "", http.StatusOK)
out := string(bytesOut)
if strings.Contains(out, "Http_Query=testing=1") == false {
t.Fatalf("want: %s, got: %s", "Http_Query=testing=1", out)
}
})
}

func Test_Invoke(t *testing.T) {
cases := []FunctionTestCase{
{
name: "Invoke test with different verbs",
function: types.FunctionDeployment{
Image: "functions/alpine:latest",
Service: "env-test-verbs",
EnvProcess: "env",
EnvVars: map[string]string{},
Namespace: config.DefaultNamespace,
},
},
{
name: "Invoke propogates redirect to the caller",
function: types.FunctionDeployment{
Image: "theaxer/redirector:latest",
Service: "redirector-test",
EnvProcess: "./handler",
EnvVars: map[string]string{"destination": "http://example.com"},
Namespace: config.DefaultNamespace,
},
},
{
name: "Invoke with custom env vars and query string",
function: types.FunctionDeployment{
Image: "functions/alpine:latest",
Service: "env-test",
EnvProcess: "env",
EnvVars: map[string]string{"custom_env": "custom_env_value"},
Namespace: config.DefaultNamespace,
},
},
}

cases = copyNamespacesTest(cases)

for _, c := range cases {
t.Run(c.name, func(t *testing.T) {
functionRequest := createDeploymentSpec(c)
deployStatus := deploy(t, functionRequest)
if deployStatus != http.StatusOK && deployStatus != http.StatusAccepted {
t.Fatalf("got %d, wanted %d or %d", deployStatus, http.StatusOK, http.StatusAccepted)
return
}

list(t, http.StatusOK, functionRequest.Namespace)

switch service := c.function.Service; service {
case "env-test-verbs":
invokeWithSupportedVerbs(t, functionRequest)
case "redirector-test":
_ = invoke(t, functionRequest, emptyQueryString, "", http.StatusFound)
case "env-test":
invokeWithCustomEnvVarsAndQueryString(t, functionRequest)
default:
t.Fatalf("Invoke tests does not handle %s. Please raise an issue on repository", c.function.Service)
}
})
}
}
7 changes: 2 additions & 5 deletions tests/logs_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -27,6 +27,7 @@ func Test_FunctionLogs(t *testing.T) {
FunctionName: "test-logger",
Network: "func_functions",
FProcess: "cat",
Namespace: config.DefaultNamespace,
},
expectedLogs: []string{
"Forking fprocess",
Expand Down Expand Up @@ -65,17 +66,13 @@ func Test_FunctionLogs(t *testing.T) {
// each invoke should output two lines
// - Forking fprocess.
// - Wrote 132 Bytes - Duration: ...
name := c.function.FunctionName
if c.function.Namespace != "" {
name = name + "." + c.function.Namespace
}

ns := c.function.Namespace
if ns == "" {
ns = config.DefaultNamespace
}

data := invoke(t, name, "", ns, http.StatusOK)
data := invoke(t, &c.function, "", ns, http.StatusOK)
if string(data) != ns {
t.Fatalf("got invoke response %s, expected %s", string(data), ns)
}
Expand Down
7 changes: 3 additions & 4 deletions tests/main_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,10 +18,9 @@ import (
)

var (
config = Config{}
defaultNamespace = ""
swarm = flag.Bool("swarm", false, "helper flag to run only swarm-compatible tests only")
token = flag.String("token", "", "authentication Bearer token override, enables auth automatically")
config = Config{}
swarm = flag.Bool("swarm", false, "helper flag to run only swarm-compatible tests only")
token = flag.String("token", "", "authentication Bearer token override, enables auth automatically")
)

func init() {
Expand Down
Loading

0 comments on commit 82821dd

Please sign in to comment.