Refactor e2e tests to use testify y httpexpect

This commit is contained in:
Manuel Alejandro de Brito Fontes 2020-02-19 00:08:56 -03:00
parent 046e2d959d
commit f9624cbe46
80 changed files with 2280 additions and 2631 deletions

View file

@ -22,10 +22,8 @@ import (
"strings" "strings"
"time" "time"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
networking "k8s.io/api/networking/v1beta1" networking "k8s.io/api/networking/v1beta1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/util/intstr" "k8s.io/apimachinery/pkg/util/intstr"
@ -36,11 +34,11 @@ import (
var _ = framework.DescribeAnnotation("affinity session-cookie-name", func() { var _ = framework.DescribeAnnotation("affinity session-cookie-name", func() {
f := framework.NewDefaultFramework("affinity") f := framework.NewDefaultFramework("affinity")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeploymentWithReplicas(2)
}) })
It("should set sticky cookie SERVERID", func() { ginkgo.It("should set sticky cookie SERVERID", func() {
host := "sticky.foo.com" host := "sticky.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/affinity": "cookie", "nginx.ingress.kubernetes.io/affinity": "cookie",
@ -55,17 +53,15 @@ var _ = framework.DescribeAnnotation("affinity session-cookie-name", func() {
return strings.Contains(server, fmt.Sprintf("server_name %s ;", host)) return strings.Contains(server, fmt.Sprintf("server_name %s ;", host))
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Expect(errs).Should(BeEmpty()) Header("Set-Cookie").Contains("SERVERID=")
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(resp.Header.Get("Set-Cookie")).Should(ContainSubstring("SERVERID="))
}) })
It("should change cookie name on ingress definition change", func() { ginkgo.It("should change cookie name on ingress definition change", func() {
host := "change.foo.com" host := "change.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/affinity": "cookie", "nginx.ingress.kubernetes.io/affinity": "cookie",
@ -80,29 +76,28 @@ var _ = framework.DescribeAnnotation("affinity session-cookie-name", func() {
return strings.Contains(server, fmt.Sprintf("server_name %s ;", host)) return strings.Contains(server, fmt.Sprintf("server_name %s ;", host))
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Expect(errs).Should(BeEmpty()) Header("Set-Cookie").Contains("SERVERID")
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(resp.Header.Get("Set-Cookie")).Should(ContainSubstring("SERVERID"))
ing.ObjectMeta.Annotations["nginx.ingress.kubernetes.io/session-cookie-name"] = "OTHERCOOKIENAME" ing.ObjectMeta.Annotations["nginx.ingress.kubernetes.io/session-cookie-name"] = "OTHERCOOKIENAME"
f.EnsureIngress(ing)
resp, _, errs = gorequest.New(). _, err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Update(ing)
Get(f.GetURL(framework.HTTP)). assert.Nil(ginkgo.GinkgoT(), err, "updating ingress")
Set("Host", host). time.Sleep(5 * time.Second)
End()
Expect(errs).Should(BeEmpty()) f.HTTPTestClient().
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) GET("/").
Expect(resp.Header.Get("Set-Cookie")).Should(ContainSubstring("OTHERCOOKIENAME")) WithHeader("Host", host).
Expect().
Status(http.StatusOK).
Header("Set-Cookie").Contains("OTHERCOOKIENAME")
}) })
It("should set the path to /something on the generated cookie", func() { ginkgo.It("should set the path to /something on the generated cookie", func() {
host := "path.foo.com" host := "path.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/affinity": "cookie", "nginx.ingress.kubernetes.io/affinity": "cookie",
@ -117,17 +112,15 @@ var _ = framework.DescribeAnnotation("affinity session-cookie-name", func() {
return strings.Contains(server, fmt.Sprintf("server_name %s ;", host)) return strings.Contains(server, fmt.Sprintf("server_name %s ;", host))
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+"/something"). GET("/something").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Expect(errs).Should(BeEmpty()) Header("Set-Cookie").Contains("Path=/something")
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(resp.Header.Get("Set-Cookie")).Should(ContainSubstring("Path=/something"))
}) })
It("does not set the path to / on the generated cookie if there's more than one rule referring to the same backend", func() { ginkgo.It("does not set the path to / on the generated cookie if there's more than one rule referring to the same backend", func() {
host := "morethanonerule.foo.com" host := "morethanonerule.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/affinity": "cookie", "nginx.ingress.kubernetes.io/affinity": "cookie",
@ -174,26 +167,22 @@ var _ = framework.DescribeAnnotation("affinity session-cookie-name", func() {
return strings.Contains(server, fmt.Sprintf("server_name %s ;", host)) return strings.Contains(server, fmt.Sprintf("server_name %s ;", host))
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+"/something"). GET("/something").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Header("Set-Cookie").Contains("Path=/something")
Expect(errs).Should(BeEmpty()) f.HTTPTestClient().
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) GET("/somewhereelese").
Expect(resp.Header.Get("Set-Cookie")).Should(ContainSubstring("Path=/something;")) WithHeader("Host", host).
Expect().
resp, _, errs = gorequest.New(). Status(http.StatusOK).
Get(f.GetURL(framework.HTTP)+"/somewhereelese"). Header("Set-Cookie").Contains("Path=/somewhereelese")
Set("Host", host).
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(resp.Header.Get("Set-Cookie")).Should(ContainSubstring("Path=/somewhereelese;"))
}) })
It("should set cookie with expires", func() { ginkgo.It("should set cookie with expires", func() {
host := "cookieexpires.foo.com" host := "cookieexpires.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/affinity": "cookie", "nginx.ingress.kubernetes.io/affinity": "cookie",
@ -210,25 +199,22 @@ var _ = framework.DescribeAnnotation("affinity session-cookie-name", func() {
return strings.Contains(server, fmt.Sprintf("server_name %s ;", host)) return strings.Contains(server, fmt.Sprintf("server_name %s ;", host))
}) })
resp, _, errs := gorequest.New().
Get(f.GetURL(framework.HTTP)).
Set("Host", host).
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
local, err := time.LoadLocation("GMT") local, err := time.LoadLocation("GMT")
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err, "loading GMT location")
Expect(local).ShouldNot(BeNil()) assert.NotNil(ginkgo.GinkgoT(), local, "expected a location but none returned")
duration, _ := time.ParseDuration("48h") duration, _ := time.ParseDuration("48h")
expected := time.Now().In(local).Add(duration).Format("Mon, 02-Jan-06 15:04") expected := time.Now().In(local).Add(duration).Format("Mon, 02-Jan-06 15:04")
Expect(resp.Header.Get("Set-Cookie")).Should(ContainSubstring(fmt.Sprintf("Expires=%s", expected))) f.HTTPTestClient().
Expect(resp.Header.Get("Set-Cookie")).Should(ContainSubstring("Max-Age=259200")) GET("/").
WithHeader("Host", host).
Expect().
Status(http.StatusOK).
Header("Set-Cookie").Contains(fmt.Sprintf("Expires=%s", expected)).Contains("Max-Age=259200")
}) })
It("should work with use-regex annotation and session-cookie-path", func() { ginkgo.It("should work with use-regex annotation and session-cookie-path", func() {
host := "useregex.foo.com" host := "useregex.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/affinity": "cookie", "nginx.ingress.kubernetes.io/affinity": "cookie",
@ -245,18 +231,15 @@ var _ = framework.DescribeAnnotation("affinity session-cookie-name", func() {
return strings.Contains(server, fmt.Sprintf("server_name %s ;", host)) return strings.Contains(server, fmt.Sprintf("server_name %s ;", host))
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+"/foo/bar"). GET("/foo/bar").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Expect(errs).Should(BeEmpty()) Header("Set-Cookie").Contains("Path=/foo/bar").Contains("SERVERID=")
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(resp.Header.Get("Set-Cookie")).Should(ContainSubstring("SERVERID="))
Expect(resp.Header.Get("Set-Cookie")).Should(ContainSubstring("Path=/foo/bar"))
}) })
It("should warn user when use-regex is true and session-cookie-path is not set", func() { ginkgo.It("should warn user when use-regex is true and session-cookie-path is not set", func() {
host := "useregexwarn.foo.com" host := "useregexwarn.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/affinity": "cookie", "nginx.ingress.kubernetes.io/affinity": "cookie",
@ -272,20 +255,18 @@ var _ = framework.DescribeAnnotation("affinity session-cookie-name", func() {
return strings.Contains(server, fmt.Sprintf("server_name %s ;", host)) return strings.Contains(server, fmt.Sprintf("server_name %s ;", host))
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+"/foo/bar"). GET("/foo/bar").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK)
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
logs, err := f.NginxLogs() logs, err := f.NginxLogs()
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err, "obtaining nginx logs")
Expect(logs).To(ContainSubstring(`session-cookie-path should be set when use-regex is true`)) assert.Contains(ginkgo.GinkgoT(), logs, `session-cookie-path should be set when use-regex is true`)
}) })
It("should not set affinity across all server locations when using separate ingresses", func() { ginkgo.It("should not set affinity across all server locations when using separate ingresses", func() {
host := "separate.foo.com" host := "separate.foo.com"
annotations := map[string]string{ annotations := map[string]string{
@ -302,26 +283,22 @@ var _ = framework.DescribeAnnotation("affinity session-cookie-name", func() {
return strings.Contains(server, `location /foo/bar`) && strings.Contains(server, `location /foo`) return strings.Contains(server, `location /foo/bar`) && strings.Contains(server, `location /foo`)
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+"/foo"). GET("/foo").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Header("Set-Cookie").Empty()
Expect(errs).Should(BeEmpty()) f.HTTPTestClient().
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) GET("/foo/bar").
Expect(resp.Header.Get("Set-Cookie")).Should(Equal("")) WithHeader("Host", host).
Expect().
resp, _, errs = gorequest.New(). Status(http.StatusOK).
Get(f.GetURL(framework.HTTP)+"/foo/bar"). Header("Set-Cookie").Contains("Path=/foo/bar")
Set("Host", host).
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(resp.Header.Get("Set-Cookie")).Should(ContainSubstring("Path=/foo/bar"))
}) })
It("should set sticky cookie without host", func() { ginkgo.It("should set sticky cookie without host", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/affinity": "cookie", "nginx.ingress.kubernetes.io/affinity": "cookie",
"nginx.ingress.kubernetes.io/session-cookie-name": "SERVERID", "nginx.ingress.kubernetes.io/session-cookie-name": "SERVERID",
@ -335,12 +312,10 @@ var _ = framework.DescribeAnnotation("affinity session-cookie-name", func() {
return strings.Contains(server, "server_name _") return strings.Contains(server, "server_name _")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
End() Expect().
Status(http.StatusOK).
Expect(errs).Should(BeEmpty()) Header("Set-Cookie").Contains("SERVERID=")
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(resp.Header.Get("Set-Cookie")).Should(ContainSubstring("SERVERID="))
}) })
}) })

View file

@ -19,10 +19,9 @@ package annotations
import ( import (
"fmt" "fmt"
"net/http" "net/http"
"strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -30,42 +29,37 @@ import (
var _ = framework.DescribeAnnotation("server-alias", func() { var _ = framework.DescribeAnnotation("server-alias", func() {
f := framework.NewDefaultFramework("alias") f := framework.NewDefaultFramework("alias")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
It("should return status code 200 for host 'foo' and 404 for 'bar'", func() { ginkgo.It("should return status code 200 for host 'foo' and 404 for 'bar'", func() {
host := "foo" host := "foo"
annotations := map[string]string{}
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name foo")) return strings.Contains(server, fmt.Sprintf("server_name %v", host))
}) })
resp, body, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Body().Contains(fmt.Sprintf("host=%v", host))
Expect(errs).Should(BeEmpty()) f.HTTPTestClient().
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) GET("/").
Expect(body).Should(ContainSubstring(fmt.Sprintf("host=%v", host))) WithHeader("Host", "bar").
Expect().
resp, body, errs = gorequest.New(). Status(http.StatusNotFound).
Get(f.GetURL(framework.HTTP)). Body().Contains("404 Not Found")
Set("Host", "bar").
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusNotFound))
Expect(body).Should(ContainSubstring("404 Not Found"))
}) })
It("should return status code 200 for host 'foo' and 'bar'", func() { ginkgo.It("should return status code 200 for host 'foo' and 'bar'", func() {
host := "foo" host := "foo"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/server-alias": "bar", "nginx.ingress.kubernetes.io/server-alias": "bar",
@ -76,19 +70,17 @@ var _ = framework.DescribeAnnotation("server-alias", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name foo")) return strings.Contains(server, fmt.Sprintf("server_name %v", host))
}) })
hosts := []string{"foo", "bar"} hosts := []string{"foo", "bar"}
for _, host := range hosts { for _, host := range hosts {
resp, body, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Expect(errs).Should(BeEmpty()) Body().Contains(fmt.Sprintf("host=%v", host))
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(fmt.Sprintf("host=%v", host)))
} }
}) })
}) })

View file

@ -18,22 +18,21 @@ package annotations
import ( import (
"net/http" "net/http"
"time" "strings"
"github.com/onsi/ginkgo"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeAnnotation("app-root", func() { var _ = framework.DescribeAnnotation("app-root", func() {
f := framework.NewDefaultFramework("approot") f := framework.NewDefaultFramework("approot")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeployment()
}) })
It("should redirect to /foo", func() { ginkgo.It("should redirect to /foo", func() {
host := "approot.bar.com" host := "approot.bar.com"
annotations := map[string]string{ annotations := map[string]string{
@ -45,19 +44,15 @@ var _ = framework.DescribeAnnotation("app-root", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring(`if ($uri = /) {`)) && return strings.Contains(server, `if ($uri = /) {`) &&
Expect(server).Should(ContainSubstring(`return 302 /foo;`)) strings.Contains(server, `return 302 /foo;`)
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
RedirectPolicy(noRedirectPolicyFunc). Expect().
Set("Host", host). Status(http.StatusFound).
End() Header("Location").Equal("http://approot.bar.com/foo")
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusFound))
Expect(resp.Header.Get("Location")).Should(Equal("http://approot.bar.com/foo"))
}) })
}) })

View file

@ -21,11 +21,11 @@ import (
"net/http" "net/http"
"net/url" "net/url"
"os/exec" "os/exec"
"time" "regexp"
"strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
corev1 "k8s.io/api/core/v1" corev1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
@ -36,14 +36,11 @@ import (
var _ = framework.DescribeAnnotation("auth-*", func() { var _ = framework.DescribeAnnotation("auth-*", func() {
f := framework.NewDefaultFramework("auth") f := framework.NewDefaultFramework("auth")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
AfterEach(func() { ginkgo.It("should return status code 200 when no authentication is configured", func() {
})
It("should return status code 200 when no authentication is configured", func() {
host := "auth" host := "auth"
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil) ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil)
@ -51,21 +48,18 @@ var _ = framework.DescribeAnnotation("auth-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name auth")) return strings.Contains(server, "server_name auth")
}) })
resp, body, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
Set("Host", host). Expect().
End() Status(http.StatusOK).
Body().Contains(fmt.Sprintf("host=%v", host))
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(fmt.Sprintf("host=%v", host)))
}) })
It("should return status code 503 when authentication is configured with an invalid secret", func() { ginkgo.It("should return status code 503 when authentication is configured with an invalid secret", func() {
host := "auth" host := "auth"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/auth-type": "basic", "nginx.ingress.kubernetes.io/auth-type": "basic",
@ -78,21 +72,18 @@ var _ = framework.DescribeAnnotation("auth-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name auth")) return strings.Contains(server, "server_name auth")
}) })
resp, body, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
Set("Host", host). Expect().
End() Status(http.StatusServiceUnavailable).
Body().Contains("503 Service Temporarily Unavailable")
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusServiceUnavailable))
Expect(body).Should(ContainSubstring("503 Service Temporarily Unavailable"))
}) })
It("should return status code 401 when authentication is configured but Authorization header is not configured", func() { ginkgo.It("should return status code 401 when authentication is configured but Authorization header is not configured", func() {
host := "auth" host := "auth"
s := f.EnsureSecret(buildSecret("foo", "bar", "test", f.Namespace)) s := f.EnsureSecret(buildSecret("foo", "bar", "test", f.Namespace))
@ -108,21 +99,18 @@ var _ = framework.DescribeAnnotation("auth-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name auth")) return strings.Contains(server, "server_name auth")
}) })
resp, body, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
Set("Host", host). Expect().
End() Status(http.StatusUnauthorized).
Body().Contains("401 Authorization Required")
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusUnauthorized))
Expect(body).Should(ContainSubstring("401 Authorization Required"))
}) })
It("should return status code 401 when authentication is configured and Authorization header is sent with invalid credentials", func() { ginkgo.It("should return status code 401 when authentication is configured and Authorization header is sent with invalid credentials", func() {
host := "auth" host := "auth"
s := f.EnsureSecret(buildSecret("foo", "bar", "test", f.Namespace)) s := f.EnsureSecret(buildSecret("foo", "bar", "test", f.Namespace))
@ -138,22 +126,19 @@ var _ = framework.DescribeAnnotation("auth-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name auth")) return strings.Contains(server, "server_name auth")
}) })
resp, body, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
Set("Host", host). WithBasicAuth("user", "pass").
SetBasicAuth("user", "pass"). Expect().
End() Status(http.StatusUnauthorized).
Body().Contains("401 Authorization Required")
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusUnauthorized))
Expect(body).Should(ContainSubstring("401 Authorization Required"))
}) })
It("should return status code 200 when authentication is configured and Authorization header is sent", func() { ginkgo.It("should return status code 200 when authentication is configured and Authorization header is sent", func() {
host := "auth" host := "auth"
s := f.EnsureSecret(buildSecret("foo", "bar", "test", f.Namespace)) s := f.EnsureSecret(buildSecret("foo", "bar", "test", f.Namespace))
@ -169,21 +154,18 @@ var _ = framework.DescribeAnnotation("auth-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name auth")) return strings.Contains(server, "server_name auth")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
Set("Host", host). WithBasicAuth("foo", "bar").
SetBasicAuth("foo", "bar"). Expect().
End() Status(http.StatusOK)
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
}) })
It("should return status code 200 when authentication is configured with a map and Authorization header is sent", func() { ginkgo.It("should return status code 200 when authentication is configured with a map and Authorization header is sent", func() {
host := "auth" host := "auth"
s := f.EnsureSecret(buildMapSecret("foo", "bar", "test", f.Namespace)) s := f.EnsureSecret(buildMapSecret("foo", "bar", "test", f.Namespace))
@ -200,21 +182,18 @@ var _ = framework.DescribeAnnotation("auth-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name auth")) return strings.Contains(server, "server_name auth")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
Set("Host", host). WithBasicAuth("foo", "bar").
SetBasicAuth("foo", "bar"). Expect().
End() Status(http.StatusOK)
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
}) })
It("should return status code 401 when authentication is configured with invalid content and Authorization header is sent", func() { ginkgo.It("should return status code 401 when authentication is configured with invalid content and Authorization header is sent", func() {
host := "auth" host := "auth"
s := f.EnsureSecret( s := f.EnsureSecret(
@ -242,21 +221,18 @@ var _ = framework.DescribeAnnotation("auth-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name auth")) return strings.Contains(server, "server_name auth")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
Set("Host", host). WithBasicAuth("foo", "bar").
SetBasicAuth("foo", "bar"). Expect().
End() Status(http.StatusUnauthorized)
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusUnauthorized))
}) })
It(`should set snippet "proxy_set_header My-Custom-Header 42;" when external auth is configured`, func() { ginkgo.It(`should set snippet "proxy_set_header My-Custom-Header 42;" when external auth is configured`, func() {
host := "auth" host := "auth"
annotations := map[string]string{ annotations := map[string]string{
@ -270,11 +246,11 @@ var _ = framework.DescribeAnnotation("auth-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring(`proxy_set_header My-Custom-Header 42;`)) return strings.Contains(server, `proxy_set_header My-Custom-Header 42;`)
}) })
}) })
It(`should not set snippet "proxy_set_header My-Custom-Header 42;" when external auth is not configured`, func() { ginkgo.It(`should not set snippet "proxy_set_header My-Custom-Header 42;" when external auth is not configured`, func() {
host := "auth" host := "auth"
annotations := map[string]string{ annotations := map[string]string{
@ -287,11 +263,11 @@ var _ = framework.DescribeAnnotation("auth-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).ShouldNot(ContainSubstring(`proxy_set_header My-Custom-Header 42;`)) return !strings.Contains(server, `proxy_set_header My-Custom-Header 42;`)
}) })
}) })
It(`should set "proxy_set_header 'My-Custom-Header' '42';" when auth-headers are set`, func() { ginkgo.It(`should set "proxy_set_header 'My-Custom-Header' '42';" when auth-headers are set`, func() {
host := "auth" host := "auth"
annotations := map[string]string{ annotations := map[string]string{
@ -308,11 +284,11 @@ var _ = framework.DescribeAnnotation("auth-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring(`proxy_set_header 'My-Custom-Header' '42';`)) return strings.Contains(server, `proxy_set_header 'My-Custom-Header' '42';`)
}) })
}) })
It(`should set cache_key when external auth cache is configured`, func() { ginkgo.It(`should set cache_key when external auth cache is configured`, func() {
host := "auth" host := "auth"
annotations := map[string]string{ annotations := map[string]string{
@ -324,16 +300,18 @@ var _ = framework.DescribeAnnotation("auth-*", func() {
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
cacheRegex := regexp.MustCompile(`\$cache_key.*foo`)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(MatchRegexp(`\$cache_key.*foo`)) && return cacheRegex.MatchString(server) &&
Expect(server).Should(ContainSubstring(`proxy_cache_valid 200 202 401 30m;`)) strings.Contains(server, `proxy_cache_valid 200 202 401 30m;`)
}) })
}) })
It("retains cookie set by external authentication server", func() { ginkgo.It("retains cookie set by external authentication server", func() {
Skip("Skipping test until refactoring") ginkgo.Skip("Skipping test until refactoring")
// TODO: this test should look like https://gist.github.com/aledbf/250645d76c080677c695929273f8fd22 // TODO: this test should look like https://gist.github.com/aledbf/250645d76c080677c695929273f8fd22
host := "auth" host := "auth"
@ -343,10 +321,10 @@ var _ = framework.DescribeAnnotation("auth-*", func() {
var httpbinIP string var httpbinIP string
err := framework.WaitForEndpoints(f.KubeClientSet, framework.DefaultTimeout, framework.HTTPBinService, f.Namespace, 1) err := framework.WaitForEndpoints(f.KubeClientSet, framework.DefaultTimeout, framework.HTTPBinService, f.Namespace, 1)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
e, err := f.KubeClientSet.CoreV1().Endpoints(f.Namespace).Get(framework.HTTPBinService, metav1.GetOptions{}) e, err := f.KubeClientSet.CoreV1().Endpoints(f.Namespace).Get(framework.HTTPBinService, metav1.GetOptions{})
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
httpbinIP = e.Subsets[0].Addresses[0].IP httpbinIP = e.Subsets[0].Addresses[0].IP
@ -359,38 +337,32 @@ var _ = framework.DescribeAnnotation("auth-*", func() {
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer(host, func(server string) bool { f.WaitForNginxServer(host, func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name auth")) return strings.Contains(server, "server_name auth")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
Set("Host", host). WithQuery("a", "b").
Param("a", "b"). WithQuery("c", "d").
Param("c", "d"). Expect().
End() Status(http.StatusOK).
Header("Set-Cookie").Contains("alma=armud")
for _, err := range errs {
Expect(err).NotTo(HaveOccurred())
}
framework.Logf("Cookie: %v", resp.Header)
Expect(resp.Header.Get("Set-Cookie")).Should(ContainSubstring("alma=armud"))
}) })
Context("when external authentication is configured", func() { ginkgo.Context("when external authentication is configured", func() {
host := "auth" host := "auth"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewHttpbinDeployment() f.NewHttpbinDeployment()
var httpbinIP string var httpbinIP string
err := framework.WaitForEndpoints(f.KubeClientSet, framework.DefaultTimeout, framework.HTTPBinService, f.Namespace, 1) err := framework.WaitForEndpoints(f.KubeClientSet, framework.DefaultTimeout, framework.HTTPBinService, f.Namespace, 1)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
e, err := f.KubeClientSet.CoreV1().Endpoints(f.Namespace).Get(framework.HTTPBinService, metav1.GetOptions{}) e, err := f.KubeClientSet.CoreV1().Endpoints(f.Namespace).Get(framework.HTTPBinService, metav1.GetOptions{})
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
httpbinIP = e.Subsets[0].Addresses[0].IP httpbinIP = e.Subsets[0].Addresses[0].IP
@ -403,61 +375,48 @@ var _ = framework.DescribeAnnotation("auth-*", func() {
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer(host, func(server string) bool { f.WaitForNginxServer(host, func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name auth")) return strings.Contains(server, "server_name auth")
}) })
}) })
It("should return status code 200 when signed in", func() { ginkgo.It("should return status code 200 when signed in", func() {
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
Set("Host", host). WithBasicAuth("user", "password").
SetBasicAuth("user", "password"). Expect().
End() Status(http.StatusOK)
for _, err := range errs {
Expect(err).NotTo(HaveOccurred())
}
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
}) })
It("should redirect to signin url when not signed in", func() { ginkgo.It("should redirect to signin url when not signed in", func() {
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
Set("Host", host). WithQuery("a", "b").
RedirectPolicy(func(req gorequest.Request, via []gorequest.Request) error { WithQuery("c", "d").
return http.ErrUseLastResponse Expect().
}). Status(http.StatusFound).
Param("a", "b"). Header("Location").Equal(fmt.Sprintf("http://%s/auth/start?rd=http://%s%s", host, host, url.QueryEscape("/?a=b&c=d")))
Param("c", "d").
End()
for _, err := range errs {
Expect(err).NotTo(HaveOccurred())
}
Expect(resp.StatusCode).Should(Equal(http.StatusFound))
Expect(resp.Header.Get("Location")).Should(Equal(fmt.Sprintf("http://%s/auth/start?rd=http://%s%s", host, host, url.QueryEscape("/?a=b&c=d"))))
}) })
}) })
Context("when external authentication with caching is configured", func() { ginkgo.Context("when external authentication with caching is configured", func() {
thisHost := "auth" thisHost := "auth"
thatHost := "different" thatHost := "different"
fooPath := "/foo" fooPath := "/foo"
barPath := "/bar" barPath := "/bar"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewHttpbinDeployment() f.NewHttpbinDeployment()
var httpbinIP string var httpbinIP string
err := framework.WaitForEndpoints(f.KubeClientSet, framework.DefaultTimeout, framework.HTTPBinService, f.Namespace, 1) err := framework.WaitForEndpoints(f.KubeClientSet, framework.DefaultTimeout, framework.HTTPBinService, f.Namespace, 1)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
e, err := f.KubeClientSet.CoreV1().Endpoints(f.Namespace).Get(framework.HTTPBinService, metav1.GetOptions{}) e, err := f.KubeClientSet.CoreV1().Endpoints(f.Namespace).Get(framework.HTTPBinService, metav1.GetOptions{})
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
httpbinIP = e.Subsets[0].Addresses[0].IP httpbinIP = e.Subsets[0].Addresses[0].IP
@ -469,154 +428,106 @@ var _ = framework.DescribeAnnotation("auth-*", func() {
} }
for _, host := range []string{thisHost, thatHost} { for _, host := range []string{thisHost, thatHost} {
By("Adding an ingress rule for /foo") ginkgo.By("Adding an ingress rule for /foo")
fooIng := framework.NewSingleIngress(fmt.Sprintf("foo-%s-ing", host), fooPath, host, f.Namespace, framework.EchoService, 80, annotations) fooIng := framework.NewSingleIngress(fmt.Sprintf("foo-%s-ing", host), fooPath, host, f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(fooIng) f.EnsureIngress(fooIng)
f.WaitForNginxServer(host, func(server string) bool { f.WaitForNginxServer(host, func(server string) bool {
return Expect(server).Should(ContainSubstring("location /foo")) return strings.Contains(server, "location /foo")
}) })
By("Adding an ingress rule for /bar") ginkgo.By("Adding an ingress rule for /bar")
barIng := framework.NewSingleIngress(fmt.Sprintf("bar-%s-ing", host), barPath, host, f.Namespace, framework.EchoService, 80, annotations) barIng := framework.NewSingleIngress(fmt.Sprintf("bar-%s-ing", host), barPath, host, f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(barIng) f.EnsureIngress(barIng)
f.WaitForNginxServer(host, func(server string) bool { f.WaitForNginxServer(host, func(server string) bool {
return Expect(server).Should(ContainSubstring("location /bar")) return strings.Contains(server, "location /bar")
}) })
} }
}) })
It("should return status code 200 when signed in after auth backend is deleted ", func() { ginkgo.It("should return status code 200 when signed in after auth backend is deleted ", func() {
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+fooPath). GET(fooPath).
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", thisHost).
Set("Host", thisHost). WithBasicAuth("user", "password").
SetBasicAuth("user", "password"). Expect().
End() Status(http.StatusOK)
for _, err := range errs {
Expect(err).NotTo(HaveOccurred())
}
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
err := f.DeleteDeployment(framework.HTTPBinService) err := f.DeleteDeployment(framework.HTTPBinService)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
resp, _, errs = gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+fooPath). GET(fooPath).
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", thisHost).
Set("Host", thisHost). WithBasicAuth("user", "password").
SetBasicAuth("user", "password"). Expect().
End() Status(http.StatusOK)
for _, err := range errs {
Expect(err).NotTo(HaveOccurred())
}
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
}) })
It("should deny login for different location on same server", func() { ginkgo.It("should deny login for different location on same server", func() {
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+fooPath). GET(fooPath).
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", thisHost).
Set("Host", thisHost). WithBasicAuth("user", "password").
SetBasicAuth("user", "password"). Expect().
End() Status(http.StatusOK)
for _, err := range errs {
Expect(err).NotTo(HaveOccurred())
}
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
err := f.DeleteDeployment(framework.HTTPBinService) err := f.DeleteDeployment(framework.HTTPBinService)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
_, _, errs = gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+fooPath). GET(fooPath).
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", thisHost).
Set("Host", thisHost). WithBasicAuth("user", "password").
SetBasicAuth("user", "password"). Expect().
End() Status(http.StatusOK)
for _, err := range errs { ginkgo.By("receiving an internal server error without cache on location /bar")
Expect(err).NotTo(HaveOccurred()) f.HTTPTestClient().
} GET(barPath).
WithHeader("Host", thisHost).
WithBasicAuth("user", "password").
Expect().
Status(http.StatusInternalServerError)
resp, _, errs = gorequest.New().
Get(f.GetURL(framework.HTTP)+barPath).
Retry(10, 1*time.Second, http.StatusNotFound).
Set("Host", thisHost).
SetBasicAuth("user", "password").
End()
for _, err := range errs {
Expect(err).NotTo(HaveOccurred())
}
By("receiving an internal server error without cache on location /bar")
Expect(resp.StatusCode).Should(Equal(http.StatusInternalServerError))
}) })
It("should deny login for different servers", func() { ginkgo.It("should deny login for different servers", func() {
By("logging into server thisHost /foo") ginkgo.By("logging into server thisHost /foo")
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+fooPath). GET(fooPath).
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", thisHost).
Set("Host", thisHost). WithBasicAuth("user", "password").
SetBasicAuth("user", "password"). Expect().
End() Status(http.StatusOK)
for _, err := range errs {
Expect(err).NotTo(HaveOccurred())
}
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
err := f.DeleteDeployment(framework.HTTPBinService) err := f.DeleteDeployment(framework.HTTPBinService)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
resp, _, errs = gorequest.New(). ginkgo.By("receiving an internal server error without cache on thisHost location /bar")
Get(f.GetURL(framework.HTTP)+fooPath). f.HTTPTestClient().
Retry(10, 1*time.Second, http.StatusNotFound). GET(fooPath).
Set("Host", thisHost). WithHeader("Host", thisHost).
SetBasicAuth("user", "password"). WithBasicAuth("user", "password").
End() Expect().
Status(http.StatusOK)
for _, err := range errs { f.HTTPTestClient().
Expect(err).NotTo(HaveOccurred()) GET(fooPath).
} WithHeader("Host", thatHost).
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) WithBasicAuth("user", "password").
Expect().
resp, _, errs = gorequest.New(). Status(http.StatusInternalServerError)
Get(f.GetURL(framework.HTTP)+fooPath).
Retry(10, 1*time.Second, http.StatusNotFound).
Set("Host", thatHost).
SetBasicAuth("user", "password").
End()
for _, err := range errs {
Expect(err).NotTo(HaveOccurred())
}
By("receiving an internal server error without cache on thisHost location /bar")
Expect(resp.StatusCode).Should(Equal(http.StatusInternalServerError))
}) })
It("should redirect to signin url when not signed in", func() { ginkgo.It("should redirect to signin url when not signed in", func() {
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", thisHost).
Set("Host", thisHost). WithQuery("a", "b").
RedirectPolicy(func(req gorequest.Request, via []gorequest.Request) error { WithQuery("c", "d").
return http.ErrUseLastResponse Expect().
}). Status(http.StatusFound).
Param("a", "b"). Header("Location").Equal(fmt.Sprintf("http://%s/auth/start?rd=http://%s%s", thisHost, thisHost, url.QueryEscape("/?a=b&c=d")))
Param("c", "d").
End()
for _, err := range errs {
Expect(err).NotTo(HaveOccurred())
}
Expect(resp.StatusCode).Should(Equal(http.StatusFound))
Expect(resp.Header.Get("Location")).Should(Equal(fmt.Sprintf("http://%s/auth/start?rd=http://%s%s", thisHost, thisHost, url.QueryEscape("/?a=b&c=d"))))
}) })
}) })
}) })
@ -630,7 +541,7 @@ var _ = framework.DescribeAnnotation("auth-*", func() {
func buildSecret(username, password, name, namespace string) *corev1.Secret { func buildSecret(username, password, name, namespace string) *corev1.Secret {
out, err := exec.Command("openssl", "passwd", "-crypt", password).CombinedOutput() out, err := exec.Command("openssl", "passwd", "-crypt", password).CombinedOutput()
encpass := fmt.Sprintf("%v:%s\n", username, out) encpass := fmt.Sprintf("%v:%s\n", username, out)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
return &corev1.Secret{ return &corev1.Secret{
ObjectMeta: metav1.ObjectMeta{ ObjectMeta: metav1.ObjectMeta{
@ -647,7 +558,7 @@ func buildSecret(username, password, name, namespace string) *corev1.Secret {
func buildMapSecret(username, password, name, namespace string) *corev1.Secret { func buildMapSecret(username, password, name, namespace string) *corev1.Secret {
out, err := exec.Command("openssl", "passwd", "-crypt", password).CombinedOutput() out, err := exec.Command("openssl", "passwd", "-crypt", password).CombinedOutput()
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
return &corev1.Secret{ return &corev1.Secret{
ObjectMeta: metav1.ObjectMeta{ ObjectMeta: metav1.ObjectMeta{

View file

@ -22,20 +22,19 @@ import (
"net/http" "net/http"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeAnnotation("auth-tls-*", func() { var _ = framework.DescribeAnnotation("auth-tls-*", func() {
f := framework.NewDefaultFramework("authtls") f := framework.NewDefaultFramework("authtls")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeploymentWithReplicas(2)
}) })
It("should set valid auth-tls-secret", func() { ginkgo.It("should set valid auth-tls-secret", func() {
host := "authtls.foo.com" host := "authtls.foo.com"
nameSpace := f.Namespace nameSpace := f.Namespace
@ -44,7 +43,7 @@ var _ = framework.DescribeAnnotation("auth-tls-*", func() {
host, host,
host, host,
nameSpace) nameSpace)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/auth-tls-secret": nameSpace + "/" + host, "nginx.ingress.kubernetes.io/auth-tls-secret": nameSpace + "/" + host,
@ -55,27 +54,23 @@ var _ = framework.DescribeAnnotation("auth-tls-*", func() {
assertSslClientCertificateConfig(f, host, "on", "1") assertSslClientCertificateConfig(f, host, "on", "1")
// Send Request without Client Certs // Send Request without Client Certs
req := gorequest.New() f.HTTPTestClientWithTLSConfig(&tls.Config{ServerName: host, InsecureSkipVerify: true}).
uri := "/" GET("/").
resp, _, errs := req. WithURL(f.GetURL(framework.HTTPS)).
Get(f.GetURL(framework.HTTPS)+uri). WithHeader("Host", host).
TLSClientConfig(&tls.Config{ServerName: host, InsecureSkipVerify: true}). Expect().
Set("Host", host). Status(http.StatusBadRequest)
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusBadRequest))
// Send Request Passing the Client Certs // Send Request Passing the Client Certs
resp, _, errs = req. f.HTTPTestClientWithTLSConfig(clientConfig).
Get(f.GetURL(framework.HTTPS)+uri). GET("/").
TLSClientConfig(clientConfig). WithURL(f.GetURL(framework.HTTPS)).
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).Should(BeEmpty()) Status(http.StatusOK)
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
}) })
It("should set valid auth-tls-secret, sslVerify to off, and sslVerifyDepth to 2", func() { ginkgo.It("should set valid auth-tls-secret, sslVerify to off, and sslVerifyDepth to 2", func() {
host := "authtls.foo.com" host := "authtls.foo.com"
nameSpace := f.Namespace nameSpace := f.Namespace
@ -84,7 +79,7 @@ var _ = framework.DescribeAnnotation("auth-tls-*", func() {
host, host,
host, host,
nameSpace) nameSpace)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/auth-tls-secret": nameSpace + "/" + host, "nginx.ingress.kubernetes.io/auth-tls-secret": nameSpace + "/" + host,
@ -97,18 +92,15 @@ var _ = framework.DescribeAnnotation("auth-tls-*", func() {
assertSslClientCertificateConfig(f, host, "off", "2") assertSslClientCertificateConfig(f, host, "off", "2")
// Send Request without Client Certs // Send Request without Client Certs
req := gorequest.New() f.HTTPTestClient().
uri := "/" GET("/").
resp, _, errs := req. WithURL(f.GetURL(framework.HTTPS)).
Get(f.GetURL(framework.HTTPS)+uri). WithHeader("Host", host).
TLSClientConfig(&tls.Config{ServerName: host, InsecureSkipVerify: true}). Expect().
Set("Host", host). Status(http.StatusOK)
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
}) })
It("should set valid auth-tls-secret, pass certificate to upstream, and error page", func() { ginkgo.It("should set valid auth-tls-secret, pass certificate to upstream, and error page", func() {
host := "authtls.foo.com" host := "authtls.foo.com"
nameSpace := f.Namespace nameSpace := f.Namespace
@ -119,7 +111,7 @@ var _ = framework.DescribeAnnotation("auth-tls-*", func() {
host, host,
host, host,
nameSpace) nameSpace)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/auth-tls-secret": nameSpace + "/" + host, "nginx.ingress.kubernetes.io/auth-tls-secret": nameSpace + "/" + host,
@ -141,26 +133,21 @@ var _ = framework.DescribeAnnotation("auth-tls-*", func() {
}) })
// Send Request without Client Certs // Send Request without Client Certs
req := gorequest.New() f.HTTPTestClient().
uri := "/" GET("/").
resp, _, errs := req. WithURL(f.GetURL(framework.HTTPS)).
Get(f.GetURL(framework.HTTPS)+uri). WithHeader("Host", host).
TLSClientConfig(&tls.Config{ServerName: host, InsecureSkipVerify: true}). Expect().
Set("Host", host). Status(http.StatusFound).
RedirectPolicy(noRedirectPolicyFunc). Header("Location").Equal(f.GetURL(framework.HTTP) + errorPath)
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusFound))
Expect(resp.Header.Get("Location")).Should(Equal(f.GetURL(framework.HTTP) + errorPath))
// Send Request Passing the Client Certs // Send Request Passing the Client Certs
resp, _, errs = req. f.HTTPTestClientWithTLSConfig(clientConfig).
Get(f.GetURL(framework.HTTPS)+uri). GET("/").
TLSClientConfig(clientConfig). WithURL(f.GetURL(framework.HTTPS)).
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).Should(BeEmpty()) Status(http.StatusOK)
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
}) })
}) })

View file

@ -17,19 +17,21 @@ limitations under the License.
package annotations package annotations
import ( import (
. "github.com/onsi/ginkgo" "strings"
. "github.com/onsi/gomega"
"github.com/onsi/ginkgo"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeAnnotation("backend-protocol", func() { var _ = framework.DescribeAnnotation("backend-protocol", func() {
f := framework.NewDefaultFramework("backendprotocol") f := framework.NewDefaultFramework("backendprotocol")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeployment()
}) })
It("should set backend protocol to https:// and use proxy_pass", func() { ginkgo.It("should set backend protocol to https:// and use proxy_pass", func() {
host := "backendprotocol.foo.com" host := "backendprotocol.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/backend-protocol": "HTTPS", "nginx.ingress.kubernetes.io/backend-protocol": "HTTPS",
@ -40,11 +42,11 @@ var _ = framework.DescribeAnnotation("backend-protocol", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("proxy_pass https://upstream_balancer;")) return strings.Contains(server, "proxy_pass https://upstream_balancer;")
}) })
}) })
It("should set backend protocol to grpc:// and use grpc_pass", func() { ginkgo.It("should set backend protocol to grpc:// and use grpc_pass", func() {
host := "backendprotocol.foo.com" host := "backendprotocol.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/backend-protocol": "GRPC", "nginx.ingress.kubernetes.io/backend-protocol": "GRPC",
@ -55,11 +57,11 @@ var _ = framework.DescribeAnnotation("backend-protocol", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("grpc_pass grpc://upstream_balancer;")) return strings.Contains(server, "grpc_pass grpc://upstream_balancer;")
}) })
}) })
It("should set backend protocol to grpcs:// and use grpc_pass", func() { ginkgo.It("should set backend protocol to grpcs:// and use grpc_pass", func() {
host := "backendprotocol.foo.com" host := "backendprotocol.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/backend-protocol": "GRPCS", "nginx.ingress.kubernetes.io/backend-protocol": "GRPCS",
@ -70,11 +72,11 @@ var _ = framework.DescribeAnnotation("backend-protocol", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("grpc_pass grpcs://upstream_balancer;")) return strings.Contains(server, "grpc_pass grpcs://upstream_balancer;")
}) })
}) })
It("should set backend protocol to '' and use fastcgi_pass", func() { ginkgo.It("should set backend protocol to '' and use fastcgi_pass", func() {
host := "backendprotocol.foo.com" host := "backendprotocol.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/backend-protocol": "FCGI", "nginx.ingress.kubernetes.io/backend-protocol": "FCGI",
@ -85,11 +87,11 @@ var _ = framework.DescribeAnnotation("backend-protocol", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("fastcgi_pass upstream_balancer;")) return strings.Contains(server, "fastcgi_pass upstream_balancer;")
}) })
}) })
It("should set backend protocol to '' and use ajp_pass", func() { ginkgo.It("should set backend protocol to '' and use ajp_pass", func() {
host := "backendprotocol.foo.com" host := "backendprotocol.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/backend-protocol": "AJP", "nginx.ingress.kubernetes.io/backend-protocol": "AJP",
@ -100,7 +102,7 @@ var _ = framework.DescribeAnnotation("backend-protocol", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("ajp_pass upstream_balancer;")) return strings.Contains(server, "ajp_pass upstream_balancer;")
}) })
}) })
}) })

View file

@ -19,11 +19,12 @@ package annotations
import ( import (
"fmt" "fmt"
"net/http" "net/http"
"strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
networking "k8s.io/api/networking/v1beta1"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -34,7 +35,7 @@ const (
var _ = framework.DescribeAnnotation("canary-*", func() { var _ = framework.DescribeAnnotation("canary-*", func() {
f := framework.NewDefaultFramework("canary") f := framework.NewDefaultFramework("canary")
BeforeEach(func() { ginkgo.BeforeEach(func() {
// Deployment for main backend // Deployment for main backend
f.NewEchoDeployment() f.NewEchoDeployment()
@ -42,17 +43,18 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
f.NewEchoDeploymentWithNameAndReplicas(canaryService, 1) f.NewEchoDeploymentWithNameAndReplicas(canaryService, 1)
}) })
Context("when canary is created", func() { ginkgo.Context("when canary is created", func() {
It("should response with a 200 status from the mainline upstream when requests are made to the mainline ingress", func() { ginkgo.It("should response with a 200 status from the mainline upstream when requests are made to the mainline ingress", func() {
host := "foo" host := "foo"
annotations := map[string]string{} annotations := map[string]string{}
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host, f.Namespace,
framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name foo")) return strings.Contains(server, "server_name foo")
}) })
canaryAnnotations := map[string]string{ canaryAnnotations := map[string]string{
@ -62,21 +64,19 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
canaryIngName := fmt.Sprintf("%v-canary", host) canaryIngName := fmt.Sprintf("%v-canary", host)
canaryIng := framework.NewSingleIngress(canaryIngName, "/", host, f.Namespace, canaryService, 80, canaryAnnotations) canaryIng := framework.NewSingleIngress(canaryIngName, "/", host,
f.Namespace, canaryService, 80, canaryAnnotations)
f.EnsureIngress(canaryIng) f.EnsureIngress(canaryIng)
resp, body, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Expect(errs).Should(BeEmpty()) Body().Contains(framework.EchoService).NotContains(canaryService)
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(framework.EchoService))
Expect(body).ShouldNot(ContainSubstring(canaryService))
}) })
It("should return 404 status for requests to the canary if no matching ingress is found", func() { ginkgo.It("should return 404 status for requests to the canary if no matching ingress is found", func() {
host := "foo" host := "foo"
canaryAnnotations := map[string]string{ canaryAnnotations := map[string]string{
@ -86,19 +86,17 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
canaryIngName := fmt.Sprintf("%v-canary", host) canaryIngName := fmt.Sprintf("%v-canary", host)
canaryIng := framework.NewSingleIngress(canaryIngName, "/", host, f.Namespace, canaryService, canaryIng := framework.NewSingleIngress(canaryIngName, "/", host,
80, canaryAnnotations) f.Namespace, canaryService, 80, canaryAnnotations)
f.EnsureIngress(canaryIng) f.EnsureIngress(canaryIng)
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
Set("CanaryByHeader", "always"). WithHeader("CanaryByHeader", "always").
End() Expect().
Status(http.StatusNotFound)
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusNotFound))
}) })
/* /*
@ -114,7 +112,7 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name foo")) return strings.Contains(server,"server_name foo")
}) })
canaryAnnotations := map[string]string{ canaryAnnotations := map[string]string{
@ -130,7 +128,7 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
By("returning a 503 status when the mainline deployment has 0 replicas and a request is sent to the canary") ginkgo.By("returning a 503 status when the mainline deployment has 0 replicas and a request is sent to the canary")
f.NewEchoDeploymentWithReplicas(0) f.NewEchoDeploymentWithReplicas(0)
@ -143,7 +141,7 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
Expect(errs).Should(BeEmpty()) Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusServiceUnavailable)) Expect(resp.StatusCode).Should(Equal(http.StatusServiceUnavailable))
By("returning a 200 status when the canary deployment has 0 replicas and a request is sent to the mainline ingress") ginkgo.By("returning a 200 status when the canary deployment has 0 replicas and a request is sent to the mainline ingress")
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeploymentWithReplicas(1)
f.NewDeployment(canaryService, "gcr.io/kubernetes-e2e-test-images/echoserver:2.2", 8080, 0) f.NewDeployment(canaryService, "gcr.io/kubernetes-e2e-test-images/echoserver:2.2", 8080, 0)
@ -159,16 +157,17 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
}) })
*/ */
It("should route requests to the correct upstream if mainline ingress is created before the canary ingress", func() { ginkgo.It("should route requests to the correct upstream if mainline ingress is created before the canary ingress", func() {
host := "foo" host := "foo"
annotations := map[string]string{} annotations := map[string]string{}
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host, f.Namespace,
framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name foo")) return strings.Contains(server, "server_name foo")
}) })
canaryAnnotations := map[string]string{ canaryAnnotations := map[string]string{
@ -178,36 +177,32 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
canaryIngName := fmt.Sprintf("%v-canary", host) canaryIngName := fmt.Sprintf("%v-canary", host)
canaryIng := framework.NewSingleIngress(canaryIngName, "/", host, f.Namespace, canaryService, canaryIng := framework.NewSingleIngress(canaryIngName, "/", host,
80, canaryAnnotations) f.Namespace, canaryService, 80, canaryAnnotations)
f.EnsureIngress(canaryIng) f.EnsureIngress(canaryIng)
By("routing requests destined for the mainline ingress to the maineline upstream") ginkgo.By("routing requests destined for the mainline ingress to the maineline upstream")
resp, body, errs := gorequest.New().
Get(f.GetURL(framework.HTTP)).
Set("Host", host).
Set("CanaryByHeader", "never").
End()
Expect(errs).Should(BeEmpty()) f.HTTPTestClient().
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) GET("/").
Expect(body).Should(ContainSubstring(framework.EchoService)) WithHeader("Host", host).
Expect(body).ShouldNot(ContainSubstring(canaryService)) WithHeader("CanaryByHeader", "never").
Expect().
Status(http.StatusOK).
Body().Contains(framework.EchoService).NotContains(canaryService)
By("routing requests destined for the canary ingress to the canary upstream") ginkgo.By("routing requests destined for the canary ingress to the canary upstream")
resp, body, errs = gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
Set("CanaryByHeader", "always"). WithHeader("CanaryByHeader", "always").
End() Expect().
Status(http.StatusOK).
Expect(errs).Should(BeEmpty()) Body().Contains(canaryService)
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(canaryService))
}) })
It("should route requests to the correct upstream if mainline ingress is created after the canary ingress", func() { ginkgo.It("should route requests to the correct upstream if mainline ingress is created after the canary ingress", func() {
host := "foo" host := "foo"
canaryAnnotations := map[string]string{ canaryAnnotations := map[string]string{
@ -217,55 +212,51 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
canaryIngName := fmt.Sprintf("%v-canary", host) canaryIngName := fmt.Sprintf("%v-canary", host)
canaryIng := framework.NewSingleIngress(canaryIngName, "/", host, f.Namespace, canaryService, canaryIng := framework.NewSingleIngress(canaryIngName, "/", host,
80, canaryAnnotations) f.Namespace, canaryService, 80, canaryAnnotations)
f.EnsureIngress(canaryIng) f.EnsureIngress(canaryIng)
annotations := map[string]string{} annotations := map[string]string{}
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host, f.Namespace,
framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name foo")) return strings.Contains(server, "server_name foo")
}) })
By("routing requests destined for the mainline ingress to the mainelin upstream") ginkgo.By("routing requests destined for the mainline ingress to the mainelin upstream")
resp, body, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
Set("CanaryByHeader", "never"). WithHeader("CanaryByHeader", "never").
End() Expect().
Status(http.StatusOK).
Body().Contains(framework.EchoService).NotContains(canaryService)
Expect(errs).Should(BeEmpty()) ginkgo.By("routing requests destined for the canary ingress to the canary upstream")
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) f.HTTPTestClient().
Expect(body).Should(ContainSubstring(framework.EchoService)) GET("/").
Expect(body).ShouldNot(ContainSubstring(canaryService)) WithHeader("Host", host).
WithHeader("CanaryByHeader", "always").
By("routing requests destined for the canary ingress to the canary upstream") Expect().
Status(http.StatusOK).
resp, body, errs = gorequest.New(). Body().Contains(canaryService)
Get(f.GetURL(framework.HTTP)).
Set("Host", host).
Set("CanaryByHeader", "always").
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(canaryService))
}) })
It("should route requests to the correct upstream if the mainline ingress is modified", func() { ginkgo.It("should route requests to the correct upstream if the mainline ingress is modified", func() {
host := "foo" host := "foo"
annotations := map[string]string{} annotations := map[string]string{}
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host, f.Namespace,
framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name foo")) return strings.Contains(server, "server_name foo")
}) })
canaryAnnotations := map[string]string{ canaryAnnotations := map[string]string{
@ -275,59 +266,54 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
canaryIngName := fmt.Sprintf("%v-canary", host) canaryIngName := fmt.Sprintf("%v-canary", host)
canaryIng := framework.NewSingleIngress(canaryIngName, "/", host, f.Namespace, canaryService, canaryIng := framework.NewSingleIngress(canaryIngName, "/", host,
80, canaryAnnotations) f.Namespace, canaryService, 80, canaryAnnotations)
f.EnsureIngress(canaryIng) f.EnsureIngress(canaryIng)
modAnnotations := map[string]string{ modAnnotations := map[string]string{
"foo": "bar", "foo": "bar",
} }
modIng := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, modAnnotations) modIng := framework.NewSingleIngress(host, "/", host, f.Namespace,
framework.EchoService, 80, modAnnotations)
f.EnsureIngress(modIng) f.EnsureIngress(modIng)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name foo")) return strings.Contains(server, "server_name foo")
}) })
By("routing requests destined fro the mainline ingress to the mainline upstream") ginkgo.By("routing requests destined fro the mainline ingress to the mainline upstream")
f.HTTPTestClient().
GET("/").
WithHeader("Host", host).
WithHeader("CanaryByHeader", "never").
Expect().
Status(http.StatusOK).
Body().Contains(framework.EchoService).NotContains(canaryService)
resp, body, errs := gorequest.New(). ginkgo.By("routing requests destined for the canary ingress to the canary upstream")
Get(f.GetURL(framework.HTTP)). f.HTTPTestClient().
Set("Host", host). GET("/").
Set("CanaryByHeader", "never"). WithHeader("Host", host).
End() WithHeader("CanaryByHeader", "always").
Expect().
Expect(errs).Should(BeEmpty()) Status(http.StatusOK).
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) Body().Contains(canaryService)
Expect(body).Should(ContainSubstring(framework.EchoService))
Expect(body).ShouldNot(ContainSubstring(canaryService))
By("routing requests destined for the canary ingress to the canary upstream")
resp, body, errs = gorequest.New().
Get(f.GetURL(framework.HTTP)).
Set("Host", host).
Set("CanaryByHeader", "always").
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(canaryService))
}) })
It("should route requests to the correct upstream if the canary ingress is modified", func() { ginkgo.It("should route requests to the correct upstream if the canary ingress is modified", func() {
host := "foo" host := "foo"
annotations := map[string]string{} annotations := map[string]string{}
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host, f.Namespace,
framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name foo")) return strings.Contains(server, "server_name foo")
}) })
canaryAnnotations := map[string]string{ canaryAnnotations := map[string]string{
@ -337,56 +323,51 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
canaryIngName := fmt.Sprintf("%v-canary", host) canaryIngName := fmt.Sprintf("%v-canary", host)
canaryIng := framework.NewSingleIngress(canaryIngName, "/", host, f.Namespace, canaryService, canaryIng := framework.NewSingleIngress(canaryIngName, "/", host,
80, canaryAnnotations) f.Namespace, canaryService, 80, canaryAnnotations)
f.EnsureIngress(canaryIng) f.EnsureIngress(canaryIng)
modCanaryAnnotations := map[string]string{ err := framework.UpdateIngress(f.KubeClientSet, f.Namespace, canaryIngName,
"nginx.ingress.kubernetes.io/canary": "true", func(ingress *networking.Ingress) error {
"nginx.ingress.kubernetes.io/canary-by-header": "CanaryByHeader2", ingress.ObjectMeta.Annotations = map[string]string{
} "nginx.ingress.kubernetes.io/canary": "true",
"nginx.ingress.kubernetes.io/canary-by-header": "CanaryByHeader2",
}
return nil
})
assert.Nil(ginkgo.GinkgoT(), err)
modCanaryIng := framework.NewSingleIngress(canaryIngName, "/", host, f.Namespace, canaryService, 80, modCanaryAnnotations) ginkgo.By("routing requests destined for the mainline ingress to the mainline upstream")
f.EnsureIngress(modCanaryIng) f.HTTPTestClient().
GET("/").
WithHeader("Host", host).
WithHeader("CanaryByHeader2", "never").
Expect().
Status(http.StatusOK).
Body().Contains(framework.EchoService).NotContains(canaryService)
By("routing requests destined for the mainline ingress to the mainline upstream") ginkgo.By("routing requests destined for the canary ingress to the canary upstream")
f.HTTPTestClient().
resp, body, errs := gorequest.New(). GET("/").
Get(f.GetURL(framework.HTTP)). WithHeader("Host", host).
Set("Host", host). WithHeader("CanaryByHeader2", "always").
Set("CanaryByHeader2", "never"). Expect().
End() Status(http.StatusOK).
Body().Contains(canaryService)
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(framework.EchoService))
Expect(body).ShouldNot(ContainSubstring(canaryService))
By("routing requests destined for the canary ingress to the canary upstream")
resp, body, errs = gorequest.New().
Get(f.GetURL(framework.HTTP)).
Set("Host", host).
Set("CanaryByHeader2", "always").
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(canaryService))
}) })
}) })
Context("when canaried by header with no value", func() { ginkgo.Context("when canaried by header with no value", func() {
It("should route requests to the correct upstream", func() { ginkgo.It("should route requests to the correct upstream", func() {
host := "foo" host := "foo"
annotations := map[string]string{}
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host, f.Namespace,
framework.EchoService, 80, nil)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name foo")) return strings.Contains(server, "server_name foo")
}) })
canaryAnnotations := map[string]string{ canaryAnnotations := map[string]string{
@ -396,61 +377,52 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
canaryIngName := fmt.Sprintf("%v-canary", host) canaryIngName := fmt.Sprintf("%v-canary", host)
canaryIng := framework.NewSingleIngress(canaryIngName, "/", host, f.Namespace, canaryService, canaryIng := framework.NewSingleIngress(canaryIngName, "/", host,
80, canaryAnnotations) f.Namespace, canaryService, 80, canaryAnnotations)
f.EnsureIngress(canaryIng) f.EnsureIngress(canaryIng)
By("routing requests to the canary upstream when header is set to 'always'") ginkgo.By("routing requests to the canary upstream when header is set to 'always'")
f.HTTPTestClient().
GET("/").
WithHeader("Host", host).
WithHeader("CanaryByHeader", "always").
Expect().
Status(http.StatusOK).
Body().Contains(canaryService)
resp, body, errs := gorequest.New(). ginkgo.By("routing requests to the mainline upstream when header is set to 'never'")
Get(f.GetURL(framework.HTTP)). f.HTTPTestClient().
Set("Host", host). GET("/").
Set("CanaryByHeader", "always"). WithHeader("Host", host).
End() WithHeader("CanaryByHeader", "never").
Expect().
Status(http.StatusOK).
Body().
Contains(framework.EchoService).NotContains(canaryService)
Expect(errs).Should(BeEmpty()) ginkgo.By("routing requests to the mainline upstream when header is set to anything else")
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) f.HTTPTestClient().
Expect(body).Should(ContainSubstring(canaryService)) GET("/").
WithHeader("Host", host).
By("routing requests to the mainline upstream when header is set to 'never'") WithHeader("CanaryByHeader", "badheadervalue").
Expect().
resp, body, errs = gorequest.New(). Status(http.StatusOK).
Get(f.GetURL(framework.HTTP)). Body().Contains(framework.EchoService).NotContains(canaryService)
Set("Host", host).
Set("CanaryByHeader", "never").
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(framework.EchoService))
Expect(body).ShouldNot(ContainSubstring(canaryService))
By("routing requests to the mainline upstream when header is set to anything else")
resp, body, errs = gorequest.New().
Get(f.GetURL(framework.HTTP)).
Set("Host", host).
Set("CanaryByHeader", "badheadervalue").
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(framework.EchoService))
Expect(body).ShouldNot(ContainSubstring(canaryService))
}) })
}) })
Context("when canaried by header with value", func() { ginkgo.Context("when canaried by header with value", func() {
It("should route requests to the correct upstream", func() { ginkgo.It("should route requests to the correct upstream", func() {
host := "foo" host := "foo"
annotations := map[string]string{} annotations := map[string]string{}
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host,
f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name foo")) return strings.Contains(server, "server_name foo")
}) })
canaryAnnotations := map[string]string{ canaryAnnotations := map[string]string{
@ -461,74 +433,60 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
canaryIngName := fmt.Sprintf("%v-canary", host) canaryIngName := fmt.Sprintf("%v-canary", host)
canaryIng := framework.NewSingleIngress(canaryIngName, "/", host, f.Namespace, canaryService, canaryIng := framework.NewSingleIngress(canaryIngName, "/", host,
80, canaryAnnotations) f.Namespace, canaryService, 80, canaryAnnotations)
f.EnsureIngress(canaryIng) f.EnsureIngress(canaryIng)
By("routing requests to the canary upstream when header is set to 'DoCanary'") ginkgo.By("routing requests to the canary upstream when header is set to 'DoCanary'")
f.HTTPTestClient().
GET("/").
WithHeader("Host", host).
WithHeader("CanaryByHeader", "DoCanary").
Expect().
Status(http.StatusOK).
Body().Contains(canaryService)
resp, body, errs := gorequest.New(). ginkgo.By("routing requests to the mainline upstream when header is set to 'always'")
Get(f.GetURL(framework.HTTP)). f.HTTPTestClient().
Set("Host", host). GET("/").
Set("CanaryByHeader", "DoCanary"). WithHeader("Host", host).
End() WithHeader("CanaryByHeader", "always").
Expect().
Status(http.StatusOK).
Body().Contains(framework.EchoService).NotContains(canaryService)
Expect(errs).Should(BeEmpty()) ginkgo.By("routing requests to the mainline upstream when header is set to 'never'")
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) f.HTTPTestClient().
Expect(body).Should(ContainSubstring(canaryService)) GET("/").
WithHeader("Host", host).
WithHeader("CanaryByHeader", "never").
Expect().
Status(http.StatusOK).
Body().Contains(framework.EchoService).NotContains(canaryService)
By("routing requests to the mainline upstream when header is set to 'always'") ginkgo.By("routing requests to the mainline upstream when header is set to anything else")
f.HTTPTestClient().
resp, body, errs = gorequest.New(). GET("/").
Get(f.GetURL(framework.HTTP)). WithHeader("Host", host).
Set("Host", host). WithHeader("CanaryByHeader", "otherheadervalue").
Set("CanaryByHeader", "always"). Expect().
End() Status(http.StatusOK).
Body().Contains(framework.EchoService).NotContains(canaryService)
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(framework.EchoService))
Expect(body).ShouldNot(ContainSubstring(canaryService))
By("routing requests to the mainline upstream when header is set to 'never'")
resp, body, errs = gorequest.New().
Get(f.GetURL(framework.HTTP)).
Set("Host", host).
Set("CanaryByHeader", "never").
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(framework.EchoService))
Expect(body).ShouldNot(ContainSubstring(canaryService))
By("routing requests to the mainline upstream when header is set to anything else")
resp, body, errs = gorequest.New().
Get(f.GetURL(framework.HTTP)).
Set("Host", host).
Set("CanaryByHeader", "otherheadervalue").
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(framework.EchoService))
Expect(body).ShouldNot(ContainSubstring(canaryService))
}) })
}) })
Context("when canaried by header with value and cookie", func() { ginkgo.Context("when canaried by header with value and cookie", func() {
It("should route requests to the correct upstream", func() { ginkgo.It("should route requests to the correct upstream", func() {
host := "foo" host := "foo"
annotations := map[string]string{} annotations := map[string]string{}
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host,
f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name foo")) return strings.Contains(server, "server_name foo")
}) })
canaryAnnotations := map[string]string{ canaryAnnotations := map[string]string{
@ -540,35 +498,34 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
canaryIngName := fmt.Sprintf("%v-canary", host) canaryIngName := fmt.Sprintf("%v-canary", host)
canaryIng := framework.NewSingleIngress(canaryIngName, "/", host, f.Namespace, canaryService, canaryIng := framework.NewSingleIngress(canaryIngName, "/", host,
80, canaryAnnotations) f.Namespace, canaryService, 80, canaryAnnotations)
f.EnsureIngress(canaryIng) f.EnsureIngress(canaryIng)
By("routing requests to the canary upstream when header value does not match and cookie is set to 'always'") ginkgo.By("routing requests to the canary upstream when header value does not match and cookie is set to 'always'")
resp, body, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
Set("CanaryByHeader", "otherheadervalue"). WithHeader("CanaryByHeader", "otherheadervalue").
AddCookie(&http.Cookie{Name: "CanaryByCookie", Value: "always"}). WithCookie("CanaryByCookie", "always").
End() Expect().
Status(http.StatusOK).
Expect(errs).Should(BeEmpty()) Body().Contains(canaryService)
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(canaryService))
}) })
}) })
Context("when canaried by cookie", func() { ginkgo.Context("when canaried by cookie", func() {
It("should route requests to the correct upstream", func() { ginkgo.It("should route requests to the correct upstream", func() {
host := "foo" host := "foo"
annotations := map[string]string{} annotations := map[string]string{}
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host,
f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name foo")) return strings.Contains(server, "server_name foo")
}) })
canaryAnnotations := map[string]string{ canaryAnnotations := map[string]string{
@ -578,111 +535,98 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
canaryIngName := fmt.Sprintf("%v-canary", host) canaryIngName := fmt.Sprintf("%v-canary", host)
canaryIng := framework.NewSingleIngress(canaryIngName, "/", host, f.Namespace, canaryService, canaryIng := framework.NewSingleIngress(canaryIngName, "/", host,
80, canaryAnnotations) f.Namespace, canaryService, 80, canaryAnnotations)
f.EnsureIngress(canaryIng) f.EnsureIngress(canaryIng)
By("routing requests to the canary upstream when cookie is set to 'always'") ginkgo.By("routing requests to the canary upstream when cookie is set to 'always'")
resp, body, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
AddCookie(&http.Cookie{Name: "Canary-By-Cookie", Value: "always"}). WithCookie("Canary-By-Cookie", "always").
End() Expect().
Status(http.StatusOK).
Body().Contains(canaryService)
Expect(errs).Should(BeEmpty()) ginkgo.By("routing requests to the mainline upstream when cookie is set to 'never'")
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) f.HTTPTestClient().
Expect(body).Should(ContainSubstring(canaryService)) GET("/").
WithHeader("Host", host).
WithCookie("Canary-By-Cookie", "never").
Expect().
Status(http.StatusOK).
Body().Contains(framework.EchoService).NotContains(canaryService)
By("routing requests to the mainline upstream when cookie is set to 'never'") ginkgo.By("routing requests to the mainline upstream when cookie is set to anything else")
f.HTTPTestClient().
resp, body, errs = gorequest.New(). GET("/").
Get(f.GetURL(framework.HTTP)). WithHeader("Host", host).
Set("Host", host). WithCookie("Canary-By-Cookie", "badcookievalue").
AddCookie(&http.Cookie{Name: "Canary-By-Cookie", Value: "never"}). Expect().
End() Status(http.StatusOK).
Body().Contains(framework.EchoService).NotContains(canaryService)
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(framework.EchoService))
Expect(body).ShouldNot(ContainSubstring(canaryService))
By("routing requests to the mainline upstream when cookie is set to anything else")
resp, body, errs = gorequest.New().
Get(f.GetURL(framework.HTTP)).
Set("Host", host).
AddCookie(&http.Cookie{Name: "Canary-By-Cookie", Value: "badcookievalue"}).
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(framework.EchoService))
Expect(body).ShouldNot(ContainSubstring(canaryService))
}) })
}) })
// TODO: add testing for canary-weight 0 < weight < 100 // TODO: add testing for canary-weight 0 < weight < 100
Context("when canaried by weight", func() { ginkgo.Context("when canaried by weight", func() {
It("should route requests to the correct upstream", func() { ginkgo.It("should route requests to the correct upstream", func() {
host := "foo" host := "foo"
annotations := map[string]string{} annotations := map[string]string{}
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host,
f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name foo")) return strings.Contains(server, "server_name foo")
}) })
canaryIngName := fmt.Sprintf("%v-canary", host)
canaryAnnotations := map[string]string{ canaryAnnotations := map[string]string{
"nginx.ingress.kubernetes.io/canary": "true", "nginx.ingress.kubernetes.io/canary": "true",
"nginx.ingress.kubernetes.io/canary-weight": "0", "nginx.ingress.kubernetes.io/canary-weight": "0",
} }
canaryIngName := fmt.Sprintf("%v-canary", host) canaryIng := framework.NewSingleIngress(canaryIngName, "/", host,
f.Namespace, canaryService, 80, canaryAnnotations)
canaryIng := framework.NewSingleIngress(canaryIngName, "/", host, f.Namespace, canaryService,
80, canaryAnnotations)
f.EnsureIngress(canaryIng) f.EnsureIngress(canaryIng)
By("returning requests from the mainline only when weight is equal to 0") ginkgo.By("returning requests from the mainline only when weight is equal to 0")
f.HTTPTestClient().
GET("/").
WithHeader("Host", host).
Expect().
Status(http.StatusOK).
Body().
Contains(framework.EchoService).
NotContains(canaryService)
resp, body, errs := gorequest.New(). ginkgo.By("returning requests from the canary only when weight is equal to 100")
Get(f.GetURL(framework.HTTP)).
Set("Host", host).
End()
Expect(errs).Should(BeEmpty()) err := framework.UpdateIngress(f.KubeClientSet, f.Namespace, canaryIngName,
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) func(ingress *networking.Ingress) error {
Expect(body).Should(ContainSubstring(framework.EchoService)) ingress.ObjectMeta.Annotations = map[string]string{
Expect(body).ShouldNot(ContainSubstring(canaryService)) "nginx.ingress.kubernetes.io/canary": "true",
"nginx.ingress.kubernetes.io/canary-weight": "100",
By("returning requests from the canary only when weight is equal to 100") }
return nil
modCanaryAnnotations := map[string]string{ })
"nginx.ingress.kubernetes.io/canary": "true", assert.Nil(ginkgo.GinkgoT(), err)
"nginx.ingress.kubernetes.io/canary-weight": "100",
}
modCanaryIng := framework.NewSingleIngress(canaryIngName, "/", host, f.Namespace, canaryService, 80, modCanaryAnnotations)
f.EnsureIngress(modCanaryIng)
resp, body, errs = gorequest.New().
Get(f.GetURL(framework.HTTP)).
Set("Host", host).
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(canaryService))
f.HTTPTestClient().
GET("/").
WithHeader("Host", host).
Expect().
Status(http.StatusOK).
Body().
Contains(canaryService)
}) })
}) })
Context("Single canary Ingress", func() { ginkgo.Context("Single canary Ingress", func() {
It("should not use canary as a catch-all server", func() { ginkgo.It("should not use canary as a catch-all server", func() {
host := "foo" host := "foo"
canaryIngName := fmt.Sprintf("%v-canary", host) canaryIngName := fmt.Sprintf("%v-canary", host)
annotations := map[string]string{ annotations := map[string]string{
@ -690,24 +634,27 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
"nginx.ingress.kubernetes.io/canary-by-header": "CanaryByHeader", "nginx.ingress.kubernetes.io/canary-by-header": "CanaryByHeader",
} }
ing := framework.NewSingleCatchAllIngress(canaryIngName, f.Namespace, canaryService, 80, annotations) ing := framework.NewSingleCatchAllIngress(canaryIngName,
f.Namespace, canaryService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
ing = framework.NewSingleCatchAllIngress(host, f.Namespace, framework.EchoService, 80, nil) ing = framework.NewSingleCatchAllIngress(host, f.Namespace,
framework.EchoService, 80, nil)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer("_", f.WaitForNginxServer("_",
func(server string) bool { func(server string) bool {
upstreamName := fmt.Sprintf(`set $proxy_upstream_name "%s-%s-%s";`, f.Namespace, framework.EchoService, "80") upstreamName := fmt.Sprintf(`set $proxy_upstream_name "%s-%s-%s";`, f.Namespace, framework.EchoService, "80")
canaryUpstreamName := fmt.Sprintf(`set $proxy_upstream_name "%s-%s-%s";`, f.Namespace, canaryService, "80") canaryUpstreamName := fmt.Sprintf(`set $proxy_upstream_name "%s-%s-%s";`, f.Namespace, canaryService, "80")
return Expect(server).Should(ContainSubstring(`set $ingress_name "`+host+`";`)) &&
Expect(server).ShouldNot(ContainSubstring(`set $proxy_upstream_name "upstream-default-backend";`)) && return strings.Contains(server, fmt.Sprintf(`set $ingress_name "%v";`, host)) &&
Expect(server).ShouldNot(ContainSubstring(canaryUpstreamName)) && !strings.Contains(server, `set $proxy_upstream_name "upstream-default-backend";`) &&
Expect(server).Should(ContainSubstring(upstreamName)) !strings.Contains(server, canaryUpstreamName) &&
strings.Contains(server, upstreamName)
}) })
}) })
It("should not use canary with domain as a server", func() { ginkgo.It("should not use canary with domain as a server", func() {
host := "foo" host := "foo"
canaryIngName := fmt.Sprintf("%v-canary", host) canaryIngName := fmt.Sprintf("%v-canary", host)
annotations := map[string]string{ annotations := map[string]string{
@ -715,21 +662,23 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
"nginx.ingress.kubernetes.io/canary-by-header": "CanaryByHeader", "nginx.ingress.kubernetes.io/canary-by-header": "CanaryByHeader",
} }
ing := framework.NewSingleIngress(canaryIngName, "/", host, f.Namespace, canaryService, 80, annotations) ing := framework.NewSingleIngress(canaryIngName, "/", host,
f.Namespace, canaryService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
otherHost := "bar" otherHost := "bar"
ing = framework.NewSingleIngress(otherHost, "/", otherHost, f.Namespace, framework.EchoService, 80, nil) ing = framework.NewSingleIngress(otherHost, "/", otherHost,
f.Namespace, framework.EchoService, 80, nil)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxConfiguration(func(cfg string) bool { f.WaitForNginxConfiguration(func(cfg string) bool {
return Expect(cfg).Should(ContainSubstring("server_name "+otherHost)) && return strings.Contains(cfg, "server_name "+otherHost) &&
Expect(cfg).ShouldNot(ContainSubstring("server_name "+host)) !strings.Contains(cfg, "server_name "+host)
}) })
}) })
}) })
It("does not crash when canary ingress has multiple paths to the same non-matching backend", func() { ginkgo.It("does not crash when canary ingress has multiple paths to the same non-matching backend", func() {
host := "foo" host := "foo"
canaryIngName := fmt.Sprintf("%v-canary", host) canaryIngName := fmt.Sprintf("%v-canary", host)
annotations := map[string]string{ annotations := map[string]string{
@ -738,15 +687,17 @@ var _ = framework.DescribeAnnotation("canary-*", func() {
} }
paths := []string{"/foo", "/bar"} paths := []string{"/foo", "/bar"}
ing := framework.NewSingleIngressWithMultiplePaths(canaryIngName, paths, host, f.Namespace, "httpy-svc-canary", 80, annotations) ing := framework.NewSingleIngressWithMultiplePaths(canaryIngName, paths, host,
f.Namespace, "httpy-svc-canary", 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
ing = framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil) ing = framework.NewSingleIngress(host, "/", host, f.Namespace,
framework.EchoService, 80, nil)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name foo")) return strings.Contains(server, "server_name foo")
}) })
}) })
}) })

View file

@ -17,19 +17,21 @@ limitations under the License.
package annotations package annotations
import ( import (
. "github.com/onsi/ginkgo" "strings"
. "github.com/onsi/gomega"
"github.com/onsi/ginkgo"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeAnnotation("client-body-buffer-size", func() { var _ = framework.DescribeAnnotation("client-body-buffer-size", func() {
f := framework.NewDefaultFramework("clientbodybuffersize") f := framework.NewDefaultFramework("clientbodybuffersize")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeployment()
}) })
It("should set client_body_buffer_size to 1000", func() { ginkgo.It("should set client_body_buffer_size to 1000", func() {
host := "proxy.foo.com" host := "proxy.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/client-body-buffer-size": "1000", "nginx.ingress.kubernetes.io/client-body-buffer-size": "1000",
@ -40,11 +42,11 @@ var _ = framework.DescribeAnnotation("client-body-buffer-size", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("client_body_buffer_size 1000;")) return strings.Contains(server, "client_body_buffer_size 1000;")
}) })
}) })
It("should set client_body_buffer_size to 1K", func() { ginkgo.It("should set client_body_buffer_size to 1K", func() {
host := "proxy.foo.com" host := "proxy.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/client-body-buffer-size": "1K", "nginx.ingress.kubernetes.io/client-body-buffer-size": "1K",
@ -55,11 +57,11 @@ var _ = framework.DescribeAnnotation("client-body-buffer-size", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("client_body_buffer_size 1K;")) return strings.Contains(server, "client_body_buffer_size 1K;")
}) })
}) })
It("should set client_body_buffer_size to 1k", func() { ginkgo.It("should set client_body_buffer_size to 1k", func() {
host := "proxy.foo.com" host := "proxy.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/client-body-buffer-size": "1k", "nginx.ingress.kubernetes.io/client-body-buffer-size": "1k",
@ -70,11 +72,11 @@ var _ = framework.DescribeAnnotation("client-body-buffer-size", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("client_body_buffer_size 1k;")) return strings.Contains(server, "client_body_buffer_size 1k;")
}) })
}) })
It("should set client_body_buffer_size to 1m", func() { ginkgo.It("should set client_body_buffer_size to 1m", func() {
host := "proxy.foo.com" host := "proxy.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/client-body-buffer-size": "1m", "nginx.ingress.kubernetes.io/client-body-buffer-size": "1m",
@ -85,11 +87,11 @@ var _ = framework.DescribeAnnotation("client-body-buffer-size", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("client_body_buffer_size 1m;")) return strings.Contains(server, "client_body_buffer_size 1m;")
}) })
}) })
It("should set client_body_buffer_size to 1M", func() { ginkgo.It("should set client_body_buffer_size to 1M", func() {
host := "proxy.foo.com" host := "proxy.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/client-body-buffer-size": "1M", "nginx.ingress.kubernetes.io/client-body-buffer-size": "1M",
@ -100,11 +102,11 @@ var _ = framework.DescribeAnnotation("client-body-buffer-size", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("client_body_buffer_size 1M;")) return strings.Contains(server, "client_body_buffer_size 1M;")
}) })
}) })
It("should not set client_body_buffer_size to invalid 1b", func() { ginkgo.It("should not set client_body_buffer_size to invalid 1b", func() {
host := "proxy.foo.com" host := "proxy.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/client-body-buffer-size": "1b", "nginx.ingress.kubernetes.io/client-body-buffer-size": "1b",
@ -115,7 +117,7 @@ var _ = framework.DescribeAnnotation("client-body-buffer-size", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).ShouldNot(ContainSubstring("client_body_buffer_size 1b;")) return !strings.Contains(server, "client_body_buffer_size 1b;")
}) })
}) })
}) })

View file

@ -19,22 +19,21 @@ package annotations
import ( import (
"fmt" "fmt"
"net/http" "net/http"
"time" "strings"
"github.com/onsi/ginkgo"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeAnnotation("connection-proxy-header", func() { var _ = framework.DescribeAnnotation("connection-proxy-header", func() {
f := framework.NewDefaultFramework("connection") f := framework.NewDefaultFramework("connection")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeployment()
}) })
It("set connection header to keep-alive", func() { ginkgo.It("set connection header to keep-alive", func() {
host := "connection.foo.com" host := "connection.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/connection-proxy-header": "keep-alive", "nginx.ingress.kubernetes.io/connection-proxy-header": "keep-alive",
@ -45,17 +44,14 @@ var _ = framework.DescribeAnnotation("connection-proxy-header", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring(`proxy_set_header Connection keep-alive;`)) return strings.Contains(server, "proxy_set_header Connection keep-alive;")
}) })
resp, body, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
Set("Host", host). Expect().
End() Status(http.StatusOK).
Body().Contains(fmt.Sprintf("connection=keep-alive"))
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(fmt.Sprintf("connection=keep-alive")))
}) })
}) })

View file

@ -18,10 +18,9 @@ package annotations
import ( import (
"net/http" "net/http"
"strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -29,11 +28,11 @@ import (
var _ = framework.DescribeAnnotation("cors-*", func() { var _ = framework.DescribeAnnotation("cors-*", func() {
f := framework.NewDefaultFramework("cors") f := framework.NewDefaultFramework("cors")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeploymentWithReplicas(2)
}) })
It("should enable cors", func() { ginkgo.It("should enable cors", func() {
host := "cors.foo.com" host := "cors.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/enable-cors": "true", "nginx.ingress.kubernetes.io/enable-cors": "true",
@ -44,39 +43,21 @@ var _ = framework.DescribeAnnotation("cors-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("more_set_headers 'Access-Control-Allow-Methods: GET, PUT, POST, DELETE, PATCH, OPTIONS';")) return strings.Contains(server, "more_set_headers 'Access-Control-Allow-Methods: GET, PUT, POST, DELETE, PATCH, OPTIONS';") &&
strings.Contains(server, "more_set_headers 'Access-Control-Allow-Origin: *';") &&
strings.Contains(server, "more_set_headers 'Access-Control-Allow-Headers: DNT,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Authorization';") &&
strings.Contains(server, "more_set_headers 'Access-Control-Max-Age: 1728000';") &&
strings.Contains(server, "more_set_headers 'Access-Control-Allow-Credentials: true';")
}) })
f.WaitForNginxServer(host, f.HTTPTestClient().
func(server string) bool { GET("/").
return Expect(server).Should(ContainSubstring("more_set_headers 'Access-Control-Allow-Origin: *';")) WithHeader("Host", host).
}) Expect().
Status(http.StatusOK)
f.WaitForNginxServer(host,
func(server string) bool {
return Expect(server).Should(ContainSubstring("more_set_headers 'Access-Control-Allow-Headers: DNT,X-CustomHeader,Keep-Alive,User-Agent,X-Requested-With,If-Modified-Since,Cache-Control,Content-Type,Authorization';"))
})
f.WaitForNginxServer(host,
func(server string) bool {
return Expect(server).Should(ContainSubstring("more_set_headers 'Access-Control-Max-Age: 1728000';"))
})
f.WaitForNginxServer(host,
func(server string) bool {
return Expect(server).Should(ContainSubstring("more_set_headers 'Access-Control-Allow-Credentials: true';"))
})
uri := "/"
resp, _, errs := gorequest.New().
Options(f.GetURL(framework.HTTP)+uri).
Set("Host", host).
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusNoContent))
}) })
It("should set cors methods to only allow POST, GET", func() { ginkgo.It("should set cors methods to only allow POST, GET", func() {
host := "cors.foo.com" host := "cors.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/enable-cors": "true", "nginx.ingress.kubernetes.io/enable-cors": "true",
@ -88,11 +69,11 @@ var _ = framework.DescribeAnnotation("cors-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("more_set_headers 'Access-Control-Allow-Methods: POST, GET';")) return strings.Contains(server, "more_set_headers 'Access-Control-Allow-Methods: POST, GET';")
}) })
}) })
It("should set cors max-age", func() { ginkgo.It("should set cors max-age", func() {
host := "cors.foo.com" host := "cors.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/enable-cors": "true", "nginx.ingress.kubernetes.io/enable-cors": "true",
@ -104,11 +85,11 @@ var _ = framework.DescribeAnnotation("cors-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("more_set_headers 'Access-Control-Max-Age: 200';")) return strings.Contains(server, "more_set_headers 'Access-Control-Max-Age: 200';")
}) })
}) })
It("should disable cors allow credentials", func() { ginkgo.It("should disable cors allow credentials", func() {
host := "cors.foo.com" host := "cors.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/enable-cors": "true", "nginx.ingress.kubernetes.io/enable-cors": "true",
@ -120,11 +101,11 @@ var _ = framework.DescribeAnnotation("cors-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).ShouldNot(ContainSubstring("more_set_headers 'Access-Control-Allow-Credentials: true';")) return !strings.Contains(server, "more_set_headers 'Access-Control-Allow-Credentials: true';")
}) })
}) })
It("should allow origin for cors", func() { ginkgo.It("should allow origin for cors", func() {
host := "cors.foo.com" host := "cors.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/enable-cors": "true", "nginx.ingress.kubernetes.io/enable-cors": "true",
@ -136,11 +117,11 @@ var _ = framework.DescribeAnnotation("cors-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("more_set_headers 'Access-Control-Allow-Origin: https://origin.cors.com:8080';")) return strings.Contains(server, "more_set_headers 'Access-Control-Allow-Origin: https://origin.cors.com:8080';")
}) })
}) })
It("should allow headers for cors", func() { ginkgo.It("should allow headers for cors", func() {
host := "cors.foo.com" host := "cors.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/enable-cors": "true", "nginx.ingress.kubernetes.io/enable-cors": "true",
@ -152,7 +133,7 @@ var _ = framework.DescribeAnnotation("cors-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("more_set_headers 'Access-Control-Allow-Headers: DNT, User-Agent';")) return strings.Contains(server, "more_set_headers 'Access-Control-Allow-Headers: DNT, User-Agent';")
}) })
}) })
}) })

View file

@ -20,8 +20,8 @@ import (
"fmt" "fmt"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
networking "k8s.io/api/networking/v1beta1" networking "k8s.io/api/networking/v1beta1"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
@ -34,11 +34,11 @@ func errorBlockName(upstreamName string, errorCode string) string {
var _ = framework.DescribeAnnotation("custom-http-errors", func() { var _ = framework.DescribeAnnotation("custom-http-errors", func() {
f := framework.NewDefaultFramework("custom-http-errors") f := framework.NewDefaultFramework("custom-http-errors")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeployment()
}) })
It("configures Nginx correctly", func() { ginkgo.It("configures Nginx correctly", func() {
host := "customerrors.foo.com" host := "customerrors.foo.com"
errorCodes := []string{"404", "500"} errorCodes := []string{"404", "500"}
@ -56,25 +56,26 @@ var _ = framework.DescribeAnnotation("custom-http-errors", func() {
return strings.Contains(serverConfig, fmt.Sprintf("server_name %s", host)) return strings.Contains(serverConfig, fmt.Sprintf("server_name %s", host))
}) })
By("turning on proxy_intercept_errors directive") ginkgo.By("turning on proxy_intercept_errors directive")
Expect(serverConfig).Should(ContainSubstring("proxy_intercept_errors on;")) assert.Contains(ginkgo.GinkgoT(), serverConfig, "proxy_intercept_errors on;")
By("configuring error_page directive") ginkgo.By("configuring error_page directive")
for _, code := range errorCodes { for _, code := range errorCodes {
Expect(serverConfig).Should(ContainSubstring(fmt.Sprintf("error_page %s = %s", code, errorBlockName("upstream-default-backend", code)))) assert.Contains(ginkgo.GinkgoT(), serverConfig, fmt.Sprintf("error_page %s = %s", code, errorBlockName("upstream-default-backend", code)))
} }
By("creating error locations") ginkgo.By("creating error locations")
for _, code := range errorCodes { for _, code := range errorCodes {
Expect(serverConfig).Should(ContainSubstring(fmt.Sprintf("location %s", errorBlockName("upstream-default-backend", code)))) assert.Contains(ginkgo.GinkgoT(), serverConfig, fmt.Sprintf("location %s", errorBlockName("upstream-default-backend", code)))
} }
By("updating configuration when only custom-http-error value changes") ginkgo.By("updating configuration when only custom-http-error value changes")
err := framework.UpdateIngress(f.KubeClientSet, f.Namespace, host, func(ingress *networking.Ingress) error { err := framework.UpdateIngress(f.KubeClientSet, f.Namespace, host, func(ingress *networking.Ingress) error {
ingress.ObjectMeta.Annotations["nginx.ingress.kubernetes.io/custom-http-errors"] = "503" ingress.ObjectMeta.Annotations["nginx.ingress.kubernetes.io/custom-http-errors"] = "503"
return nil return nil
}) })
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
f.WaitForNginxServer(host, func(sc string) bool { f.WaitForNginxServer(host, func(sc string) bool {
if serverConfig != sc { if serverConfig != sc {
serverConfig = sc serverConfig = sc
@ -82,22 +83,23 @@ var _ = framework.DescribeAnnotation("custom-http-errors", func() {
} }
return false return false
}) })
Expect(serverConfig).Should(ContainSubstring(fmt.Sprintf("location %s", errorBlockName("upstream-default-backend", "503")))) assert.Contains(ginkgo.GinkgoT(), serverConfig, fmt.Sprintf("location %s", errorBlockName("upstream-default-backend", "503")))
Expect(serverConfig).ShouldNot(ContainSubstring(fmt.Sprintf("location %s", errorBlockName("upstream-default-backend", "404")))) assert.NotContains(ginkgo.GinkgoT(), serverConfig, fmt.Sprintf("location %s", errorBlockName("upstream-default-backend", "404")))
Expect(serverConfig).ShouldNot(ContainSubstring(fmt.Sprintf("location %s", errorBlockName("upstream-default-backend", "500")))) assert.NotContains(ginkgo.GinkgoT(), serverConfig, fmt.Sprintf("location %s", errorBlockName("upstream-default-backend", "500")))
By("ignoring duplicate values (503 in this case) per server") ginkgo.By("ignoring duplicate values (503 in this case) per server")
annotations["nginx.ingress.kubernetes.io/custom-http-errors"] = "404, 503" annotations["nginx.ingress.kubernetes.io/custom-http-errors"] = "404, 503"
ing = framework.NewSingleIngress(fmt.Sprintf("%s-else", host), "/else", host, f.Namespace, framework.EchoService, 80, annotations) ing = framework.NewSingleIngress(fmt.Sprintf("%s-else", host), "/else", host, f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer(host, func(sc string) bool { f.WaitForNginxServer(host, func(sc string) bool {
serverConfig = sc serverConfig = sc
return strings.Contains(serverConfig, "location /else") return strings.Contains(serverConfig, "location /else")
}) })
count := strings.Count(serverConfig, fmt.Sprintf("location %s", errorBlockName("upstream-default-backend", "503"))) count := strings.Count(serverConfig, fmt.Sprintf("location %s", errorBlockName("upstream-default-backend", "503")))
Expect(count).Should(Equal(1)) assert.Equal(ginkgo.GinkgoT(), count, 1)
By("using the custom default-backend from annotation for upstream") ginkgo.By("using the custom default-backend from annotation for upstream")
customDefaultBackend := "from-annotation" customDefaultBackend := "from-annotation"
f.NewEchoDeploymentWithNameAndReplicas(customDefaultBackend, 1) f.NewEchoDeploymentWithNameAndReplicas(customDefaultBackend, 1)
@ -105,7 +107,8 @@ var _ = framework.DescribeAnnotation("custom-http-errors", func() {
ingress.ObjectMeta.Annotations["nginx.ingress.kubernetes.io/default-backend"] = customDefaultBackend ingress.ObjectMeta.Annotations["nginx.ingress.kubernetes.io/default-backend"] = customDefaultBackend
return nil return nil
}) })
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
f.WaitForNginxServer(host, func(sc string) bool { f.WaitForNginxServer(host, func(sc string) bool {
if serverConfig != sc { if serverConfig != sc {
serverConfig = sc serverConfig = sc
@ -113,7 +116,7 @@ var _ = framework.DescribeAnnotation("custom-http-errors", func() {
} }
return false return false
}) })
Expect(serverConfig).Should(ContainSubstring(errorBlockName(fmt.Sprintf("custom-default-backend-%s", customDefaultBackend), "503"))) assert.Contains(ginkgo.GinkgoT(), serverConfig, errorBlockName(fmt.Sprintf("custom-default-backend-%s", customDefaultBackend), "503"))
Expect(serverConfig).Should(ContainSubstring(fmt.Sprintf("error_page %s = %s", "503", errorBlockName(fmt.Sprintf("custom-default-backend-%s", customDefaultBackend), "503")))) assert.Contains(ginkgo.GinkgoT(), serverConfig, fmt.Sprintf("error_page %s = %s", "503", errorBlockName(fmt.Sprintf("custom-default-backend-%s", customDefaultBackend), "503")))
}) })
}) })

View file

@ -19,10 +19,9 @@ package annotations
import ( import (
"fmt" "fmt"
"net/http" "net/http"
"strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -30,12 +29,12 @@ import (
var _ = framework.DescribeAnnotation("default-backend", func() { var _ = framework.DescribeAnnotation("default-backend", func() {
f := framework.NewDefaultFramework("default-backend") f := framework.NewDefaultFramework("default-backend")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
Context("when default backend annotation is enabled", func() { ginkgo.Context("when default backend annotation is enabled", func() {
It("should use a custom default backend as upstream", func() { ginkgo.It("should use a custom default backend as upstream", func() {
host := "default-backend" host := "default-backend"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/default-backend": framework.EchoService, "nginx.ingress.kubernetes.io/default-backend": framework.EchoService,
@ -46,24 +45,21 @@ var _ = framework.DescribeAnnotation("default-backend", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring(fmt.Sprintf("server_name %v", host))) return strings.Contains(server, fmt.Sprintf("server_name %v", host))
}) })
uri := "/alma/armud"
requestId := "something-unique" requestId := "something-unique"
resp, body, errs := gorequest.New().
Get(f.GetURL(framework.HTTP)+uri).
Set("Host", host).
Set("x-request-id", requestId).
End()
Expect(errs).Should(BeEmpty()) f.HTTPTestClient().
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) GET("/alma/armud").
WithHeader("Host", host).
Expect(body).To(ContainSubstring("x-code=503")) WithHeader("x-request-id", requestId).
Expect(body).To(ContainSubstring(fmt.Sprintf("x-ingress-name=%s", host))) Expect().
Expect(body).To(ContainSubstring("x-service-name=invalid")) Status(http.StatusOK).
Expect(body).To(ContainSubstring(fmt.Sprintf("x-request-id=%s", requestId))) Body().Contains("x-code=503").
Contains(fmt.Sprintf("x-ingress-name=%s", host)).
Contains("x-service-name=invalid").
Contains(fmt.Sprintf("x-request-id=%s", requestId))
}) })
}) })
}) })

View file

@ -18,10 +18,10 @@ package annotations
import ( import (
"net/http" "net/http"
"strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
corev1 "k8s.io/api/core/v1" corev1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
@ -31,11 +31,11 @@ import (
var _ = framework.DescribeAnnotation("backend-protocol - FastCGI", func() { var _ = framework.DescribeAnnotation("backend-protocol - FastCGI", func() {
f := framework.NewDefaultFramework("fastcgi") f := framework.NewDefaultFramework("fastcgi")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewFastCGIHelloServerDeployment() f.NewFastCGIHelloServerDeployment()
}) })
It("should use fastcgi_pass in the configuration file", func() { ginkgo.It("should use fastcgi_pass in the configuration file", func() {
host := "fastcgi" host := "fastcgi"
annotations := map[string]string{ annotations := map[string]string{
@ -47,12 +47,12 @@ var _ = framework.DescribeAnnotation("backend-protocol - FastCGI", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("include /etc/nginx/fastcgi_params;")) && return strings.Contains(server, "include /etc/nginx/fastcgi_params;") &&
Expect(server).Should(ContainSubstring("fastcgi_pass")) strings.Contains(server, "fastcgi_pass")
}) })
}) })
It("should add fastcgi_index in the configuration file", func() { ginkgo.It("should add fastcgi_index in the configuration file", func() {
host := "fastcgi-index" host := "fastcgi-index"
annotations := map[string]string{ annotations := map[string]string{
@ -65,11 +65,11 @@ var _ = framework.DescribeAnnotation("backend-protocol - FastCGI", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("fastcgi_index \"index.php\";")) return strings.Contains(server, "fastcgi_index \"index.php\";")
}) })
}) })
It("should add fastcgi_param in the configuration file", func() { ginkgo.It("should add fastcgi_param in the configuration file", func() {
configuration := &corev1.ConfigMap{ configuration := &corev1.ConfigMap{
ObjectMeta: metav1.ObjectMeta{ ObjectMeta: metav1.ObjectMeta{
Name: "fastcgi-configmap", Name: "fastcgi-configmap",
@ -82,8 +82,8 @@ var _ = framework.DescribeAnnotation("backend-protocol - FastCGI", func() {
} }
cm, err := f.EnsureConfigMap(configuration) cm, err := f.EnsureConfigMap(configuration)
Expect(err).NotTo(HaveOccurred(), "failed to create an the configmap") assert.Nil(ginkgo.GinkgoT(), err, "creating configmap")
Expect(cm).NotTo(BeNil(), "expected a configmap but none returned") assert.NotNil(ginkgo.GinkgoT(), cm, "expected a configmap but none returned")
host := "fastcgi-params-configmap" host := "fastcgi-params-configmap"
@ -97,12 +97,12 @@ var _ = framework.DescribeAnnotation("backend-protocol - FastCGI", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("fastcgi_param SCRIPT_FILENAME \"/home/www/scripts/php$fastcgi_script_name\";")) && return strings.Contains(server, "fastcgi_param SCRIPT_FILENAME \"/home/www/scripts/php$fastcgi_script_name\";") &&
Expect(server).Should(ContainSubstring("fastcgi_param REDIRECT_STATUS \"200\";")) strings.Contains(server, "fastcgi_param REDIRECT_STATUS \"200\";")
}) })
}) })
It("should return OK for service with backend protocol FastCGI", func() { ginkgo.It("should return OK for service with backend protocol FastCGI", func() {
host := "fastcgi-helloserver" host := "fastcgi-helloserver"
path := "/hello" path := "/hello"
@ -115,16 +115,14 @@ var _ = framework.DescribeAnnotation("backend-protocol - FastCGI", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("fastcgi_pass")) return strings.Contains(server, "fastcgi_pass")
}) })
resp, body, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+path). GET(path).
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Expect(errs).Should(BeEmpty()) Body().Contains("Hello world!")
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring("Hello world!"))
}) })
}) })

View file

@ -18,22 +18,20 @@ package annotations
import ( import (
"net/http" "net/http"
"time"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeAnnotation("force-ssl-redirect", func() { var _ = framework.DescribeAnnotation("force-ssl-redirect", func() {
f := framework.NewDefaultFramework("forcesslredirect") f := framework.NewDefaultFramework("forcesslredirect")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeployment()
}) })
It("should redirect to https", func() { ginkgo.It("should redirect to https", func() {
host := "forcesslredirect.bar.com" host := "forcesslredirect.bar.com"
annotations := map[string]string{ annotations := map[string]string{
@ -43,15 +41,11 @@ var _ = framework.DescribeAnnotation("force-ssl-redirect", func() {
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
RedirectPolicy(noRedirectPolicyFunc). Expect().
Set("Host", host). Status(http.StatusPermanentRedirect).
End() Header("Location").Equal("https://forcesslredirect.bar.com/")
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusPermanentRedirect))
Expect(resp.Header.Get("Location")).Should(Equal("https://forcesslredirect.bar.com/"))
}) })
}) })

View file

@ -20,11 +20,11 @@ import (
"crypto/tls" "crypto/tls"
"fmt" "fmt"
"net/http" "net/http"
"strings"
"time" "time"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -32,12 +32,12 @@ import (
var _ = framework.DescribeAnnotation("from-to-www-redirect", func() { var _ = framework.DescribeAnnotation("from-to-www-redirect", func() {
f := framework.NewDefaultFramework("fromtowwwredirect") f := framework.NewDefaultFramework("fromtowwwredirect")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeployment()
}) })
It("should redirect from www HTTP to HTTP", func() { ginkgo.It("should redirect from www HTTP to HTTP", func() {
By("setting up server for redirect from www") ginkgo.By("setting up server for redirect from www")
host := "fromtowwwredirect.bar.com" host := "fromtowwwredirect.bar.com"
annotations := map[string]string{ annotations := map[string]string{
@ -49,26 +49,21 @@ var _ = framework.DescribeAnnotation("from-to-www-redirect", func() {
f.WaitForNginxConfiguration( f.WaitForNginxConfiguration(
func(cfg string) bool { func(cfg string) bool {
return Expect(cfg).Should(ContainSubstring(`server_name www.fromtowwwredirect.bar.com;`)) && return strings.Contains(cfg, `server_name www.fromtowwwredirect.bar.com;`) &&
Expect(cfg).Should(ContainSubstring(`return 308 $scheme://fromtowwwredirect.bar.com$request_uri;`)) strings.Contains(cfg, `return 308 $scheme://fromtowwwredirect.bar.com$request_uri;`)
}) })
By("sending request to www.fromtowwwredirect.bar.com") ginkgo.By("sending request to www.fromtowwwredirect.bar.com")
f.HTTPTestClient().
resp, _, errs := gorequest.New(). GET("/foo").
Get(fmt.Sprintf("%s/%s", f.GetURL(framework.HTTP), "foo")). WithHeader("Host", fmt.Sprintf("%s.%s", "www", host)).
Retry(10, 1*time.Second, http.StatusNotFound). Expect().
RedirectPolicy(noRedirectPolicyFunc). Status(http.StatusPermanentRedirect).
Set("Host", fmt.Sprintf("%s.%s", "www", host)). Header("Location").Equal("http://fromtowwwredirect.bar.com/foo")
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusPermanentRedirect))
Expect(resp.Header.Get("Location")).Should(Equal("http://fromtowwwredirect.bar.com/foo"))
}) })
It("should redirect from www HTTPS to HTTPS", func() { ginkgo.It("should redirect from www HTTPS to HTTPS", func() {
By("setting up server for redirect from www") ginkgo.By("setting up server for redirect from www")
fromHost := fmt.Sprintf("%s.nip.io", f.GetNginxIP()) fromHost := fmt.Sprintf("%s.nip.io", f.GetNginxIP())
toHost := fmt.Sprintf("www.%s", fromHost) toHost := fmt.Sprintf("www.%s", fromHost)
@ -85,45 +80,37 @@ var _ = framework.DescribeAnnotation("from-to-www-redirect", func() {
ing.Spec.TLS[0].Hosts, ing.Spec.TLS[0].Hosts,
ing.Spec.TLS[0].SecretName, ing.Spec.TLS[0].SecretName,
ing.Namespace) ing.Namespace)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
time.Sleep(5 * time.Second)
f.WaitForNginxServer(toHost, f.WaitForNginxServer(toHost,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring(fmt.Sprintf(`server_name %v;`, toHost))) && return strings.Contains(server, fmt.Sprintf(`server_name %v;`, toHost)) &&
Expect(server).Should(ContainSubstring(fmt.Sprintf(`return 308 $scheme://%v$request_uri;`, fromHost))) strings.Contains(server, fmt.Sprintf(`return 308 $scheme://%v$request_uri;`, fromHost))
}) })
By("sending request to www should redirect to domain without www") ginkgo.By("sending request to www should redirect to domain")
f.HTTPTestClientWithTLSConfig(&tls.Config{
InsecureSkipVerify: true,
ServerName: toHost,
}).
GET("/").
WithURL(f.GetURL(framework.HTTPS)).
WithHeader("Host", toHost).
Expect().
Status(http.StatusPermanentRedirect).
Header("Location").Equal(fmt.Sprintf("https://%v/", fromHost))
resp, _, errs := gorequest.New(). ginkgo.By("sending request to domain should not redirect to www")
TLSClientConfig(&tls.Config{ f.HTTPTestClientWithTLSConfig(&tls.Config{
InsecureSkipVerify: true, InsecureSkipVerify: true,
ServerName: toHost, ServerName: fromHost,
}). }).
Get(f.GetURL(framework.HTTPS)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithURL(f.GetURL(framework.HTTPS)).
RedirectPolicy(noRedirectPolicyFunc). WithHeader("Host", fromHost).
Set("host", toHost). Expect().
End() Status(http.StatusOK).
Header("ExpectedHost").Equal(fromHost)
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusPermanentRedirect))
Expect(resp.Header.Get("Location")).Should(Equal(fmt.Sprintf("https://%v/", fromHost)))
By("sending request to domain should redirect to domain with www")
req := gorequest.New().
TLSClientConfig(&tls.Config{
InsecureSkipVerify: true,
ServerName: toHost,
}).
Get(f.GetURL(framework.HTTPS)).
Set("host", toHost)
resp, _, errs = req.End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(resp.Header.Get("ExpectedHost")).Should(Equal(fromHost))
}) })
}) })

View file

@ -21,10 +21,9 @@ import (
"fmt" "fmt"
"strings" "strings"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
pb "github.com/moul/pb/grpcbin/go-grpc" pb "github.com/moul/pb/grpcbin/go-grpc"
"github.com/onsi/ginkgo"
"github.com/stretchr/testify/assert"
"golang.org/x/net/context" "golang.org/x/net/context"
"google.golang.org/grpc" "google.golang.org/grpc"
"google.golang.org/grpc/credentials" "google.golang.org/grpc/credentials"
@ -39,7 +38,7 @@ import (
var _ = framework.DescribeAnnotation("backend-protocol - GRPC", func() { var _ = framework.DescribeAnnotation("backend-protocol - GRPC", func() {
f := framework.NewDefaultFramework("grpc") f := framework.NewDefaultFramework("grpc")
It("should use grpc_pass in the configuration file", func() { ginkgo.It("should use grpc_pass in the configuration file", func() {
f.NewGRPCFortuneTellerDeployment() f.NewGRPCFortuneTellerDeployment()
host := "grpc" host := "grpc"
@ -53,18 +52,18 @@ var _ = framework.DescribeAnnotation("backend-protocol - GRPC", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring(fmt.Sprintf("server_name %v", host))) return strings.Contains(server, fmt.Sprintf("server_name %v", host))
}) })
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("grpc_pass")) && return strings.Contains(server, "grpc_pass") &&
Expect(server).Should(ContainSubstring("grpc_set_header")) && strings.Contains(server, "grpc_set_header") &&
Expect(server).ShouldNot(ContainSubstring("proxy_pass")) !strings.Contains(server, "proxy_pass")
}) })
}) })
It("should return OK for service with backend protocol GRPC", func() { ginkgo.It("should return OK for service with backend protocol GRPC", func() {
f.NewGRPCBinDeployment() f.NewGRPCBinDeployment()
host := "echo" host := "echo"
@ -116,14 +115,14 @@ var _ = framework.DescribeAnnotation("backend-protocol - GRPC", func() {
ctx := context.Background() ctx := context.Background()
res, err := client.HeadersUnary(ctx, &pb.EmptyMessage{}) res, err := client.HeadersUnary(ctx, &pb.EmptyMessage{})
Expect(err).Should(BeNil()) assert.Nil(ginkgo.GinkgoT(), err)
metadata := res.GetMetadata() metadata := res.GetMetadata()
Expect(metadata["content-type"].Values[0]).Should(Equal("application/grpc")) assert.Equal(ginkgo.GinkgoT(), metadata["content-type"].Values[0], "application/grpc")
}) })
It("should return OK for service with backend protocol GRPCS", func() { ginkgo.It("should return OK for service with backend protocol GRPCS", func() {
Skip("GRPCS test temporarily disabled") ginkgo.Skip("GRPCS test temporarily disabled")
f.NewGRPCBinDeployment() f.NewGRPCBinDeployment()
@ -181,9 +180,9 @@ var _ = framework.DescribeAnnotation("backend-protocol - GRPC", func() {
ctx := context.Background() ctx := context.Background()
res, err := client.HeadersUnary(ctx, &pb.EmptyMessage{}) res, err := client.HeadersUnary(ctx, &pb.EmptyMessage{})
Expect(err).Should(BeNil()) assert.Nil(ginkgo.GinkgoT(), err)
metadata := res.GetMetadata() metadata := res.GetMetadata()
Expect(metadata["content-type"].Values[0]).Should(Equal("application/grpc")) assert.Equal(ginkgo.GinkgoT(), metadata["content-type"].Values[0], "application/grpc")
}) })
}) })

View file

@ -17,19 +17,21 @@ limitations under the License.
package annotations package annotations
import ( import (
. "github.com/onsi/ginkgo" "strings"
. "github.com/onsi/gomega"
"github.com/onsi/ginkgo"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeAnnotation("http2-push-preload", func() { var _ = framework.DescribeAnnotation("http2-push-preload", func() {
f := framework.NewDefaultFramework("http2pushpreload") f := framework.NewDefaultFramework("http2pushpreload")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeployment()
}) })
It("enable the http2-push-preload directive", func() { ginkgo.It("enable the http2-push-preload directive", func() {
host := "http2pp.foo.com" host := "http2pp.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/http2-push-preload": "true", "nginx.ingress.kubernetes.io/http2-push-preload": "true",
@ -40,7 +42,7 @@ var _ = framework.DescribeAnnotation("http2-push-preload", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("http2_push_preload on;")) return strings.Contains(server, "http2_push_preload on;")
}) })
}) })
}) })

View file

@ -21,31 +21,30 @@ import (
"fmt" "fmt"
"net/http" "net/http"
"os/exec" "os/exec"
"strings"
"time" "time"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
jsoniter "github.com/json-iterator/go" jsoniter "github.com/json-iterator/go"
"github.com/parnurzeal/gorequest" "github.com/onsi/ginkgo"
"github.com/stretchr/testify/assert"
corev1 "k8s.io/api/core/v1" corev1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/util/intstr" "k8s.io/apimachinery/pkg/util/intstr"
"k8s.io/apimachinery/pkg/util/wait" "k8s.io/apimachinery/pkg/util/wait"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeAnnotation("influxdb-*", func() { var _ = framework.DescribeAnnotation("influxdb-*", func() {
f := framework.NewDefaultFramework("influxdb") f := framework.NewDefaultFramework("influxdb")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewInfluxDBDeployment() f.NewInfluxDBDeployment()
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
Context("when influxdb is enabled", func() { ginkgo.Context("when influxdb is enabled", func() {
It("should send the request metric to the influxdb server", func() { ginkgo.It("should send the request metric to the influxdb server", func() {
ifs := createInfluxDBService(f) ifs := createInfluxDBService(f)
// Ingress configured with InfluxDB annotations // Ingress configured with InfluxDB annotations
@ -66,13 +65,11 @@ var _ = framework.DescribeAnnotation("influxdb-*", func() {
// Do a request to the echo server ingress that sends metrics // Do a request to the echo server ingress that sends metrics
// to the InfluxDB backend. // to the InfluxDB backend.
res, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK)
Expect(len(errs)).Should(Equal(0))
Expect(res.StatusCode).Should(Equal(http.StatusOK))
time.Sleep(10 * time.Second) time.Sleep(10 * time.Second)
@ -86,14 +83,14 @@ var _ = framework.DescribeAnnotation("influxdb-*", func() {
} }
return true, nil return true, nil
}) })
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
var results map[string][]map[string]interface{} var results map[string][]map[string]interface{}
_ = jsoniter.ConfigCompatibleWithStandardLibrary.Unmarshal([]byte(measurements), &results) _ = jsoniter.ConfigCompatibleWithStandardLibrary.Unmarshal([]byte(measurements), &results)
Expect(len(measurements)).ShouldNot(Equal(0)) assert.NotEqual(ginkgo.GinkgoT(), len(measurements), 0)
for _, elem := range results["results"] { for _, elem := range results["results"] {
Expect(len(elem)).ShouldNot(Equal(0)) assert.NotEqual(ginkgo.GinkgoT(), len(elem), 0)
} }
}) })
}) })
@ -128,7 +125,7 @@ func createInfluxDBIngress(f *framework.Framework, host, service string, port in
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring(fmt.Sprintf("server_name %v", host))) return strings.Contains(server, fmt.Sprintf("server_name %v", host))
}) })
} }

View file

@ -19,19 +19,18 @@ package annotations
import ( import (
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeAnnotation("whitelist-source-range", func() { var _ = framework.DescribeAnnotation("whitelist-source-range", func() {
f := framework.NewDefaultFramework("ipwhitelist") f := framework.NewDefaultFramework("ipwhitelist")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeployment()
}) })
It("should set valid ip whitelist range", func() { ginkgo.It("should set valid ip whitelist range", func() {
host := "ipwhitelist.foo.com" host := "ipwhitelist.foo.com"
nameSpace := f.Namespace nameSpace := f.Namespace

View file

@ -17,8 +17,9 @@ limitations under the License.
package annotations package annotations
import ( import (
. "github.com/onsi/ginkgo" "strings"
. "github.com/onsi/gomega"
"github.com/onsi/ginkgo"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -26,11 +27,11 @@ import (
var _ = framework.DescribeAnnotation("enable-access-log enable-rewrite-log", func() { var _ = framework.DescribeAnnotation("enable-access-log enable-rewrite-log", func() {
f := framework.NewDefaultFramework("log") f := framework.NewDefaultFramework("log")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeployment()
}) })
It("set access_log off", func() { ginkgo.It("set access_log off", func() {
host := "log.foo.com" host := "log.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/enable-access-log": "false", "nginx.ingress.kubernetes.io/enable-access-log": "false",
@ -41,11 +42,11 @@ var _ = framework.DescribeAnnotation("enable-access-log enable-rewrite-log", fun
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring(`access_log off;`)) return strings.Contains(server, `access_log off;`)
}) })
}) })
It("set rewrite_log on", func() { ginkgo.It("set rewrite_log on", func() {
host := "log.foo.com" host := "log.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/enable-rewrite-log": "true", "nginx.ingress.kubernetes.io/enable-rewrite-log": "true",
@ -56,7 +57,7 @@ var _ = framework.DescribeAnnotation("enable-access-log enable-rewrite-log", fun
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring(`rewrite_log on;`)) return strings.Contains(server, `rewrite_log on;`)
}) })
}) })
}) })

View file

@ -20,7 +20,7 @@ import (
"fmt" "fmt"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -29,11 +29,11 @@ var _ = framework.DescribeAnnotation("mirror-*", func() {
f := framework.NewDefaultFramework("mirror") f := framework.NewDefaultFramework("mirror")
host := "mirror.foo.com" host := "mirror.foo.com"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
It("should set mirror-target to http://localhost/mirror", func() { ginkgo.It("should set mirror-target to http://localhost/mirror", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/mirror-target": "http://localhost/mirror", "nginx.ingress.kubernetes.io/mirror-target": "http://localhost/mirror",
} }
@ -48,7 +48,7 @@ var _ = framework.DescribeAnnotation("mirror-*", func() {
}) })
}) })
It("should set mirror-target to https://test.env.com/$request_uri", func() { ginkgo.It("should set mirror-target to https://test.env.com/$request_uri", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/mirror-target": "https://test.env.com/$request_uri", "nginx.ingress.kubernetes.io/mirror-target": "https://test.env.com/$request_uri",
} }
@ -64,7 +64,7 @@ var _ = framework.DescribeAnnotation("mirror-*", func() {
}) })
}) })
It("should disable mirror-request-body", func() { ginkgo.It("should disable mirror-request-body", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/mirror-target": "http://localhost/mirror", "nginx.ingress.kubernetes.io/mirror-target": "http://localhost/mirror",
"nginx.ingress.kubernetes.io/mirror-request-body": "off", "nginx.ingress.kubernetes.io/mirror-request-body": "off",

View file

@ -19,18 +19,18 @@ package annotations
import ( import (
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeAnnotation("modsecurity owasp", func() { var _ = framework.DescribeAnnotation("modsecurity owasp", func() {
f := framework.NewDefaultFramework("modsecuritylocation") f := framework.NewDefaultFramework("modsecuritylocation")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
It("should enable modsecurity", func() { ginkgo.It("should enable modsecurity", func() {
host := "modsecurity.foo.com" host := "modsecurity.foo.com"
nameSpace := f.Namespace nameSpace := f.Namespace
@ -48,7 +48,7 @@ var _ = framework.DescribeAnnotation("modsecurity owasp", func() {
}) })
}) })
It("should enable modsecurity with transaction ID and OWASP rules", func() { ginkgo.It("should enable modsecurity with transaction ID and OWASP rules", func() {
host := "modsecurity.foo.com" host := "modsecurity.foo.com"
nameSpace := f.Namespace nameSpace := f.Namespace
@ -69,7 +69,7 @@ var _ = framework.DescribeAnnotation("modsecurity owasp", func() {
}) })
}) })
It("should disable modsecurity", func() { ginkgo.It("should disable modsecurity", func() {
host := "modsecurity.foo.com" host := "modsecurity.foo.com"
nameSpace := f.Namespace nameSpace := f.Namespace
@ -86,7 +86,7 @@ var _ = framework.DescribeAnnotation("modsecurity owasp", func() {
}) })
}) })
It("should enable modsecurity with snippet", func() { ginkgo.It("should enable modsecurity with snippet", func() {
host := "modsecurity.foo.com" host := "modsecurity.foo.com"
nameSpace := f.Namespace nameSpace := f.Namespace

View file

@ -19,8 +19,7 @@ package annotations
import ( import (
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -29,11 +28,11 @@ var _ = framework.DescribeAnnotation("proxy-*", func() {
f := framework.NewDefaultFramework("proxy") f := framework.NewDefaultFramework("proxy")
host := "proxy.foo.com" host := "proxy.foo.com"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeployment()
}) })
It("should set proxy_redirect to off", func() { ginkgo.It("should set proxy_redirect to off", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-redirect-from": "off", "nginx.ingress.kubernetes.io/proxy-redirect-from": "off",
"nginx.ingress.kubernetes.io/proxy-redirect-to": "goodbye.com", "nginx.ingress.kubernetes.io/proxy-redirect-to": "goodbye.com",
@ -44,11 +43,11 @@ var _ = framework.DescribeAnnotation("proxy-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("proxy_redirect off;")) return strings.Contains(server, "proxy_redirect off;")
}) })
}) })
It("should set proxy_redirect to default", func() { ginkgo.It("should set proxy_redirect to default", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-redirect-from": "default", "nginx.ingress.kubernetes.io/proxy-redirect-from": "default",
"nginx.ingress.kubernetes.io/proxy-redirect-to": "goodbye.com", "nginx.ingress.kubernetes.io/proxy-redirect-to": "goodbye.com",
@ -59,11 +58,11 @@ var _ = framework.DescribeAnnotation("proxy-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("proxy_redirect default;")) return strings.Contains(server, "proxy_redirect default;")
}) })
}) })
It("should set proxy_redirect to hello.com goodbye.com", func() { ginkgo.It("should set proxy_redirect to hello.com goodbye.com", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-redirect-from": "hello.com", "nginx.ingress.kubernetes.io/proxy-redirect-from": "hello.com",
"nginx.ingress.kubernetes.io/proxy-redirect-to": "goodbye.com", "nginx.ingress.kubernetes.io/proxy-redirect-to": "goodbye.com",
@ -74,11 +73,11 @@ var _ = framework.DescribeAnnotation("proxy-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("proxy_redirect hello.com goodbye.com;")) return strings.Contains(server, "proxy_redirect hello.com goodbye.com;")
}) })
}) })
It("should set proxy client-max-body-size to 8m", func() { ginkgo.It("should set proxy client-max-body-size to 8m", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-body-size": "8m", "nginx.ingress.kubernetes.io/proxy-body-size": "8m",
} }
@ -88,11 +87,11 @@ var _ = framework.DescribeAnnotation("proxy-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("client_max_body_size 8m;")) return strings.Contains(server, "client_max_body_size 8m;")
}) })
}) })
It("should not set proxy client-max-body-size to incorrect value", func() { ginkgo.It("should not set proxy client-max-body-size to incorrect value", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-body-size": "15r", "nginx.ingress.kubernetes.io/proxy-body-size": "15r",
} }
@ -102,11 +101,11 @@ var _ = framework.DescribeAnnotation("proxy-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).ShouldNot(ContainSubstring("client_max_body_size 15r;")) return !strings.Contains(server, "client_max_body_size 15r;")
}) })
}) })
It("should set valid proxy timeouts", func() { ginkgo.It("should set valid proxy timeouts", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-connect-timeout": "50", "nginx.ingress.kubernetes.io/proxy-connect-timeout": "50",
"nginx.ingress.kubernetes.io/proxy-send-timeout": "20", "nginx.ingress.kubernetes.io/proxy-send-timeout": "20",
@ -124,7 +123,7 @@ var _ = framework.DescribeAnnotation("proxy-*", func() {
}) })
}) })
It("should not set invalid proxy timeouts", func() { ginkgo.It("should not set invalid proxy timeouts", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-connect-timeout": "50k", "nginx.ingress.kubernetes.io/proxy-connect-timeout": "50k",
"nginx.ingress.kubernetes.io/proxy-send-timeout": "20k", "nginx.ingress.kubernetes.io/proxy-send-timeout": "20k",
@ -142,7 +141,7 @@ var _ = framework.DescribeAnnotation("proxy-*", func() {
}) })
}) })
It("should turn on proxy-buffering", func() { ginkgo.It("should turn on proxy-buffering", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-buffering": "on", "nginx.ingress.kubernetes.io/proxy-buffering": "on",
"nginx.ingress.kubernetes.io/proxy-buffers-number": "8", "nginx.ingress.kubernetes.io/proxy-buffers-number": "8",
@ -161,7 +160,7 @@ var _ = framework.DescribeAnnotation("proxy-*", func() {
}) })
}) })
It("should turn off proxy-request-buffering", func() { ginkgo.It("should turn off proxy-request-buffering", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-request-buffering": "off", "nginx.ingress.kubernetes.io/proxy-request-buffering": "off",
} }
@ -171,11 +170,11 @@ var _ = framework.DescribeAnnotation("proxy-*", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("proxy_request_buffering off;")) return strings.Contains(server, "proxy_request_buffering off;")
}) })
}) })
It("should build proxy next upstream", func() { ginkgo.It("should build proxy next upstream", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-next-upstream": "error timeout http_502", "nginx.ingress.kubernetes.io/proxy-next-upstream": "error timeout http_502",
"nginx.ingress.kubernetes.io/proxy-next-upstream-timeout": "999999", "nginx.ingress.kubernetes.io/proxy-next-upstream-timeout": "999999",
@ -193,7 +192,7 @@ var _ = framework.DescribeAnnotation("proxy-*", func() {
}) })
}) })
It("should build proxy next upstream using configmap values", func() { ginkgo.It("should build proxy next upstream using configmap values", func() {
annotations := map[string]string{} annotations := map[string]string{}
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
@ -212,7 +211,7 @@ var _ = framework.DescribeAnnotation("proxy-*", func() {
}) })
}) })
It("should setup proxy cookies", func() { ginkgo.It("should setup proxy cookies", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-cookie-domain": "localhost example.org", "nginx.ingress.kubernetes.io/proxy-cookie-domain": "localhost example.org",
"nginx.ingress.kubernetes.io/proxy-cookie-path": "/one/ /", "nginx.ingress.kubernetes.io/proxy-cookie-path": "/one/ /",
@ -228,7 +227,7 @@ var _ = framework.DescribeAnnotation("proxy-*", func() {
}) })
}) })
It("should change the default proxy HTTP version", func() { ginkgo.It("should change the default proxy HTTP version", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-http-version": "1.0", "nginx.ingress.kubernetes.io/proxy-http-version": "1.0",
} }

View file

@ -20,26 +20,27 @@ import (
"fmt" "fmt"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeAnnotation("proxy-ssl-*", func() { var _ = framework.DescribeAnnotation("proxy-ssl-*", func() {
f := framework.NewDefaultFramework("proxyssl") f := framework.NewDefaultFramework("proxyssl")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeployment()
}) })
It("should set valid proxy-ssl-secret", func() { ginkgo.It("should set valid proxy-ssl-secret", func() {
host := "proxyssl.foo.com" host := "proxyssl.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-ssl-secret": f.Namespace + "/" + host, "nginx.ingress.kubernetes.io/proxy-ssl-secret": f.Namespace + "/" + host,
} }
_, err := framework.CreateIngressMASecret(f.KubeClientSet, host, host, f.Namespace) _, err := framework.CreateIngressMASecret(f.KubeClientSet, host, host, f.Namespace)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
ing := framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
@ -47,7 +48,7 @@ var _ = framework.DescribeAnnotation("proxy-ssl-*", func() {
assertProxySSL(f, host, "DEFAULT", "TLSv1 TLSv1.1 TLSv1.2", "off", 1) assertProxySSL(f, host, "DEFAULT", "TLSv1 TLSv1.1 TLSv1.2", "off", 1)
}) })
It("should set valid proxy-ssl-secret, proxy-ssl-verify to on, and proxy-ssl-verify-depth to 2", func() { ginkgo.It("should set valid proxy-ssl-secret, proxy-ssl-verify to on, and proxy-ssl-verify-depth to 2", func() {
host := "proxyssl.foo.com" host := "proxyssl.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-ssl-secret": f.Namespace + "/" + host, "nginx.ingress.kubernetes.io/proxy-ssl-secret": f.Namespace + "/" + host,
@ -56,7 +57,7 @@ var _ = framework.DescribeAnnotation("proxy-ssl-*", func() {
} }
_, err := framework.CreateIngressMASecret(f.KubeClientSet, host, host, f.Namespace) _, err := framework.CreateIngressMASecret(f.KubeClientSet, host, host, f.Namespace)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
ing := framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
@ -64,7 +65,7 @@ var _ = framework.DescribeAnnotation("proxy-ssl-*", func() {
assertProxySSL(f, host, "DEFAULT", "TLSv1 TLSv1.1 TLSv1.2", "on", 2) assertProxySSL(f, host, "DEFAULT", "TLSv1 TLSv1.1 TLSv1.2", "on", 2)
}) })
It("should set valid proxy-ssl-secret, proxy-ssl-ciphers to HIGH:!AES", func() { ginkgo.It("should set valid proxy-ssl-secret, proxy-ssl-ciphers to HIGH:!AES", func() {
host := "proxyssl.foo.com" host := "proxyssl.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-ssl-secret": f.Namespace + "/" + host, "nginx.ingress.kubernetes.io/proxy-ssl-secret": f.Namespace + "/" + host,
@ -72,7 +73,7 @@ var _ = framework.DescribeAnnotation("proxy-ssl-*", func() {
} }
_, err := framework.CreateIngressMASecret(f.KubeClientSet, host, host, f.Namespace) _, err := framework.CreateIngressMASecret(f.KubeClientSet, host, host, f.Namespace)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
ing := framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
@ -80,7 +81,7 @@ var _ = framework.DescribeAnnotation("proxy-ssl-*", func() {
assertProxySSL(f, host, "HIGH:!AES", "TLSv1 TLSv1.1 TLSv1.2", "off", 1) assertProxySSL(f, host, "HIGH:!AES", "TLSv1 TLSv1.1 TLSv1.2", "off", 1)
}) })
It("should set valid proxy-ssl-secret, proxy-ssl-protocols", func() { ginkgo.It("should set valid proxy-ssl-secret, proxy-ssl-protocols", func() {
host := "proxyssl.foo.com" host := "proxyssl.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-ssl-secret": f.Namespace + "/" + host, "nginx.ingress.kubernetes.io/proxy-ssl-secret": f.Namespace + "/" + host,
@ -88,7 +89,7 @@ var _ = framework.DescribeAnnotation("proxy-ssl-*", func() {
} }
_, err := framework.CreateIngressMASecret(f.KubeClientSet, host, host, f.Namespace) _, err := framework.CreateIngressMASecret(f.KubeClientSet, host, host, f.Namespace)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
ing := framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)

View file

@ -22,29 +22,24 @@ import (
"strconv" "strconv"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
func noRedirectPolicyFunc(gorequest.Request, []gorequest.Request) error {
return http.ErrUseLastResponse
}
var _ = framework.DescribeAnnotation("permanen-redirect permanen-redirect-code", func() { var _ = framework.DescribeAnnotation("permanen-redirect permanen-redirect-code", func() {
f := framework.NewDefaultFramework("redirect") f := framework.NewDefaultFramework("redirect")
It("should respond with a standard redirect code", func() { ginkgo.It("should respond with a standard redirect code", func() {
By("setting permanent-redirect annotation") ginkgo.By("setting permanent-redirect annotation")
host := "redirect" host := "redirect"
redirectPath := "/something" redirectPath := "/something"
redirectURL := "http://redirect.example.com" redirectURL := "http://redirect.example.com"
annotations := map[string]string{"nginx.ingress.kubernetes.io/permanent-redirect": redirectURL} annotations := map[string]string{
"nginx.ingress.kubernetes.io/permanent-redirect": redirectURL,
}
ing := framework.NewSingleIngress(host, redirectPath, host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, redirectPath, host, f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
@ -55,22 +50,17 @@ var _ = framework.DescribeAnnotation("permanen-redirect permanen-redirect-code",
strings.Contains(server, fmt.Sprintf("return 301 %s;", redirectURL)) strings.Contains(server, fmt.Sprintf("return 301 %s;", redirectURL))
}) })
By("sending request to redirected URL path") ginkgo.By("sending request to redirected URL path")
f.HTTPTestClient().
resp, body, errs := gorequest.New(). GET(redirectPath).
Get(f.GetURL(framework.HTTP)+redirectPath). WithHeader("Host", host).
Set("Host", host). Expect().
RedirectPolicy(noRedirectPolicyFunc). Status(http.StatusMovedPermanently).
End() Header("Location").Equal(redirectURL)
Expect(errs).To(BeNil())
Expect(resp.StatusCode).Should(BeNumerically("==", http.StatusMovedPermanently))
Expect(resp.Header.Get("Location")).Should(Equal(redirectURL))
Expect(body).Should(ContainSubstring("nginx/"))
}) })
It("should respond with a custom redirect code", func() { ginkgo.It("should respond with a custom redirect code", func() {
By("setting permanent-redirect-code annotation") ginkgo.By("setting permanent-redirect-code annotation")
host := "redirect" host := "redirect"
redirectPath := "/something" redirectPath := "/something"
@ -91,17 +81,12 @@ var _ = framework.DescribeAnnotation("permanen-redirect permanen-redirect-code",
strings.Contains(server, fmt.Sprintf("return %d %s;", redirectCode, redirectURL)) strings.Contains(server, fmt.Sprintf("return %d %s;", redirectCode, redirectURL))
}) })
By("sending request to redirected URL path") ginkgo.By("sending request to redirected URL path")
f.HTTPTestClient().
resp, body, errs := gorequest.New(). GET(redirectPath).
Get(f.GetURL(framework.HTTP)+redirectPath). WithHeader("Host", host).
Set("Host", host). Expect().
RedirectPolicy(noRedirectPolicyFunc). Status(redirectCode).
End() Header("Location").Equal(redirectURL)
Expect(errs).To(BeNil())
Expect(resp.StatusCode).Should(BeNumerically("==", redirectCode))
Expect(resp.Header.Get("Location")).Should(Equal(redirectURL))
Expect(body).Should(ContainSubstring("nginx/"))
}) })
}) })

View file

@ -21,10 +21,8 @@ import (
"net/http" "net/http"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -32,12 +30,12 @@ import (
var _ = framework.DescribeAnnotation("rewrite-target use-regex enable-rewrite-log", func() { var _ = framework.DescribeAnnotation("rewrite-target use-regex enable-rewrite-log", func() {
f := framework.NewDefaultFramework("rewrite") f := framework.NewDefaultFramework("rewrite")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
It("should write rewrite logs", func() { ginkgo.It("should write rewrite logs", func() {
By("setting enable-rewrite-log annotation") ginkgo.By("setting enable-rewrite-log annotation")
host := "rewrite.bar.com" host := "rewrite.bar.com"
annotations := map[string]string{ annotations := map[string]string{
@ -53,24 +51,22 @@ var _ = framework.DescribeAnnotation("rewrite-target use-regex enable-rewrite-lo
return strings.Contains(server, "rewrite_log on;") return strings.Contains(server, "rewrite_log on;")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+"/something"). GET("/something").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK)
Expect(len(errs)).Should(Equal(0))
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
logs, err := f.NginxLogs() logs, err := f.NginxLogs()
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
Expect(logs).To(ContainSubstring(`"(?i)/something" matches "/something", client:`)) assert.Contains(ginkgo.GinkgoT(), logs, `"(?i)/something" matches "/something", client:`)
Expect(logs).To(ContainSubstring(`rewritten data: "/", args: "",`)) assert.Contains(ginkgo.GinkgoT(), logs, `rewritten data: "/", args: "",`)
}) })
It("should use correct longest path match", func() { ginkgo.It("should use correct longest path match", func() {
host := "rewrite.bar.com" host := "rewrite.bar.com"
By("creating a regular ingress definition") ginkgo.By("creating a regular ingress definition")
ing := framework.NewSingleIngress("kube-lego", "/.well-known/acme/challenge", host, f.Namespace, framework.EchoService, 80, nil) ing := framework.NewSingleIngress("kube-lego", "/.well-known/acme/challenge", host, f.Namespace, framework.EchoService, 80, nil)
f.EnsureIngress(ing) f.EnsureIngress(ing)
@ -79,17 +75,17 @@ var _ = framework.DescribeAnnotation("rewrite-target use-regex enable-rewrite-lo
return strings.Contains(server, "/.well-known/acme/challenge") return strings.Contains(server, "/.well-known/acme/challenge")
}) })
By("making a request to the non-rewritten location") ginkgo.By("making a request to the non-rewritten location")
resp, body, errs := gorequest.New().
Get(f.GetURL(framework.HTTP)+"/.well-known/acme/challenge").
Set("Host", host).
End()
expectBodyRequestURI := fmt.Sprintf("request_uri=http://%v:80/.well-known/acme/challenge", host) expectBodyRequestURI := fmt.Sprintf("request_uri=http://%v:80/.well-known/acme/challenge", host)
Expect(len(errs)).Should(Equal(0))
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(expectBodyRequestURI))
By(`creating an ingress definition with the rewrite-target annotation set on the "/" location`) f.HTTPTestClient().
GET("/.well-known/acme/challenge").
WithHeader("Host", host).
Expect().
Status(http.StatusOK).
Body().Contains(expectBodyRequestURI)
ginkgo.By(`creating an ingress definition with the rewrite-target annotation set on the "/" location`)
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/rewrite-target": "/new/backend", "nginx.ingress.kubernetes.io/rewrite-target": "/new/backend",
} }
@ -102,20 +98,19 @@ var _ = framework.DescribeAnnotation("rewrite-target use-regex enable-rewrite-lo
return strings.Contains(server, `location ~* "^/" {`) && strings.Contains(server, `location ~* "^/.well-known/acme/challenge" {`) return strings.Contains(server, `location ~* "^/" {`) && strings.Contains(server, `location ~* "^/.well-known/acme/challenge" {`)
}) })
By("making a second request to the non-rewritten location") ginkgo.By("making a second request to the non-rewritten location")
resp, body, errs = gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+"/.well-known/acme/challenge"). GET("/.well-known/acme/challenge").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(len(errs)).Should(Equal(0)) Status(http.StatusOK).
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) Body().Contains(expectBodyRequestURI)
Expect(body).Should(ContainSubstring(expectBodyRequestURI))
}) })
It("should use ~* location modifier if regex annotation is present", func() { ginkgo.It("should use ~* location modifier if regex annotation is present", func() {
host := "rewrite.bar.com" host := "rewrite.bar.com"
By("creating a regular ingress definition") ginkgo.By("creating a regular ingress definition")
ing := framework.NewSingleIngress("foo", "/foo", host, f.Namespace, framework.EchoService, 80, nil) ing := framework.NewSingleIngress("foo", "/foo", host, f.Namespace, framework.EchoService, 80, nil)
f.EnsureIngress(ing) f.EnsureIngress(ing)
@ -124,7 +119,7 @@ var _ = framework.DescribeAnnotation("rewrite-target use-regex enable-rewrite-lo
return strings.Contains(server, "location /foo {") return strings.Contains(server, "location /foo {")
}) })
By(`creating an ingress definition with the use-regex amd rewrite-target annotation`) ginkgo.By(`creating an ingress definition with the use-regex amd rewrite-target annotation`)
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/use-regex": "true", "nginx.ingress.kubernetes.io/use-regex": "true",
"nginx.ingress.kubernetes.io/rewrite-target": "/new/backend", "nginx.ingress.kubernetes.io/rewrite-target": "/new/backend",
@ -137,35 +132,35 @@ var _ = framework.DescribeAnnotation("rewrite-target use-regex enable-rewrite-lo
return strings.Contains(server, `location ~* "^/foo" {`) && strings.Contains(server, `location ~* "^/foo.+" {`) return strings.Contains(server, `location ~* "^/foo" {`) && strings.Contains(server, `location ~* "^/foo.+" {`)
}) })
By("ensuring '/foo' matches '~* ^/foo'") ginkgo.By("ensuring '/foo' matches '~* ^/foo'")
resp, body, errs := gorequest.New().
Get(f.GetURL(framework.HTTP)+"/foo").
Set("Host", host).
End()
expectBodyRequestURI := fmt.Sprintf("request_uri=http://%v:80/foo", host) expectBodyRequestURI := fmt.Sprintf("request_uri=http://%v:80/foo", host)
Expect(len(errs)).Should(Equal(0))
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(expectBodyRequestURI))
By("ensuring '/foo/bar' matches '~* ^/foo.+'") f.HTTPTestClient().
resp, body, errs = gorequest.New(). GET("/foo").
Get(f.GetURL(framework.HTTP)+"/foo/bar"). WithHeader("Host", host).
Set("Host", host). Expect().
End() Status(http.StatusOK).
Body().Contains(expectBodyRequestURI)
ginkgo.By("ensuring '/foo/bar' matches '~* ^/foo.+'")
expectBodyRequestURI = fmt.Sprintf("request_uri=http://%v:80/new/backend", host) expectBodyRequestURI = fmt.Sprintf("request_uri=http://%v:80/new/backend", host)
Expect(len(errs)).Should(Equal(0))
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) f.HTTPTestClient().
Expect(body).Should(ContainSubstring(expectBodyRequestURI)) GET("/foo/bar").
WithHeader("Host", host).
Expect().
Status(http.StatusOK).
Body().Contains(expectBodyRequestURI)
}) })
It("should fail to use longest match for documented warning", func() { ginkgo.It("should fail to use longest match for documented warning", func() {
host := "rewrite.bar.com" host := "rewrite.bar.com"
By("creating a regular ingress definition") ginkgo.By("creating a regular ingress definition")
ing := framework.NewSingleIngress("foo", "/foo/bar/bar", host, f.Namespace, framework.EchoService, 80, nil) ing := framework.NewSingleIngress("foo", "/foo/bar/bar", host, f.Namespace, framework.EchoService, 80, nil)
f.EnsureIngress(ing) f.EnsureIngress(ing)
By(`creating an ingress definition with the use-regex annotation`) ginkgo.By(`creating an ingress definition with the use-regex annotation`)
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/use-regex": "true", "nginx.ingress.kubernetes.io/use-regex": "true",
"nginx.ingress.kubernetes.io/rewrite-target": "/new/backend", "nginx.ingress.kubernetes.io/rewrite-target": "/new/backend",
@ -175,24 +170,25 @@ var _ = framework.DescribeAnnotation("rewrite-target use-regex enable-rewrite-lo
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return strings.Contains(server, `location ~* "^/foo/bar/bar" {`) && strings.Contains(server, `location ~* "^/foo/bar/[a-z]{3}" {`) return strings.Contains(server, `location ~* "^/foo/bar/bar" {`) &&
strings.Contains(server, `location ~* "^/foo/bar/[a-z]{3}" {`)
}) })
By("check that '/foo/bar/bar' does not match the longest exact path") ginkgo.By("check that '/foo/bar/bar' does not match the longest exact path")
resp, body, errs := gorequest.New().
Get(f.GetURL(framework.HTTP)+"/foo/bar/bar").
Set("Host", host).
End()
expectBodyRequestURI := fmt.Sprintf("request_uri=http://%v:80/new/backend", host) expectBodyRequestURI := fmt.Sprintf("request_uri=http://%v:80/new/backend", host)
Expect(len(errs)).Should(Equal(0))
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) f.HTTPTestClient().
Expect(body).Should(ContainSubstring(expectBodyRequestURI)) GET("/foo/bar/bar").
WithHeader("Host", host).
Expect().
Status(http.StatusOK).
Body().Contains(expectBodyRequestURI)
}) })
It("should allow for custom rewrite parameters", func() { ginkgo.It("should allow for custom rewrite parameters", func() {
host := "rewrite.bar.com" host := "rewrite.bar.com"
By(`creating an ingress definition with the use-regex annotation`) ginkgo.By(`creating an ingress definition with the use-regex annotation`)
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/use-regex": "true", "nginx.ingress.kubernetes.io/use-regex": "true",
"nginx.ingress.kubernetes.io/rewrite-target": "/new/backend/$1", "nginx.ingress.kubernetes.io/rewrite-target": "/new/backend/$1",
@ -205,15 +201,14 @@ var _ = framework.DescribeAnnotation("rewrite-target use-regex enable-rewrite-lo
return strings.Contains(server, `location ~* "^/foo/bar/(.+)" {`) return strings.Contains(server, `location ~* "^/foo/bar/(.+)" {`)
}) })
By("check that '/foo/bar/bar' redirects to custom rewrite") ginkgo.By("check that '/foo/bar/bar' redirects to custom rewrite")
resp, body, errs := gorequest.New().
Get(f.GetURL(framework.HTTP)+"/foo/bar/bar").
Set("Host", host).
End()
expectBodyRequestURI := fmt.Sprintf("request_uri=http://%v:80/new/backend/bar", host) expectBodyRequestURI := fmt.Sprintf("request_uri=http://%v:80/new/backend/bar", host)
Expect(len(errs)).Should(Equal(0))
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(expectBodyRequestURI))
})
f.HTTPTestClient().
GET("/foo/bar/bar").
WithHeader("Host", host).
Expect().
Status(http.StatusOK).
Body().Contains(expectBodyRequestURI)
})
}) })

View file

@ -20,24 +20,25 @@ import (
"fmt" "fmt"
"net/http" "net/http"
"net/url" "net/url"
"time" "strings"
"github.com/onsi/ginkgo"
"github.com/stretchr/testify/assert"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"github.com/parnurzeal/gorequest"
networking "k8s.io/api/networking/v1beta1" networking "k8s.io/api/networking/v1beta1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeAnnotation("satisfy", func() { var _ = framework.DescribeAnnotation("satisfy", func() {
f := framework.NewDefaultFramework("satisfy") f := framework.NewDefaultFramework("satisfy")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
It("should configure satisfy directive correctly", func() { ginkgo.It("should configure satisfy directive correctly", func() {
host := "satisfy" host := "satisfy"
annotationKey := "nginx.ingress.kubernetes.io/satisfy" annotationKey := "nginx.ingress.kubernetes.io/satisfy"
@ -63,36 +64,33 @@ var _ = framework.DescribeAnnotation("satisfy", func() {
ingress.ObjectMeta.Annotations[annotationKey] = annotations[key] ingress.ObjectMeta.Annotations[annotationKey] = annotations[key]
return nil return nil
}) })
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring(result)) return strings.Contains(server, result)
}) })
resp, body, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
Set("Host", host). Expect().
End() Status(http.StatusOK).
Body().Contains(fmt.Sprintf("host=%v", host))
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(fmt.Sprintf("host=%v", host)))
} }
}) })
It("should allow multiple auth with satisfy any", func() { ginkgo.It("should allow multiple auth with satisfy any", func() {
host := "auth" host := "auth"
// setup external auth // setup external auth
f.NewHttpbinDeployment() f.NewHttpbinDeployment()
err := framework.WaitForEndpoints(f.KubeClientSet, framework.DefaultTimeout, framework.HTTPBinService, f.Namespace, 1) err := framework.WaitForEndpoints(f.KubeClientSet, framework.DefaultTimeout, framework.HTTPBinService, f.Namespace, 1)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
e, err := f.KubeClientSet.CoreV1().Endpoints(f.Namespace).Get(framework.HTTPBinService, metav1.GetOptions{}) e, err := f.KubeClientSet.CoreV1().Endpoints(f.Namespace).Get(framework.HTTPBinService, metav1.GetOptions{})
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
httpbinIP := e.Subsets[0].Addresses[0].IP httpbinIP := e.Subsets[0].Addresses[0].IP
@ -117,30 +115,25 @@ var _ = framework.DescribeAnnotation("satisfy", func() {
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxServer(host, func(server string) bool { f.WaitForNginxServer(host, func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name auth")) return strings.Contains(server, "server_name auth")
}) })
// with basic auth cred // with basic auth cred
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
Set("Host", host). WithBasicAuth("uname", "pwd").
SetBasicAuth("uname", "pwd").End() Expect().
Status(http.StatusOK)
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
// reroute to signin if without basic cred // reroute to signin if without basic cred
resp, _, errs = gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
Set("Host", host). WithQuery("a", "b").
RedirectPolicy(func(req gorequest.Request, via []gorequest.Request) error { WithQuery("c", "d").
return http.ErrUseLastResponse Expect().
}).Param("a", "b").Param("c", "d"). Status(http.StatusFound).
End() Header("Location").Equal(fmt.Sprintf("http://%s/auth/start?rd=http://%s%s", host, host, url.QueryEscape("/?a=b&c=d")))
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusFound))
Expect(resp.Header.Get("Location")).Should(Equal(fmt.Sprintf("http://%s/auth/start?rd=http://%s%s", host, host, url.QueryEscape("/?a=b&c=d"))))
}) })
}) })

View file

@ -28,7 +28,7 @@ var _ = framework.DescribeAnnotation("server-snippet", func() {
f := framework.NewDefaultFramework("serversnippet") f := framework.NewDefaultFramework("serversnippet")
BeforeEach(func() { BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeployment()
}) })
It(`add valid directives to server via server snippet"`, func() { It(`add valid directives to server via server snippet"`, func() {
@ -44,7 +44,8 @@ var _ = framework.DescribeAnnotation("server-snippet", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return strings.Contains(server, `more_set_headers "Content-Length: $content_length`) && strings.Contains(server, `more_set_headers "Content-Type: $content_type";`) return strings.Contains(server, `more_set_headers "Content-Length: $content_length`) &&
strings.Contains(server, `more_set_headers "Content-Type: $content_type";`)
}) })
}) })
}) })

View file

@ -17,19 +17,21 @@ limitations under the License.
package annotations package annotations
import ( import (
. "github.com/onsi/ginkgo" "strings"
. "github.com/onsi/gomega"
"github.com/onsi/ginkgo"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeAnnotation("configuration-snippet", func() { var _ = framework.DescribeAnnotation("configuration-snippet", func() {
f := framework.NewDefaultFramework("configurationsnippet") f := framework.NewDefaultFramework("configurationsnippet")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeployment()
}) })
It(`set snippet "more_set_headers "Request-Id: $req_id";" in all locations"`, func() { ginkgo.It(`set snippet "more_set_headers "Request-Id: $req_id";" in all locations"`, func() {
host := "configurationsnippet.foo.com" host := "configurationsnippet.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/configuration-snippet": ` "nginx.ingress.kubernetes.io/configuration-snippet": `
@ -41,7 +43,7 @@ var _ = framework.DescribeAnnotation("configuration-snippet", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring(`more_set_headers "Request-Id: $req_id";`)) return strings.Contains(server, `more_set_headers "Request-Id: $req_id";`)
}) })
}) })
}) })

View file

@ -17,8 +17,9 @@ limitations under the License.
package annotations package annotations
import ( import (
. "github.com/onsi/ginkgo" "strings"
. "github.com/onsi/gomega"
"github.com/onsi/ginkgo"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -26,11 +27,11 @@ import (
var _ = framework.DescribeAnnotation("ssl-ciphers", func() { var _ = framework.DescribeAnnotation("ssl-ciphers", func() {
f := framework.NewDefaultFramework("sslciphers") f := framework.NewDefaultFramework("sslciphers")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeployment()
}) })
It("should change ssl ciphers", func() { ginkgo.It("should change ssl ciphers", func() {
host := "ciphers.foo.com" host := "ciphers.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/ssl-ciphers": "ALL:!aNULL:!EXPORT56:RC4+RSA:+HIGH:+MEDIUM:+LOW:+SSLv2:+EXP", "nginx.ingress.kubernetes.io/ssl-ciphers": "ALL:!aNULL:!EXPORT56:RC4+RSA:+HIGH:+MEDIUM:+LOW:+SSLv2:+EXP",
@ -41,7 +42,7 @@ var _ = framework.DescribeAnnotation("ssl-ciphers", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("ssl_ciphers ALL:!aNULL:!EXPORT56:RC4+RSA:+HIGH:+MEDIUM:+LOW:+SSLv2:+EXP;")) return strings.Contains(server, "ssl_ciphers ALL:!aNULL:!EXPORT56:RC4+RSA:+HIGH:+MEDIUM:+LOW:+SSLv2:+EXP;")
}) })
}) })
}) })

View file

@ -22,9 +22,8 @@ import (
"regexp" "regexp"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
"k8s.io/apimachinery/pkg/util/wait" "k8s.io/apimachinery/pkg/util/wait"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
@ -41,32 +40,34 @@ func startIngress(f *framework.Framework, annotations map[string]string) map[str
}) })
err := wait.PollImmediate(framework.Poll, framework.DefaultTimeout, func() (bool, error) { err := wait.PollImmediate(framework.Poll, framework.DefaultTimeout, func() (bool, error) {
resp, _, _ := gorequest.New().
Get(f.GetURL(framework.HTTP)). resp := f.HTTPTestClient().
Set("Host", host). GET("/").
End() WithHeader("Host", host).
Expect().Raw()
if resp.StatusCode == http.StatusOK { if resp.StatusCode == http.StatusOK {
return true, nil return true, nil
} }
return false, nil return false, nil
}) })
Expect(err).Should(BeNil())
assert.Nil(ginkgo.GinkgoT(), err)
re, _ := regexp.Compile(fmt.Sprintf(`Hostname: %v.*`, framework.EchoService)) re, _ := regexp.Compile(fmt.Sprintf(`Hostname: %v.*`, framework.EchoService))
podMap := map[string]bool{} podMap := map[string]bool{}
for i := 0; i < 100; i++ { for i := 0; i < 100; i++ {
_, body, errs := gorequest.New(). data := f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Body().Raw()
Expect(errs).Should(BeEmpty()) podName := re.FindString(data)
assert.NotEmpty(ginkgo.GinkgoT(), podName, "expected a pod name")
podName := re.FindString(body)
Expect(podName).ShouldNot(Equal(""))
podMap[podName] = true podMap[podName] = true
} }
return podMap return podMap
@ -75,21 +76,20 @@ func startIngress(f *framework.Framework, annotations map[string]string) map[str
var _ = framework.DescribeAnnotation("upstream-hash-by-*", func() { var _ = framework.DescribeAnnotation("upstream-hash-by-*", func() {
f := framework.NewDefaultFramework("upstream-hash-by") f := framework.NewDefaultFramework("upstream-hash-by")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(6) f.NewEchoDeploymentWithReplicas(6)
}) })
It("should connect to the same pod", func() { ginkgo.It("should connect to the same pod", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/upstream-hash-by": "$request_uri", "nginx.ingress.kubernetes.io/upstream-hash-by": "$request_uri",
} }
podMap := startIngress(f, annotations) podMap := startIngress(f, annotations)
Expect(len(podMap)).Should(Equal(1)) assert.Equal(ginkgo.GinkgoT(), len(podMap), 1)
}) })
It("should connect to the same subset of pods", func() { ginkgo.It("should connect to the same subset of pods", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/upstream-hash-by": "$request_uri", "nginx.ingress.kubernetes.io/upstream-hash-by": "$request_uri",
"nginx.ingress.kubernetes.io/upstream-hash-by-subset": "true", "nginx.ingress.kubernetes.io/upstream-hash-by-subset": "true",
@ -97,6 +97,6 @@ var _ = framework.DescribeAnnotation("upstream-hash-by-*", func() {
} }
podMap := startIngress(f, annotations) podMap := startIngress(f, annotations)
Expect(len(podMap)).Should(Equal(3)) assert.Equal(ginkgo.GinkgoT(), len(podMap), 3)
}) })
}) })

View file

@ -17,19 +17,21 @@ limitations under the License.
package annotations package annotations
import ( import (
. "github.com/onsi/ginkgo" "strings"
. "github.com/onsi/gomega"
"github.com/onsi/ginkgo"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeAnnotation("upstream-vhost", func() { var _ = framework.DescribeAnnotation("upstream-vhost", func() {
f := framework.NewDefaultFramework("upstreamvhost") f := framework.NewDefaultFramework("upstreamvhost")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(2) f.NewEchoDeployment()
}) })
It("set host to upstreamvhost.bar.com", func() { ginkgo.It("set host to upstreamvhost.bar.com", func() {
host := "upstreamvhost.foo.com" host := "upstreamvhost.foo.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/upstream-vhost": "upstreamvhost.bar.com", "nginx.ingress.kubernetes.io/upstream-vhost": "upstreamvhost.bar.com",
@ -40,7 +42,7 @@ var _ = framework.DescribeAnnotation("upstream-vhost", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring(`proxy_set_header Host "upstreamvhost.bar.com";`)) return strings.Contains(server, `proxy_set_header Host "upstreamvhost.bar.com";`)
}) })
}) })
}) })

View file

@ -18,21 +18,21 @@ package annotations
import ( import (
"net/http" "net/http"
"strings"
"github.com/onsi/ginkgo"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeAnnotation("x-forwarded-prefix", func() { var _ = framework.DescribeAnnotation("x-forwarded-prefix", func() {
f := framework.NewDefaultFramework("xforwardedprefix") f := framework.NewDefaultFramework("xforwardedprefix")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
It("should set the X-Forwarded-Prefix to the annotation value", func() { ginkgo.It("should set the X-Forwarded-Prefix to the annotation value", func() {
host := "xfp.baz.com" host := "xfp.baz.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/x-forwarded-prefix": "/test/value", "nginx.ingress.kubernetes.io/x-forwarded-prefix": "/test/value",
@ -42,21 +42,19 @@ var _ = framework.DescribeAnnotation("x-forwarded-prefix", func() {
f.EnsureIngress(framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations)) f.EnsureIngress(framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations))
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("proxy_set_header X-Forwarded-Prefix \"/test/value\";")) return strings.Contains(server, host) &&
strings.Contains(server, "proxy_set_header X-Forwarded-Prefix \"/test/value\";")
}) })
uri := "/" f.HTTPTestClient().
resp, body, errs := gorequest.New(). GET("/").
Get(f.GetURL(framework.HTTP)+uri). WithHeader("Host", host).
Set("Host", host). Expect().
End() Status(http.StatusOK).
Body().Contains("x-forwarded-prefix=/test/value")
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).To(ContainSubstring("x-forwarded-prefix=/test/value"))
}) })
It("should not add X-Forwarded-Prefix if the annotation value is empty", func() { ginkgo.It("should not add X-Forwarded-Prefix if the annotation value is empty", func() {
host := "noxfp.baz.com" host := "noxfp.baz.com"
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/x-forwarded-prefix": "", "nginx.ingress.kubernetes.io/x-forwarded-prefix": "",
@ -66,17 +64,15 @@ var _ = framework.DescribeAnnotation("x-forwarded-prefix", func() {
f.EnsureIngress(framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations)) f.EnsureIngress(framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations))
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(And(ContainSubstring(host), Not(ContainSubstring("proxy_set_header X-Forwarded-Prefix")))) return strings.Contains(server, host) &&
!strings.Contains(server, "proxy_set_header X-Forwarded-Prefix")
}) })
uri := "/" f.HTTPTestClient().
resp, body, errs := gorequest.New(). GET("/").
Get(f.GetURL(framework.HTTP)+uri). WithHeader("Host", host).
Set("Host", host). Expect().
End() Status(http.StatusOK).
Body().NotContains("x-forwarded-prefix")
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).To(Not(ContainSubstring("x-forwarded-prefix")))
}) })
}) })

View file

@ -20,8 +20,8 @@ import (
"encoding/json" "encoding/json"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -30,60 +30,59 @@ var _ = framework.IngressNginxDescribe("Debug CLI", func() {
f := framework.NewDefaultFramework("debug-tool") f := framework.NewDefaultFramework("debug-tool")
host := "foo.com" host := "foo.com"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeployment()
}) })
It("should list the backend servers", func() { ginkgo.It("should list the backend servers", func() {
annotations := map[string]string{} annotations := map[string]string{}
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxConfiguration(func(cfg string) bool { f.WaitForNginxConfiguration(func(cfg string) bool {
return Expect(cfg).Should(ContainSubstring(host)) return strings.Contains(cfg, host)
}) })
cmd := "/dbg backends list" cmd := "/dbg backends list"
output, err := f.ExecIngressPod(cmd) output, err := f.ExecIngressPod(cmd)
Expect(err).Should(BeNil()) assert.Nil(ginkgo.GinkgoT(), err)
// Should be 2: the default and the echo deployment // Should be 2: the default and the echo deployment
numUpstreams := len(strings.Split(strings.Trim(string(output), "\n"), "\n")) numUpstreams := len(strings.Split(strings.Trim(string(output), "\n"), "\n"))
Expect(numUpstreams).Should(Equal(2)) assert.Equal(ginkgo.GinkgoT(), numUpstreams, 2)
}) })
It("should get information for a specific backend server", func() { ginkgo.It("should get information for a specific backend server", func() {
annotations := map[string]string{} annotations := map[string]string{}
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
f.WaitForNginxConfiguration(func(cfg string) bool { f.WaitForNginxConfiguration(func(cfg string) bool {
return Expect(cfg).Should(ContainSubstring(host)) return strings.Contains(cfg, host)
}) })
cmd := "/dbg backends list" cmd := "/dbg backends list"
output, err := f.ExecIngressPod(cmd) output, err := f.ExecIngressPod(cmd)
Expect(err).Should(BeNil()) assert.Nil(ginkgo.GinkgoT(), err)
backends := strings.Split(string(output), "\n") backends := strings.Split(string(output), "\n")
Expect(len(backends)).Should(BeNumerically(">", 0)) assert.Greater(ginkgo.GinkgoT(), len(backends), 0)
getCmd := "/dbg backends get " + backends[0] getCmd := "/dbg backends get " + backends[0]
output, err = f.ExecIngressPod(getCmd) output, err = f.ExecIngressPod(getCmd)
Expect(err).Should(BeNil()) assert.Nil(ginkgo.GinkgoT(), err)
var f map[string]interface{} var f map[string]interface{}
unmarshalErr := json.Unmarshal([]byte(output), &f) err = json.Unmarshal([]byte(output), &f)
Expect(unmarshalErr).Should(BeNil()) assert.Nil(ginkgo.GinkgoT(), err)
// Check that the backend we've gotten has the same name as the one we requested // Check that the backend we've gotten has the same name as the one we requested
Expect(backends[0]).Should(Equal(f["name"].(string))) assert.Equal(ginkgo.GinkgoT(), backends[0], f["name"].(string))
}) })
It("should produce valid JSON for /dbg general", func() { ginkgo.It("should produce valid JSON for /dbg general", func() {
annotations := map[string]string{} annotations := map[string]string{}
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, annotations)
@ -91,10 +90,10 @@ var _ = framework.IngressNginxDescribe("Debug CLI", func() {
cmd := "/dbg general" cmd := "/dbg general"
output, err := f.ExecIngressPod(cmd) output, err := f.ExecIngressPod(cmd)
Expect(err).Should(BeNil()) assert.Nil(ginkgo.GinkgoT(), err)
var f interface{} var f interface{}
unmarshalErr := json.Unmarshal([]byte(output), &f) err = json.Unmarshal([]byte(output), &f)
Expect(unmarshalErr).Should(BeNil()) assert.Nil(ginkgo.GinkgoT(), err)
}) })
}) })

View file

@ -22,11 +22,8 @@ import (
"strings" "strings"
"time" "time"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
appsv1 "k8s.io/api/apps/v1" appsv1 "k8s.io/api/apps/v1"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
@ -35,8 +32,8 @@ import (
var _ = framework.IngressNginxDescribe("[Default Backend] custom service", func() { var _ = framework.IngressNginxDescribe("[Default Backend] custom service", func() {
f := framework.NewDefaultFramework("custom-default-backend") f := framework.NewDefaultFramework("custom-default-backend")
BeforeEach(func() { ginkgo.It("uses custom default backend that returns 200 as status code", func() {
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeployment()
err := framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1, err := framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1,
func(deployment *appsv1.Deployment) error { func(deployment *appsv1.Deployment) error {
@ -44,21 +41,21 @@ var _ = framework.IngressNginxDescribe("[Default Backend] custom service", func(
args = append(args, fmt.Sprintf("--default-backend-service=%v/%v", f.Namespace, framework.EchoService)) args = append(args, fmt.Sprintf("--default-backend-service=%v/%v", f.Namespace, framework.EchoService))
deployment.Spec.Template.Spec.Containers[0].Args = args deployment.Spec.Template.Spec.Containers[0].Args = args
_, err := f.KubeClientSet.AppsV1().Deployments(f.Namespace).Update(deployment) _, err := f.KubeClientSet.AppsV1().Deployments(f.Namespace).Update(deployment)
time.Sleep(5 * time.Second)
return err return err
}) })
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err, "updating deployment")
time.Sleep(5 * time.Second) time.Sleep(5 * time.Second)
f.WaitForNginxServer("_", f.WaitForNginxServer("_",
func(server string) bool { func(server string) bool {
return strings.Contains(server, `set $proxy_upstream_name "upstream-default-backend"`) return strings.Contains(server, `set $proxy_upstream_name "upstream-default-backend"`)
}) })
})
It("uses custom default backend", func() { f.HTTPTestClient().
resp, _, errs := gorequest.New().Get(f.GetURL(framework.HTTP)).End() GET("/").
Expect(errs).Should(BeEmpty()) Expect().
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) Status(http.StatusOK)
}) })
}) })

View file

@ -17,12 +17,11 @@ limitations under the License.
package defaultbackend package defaultbackend
import ( import (
"crypto/tls"
"net/http" "net/http"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest" "gopkg.in/gavv/httpexpect.v2"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -30,7 +29,7 @@ import (
var _ = framework.IngressNginxDescribe("[Default Backend]", func() { var _ = framework.IngressNginxDescribe("[Default Backend]", func() {
f := framework.NewDefaultFramework("default-backend") f := framework.NewDefaultFramework("default-backend")
It("should return 404 sending requests when only a default backend is running", func() { ginkgo.It("should return 404 sending requests when only a default backend is running", func() {
testCases := []struct { testCases := []struct {
Name string Name string
Host string Host string
@ -61,65 +60,55 @@ var _ = framework.IngressNginxDescribe("[Default Backend]", func() {
} }
for _, test := range testCases { for _, test := range testCases {
By(test.Name) ginkgo.By(test.Name)
request := gorequest.New() var req *httpexpect.Request
var cm *gorequest.SuperAgent
switch test.Scheme { switch test.Scheme {
case framework.HTTP: case framework.HTTP:
cm = request.CustomMethod(test.Method, f.GetURL(framework.HTTP)) req = f.HTTPTestClient().Request(test.Method, test.Path)
req.WithURL(f.GetURL(framework.HTTP) + test.Path)
case framework.HTTPS: case framework.HTTPS:
cm = request.CustomMethod(test.Method, f.GetURL(framework.HTTPS)) req = f.HTTPTestClient().Request(test.Method, test.Path)
// the default backend uses a self generated certificate req.WithURL(f.GetURL(framework.HTTPS) + test.Path)
cm.Transport = &http.Transport{
TLSClientConfig: &tls.Config{
InsecureSkipVerify: true,
},
}
default: default:
Fail("Unexpected request scheme") ginkgo.Fail("Unexpected request scheme")
} }
if test.Host != "" { if test.Host != "" {
cm.Set("Host", test.Host) req.WithHeader("Host", test.Host)
} }
resp, _, errs := cm.End() req.Expect().
Expect(errs).Should(BeEmpty()) Status(test.Status)
Expect(resp.StatusCode).Should(Equal(test.Status))
} }
}) })
It("enables access logging for default backend", func() { ginkgo.It("enables access logging for default backend", func() {
f.UpdateNginxConfigMapData("enable-access-log-for-default-backend", "true") f.UpdateNginxConfigMapData("enable-access-log-for-default-backend", "true")
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+"/somethingOne"). GET("/somethingOne").
Set("Host", "foo"). WithHeader("Host", "foo").
End() Expect().
Status(http.StatusNotFound)
Expect(len(errs)).Should(Equal(0))
Expect(resp.StatusCode).Should(Equal(http.StatusNotFound))
logs, err := f.NginxLogs() logs, err := f.NginxLogs()
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err, "obtaining nginx logs")
Expect(logs).To(ContainSubstring("/somethingOne")) assert.Contains(ginkgo.GinkgoT(), logs, "/somethingOne")
}) })
It("disables access logging for default backend", func() { ginkgo.It("disables access logging for default backend", func() {
f.UpdateNginxConfigMapData("enable-access-log-for-default-backend", "false") f.UpdateNginxConfigMapData("enable-access-log-for-default-backend", "false")
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+"/somethingTwo"). GET("/somethingTwo").
Set("Host", "bar"). WithHeader("Host", "bar").
End() Expect().
Status(http.StatusNotFound)
Expect(len(errs)).Should(Equal(0))
Expect(resp.StatusCode).Should(Equal(http.StatusNotFound))
logs, err := f.NginxLogs() logs, err := f.NginxLogs()
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err, "obtaining nginx logs")
Expect(logs).ToNot(ContainSubstring("/somethingTwo")) assert.NotContains(ginkgo.GinkgoT(), logs, "/somethingTwo")
}) })
}) })

View file

@ -17,11 +17,8 @@ limitations under the License.
package defaultbackend package defaultbackend
import ( import (
"crypto/tls" "github.com/onsi/ginkgo"
"github.com/stretchr/testify/assert"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -29,35 +26,31 @@ import (
var _ = framework.IngressNginxDescribe("[Default Backend] SSL", func() { var _ = framework.IngressNginxDescribe("[Default Backend] SSL", func() {
f := framework.NewDefaultFramework("default-backend") f := framework.NewDefaultFramework("default-backend")
It("should return a self generated SSL certificate", func() { ginkgo.It("should return a self generated SSL certificate", func() {
By("checking SSL Certificate using the NGINX IP address") ginkgo.By("checking SSL Certificate using the NGINX IP address")
resp, _, errs := gorequest.New(). resp := f.HTTPTestClient().
Post(f.GetURL(framework.HTTPS)). GET("/").
TLSClientConfig(&tls.Config{ WithURL(f.GetURL(framework.HTTPS)).
// the default backend uses a self generated certificate Expect().
InsecureSkipVerify: true, Raw()
}).End()
Expect(errs).Should(BeEmpty()) assert.Equal(ginkgo.GinkgoT(), len(resp.TLS.PeerCertificates), 1)
Expect(len(resp.TLS.PeerCertificates)).Should(BeNumerically("==", 1))
for _, pc := range resp.TLS.PeerCertificates { for _, pc := range resp.TLS.PeerCertificates {
Expect(pc.Issuer.CommonName).Should(Equal("Kubernetes Ingress Controller Fake Certificate")) assert.Equal(ginkgo.GinkgoT(), pc.Issuer.CommonName, "Kubernetes Ingress Controller Fake Certificate")
} }
By("checking SSL Certificate using the NGINX catch all server") ginkgo.By("checking SSL Certificate using the NGINX catch all server")
resp, _, errs = gorequest.New(). resp = f.HTTPTestClient().
Post(f.GetURL(framework.HTTPS)). GET("/").
TLSClientConfig(&tls.Config{ WithURL(f.GetURL(framework.HTTPS)).
// the default backend uses a self generated certificate WithHeader("Host", "foo.bar.com").
InsecureSkipVerify: true, Expect().
}). Raw()
Set("Host", "foo.bar.com").End()
Expect(errs).Should(BeEmpty()) assert.Equal(ginkgo.GinkgoT(), len(resp.TLS.PeerCertificates), 1)
Expect(len(resp.TLS.PeerCertificates)).Should(BeNumerically("==", 1))
for _, pc := range resp.TLS.PeerCertificates { for _, pc := range resp.TLS.PeerCertificates {
Expect(pc.Issuer.CommonName).Should(Equal("Kubernetes Ingress Controller Fake Certificate")) assert.Equal(ginkgo.GinkgoT(), pc.Issuer.CommonName, "Kubernetes Ingress Controller Fake Certificate")
} }
}) })
}) })

View file

@ -17,13 +17,11 @@ limitations under the License.
package defaultbackend package defaultbackend
import ( import (
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"net/http" "net/http"
"strings" "strings"
"github.com/parnurzeal/gorequest" "github.com/onsi/ginkgo"
networking "k8s.io/api/networking/v1beta1" networking "k8s.io/api/networking/v1beta1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/util/intstr" "k8s.io/apimachinery/pkg/util/intstr"
@ -34,11 +32,11 @@ var _ = framework.IngressNginxDescribe("[Default Backend] change default setting
f := framework.NewDefaultFramework("default-backend-hosts") f := framework.NewDefaultFramework("default-backend-hosts")
host := "foo.com" host := "foo.com"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeployment()
}) })
It("should apply the annotation to the default backend", func() { ginkgo.It("should apply the annotation to the default backend", func() {
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-buffer-size": "8k", "nginx.ingress.kubernetes.io/proxy-buffer-size": "8k",
} }
@ -69,13 +67,10 @@ var _ = framework.IngressNginxDescribe("[Default Backend] change default setting
return strings.Contains(server, "proxy_buffer_size 8k;") return strings.Contains(server, "proxy_buffer_size 8k;")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", "foo.com"). WithHeader("Host", "foo.com").
End() Expect().
Status(http.StatusOK)
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
}) })
}) })

View file

@ -22,7 +22,6 @@ import (
"github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
"github.com/onsi/ginkgo/config" "github.com/onsi/ginkgo/config"
"github.com/onsi/gomega"
"k8s.io/component-base/logs" "k8s.io/component-base/logs"
// required // required
@ -52,8 +51,6 @@ func RunE2ETests(t *testing.T) {
logs.InitLogs() logs.InitLogs()
defer logs.FlushLogs() defer logs.FlushLogs()
gomega.RegisterFailHandler(ginkgo.Fail)
// Disable skipped tests unless they are explicitly requested. // Disable skipped tests unless they are explicitly requested.
if config.GinkgoConfig.FocusString == "" && config.GinkgoConfig.SkipString == "" { if config.GinkgoConfig.FocusString == "" && config.GinkgoConfig.SkipString == "" {
config.GinkgoConfig.SkipString = `\[Flaky\]|\[Feature:.+\]` config.GinkgoConfig.SkipString = `\[Flaky\]|\[Feature:.+\]`

View file

@ -379,13 +379,13 @@ func (f *Framework) DeleteDeployment(name string) error {
func (f *Framework) ScaleDeploymentToZero(name string) { func (f *Framework) ScaleDeploymentToZero(name string) {
d, err := f.KubeClientSet.AppsV1().Deployments(f.Namespace).Get(name, metav1.GetOptions{}) d, err := f.KubeClientSet.AppsV1().Deployments(f.Namespace).Get(name, metav1.GetOptions{})
assert.Nil(ginkgo.GinkgoT(), err, "getting deployment") assert.Nil(ginkgo.GinkgoT(), err, "getting deployment")
assert.Nil(ginkgo.GinkgoT(), d, "expected a deployment but none returned") assert.NotNil(ginkgo.GinkgoT(), d, "expected a deployment but none returned")
d.Spec.Replicas = NewInt32(0) d.Spec.Replicas = NewInt32(0)
d, err = f.KubeClientSet.AppsV1().Deployments(f.Namespace).Update(d) d, err = f.KubeClientSet.AppsV1().Deployments(f.Namespace).Update(d)
assert.Nil(ginkgo.GinkgoT(), err, "getting deployment") assert.Nil(ginkgo.GinkgoT(), err, "getting deployment")
assert.Nil(ginkgo.GinkgoT(), d, "expected a deployment but none returned") assert.NotNil(ginkgo.GinkgoT(), d, "expected a deployment but none returned")
err = WaitForEndpoints(f.KubeClientSet, DefaultTimeout, name, f.Namespace, 0) err = WaitForEndpoints(f.KubeClientSet, DefaultTimeout, name, f.Namespace, 0)
assert.Nil(ginkgo.GinkgoT(), err, "waiting for no endpoints") assert.Nil(ginkgo.GinkgoT(), err, "waiting for no endpoints")

View file

@ -205,7 +205,7 @@ func (f *Framework) GetURL(scheme RequestScheme) string {
func (f *Framework) WaitForNginxServer(name string, matcher func(cfg string) bool) { func (f *Framework) WaitForNginxServer(name string, matcher func(cfg string) bool) {
err := wait.Poll(Poll, DefaultTimeout, f.matchNginxConditions(name, matcher)) err := wait.Poll(Poll, DefaultTimeout, f.matchNginxConditions(name, matcher))
assert.Nil(ginkgo.GinkgoT(), err, "waiting for nginx server condition/s") assert.Nil(ginkgo.GinkgoT(), err, "waiting for nginx server condition/s")
time.Sleep(1 * time.Second) time.Sleep(5 * time.Second)
} }
// WaitForNginxConfiguration waits until the nginx configuration contains a particular configuration // WaitForNginxConfiguration waits until the nginx configuration contains a particular configuration
@ -298,7 +298,7 @@ func (f *Framework) SetNginxConfigMapData(cmData map[string]string) {
Update(cfgMap) Update(cfgMap)
assert.Nil(ginkgo.GinkgoT(), err, "updating configuration configmap") assert.Nil(ginkgo.GinkgoT(), err, "updating configuration configmap")
time.Sleep(1 * time.Second) time.Sleep(5 * time.Second)
} }
func (f *Framework) CreateConfigMap(name string, data map[string]string) { func (f *Framework) CreateConfigMap(name string, data map[string]string) {
@ -309,7 +309,7 @@ func (f *Framework) CreateConfigMap(name string, data map[string]string) {
}, },
Data: data, Data: data,
}) })
assert.Nil(ginkgo.GinkgoT(), err, "failed to create configMap") assert.Nil(ginkgo.GinkgoT(), err, "creating configMap")
} }
// UpdateNginxConfigMapData updates single field in ingress-nginx's nginx-ingress-controller map data // UpdateNginxConfigMapData updates single field in ingress-nginx's nginx-ingress-controller map data
@ -326,7 +326,7 @@ func (f *Framework) UpdateNginxConfigMapData(key string, value string) {
Update(config) Update(config)
assert.Nil(ginkgo.GinkgoT(), err, "updating configuration configmap") assert.Nil(ginkgo.GinkgoT(), err, "updating configuration configmap")
time.Sleep(1 * time.Second) time.Sleep(5 * time.Second)
} }
// DeleteNGINXPod deletes the currently running pod. It waits for the replacement pod to be up. // DeleteNGINXPod deletes the currently running pod. It waits for the replacement pod to be up.
@ -397,6 +397,14 @@ func UpdateDeployment(kubeClientSet kubernetes.Interface, namespace string, name
} }
} }
if *deployment.Spec.Replicas != int32(replicas) {
deployment.Spec.Replicas = NewInt32(int32(replicas))
_, err = kubeClientSet.AppsV1().Deployments(namespace).Update(deployment)
if err != nil {
return errors.Wrapf(err, "scaling the number of replicas to %v", replicas)
}
}
err = WaitForPodsReady(kubeClientSet, DefaultTimeout, replicas, namespace, metav1.ListOptions{ err = WaitForPodsReady(kubeClientSet, DefaultTimeout, replicas, namespace, metav1.ListOptions{
LabelSelector: fields.SelectorFromSet(fields.Set(deployment.Spec.Template.ObjectMeta.Labels)).String(), LabelSelector: fields.SelectorFromSet(fields.Set(deployment.Spec.Template.ObjectMeta.Labels)).String(),
}) })
@ -414,12 +422,25 @@ func UpdateIngress(kubeClientSet kubernetes.Interface, namespace string, name st
return err return err
} }
if ingress == nil {
return fmt.Errorf("there is no ingress with name %v in namespace %v", name, namespace)
}
if ingress.ObjectMeta.Annotations == nil {
ingress.ObjectMeta.Annotations = map[string]string{}
}
if err := updateFunc(ingress); err != nil { if err := updateFunc(ingress); err != nil {
return err return err
} }
_, err = kubeClientSet.NetworkingV1beta1().Ingresses(namespace).Update(ingress) _, err = kubeClientSet.NetworkingV1beta1().Ingresses(namespace).Update(ingress)
return err if err != nil {
return err
}
time.Sleep(5 * time.Second)
return nil
} }
// NewSingleIngressWithTLS creates a simple ingress rule with TLS spec included // NewSingleIngressWithTLS creates a simple ingress rule with TLS spec included

View file

@ -139,5 +139,5 @@ func (f *Framework) NewInfluxDBDeployment() {
err = WaitForPodsReady(f.KubeClientSet, DefaultTimeout, 1, f.Namespace, metav1.ListOptions{ err = WaitForPodsReady(f.KubeClientSet, DefaultTimeout, 1, f.Namespace, metav1.ListOptions{
LabelSelector: fields.SelectorFromSet(fields.Set(d.Spec.Template.ObjectMeta.Labels)).String(), LabelSelector: fields.SelectorFromSet(fields.Set(d.Spec.Template.ObjectMeta.Labels)).String(),
}) })
assert.NotNil(ginkgo.GinkgoT(), err, "failed to wait for influxdb to become ready") assert.Nil(ginkgo.GinkgoT(), err, "waiting for influxdb pod to become ready")
} }

View file

@ -75,7 +75,7 @@ func (f *Framework) EnsureIngress(ingress *networking.Ingress) *networking.Ingre
} }
// creating an ingress requires a reload. // creating an ingress requires a reload.
time.Sleep(4 * time.Second) time.Sleep(5 * time.Second)
return ing return ing
} }

View file

@ -18,11 +18,11 @@ package gracefulshutdown
import ( import (
"net/http" "net/http"
"strings"
"time" "time"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
appsv1 "k8s.io/api/apps/v1" appsv1 "k8s.io/api/apps/v1"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
@ -33,39 +33,42 @@ var _ = framework.IngressNginxDescribe("[Shutdown] ingress controller", func() {
host := "shutdown" host := "shutdown"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.UpdateNginxConfigMapData("worker-shutdown-timeout", "600s") f.UpdateNginxConfigMapData("worker-shutdown-timeout", "600s")
f.NewSlowEchoDeployment() f.NewSlowEchoDeployment()
}) })
It("should shutdown in less than 60 secons without pending connections", func() { ginkgo.It("should shutdown in less than 60 secons without pending connections", func() {
defer ginkgo.GinkgoRecover()
f.EnsureIngress(framework.NewSingleIngress(host, "/", host, f.Namespace, framework.SlowEchoService, 80, nil)) f.EnsureIngress(framework.NewSingleIngress(host, "/", host, f.Namespace, framework.SlowEchoService, 80, nil))
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name shutdown")) return strings.Contains(server, "server_name shutdown")
}) })
resp, _, _ := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+"/sleep/1"). GET("/sleep/1").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) Status(http.StatusOK)
startTime := time.Now() startTime := time.Now()
f.ScaleDeploymentToZero("nginx-ingress-controller") f.ScaleDeploymentToZero("nginx-ingress-controller")
Expect(time.Since(startTime).Seconds()).To(BeNumerically("<=", 60), "waiting shutdown") assert.LessOrEqual(ginkgo.GinkgoT(), int(time.Since(startTime).Seconds()), 60, "waiting shutdown")
}) })
type asyncResult struct { type asyncResult struct {
errs []error
status int status int
} }
It("should shutdown after waiting 60 seconds for pending connections to be closed", func() { ginkgo.It("should shutdown after waiting 60 seconds for pending connections to be closed", func() {
defer ginkgo.GinkgoRecover()
err := framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1, err := framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1,
func(deployment *appsv1.Deployment) error { func(deployment *appsv1.Deployment) error {
grace := int64(3600) grace := int64(3600)
@ -73,7 +76,8 @@ var _ = framework.IngressNginxDescribe("[Shutdown] ingress controller", func() {
_, err := f.KubeClientSet.AppsV1().Deployments(f.Namespace).Update(deployment) _, err := f.KubeClientSet.AppsV1().Deployments(f.Namespace).Update(deployment)
return err return err
}) })
Expect(err).NotTo(HaveOccurred())
assert.Nil(ginkgo.GinkgoT(), err)
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-send-timeout": "600", "nginx.ingress.kubernetes.io/proxy-send-timeout": "600",
@ -83,7 +87,7 @@ var _ = framework.IngressNginxDescribe("[Shutdown] ingress controller", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name shutdown")) return strings.Contains(server, "server_name shutdown")
}) })
result := make(chan *asyncResult) result := make(chan *asyncResult)
@ -91,17 +95,20 @@ var _ = framework.IngressNginxDescribe("[Shutdown] ingress controller", func() {
startTime := time.Now() startTime := time.Now()
go func(host string, c chan *asyncResult) { go func(host string, c chan *asyncResult) {
resp, _, errs := gorequest.New(). defer ginkgo.GinkgoRecover()
Get(f.GetURL(framework.HTTP)+"/sleep/70").
Set("Host", host). resp := f.HTTPTestClient().
End() GET("/sleep/70").
WithHeader("Host", host).
Expect().
Raw()
code := 0 code := 0
if resp != nil { if resp != nil {
code = resp.StatusCode code = resp.StatusCode
} }
c <- &asyncResult{errs, code} c <- &asyncResult{code}
}(host, result) }(host, result)
time.Sleep(5 * time.Second) time.Sleep(5 * time.Second)
@ -113,9 +120,8 @@ var _ = framework.IngressNginxDescribe("[Shutdown] ingress controller", func() {
for { for {
select { select {
case res := <-result: case res := <-result:
Expect(res.errs).Should(BeEmpty()) assert.Equal(ginkgo.GinkgoT(), res.status, http.StatusOK, "expecting a valid response from HTTP request")
Expect(res.status).To(Equal(http.StatusOK), "expecting a valid response from HTTP request") assert.GreaterOrEqual(ginkgo.GinkgoT(), int(time.Since(startTime).Seconds()), 60, "waiting shutdown")
Expect(time.Since(startTime).Seconds()).To(BeNumerically(">", 60), "waiting shutdown")
ticker.Stop() ticker.Stop()
return return
case <-ticker.C: case <-ticker.C:
@ -124,7 +130,7 @@ var _ = framework.IngressNginxDescribe("[Shutdown] ingress controller", func() {
} }
}) })
It("should shutdown after waiting 150 seconds for pending connections to be closed", func() { ginkgo.It("should shutdown after waiting 150 seconds for pending connections to be closed", func() {
err := framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1, err := framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1,
func(deployment *appsv1.Deployment) error { func(deployment *appsv1.Deployment) error {
grace := int64(3600) grace := int64(3600)
@ -132,7 +138,7 @@ var _ = framework.IngressNginxDescribe("[Shutdown] ingress controller", func() {
_, err := f.KubeClientSet.AppsV1().Deployments(f.Namespace).Update(deployment) _, err := f.KubeClientSet.AppsV1().Deployments(f.Namespace).Update(deployment)
return err return err
}) })
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/proxy-send-timeout": "600", "nginx.ingress.kubernetes.io/proxy-send-timeout": "600",
@ -142,7 +148,7 @@ var _ = framework.IngressNginxDescribe("[Shutdown] ingress controller", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("server_name shutdown")) return strings.Contains(server, "server_name shutdown")
}) })
result := make(chan *asyncResult) result := make(chan *asyncResult)
@ -150,17 +156,20 @@ var _ = framework.IngressNginxDescribe("[Shutdown] ingress controller", func() {
startTime := time.Now() startTime := time.Now()
go func(host string, c chan *asyncResult) { go func(host string, c chan *asyncResult) {
resp, _, errs := gorequest.New(). defer ginkgo.GinkgoRecover()
Get(f.GetURL(framework.HTTP)+"/sleep/150").
Set("Host", host). resp := f.HTTPTestClient().
End() GET("/sleep/150").
WithHeader("Host", host).
Expect().
Raw()
code := 0 code := 0
if resp != nil { if resp != nil {
code = resp.StatusCode code = resp.StatusCode
} }
c <- &asyncResult{errs, code} c <- &asyncResult{code}
}(host, result) }(host, result)
time.Sleep(5 * time.Second) time.Sleep(5 * time.Second)
@ -172,9 +181,8 @@ var _ = framework.IngressNginxDescribe("[Shutdown] ingress controller", func() {
for { for {
select { select {
case res := <-result: case res := <-result:
Expect(res.errs).Should(BeEmpty()) assert.Equal(ginkgo.GinkgoT(), res.status, http.StatusOK, "expecting a valid response from HTTP request")
Expect(res.status).To(Equal(http.StatusOK), "expecting a valid response from HTTP request") assert.GreaterOrEqual(ginkgo.GinkgoT(), int(time.Since(startTime).Seconds()), 150, "waiting shutdown")
Expect(time.Since(startTime).Seconds()).To(BeNumerically(">", 150), "waiting shutdown")
ticker.Stop() ticker.Stop()
return return
case <-ticker.C: case <-ticker.C:

View file

@ -21,21 +21,20 @@ import (
"strings" "strings"
"time" "time"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.IngressNginxDescribe("[Shutdown] Graceful shutdown with pending request", func() { var _ = framework.IngressNginxDescribe("[Shutdown] Graceful shutdown with pending request", func() {
f := framework.NewDefaultFramework("shutdown-slow-requests") f := framework.NewDefaultFramework("shutdown-slow-requests")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewSlowEchoDeployment() f.NewSlowEchoDeployment()
f.UpdateNginxConfigMapData("worker-shutdown-timeout", "50s") f.UpdateNginxConfigMapData("worker-shutdown-timeout", "50s")
}) })
It("should let slow requests finish before shutting down", func() { ginkgo.It("should let slow requests finish before shutting down", func() {
host := "graceful-shutdown" host := "graceful-shutdown"
f.EnsureIngress(framework.NewSingleIngress(host, "/", host, f.Namespace, framework.SlowEchoService, 80, nil)) f.EnsureIngress(framework.NewSingleIngress(host, "/", host, f.Namespace, framework.SlowEchoService, 80, nil))
@ -47,13 +46,13 @@ var _ = framework.IngressNginxDescribe("[Shutdown] Graceful shutdown with pendin
done := make(chan bool) done := make(chan bool)
go func() { go func() {
defer func() { done <- true }() defer func() { done <- true }()
defer GinkgoRecover() defer ginkgo.GinkgoRecover()
resp, _, errs := gorequest.New().
Get(f.GetURL(framework.HTTP)+"/sleep/30"). f.HTTPTestClient().
Set("Host", host). GET("/sleep/30").
End() WithHeader("Host", host).
Expect(errs).To(BeNil()) Expect().
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) Status(http.StatusOK)
}() }()
time.Sleep(1 * time.Second) time.Sleep(1 * time.Second)

View file

@ -23,10 +23,8 @@ import (
"strings" "strings"
"time" "time"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
pool "gopkg.in/go-playground/pool.v3" pool "gopkg.in/go-playground/pool.v3"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
@ -36,7 +34,7 @@ import (
var _ = framework.IngressNginxDescribe("[Memory Leak] Dynamic Certificates", func() { var _ = framework.IngressNginxDescribe("[Memory Leak] Dynamic Certificates", func() {
f := framework.NewDefaultFramework("lua-dynamic-certificates") f := framework.NewDefaultFramework("lua-dynamic-certificates")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
@ -44,11 +42,11 @@ var _ = framework.IngressNginxDescribe("[Memory Leak] Dynamic Certificates", fun
hostCount := 1000 hostCount := 1000
iterations := 10 iterations := 10
By("Waiting a minute before starting the test") ginkgo.By("Waiting a minute before starting the test")
time.Sleep(1 * time.Minute) time.Sleep(1 * time.Minute)
for iteration := 1; iteration <= iterations; iteration++ { for iteration := 1; iteration <= iterations; iteration++ {
By(fmt.Sprintf("Running iteration %v", iteration)) ginkgo.By(fmt.Sprintf("Running iteration %v", iteration))
p := pool.NewLimited(200) p := pool.NewLimited(200)
@ -64,7 +62,7 @@ var _ = framework.IngressNginxDescribe("[Memory Leak] Dynamic Certificates", fun
p.Close() p.Close()
By("waiting one minute before next iteration") ginkgo.By("waiting one minute before next iteration")
time.Sleep(1 * time.Minute) time.Sleep(1 * time.Minute)
} }
}) })
@ -76,7 +74,7 @@ func privisionIngress(hostname string, f *framework.Framework) {
ing.Spec.TLS[0].Hosts, ing.Spec.TLS[0].Hosts,
ing.Spec.TLS[0].SecretName, ing.Spec.TLS[0].SecretName,
ing.Namespace) ing.Namespace)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
f.WaitForNginxServer(hostname, f.WaitForNginxServer(hostname,
func(server string) bool { func(server string) bool {
@ -86,23 +84,26 @@ func privisionIngress(hostname string, f *framework.Framework) {
} }
func checkIngress(hostname string, f *framework.Framework) { func checkIngress(hostname string, f *framework.Framework) {
req := gorequest.New() resp := f.HTTPTestClientWithTLSConfig(&tls.Config{
resp, _, errs := req. ServerName: hostname,
Get(f.GetURL(framework.HTTPS)). InsecureSkipVerify: true,
TLSClientConfig(&tls.Config{ServerName: hostname, InsecureSkipVerify: true}). }).
Set("Host", hostname). GET("/").
End() WithURL(f.GetURL(framework.HTTPS)).
Expect(errs).Should(BeEmpty()) WithHeader("Host", hostname).
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) Expect().
Raw()
assert.Equal(ginkgo.GinkgoT(), resp.StatusCode, http.StatusOK)
// check the returned secret is not the fake one // check the returned secret is not the fake one
cert := resp.TLS.PeerCertificates[0] cert := resp.TLS.PeerCertificates[0]
Expect(cert.DNSNames[0]).Should(Equal(hostname)) assert.Equal(ginkgo.GinkgoT(), cert.DNSNames[0], hostname)
} }
func deleteIngress(hostname string, f *framework.Framework) { func deleteIngress(hostname string, f *framework.Framework) {
err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Delete(hostname, &metav1.DeleteOptions{}) err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Delete(hostname, &metav1.DeleteOptions{})
Expect(err).NotTo(HaveOccurred(), "unexpected error deleting ingress") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error deleting ingress")
} }
func run(host string, f *framework.Framework) pool.WorkFunc { func run(host string, f *framework.Framework) pool.WorkFunc {
@ -111,15 +112,15 @@ func run(host string, f *framework.Framework) pool.WorkFunc {
return nil, nil return nil, nil
} }
By(fmt.Sprintf("\tcreating ingress for host %v", host)) ginkgo.By(fmt.Sprintf("\tcreating ingress for host %v", host))
privisionIngress(host, f) privisionIngress(host, f)
time.Sleep(100 * time.Millisecond) time.Sleep(100 * time.Millisecond)
By(fmt.Sprintf("\tchecking ingress for host %v", host)) ginkgo.By(fmt.Sprintf("\tchecking ingress for host %v", host))
checkIngress(host, f) checkIngress(host, f)
By(fmt.Sprintf("\tdestroying ingress for host %v", host)) ginkgo.By(fmt.Sprintf("\tdestroying ingress for host %v", host))
deleteIngress(host, f) deleteIngress(host, f)
return true, nil return true, nil

View file

@ -19,8 +19,8 @@ package loadbalance
import ( import (
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -28,11 +28,11 @@ import (
var _ = framework.DescribeSetting("[Load Balancer] load-balance", func() { var _ = framework.DescribeSetting("[Load Balancer] load-balance", func() {
f := framework.NewDefaultFramework("lb-configmap") f := framework.NewDefaultFramework("lb-configmap")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeployment()
}) })
It("should apply the configmap load-balance setting", func() { ginkgo.It("should apply the configmap load-balance setting", func() {
host := "load-balance.com" host := "load-balance.com"
f.UpdateNginxConfigMapData("load-balance", "ewma") f.UpdateNginxConfigMapData("load-balance", "ewma")
@ -44,7 +44,7 @@ var _ = framework.DescribeSetting("[Load Balancer] load-balance", func() {
}) })
algorithm, err := f.GetLbAlgorithm(framework.EchoService, 80) algorithm, err := f.GetLbAlgorithm(framework.EchoService, 80)
Expect(err).Should(BeNil()) assert.Nil(ginkgo.GinkgoT(), err)
Expect(algorithm).Should(Equal("ewma")) assert.Equal(ginkgo.GinkgoT(), algorithm, "ewma")
}) })
}) })

View file

@ -18,13 +18,12 @@ package loadbalance
import ( import (
"fmt" "fmt"
"net/http"
"regexp" "regexp"
"strings" "strings"
"github.com/parnurzeal/gorequest" "github.com/onsi/ginkgo"
"github.com/stretchr/testify/assert"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -32,7 +31,7 @@ import (
var _ = framework.DescribeSetting("[Load Balancer] EWMA", func() { var _ = framework.DescribeSetting("[Load Balancer] EWMA", func() {
f := framework.NewDefaultFramework("ewma") f := framework.NewDefaultFramework("ewma")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(3) f.NewEchoDeploymentWithReplicas(3)
f.SetNginxConfigMapData(map[string]string{ f.SetNginxConfigMapData(map[string]string{
"worker-processes": "2", "worker-processes": "2",
@ -40,7 +39,7 @@ var _ = framework.DescribeSetting("[Load Balancer] EWMA", func() {
) )
}) })
It("does not fail requests", func() { ginkgo.It("does not fail requests", func() {
host := "load-balance.com" host := "load-balance.com"
f.EnsureIngress(framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil)) f.EnsureIngress(framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil))
@ -50,21 +49,21 @@ var _ = framework.DescribeSetting("[Load Balancer] EWMA", func() {
}) })
algorithm, err := f.GetLbAlgorithm(framework.EchoService, 80) algorithm, err := f.GetLbAlgorithm(framework.EchoService, 80)
Expect(err).Should(BeNil()) assert.Nil(ginkgo.GinkgoT(), err)
Expect(algorithm).Should(Equal("ewma")) assert.Equal(ginkgo.GinkgoT(), algorithm, "ewma")
re, _ := regexp.Compile(fmt.Sprintf(`%v.*`, framework.EchoService)) re, _ := regexp.Compile(fmt.Sprintf(`%v.*`, framework.EchoService))
replicaRequestCount := map[string]int{} replicaRequestCount := map[string]int{}
for i := 0; i < 30; i++ { for i := 0; i < 30; i++ {
_, body, errs := gorequest.New(). body := f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).Should(BeEmpty()) Status(http.StatusOK).Body().Raw()
replica := re.FindString(body) replica := re.FindString(body)
Expect(replica).ShouldNot(Equal("")) assert.NotEmpty(ginkgo.GinkgoT(), replica)
if _, ok := replicaRequestCount[replica]; !ok { if _, ok := replicaRequestCount[replica]; !ok {
replicaRequestCount[replica] = 1 replicaRequestCount[replica] = 1
@ -78,6 +77,6 @@ var _ = framework.DescribeSetting("[Load Balancer] EWMA", func() {
for _, v := range replicaRequestCount { for _, v := range replicaRequestCount {
actualCount += v actualCount += v
} }
Expect(actualCount).Should(Equal(30)) assert.Equal(ginkgo.GinkgoT(), actualCount, 30)
}) })
}) })

View file

@ -18,13 +18,12 @@ package loadbalance
import ( import (
"fmt" "fmt"
"net/http"
"regexp" "regexp"
"strings" "strings"
"github.com/parnurzeal/gorequest" "github.com/onsi/ginkgo"
"github.com/stretchr/testify/assert"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -32,12 +31,12 @@ import (
var _ = framework.DescribeSetting("[Load Balancer] round-robin", func() { var _ = framework.DescribeSetting("[Load Balancer] round-robin", func() {
f := framework.NewDefaultFramework("round-robin") f := framework.NewDefaultFramework("round-robin")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(3) f.NewEchoDeploymentWithReplicas(3)
f.UpdateNginxConfigMapData("worker-processes", "1") f.UpdateNginxConfigMapData("worker-processes", "1")
}) })
It("should evenly distribute requests with round-robin (default algorithm)", func() { ginkgo.It("should evenly distribute requests with round-robin (default algorithm)", func() {
host := "load-balance.com" host := "load-balance.com"
f.EnsureIngress(framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil)) f.EnsureIngress(framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil))
@ -50,14 +49,14 @@ var _ = framework.DescribeSetting("[Load Balancer] round-robin", func() {
replicaRequestCount := map[string]int{} replicaRequestCount := map[string]int{}
for i := 0; i < 600; i++ { for i := 0; i < 600; i++ {
_, body, errs := gorequest.New(). body := f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).Should(BeEmpty()) Status(http.StatusOK).Body().Raw()
replica := re.FindString(body) replica := re.FindString(body)
Expect(replica).ShouldNot(Equal("")) assert.NotEmpty(ginkgo.GinkgoT(), replica)
if _, ok := replicaRequestCount[replica]; !ok { if _, ok := replicaRequestCount[replica]; !ok {
replicaRequestCount[replica] = 1 replicaRequestCount[replica] = 1
@ -67,7 +66,7 @@ var _ = framework.DescribeSetting("[Load Balancer] round-robin", func() {
} }
for _, v := range replicaRequestCount { for _, v := range replicaRequestCount {
Expect(v).Should(Equal(200)) assert.Equal(ginkgo.GinkgoT(), v, 200)
} }
}) })
}) })

View file

@ -18,15 +18,15 @@ package lua
import ( import (
"fmt" "fmt"
"net/http"
"strings" "strings"
"time" "time"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
dto "github.com/prometheus/client_model/go" dto "github.com/prometheus/client_model/go"
"github.com/prometheus/common/expfmt" "github.com/prometheus/common/expfmt"
"github.com/prometheus/common/model" "github.com/prometheus/common/model"
"github.com/stretchr/testify/assert"
networking "k8s.io/api/networking/v1beta1" networking "k8s.io/api/networking/v1beta1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
@ -37,15 +37,15 @@ var _ = framework.IngressNginxDescribe("[Lua] dynamic certificates", func() {
f := framework.NewDefaultFramework("dynamic-certificate") f := framework.NewDefaultFramework("dynamic-certificate")
host := "foo.com" host := "foo.com"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeployment()
}) })
It("picks up the certificate when we add TLS spec to existing ingress", func() { ginkgo.It("picks up the certificate when we add TLS spec to existing ingress", func() {
ensureIngress(f, host, framework.EchoService) ensureIngress(f, host, framework.EchoService)
ing, err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Get(host, metav1.GetOptions{}) ing, err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Get(host, metav1.GetOptions{})
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
ing.Spec.TLS = []networking.IngressTLS{ ing.Spec.TLS = []networking.IngressTLS{
{ {
Hosts: []string{host}, Hosts: []string{host},
@ -56,15 +56,17 @@ var _ = framework.IngressNginxDescribe("[Lua] dynamic certificates", func() {
ing.Spec.TLS[0].Hosts, ing.Spec.TLS[0].Hosts,
ing.Spec.TLS[0].SecretName, ing.Spec.TLS[0].SecretName,
ing.Namespace) ing.Namespace)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
_, err = f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Update(ing) _, err = f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Update(ing)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
time.Sleep(waitForLuaSync) time.Sleep(waitForLuaSync)
ensureHTTPSRequest(f.GetURL(framework.HTTPS), host, host) ensureHTTPSRequest(f, f.GetURL(framework.HTTPS), host, host)
}) })
It("picks up the previously missing secret for a given ingress without reloading", func() { ginkgo.It("picks up the previously missing secret for a given ingress without reloading", func() {
ing := framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, nil) ing := framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, nil)
f.EnsureIngress(ing) f.EnsureIngress(ing)
@ -72,56 +74,57 @@ var _ = framework.IngressNginxDescribe("[Lua] dynamic certificates", func() {
ip := f.GetNginxPodIP() ip := f.GetNginxPodIP()
mf, err := f.GetMetric("nginx_ingress_controller_success", ip[0]) mf, err := f.GetMetric("nginx_ingress_controller_success", ip[0])
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
Expect(mf).ToNot(BeNil()) assert.NotNil(ginkgo.GinkgoT(), mf)
rc0, err := extractReloadCount(mf) rc0, err := extractReloadCount(mf)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
ensureHTTPSRequest(fmt.Sprintf("%s?id=dummy_log_splitter_foo_bar", f.GetURL(framework.HTTPS)), host, "ingress.local") ensureHTTPSRequest(f, fmt.Sprintf("%s?id=dummy_log_splitter_foo_bar", f.GetURL(framework.HTTPS)), host, "ingress.local")
_, err = framework.CreateIngressTLSSecret(f.KubeClientSet, _, err = framework.CreateIngressTLSSecret(f.KubeClientSet,
ing.Spec.TLS[0].Hosts, ing.Spec.TLS[0].Hosts,
ing.Spec.TLS[0].SecretName, ing.Spec.TLS[0].SecretName,
ing.Namespace) ing.Namespace)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
time.Sleep(waitForLuaSync) time.Sleep(waitForLuaSync)
By("serving the configured certificate on HTTPS endpoint") ginkgo.By("serving the configured certificate on HTTPS endpoint")
ensureHTTPSRequest(f.GetURL(framework.HTTPS), host, host) ensureHTTPSRequest(f, f.GetURL(framework.HTTPS), host, host)
log, err := f.NginxLogs() log, err := f.NginxLogs()
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
Expect(log).ToNot(BeEmpty()) assert.NotEmpty(ginkgo.GinkgoT(), log)
By("skipping Nginx reload") ginkgo.By("skipping Nginx reload")
mf, err = f.GetMetric("nginx_ingress_controller_success", ip[0]) mf, err = f.GetMetric("nginx_ingress_controller_success", ip[0])
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
Expect(mf).ToNot(BeNil()) assert.NotNil(ginkgo.GinkgoT(), mf)
rc1, err := extractReloadCount(mf) rc1, err := extractReloadCount(mf)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
Expect(rc0).To(BeEquivalentTo(rc1)) assert.Equal(ginkgo.GinkgoT(), rc0, rc1)
}) })
Context("given an ingress with TLS correctly configured", func() { ginkgo.Context("given an ingress with TLS correctly configured", func() {
BeforeEach(func() { ginkgo.BeforeEach(func() {
ing := f.EnsureIngress(framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, nil)) ing := f.EnsureIngress(framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, nil))
time.Sleep(waitForLuaSync) time.Sleep(waitForLuaSync)
ensureHTTPSRequest(f.GetURL(framework.HTTPS), host, "ingress.local") ensureHTTPSRequest(f, f.GetURL(framework.HTTPS), host, "ingress.local")
_, err := framework.CreateIngressTLSSecret(f.KubeClientSet, _, err := framework.CreateIngressTLSSecret(f.KubeClientSet,
ing.Spec.TLS[0].Hosts, ing.Spec.TLS[0].Hosts,
ing.Spec.TLS[0].SecretName, ing.Spec.TLS[0].SecretName,
ing.Namespace) ing.Namespace)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
time.Sleep(waitForLuaSync) time.Sleep(waitForLuaSync)
By("configuring certificate_by_lua and skipping Nginx configuration of the new certificate") ginkgo.By("configuring certificate_by_lua and skipping Nginx configuration of the new certificate")
f.WaitForNginxServer(ing.Spec.TLS[0].Hosts[0], f.WaitForNginxServer(ing.Spec.TLS[0].Hosts[0],
func(server string) bool { func(server string) bool {
return strings.Contains(server, "listen 443") return strings.Contains(server, "listen 443")
@ -129,8 +132,8 @@ var _ = framework.IngressNginxDescribe("[Lua] dynamic certificates", func() {
time.Sleep(waitForLuaSync) time.Sleep(waitForLuaSync)
By("serving the configured certificate on HTTPS endpoint") ginkgo.By("serving the configured certificate on HTTPS endpoint")
ensureHTTPSRequest(f.GetURL(framework.HTTPS), host, host) ensureHTTPSRequest(f, f.GetURL(framework.HTTPS), host, host)
}) })
/* /*
@ -138,98 +141,109 @@ var _ = framework.IngressNginxDescribe("[Lua] dynamic certificates", func() {
because Go transport code strips (https://github.com/golang/go/blob/431b5c69ca214ce4291f008c1ce2a50b22bc2d2d/src/crypto/tls/handshake_messages.go#L424) because Go transport code strips (https://github.com/golang/go/blob/431b5c69ca214ce4291f008c1ce2a50b22bc2d2d/src/crypto/tls/handshake_messages.go#L424)
trailing dot from SNI as suggest by the standard (https://tools.ietf.org/html/rfc6066#section-3). trailing dot from SNI as suggest by the standard (https://tools.ietf.org/html/rfc6066#section-3).
*/ */
It("supports requests with domain with trailing dot", func() { ginkgo.It("supports requests with domain with trailing dot", func() {
ensureHTTPSRequest(f.GetURL(framework.HTTPS), host+".", host) ensureHTTPSRequest(f, f.GetURL(framework.HTTPS), host+".", host)
}) })
It("picks up the updated certificate without reloading", func() { ginkgo.It("picks up the updated certificate without reloading", func() {
ing, err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Get(host, metav1.GetOptions{}) ing, err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Get(host, metav1.GetOptions{})
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
ensureHTTPSRequest(fmt.Sprintf("%s?id=dummy_log_splitter_foo_bar", f.GetURL(framework.HTTPS)), host, host) ensureHTTPSRequest(f, fmt.Sprintf("%s?id=dummy_log_splitter_foo_bar", f.GetURL(framework.HTTPS)), host, host)
_, err = framework.CreateIngressTLSSecret(f.KubeClientSet, _, err = framework.CreateIngressTLSSecret(f.KubeClientSet,
ing.Spec.TLS[0].Hosts, ing.Spec.TLS[0].Hosts,
ing.Spec.TLS[0].SecretName, ing.Spec.TLS[0].SecretName,
ing.Namespace) ing.Namespace)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
time.Sleep(waitForLuaSync) time.Sleep(waitForLuaSync)
By("configuring certificate_by_lua and skipping Nginx configuration of the new certificate") ginkgo.By("configuring certificate_by_lua and skipping Nginx configuration of the new certificate")
f.WaitForNginxServer(ing.Spec.TLS[0].Hosts[0], f.WaitForNginxServer(ing.Spec.TLS[0].Hosts[0],
func(server string) bool { func(server string) bool {
return strings.Contains(server, "listen 443") return strings.Contains(server, "listen 443")
}) })
By("serving the configured certificate on HTTPS endpoint") ginkgo.By("serving the configured certificate on HTTPS endpoint")
ensureHTTPSRequest(f.GetURL(framework.HTTPS), host, host) ensureHTTPSRequest(f, f.GetURL(framework.HTTPS), host, host)
log, err := f.NginxLogs() log, err := f.NginxLogs()
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
Expect(log).ToNot(BeEmpty()) assert.NotEmpty(ginkgo.GinkgoT(), log)
index := strings.Index(log, "id=dummy_log_splitter_foo_bar") index := strings.Index(log, "id=dummy_log_splitter_foo_bar")
assert.GreaterOrEqual(ginkgo.GinkgoT(), index, 0, "log does not contains id=dummy_log_splitter_foo_bar")
restOfLogs := log[index:] restOfLogs := log[index:]
By("skipping Nginx reload") ginkgo.By("skipping Nginx reload")
Expect(restOfLogs).ToNot(ContainSubstring(logRequireBackendReload)) assert.NotContains(ginkgo.GinkgoT(), restOfLogs, logRequireBackendReload)
Expect(restOfLogs).ToNot(ContainSubstring(logBackendReloadSuccess)) assert.NotContains(ginkgo.GinkgoT(), restOfLogs, logBackendReloadSuccess)
}) })
It("falls back to using default certificate when secret gets deleted without reloading", func() { ginkgo.It("falls back to using default certificate when secret gets deleted without reloading", func() {
ing, err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Get(host, metav1.GetOptions{}) ing, err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Get(host, metav1.GetOptions{})
ensureHTTPSRequest(fmt.Sprintf("%s?id=dummy_log_splitter_foo_bar", f.GetURL(framework.HTTPS)), host, host) ensureHTTPSRequest(f, fmt.Sprintf("%s?id=dummy_log_splitter_foo_bar", f.GetURL(framework.HTTPS)), host, host)
ip := f.GetNginxPodIP() ip := f.GetNginxPodIP()
mf, err := f.GetMetric("nginx_ingress_controller_success", ip[0]) mf, err := f.GetMetric("nginx_ingress_controller_success", ip[0])
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
Expect(mf).ToNot(BeNil()) assert.NotNil(ginkgo.GinkgoT(), mf)
rc0, err := extractReloadCount(mf) rc0, err := extractReloadCount(mf)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
err = f.KubeClientSet.CoreV1().Secrets(ing.Namespace).Delete(ing.Spec.TLS[0].SecretName, nil) err = f.KubeClientSet.CoreV1().Secrets(ing.Namespace).Delete(ing.Spec.TLS[0].SecretName, nil)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
time.Sleep(waitForLuaSync * 2) time.Sleep(waitForLuaSync)
By("serving the default certificate on HTTPS endpoint") ginkgo.By("serving the default certificate on HTTPS endpoint")
ensureHTTPSRequest(f.GetURL(framework.HTTPS), host, "ingress.local") ensureHTTPSRequest(f, f.GetURL(framework.HTTPS), host, "ingress.local")
mf, err = f.GetMetric("nginx_ingress_controller_success", ip[0]) mf, err = f.GetMetric("nginx_ingress_controller_success", ip[0])
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
Expect(mf).ToNot(BeNil()) assert.NotNil(ginkgo.GinkgoT(), mf)
rc1, err := extractReloadCount(mf) rc1, err := extractReloadCount(mf)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
By("skipping Nginx reload") ginkgo.By("skipping Nginx reload")
Expect(rc0).To(BeEquivalentTo(rc1)) assert.Equal(ginkgo.GinkgoT(), rc0, rc1)
}) })
It("picks up a non-certificate only change", func() { ginkgo.It("picks up a non-certificate only change", func() {
newHost := "foo2.com" newHost := "foo2.com"
ing, err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Get(host, metav1.GetOptions{}) ing, err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Get(host, metav1.GetOptions{})
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
ing.Spec.Rules[0].Host = newHost ing.Spec.Rules[0].Host = newHost
_, err = f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Update(ing) _, err = f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Update(ing)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
time.Sleep(waitForLuaSync) time.Sleep(waitForLuaSync)
By("serving the configured certificate on HTTPS endpoint") ginkgo.By("serving the configured certificate on HTTPS endpoint")
ensureHTTPSRequest(f.GetURL(framework.HTTPS), newHost, "ingress.local") ensureHTTPSRequest(f, f.GetURL(framework.HTTPS), newHost, "ingress.local")
}) })
It("removes HTTPS configuration when we delete TLS spec", func() { ginkgo.It("removes HTTPS configuration when we delete TLS spec", func() {
ing, err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Get(host, metav1.GetOptions{}) ing, err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Get(host, metav1.GetOptions{})
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
ing.Spec.TLS = []networking.IngressTLS{} ing.Spec.TLS = []networking.IngressTLS{}
_, err = f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Update(ing) _, err = f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Update(ing)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
time.Sleep(waitForLuaSync) time.Sleep(waitForLuaSync)
ensureRequest(f, host) f.HTTPTestClient().
GET("/").
WithHeader("Host", host).
Expect().
Status(http.StatusOK)
}) })
}) })
}) })

View file

@ -23,10 +23,8 @@ import (
"strings" "strings"
"time" "time"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
networking "k8s.io/api/networking/v1beta1" networking "k8s.io/api/networking/v1beta1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
@ -40,18 +38,19 @@ const (
logRequireBackendReload = "Configuration changes detected, backend reload required" logRequireBackendReload = "Configuration changes detected, backend reload required"
logBackendReloadSuccess = "Backend successfully reloaded" logBackendReloadSuccess = "Backend successfully reloaded"
logInitialConfigSync = "Initial synchronization of the NGINX configuration" logInitialConfigSync = "Initial synchronization of the NGINX configuration"
waitForLuaSync = 5 * time.Second
waitForLuaSync = 5 * time.Second
) )
var _ = framework.IngressNginxDescribe("[Lua] dynamic configuration", func() { var _ = framework.IngressNginxDescribe("[Lua] dynamic configuration", func() {
f := framework.NewDefaultFramework("dynamic-configuration") f := framework.NewDefaultFramework("dynamic-configuration")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeploymentWithReplicas(1)
ensureIngress(f, "foo.com", framework.EchoService) ensureIngress(f, "foo.com", framework.EchoService)
}) })
It("configures balancer Lua middleware correctly", func() { ginkgo.It("configures balancer Lua middleware correctly", func() {
f.WaitForNginxConfiguration(func(cfg string) bool { f.WaitForNginxConfiguration(func(cfg string) bool {
return strings.Contains(cfg, "balancer.init_worker()") && strings.Contains(cfg, "balancer.balance()") return strings.Contains(cfg, "balancer.init_worker()") && strings.Contains(cfg, "balancer.balance()")
}) })
@ -62,8 +61,8 @@ var _ = framework.IngressNginxDescribe("[Lua] dynamic configuration", func() {
}) })
}) })
Context("when only backends change", func() { ginkgo.Context("when only backends change", func() {
It("handles endpoints only changes", func() { ginkgo.It("handles endpoints only changes", func() {
var nginxConfig string var nginxConfig string
f.WaitForNginxConfiguration(func(cfg string) bool { f.WaitForNginxConfiguration(func(cfg string) bool {
nginxConfig = cfg nginxConfig = cfg
@ -72,19 +71,23 @@ var _ = framework.IngressNginxDescribe("[Lua] dynamic configuration", func() {
replicas := 2 replicas := 2
err := framework.UpdateDeployment(f.KubeClientSet, f.Namespace, framework.EchoService, replicas, nil) err := framework.UpdateDeployment(f.KubeClientSet, f.Namespace, framework.EchoService, replicas, nil)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
ensureRequest(f, "foo.com") f.HTTPTestClient().
GET("/").
WithHeader("Host", "foo.com").
Expect().
Status(http.StatusOK)
var newNginxConfig string var newNginxConfig string
f.WaitForNginxConfiguration(func(cfg string) bool { f.WaitForNginxConfiguration(func(cfg string) bool {
newNginxConfig = cfg newNginxConfig = cfg
return true return true
}) })
Expect(nginxConfig).Should(Equal(newNginxConfig)) assert.Equal(ginkgo.GinkgoT(), nginxConfig, newNginxConfig)
}) })
It("handles endpoints only changes (down scaling of replicas)", func() { ginkgo.It("handles endpoints only changes (down scaling of replicas)", func() {
var nginxConfig string var nginxConfig string
f.WaitForNginxConfiguration(func(cfg string) bool { f.WaitForNginxConfiguration(func(cfg string) bool {
nginxConfig = cfg nginxConfig = cfg
@ -93,52 +96,79 @@ var _ = framework.IngressNginxDescribe("[Lua] dynamic configuration", func() {
replicas := 2 replicas := 2
err := framework.UpdateDeployment(f.KubeClientSet, f.Namespace, framework.EchoService, replicas, nil) err := framework.UpdateDeployment(f.KubeClientSet, f.Namespace, framework.EchoService, replicas, nil)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
time.Sleep(waitForLuaSync * 2)
ensureRequest(f, "foo.com") time.Sleep(waitForLuaSync)
f.HTTPTestClient().
GET("/").
WithHeader("Host", "foo.com").
Expect().
Status(http.StatusOK)
var newNginxConfig string var newNginxConfig string
f.WaitForNginxConfiguration(func(cfg string) bool { f.WaitForNginxConfiguration(func(cfg string) bool {
newNginxConfig = cfg newNginxConfig = cfg
return true return true
}) })
Expect(nginxConfig).Should(Equal(newNginxConfig)) assert.Equal(ginkgo.GinkgoT(), nginxConfig, newNginxConfig)
err = framework.UpdateDeployment(f.KubeClientSet, f.Namespace, framework.EchoService, 0, nil) err = framework.UpdateDeployment(f.KubeClientSet, f.Namespace, framework.EchoService, 0, nil)
assert.Nil(ginkgo.GinkgoT(), err)
Expect(err).NotTo(HaveOccurred()) time.Sleep(waitForLuaSync)
time.Sleep(waitForLuaSync * 2)
ensureRequestWithStatus(f, "foo.com", 503) f.HTTPTestClient().
GET("/").
WithHeader("Host", "foo.com").
Expect().
Status(503)
}) })
It("handles endpoints only changes consistently (down scaling of replicas vs. empty service)", func() { ginkgo.It("handles endpoints only changes consistently (down scaling of replicas vs. empty service)", func() {
deploymentName := "scalingecho" deploymentName := "scalingecho"
f.NewEchoDeploymentWithNameAndReplicas(deploymentName, 0) f.NewEchoDeploymentWithNameAndReplicas(deploymentName, 0)
createIngress(f, "scaling.foo.com", deploymentName) createIngress(f, "scaling.foo.com", deploymentName)
originalResponseCode := runRequest(f, "scaling.foo.com")
resp := f.HTTPTestClient().
GET("/").
WithHeader("Host", "scaling.foo.com").
Expect().Raw()
originalResponseCode := resp.StatusCode
replicas := 2 replicas := 2
err := framework.UpdateDeployment(f.KubeClientSet, f.Namespace, deploymentName, replicas, nil) err := framework.UpdateDeployment(f.KubeClientSet, f.Namespace, deploymentName, replicas, nil)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
time.Sleep(waitForLuaSync * 2)
expectedSuccessResponseCode := runRequest(f, "scaling.foo.com") time.Sleep(waitForLuaSync)
resp = f.HTTPTestClient().
GET("/").
WithHeader("Host", "scaling.foo.com").
Expect().Raw()
expectedSuccessResponseCode := resp.StatusCode
replicas = 0 replicas = 0
err = framework.UpdateDeployment(f.KubeClientSet, f.Namespace, deploymentName, replicas, nil) err = framework.UpdateDeployment(f.KubeClientSet, f.Namespace, deploymentName, replicas, nil)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
time.Sleep(waitForLuaSync * 2)
expectedFailureResponseCode := runRequest(f, "scaling.foo.com") time.Sleep(waitForLuaSync)
Expect(originalResponseCode).To(Equal(503), "Expected empty service to return 503 response.") resp = f.HTTPTestClient().
Expect(expectedFailureResponseCode).To(Equal(503), "Expected downscaled replicaset to return 503 response.") GET("/").
Expect(expectedSuccessResponseCode).To(Equal(200), "Expected intermediate scaled replicaset to return a 200 response.") WithHeader("Host", "scaling.foo.com").
Expect().Raw()
expectedFailureResponseCode := resp.StatusCode
assert.Equal(ginkgo.GinkgoT(), originalResponseCode, 503, "Expected empty service to return 503 response.")
assert.Equal(ginkgo.GinkgoT(), expectedFailureResponseCode, 503, "Expected downscaled replicaset to return 503 response.")
assert.Equal(ginkgo.GinkgoT(), expectedSuccessResponseCode, 200, "Expected intermediate scaled replicaset to return a 200 response.")
}) })
It("handles an annotation change", func() { ginkgo.It("handles an annotation change", func() {
var nginxConfig string var nginxConfig string
f.WaitForNginxConfiguration(func(cfg string) bool { f.WaitForNginxConfiguration(func(cfg string) bool {
nginxConfig = cfg nginxConfig = cfg
@ -146,13 +176,17 @@ var _ = framework.IngressNginxDescribe("[Lua] dynamic configuration", func() {
}) })
ingress, err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Get("foo.com", metav1.GetOptions{}) ingress, err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Get("foo.com", metav1.GetOptions{})
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
ingress.ObjectMeta.Annotations["nginx.ingress.kubernetes.io/load-balance"] = "round_robin" ingress.ObjectMeta.Annotations["nginx.ingress.kubernetes.io/load-balance"] = "round_robin"
_, err = f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Update(ingress) _, err = f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Update(ingress)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
ensureRequest(f, "foo.com") f.HTTPTestClient().
GET("/").
WithHeader("Host", "foo.com").
Expect().
Status(http.StatusOK)
var newNginxConfig string var newNginxConfig string
f.WaitForNginxConfiguration(func(cfg string) bool { f.WaitForNginxConfiguration(func(cfg string) bool {
@ -160,31 +194,35 @@ var _ = framework.IngressNginxDescribe("[Lua] dynamic configuration", func() {
return true return true
}) })
Expect(nginxConfig).Should(Equal(newNginxConfig)) assert.Equal(ginkgo.GinkgoT(), nginxConfig, newNginxConfig)
}) })
}) })
It("sets controllerPodsCount in Lua general configuration", func() { ginkgo.It("sets controllerPodsCount in Lua general configuration", func() {
// https://github.com/curl/curl/issues/936 // https://github.com/curl/curl/issues/936
curlCmd := fmt.Sprintf("curl --fail --silent http://localhost:%v/configuration/general", nginx.StatusPort) curlCmd := fmt.Sprintf("curl --fail --silent http://localhost:%v/configuration/general", nginx.StatusPort)
output, err := f.ExecIngressPod(curlCmd) output, err := f.ExecIngressPod(curlCmd)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
Expect(output).Should(Equal(`{"controllerPodsCount":1}`)) assert.Equal(ginkgo.GinkgoT(), output, `{"controllerPodsCount":1}`)
err = framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 3, nil) err = framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 3, nil)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
output, err = f.ExecIngressPod(curlCmd) output, err = f.ExecIngressPod(curlCmd)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
Expect(output).Should(Equal(`{"controllerPodsCount":3}`)) assert.Equal(ginkgo.GinkgoT(), output, `{"controllerPodsCount":3}`)
}) })
}) })
func ensureIngress(f *framework.Framework, host string, deploymentName string) *networking.Ingress { func ensureIngress(f *framework.Framework, host string, deploymentName string) *networking.Ingress {
ing := createIngress(f, host, deploymentName) ing := createIngress(f, host, deploymentName)
ensureRequest(f, host) f.HTTPTestClient().
GET("/").
WithHeader("Host", host).
Expect().
Status(http.StatusOK)
return ing return ing
} }
@ -205,44 +243,18 @@ func createIngress(f *framework.Framework, host string, deploymentName string) *
return ing return ing
} }
func ensureRequest(f *framework.Framework, host string) { func ensureHTTPSRequest(f *framework.Framework, url string, host string, expectedDNSName string) {
resp, _, errs := gorequest.New(). resp := f.HTTPTestClientWithTLSConfig(&tls.Config{
Get(f.GetURL(framework.HTTP)). ServerName: host,
Set("Host", host). InsecureSkipVerify: true,
End() }).
Expect(errs).Should(BeEmpty()) GET("/").
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) WithURL(url).
} WithHeader("Host", host).
Expect().
Raw()
func ensureRequestWithStatus(f *framework.Framework, host string, statusCode int) { assert.Equal(ginkgo.GinkgoT(), resp.StatusCode, http.StatusOK)
resp, _, errs := gorequest.New(). assert.Equal(ginkgo.GinkgoT(), len(resp.TLS.PeerCertificates), 1)
Get(f.GetURL(framework.HTTP)). assert.Equal(ginkgo.GinkgoT(), resp.TLS.PeerCertificates[0].DNSNames[0], expectedDNSName)
Set("Host", host).
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(statusCode))
}
func runRequest(f *framework.Framework, host string) int {
resp, _, errs := gorequest.New().
Get(f.GetURL(framework.HTTP)).
Set("Host", host).
End()
Expect(errs).Should(BeEmpty())
return resp.StatusCode
}
func ensureHTTPSRequest(url string, host string, expectedDNSName string) {
resp, _, errs := gorequest.New().
Get(url).
Set("Host", host).
TLSClientConfig(&tls.Config{
InsecureSkipVerify: true,
ServerName: host,
}).
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(len(resp.TLS.PeerCertificates)).Should(BeNumerically("==", 1))
Expect(resp.TLS.PeerCertificates[0].DNSNames[0]).Should(Equal(expectedDNSName))
} }

View file

@ -23,8 +23,8 @@ import (
"strings" "strings"
"time" "time"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -32,11 +32,11 @@ import (
var _ = framework.IngressNginxDescribe("[Security] request smuggling", func() { var _ = framework.IngressNginxDescribe("[Security] request smuggling", func() {
f := framework.NewDefaultFramework("request-smuggling") f := framework.NewDefaultFramework("request-smuggling")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
It("should not return body content from error_page", func() { ginkgo.It("should not return body content from error_page", func() {
host := "foo.bar.com" host := "foo.bar.com"
snippet := ` snippet := `
@ -62,8 +62,8 @@ server {
}) })
out, err := smugglingRequest(host, f.GetNginxIP(), 80) out, err := smugglingRequest(host, f.GetNginxIP(), 80)
Expect(err).NotTo(HaveOccurred(), "obtaining response of request smuggling check") assert.Nil(ginkgo.GinkgoT(), err, "obtaining response of request smuggling check")
Expect(out).ShouldNot(ContainSubstring("This should be hidden!")) assert.NotContains(ginkgo.GinkgoT(), out, "This should be hidden!")
}) })
}) })

View file

@ -17,13 +17,10 @@ limitations under the License.
package servicebackend package servicebackend
import ( import (
"net/http"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"github.com/parnurzeal/gorequest"
corev1 "k8s.io/api/core/v1" corev1 "k8s.io/api/core/v1"
networking "k8s.io/api/networking/v1beta1" networking "k8s.io/api/networking/v1beta1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
@ -35,7 +32,7 @@ import (
var _ = framework.IngressNginxDescribe("[Service] backend status code 503", func() { var _ = framework.IngressNginxDescribe("[Service] backend status code 503", func() {
f := framework.NewDefaultFramework("service-backend") f := framework.NewDefaultFramework("service-backend")
It("should return 503 when backend service does not exist", func() { ginkgo.It("should return 503 when backend service does not exist", func() {
host := "nonexistent.svc.com" host := "nonexistent.svc.com"
bi := buildIngressWithNonexistentService(host, f.Namespace, "/") bi := buildIngressWithNonexistentService(host, f.Namespace, "/")
@ -46,15 +43,14 @@ var _ = framework.IngressNginxDescribe("[Service] backend status code 503", func
return strings.Contains(server, "proxy_pass http://upstream_balancer;") return strings.Contains(server, "proxy_pass http://upstream_balancer;")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).Should(BeEmpty()) Status(http.StatusServiceUnavailable)
Expect(resp.StatusCode).Should(Equal(503))
}) })
It("should return 503 when all backend service endpoints are unavailable", func() { ginkgo.It("should return 503 when all backend service endpoints are unavailable", func() {
host := "unavailable.svc.com" host := "unavailable.svc.com"
bi, bs := buildIngressWithUnavailableServiceEndpoints(host, f.Namespace, "/") bi, bs := buildIngressWithUnavailableServiceEndpoints(host, f.Namespace, "/")
@ -67,14 +63,12 @@ var _ = framework.IngressNginxDescribe("[Service] backend status code 503", func
return strings.Contains(server, "proxy_pass http://upstream_balancer;") return strings.Contains(server, "proxy_pass http://upstream_balancer;")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).Should(BeEmpty()) Status(http.StatusServiceUnavailable)
Expect(resp.StatusCode).Should(Equal(503))
}) })
}) })
func buildIngressWithNonexistentService(host, namespace, path string) *networking.Ingress { func buildIngressWithNonexistentService(host, namespace, path string) *networking.Ingress {

View file

@ -17,13 +17,10 @@ limitations under the License.
package servicebackend package servicebackend
import ( import (
"net/http"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"github.com/parnurzeal/gorequest"
core "k8s.io/api/core/v1" core "k8s.io/api/core/v1"
corev1 "k8s.io/api/core/v1" corev1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
@ -35,7 +32,7 @@ import (
var _ = framework.IngressNginxDescribe("[Service] Type ExternalName", func() { var _ = framework.IngressNginxDescribe("[Service] Type ExternalName", func() {
f := framework.NewDefaultFramework("type-externalname") f := framework.NewDefaultFramework("type-externalname")
It("works with external name set to incomplete fdqn", func() { ginkgo.It("works with external name set to incomplete fdqn", func() {
f.NewEchoDeployment() f.NewEchoDeployment()
host := "echo" host := "echo"
@ -61,15 +58,14 @@ var _ = framework.IngressNginxDescribe("[Service] Type ExternalName", func() {
return strings.Contains(server, "proxy_pass http://upstream_balancer;") return strings.Contains(server, "proxy_pass http://upstream_balancer;")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+"/get"). GET("/get").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).Should(BeEmpty()) Status(http.StatusOK)
Expect(resp.StatusCode).Should(Equal(200))
}) })
It("should return 200 for service type=ExternalName without a port defined", func() { ginkgo.It("should return 200 for service type=ExternalName without a port defined", func() {
host := "echo" host := "echo"
svc := &core.Service{ svc := &core.Service{
@ -93,15 +89,14 @@ var _ = framework.IngressNginxDescribe("[Service] Type ExternalName", func() {
return strings.Contains(server, "proxy_pass http://upstream_balancer;") return strings.Contains(server, "proxy_pass http://upstream_balancer;")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+"/get"). GET("/get").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).Should(BeEmpty()) Status(http.StatusOK)
Expect(resp.StatusCode).Should(Equal(200))
}) })
It("should return 200 for service type=ExternalName with a port defined", func() { ginkgo.It("should return 200 for service type=ExternalName with a port defined", func() {
host := "echo" host := "echo"
svc := &core.Service{ svc := &core.Service{
@ -132,15 +127,14 @@ var _ = framework.IngressNginxDescribe("[Service] Type ExternalName", func() {
return strings.Contains(server, "proxy_pass http://upstream_balancer;") return strings.Contains(server, "proxy_pass http://upstream_balancer;")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+"/get"). GET("/get").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).Should(BeEmpty()) Status(http.StatusOK)
Expect(resp.StatusCode).Should(Equal(200))
}) })
It("should return status 502 for service type=ExternalName with an invalid host", func() { ginkgo.It("should return status 502 for service type=ExternalName with an invalid host", func() {
host := "echo" host := "echo"
svc := &core.Service{ svc := &core.Service{
@ -164,15 +158,14 @@ var _ = framework.IngressNginxDescribe("[Service] Type ExternalName", func() {
return strings.Contains(server, "proxy_pass http://upstream_balancer;") return strings.Contains(server, "proxy_pass http://upstream_balancer;")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+"/get"). GET("/get").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).Should(BeEmpty()) Status(http.StatusBadGateway)
Expect(resp.StatusCode).Should(Equal(502))
}) })
It("should return 200 for service type=ExternalName using a port name", func() { ginkgo.It("should return 200 for service type=ExternalName using a port name", func() {
host := "echo" host := "echo"
svc := &core.Service{ svc := &core.Service{
@ -204,12 +197,10 @@ var _ = framework.IngressNginxDescribe("[Service] Type ExternalName", func() {
return strings.Contains(server, "proxy_pass http://upstream_balancer;") return strings.Contains(server, "proxy_pass http://upstream_balancer;")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+"/get"). GET("/get").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).Should(BeEmpty()) Status(http.StatusOK)
Expect(resp.StatusCode).Should(Equal(200))
}) })
}) })

View file

@ -20,8 +20,8 @@ import (
"regexp" "regexp"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -29,17 +29,17 @@ import (
var _ = framework.DescribeSetting("Configmap change", func() { var _ = framework.DescribeSetting("Configmap change", func() {
f := framework.NewDefaultFramework("configmap-change") f := framework.NewDefaultFramework("configmap-change")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
It("should reload after an update in the configuration", func() { ginkgo.It("should reload after an update in the configuration", func() {
host := "configmap-change" host := "configmap-change"
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil) ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil)
f.EnsureIngress(ing) f.EnsureIngress(ing)
By("adding a whitelist-source-range") ginkgo.By("adding a whitelist-source-range")
f.UpdateNginxConfigMapData("whitelist-source-range", "1.1.1.1") f.UpdateNginxConfigMapData("whitelist-source-range", "1.1.1.1")
@ -56,9 +56,9 @@ var _ = framework.DescribeSetting("Configmap change", func() {
return strings.Contains(cfg, "allow 1.1.1.1;") return strings.Contains(cfg, "allow 1.1.1.1;")
}) })
Expect(checksum).NotTo(BeEmpty()) assert.NotEmpty(ginkgo.GinkgoT(), checksum)
By("changing error-log-level") ginkgo.By("changing error-log-level")
f.UpdateNginxConfigMapData("error-log-level", "debug") f.UpdateNginxConfigMapData("error-log-level", "debug")
@ -72,6 +72,6 @@ var _ = framework.DescribeSetting("Configmap change", func() {
return strings.ContainsAny(cfg, "error_log /var/log/nginx/error.log debug;") return strings.ContainsAny(cfg, "error_log /var/log/nginx/error.log debug;")
}) })
Expect(checksum).NotTo(BeEquivalentTo(newChecksum)) assert.NotEqual(ginkgo.GinkgoT(), checksum, newChecksum)
}) })
}) })

View file

@ -21,55 +21,48 @@ import (
"net/http" "net/http"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeSetting("Add custom headers", func() { var _ = framework.DescribeSetting("add-headers", func() {
f := framework.NewDefaultFramework("custom-header") f := framework.NewDefaultFramework("custom-header")
host := "custom-header" host := "custom-header"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil) ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil)
f.EnsureIngress(ing) f.EnsureIngress(ing)
}) })
AfterEach(func() { ginkgo.It("Add a custom header", func() {
})
It("Add a custom header", func() {
customHeader := "X-A-Custom-Header" customHeader := "X-A-Custom-Header"
customHeaderValue := "customHeaderValue" customHeaderValue := "customHeaderValue"
h := make(map[string]string) h := make(map[string]string)
h[customHeader] = customHeaderValue h[customHeader] = customHeaderValue
f.CreateConfigMap("add-headers-configmap", h) cfgMap := "add-headers-configmap"
wlKey := "add-headers" f.CreateConfigMap(cfgMap, h)
wlValue := f.Namespace + "/add-headers-configmap"
f.UpdateNginxConfigMapData(wlKey, wlValue) f.UpdateNginxConfigMapData("add-headers", fmt.Sprintf("%v/%v", f.Namespace, cfgMap))
f.WaitForNginxConfiguration(func(server string) bool { f.WaitForNginxConfiguration(func(server string) bool {
return strings.Contains(server, fmt.Sprintf("more_set_headers \"%s: %s\";", customHeader, customHeaderValue)) return strings.Contains(server, fmt.Sprintf("more_set_headers \"%s: %s\";", customHeader, customHeaderValue))
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Expect(errs).Should(BeEmpty()) Header(customHeader).Contains(customHeaderValue)
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(resp.Header.Get(customHeader)).Should(ContainSubstring(customHeaderValue))
}) })
It("Add multiple custom headers", func() { ginkgo.It("Add multiple custom headers", func() {
firstCustomHeader := "X-First" firstCustomHeader := "X-First"
firstCustomHeaderValue := "Prepare for trouble!" firstCustomHeaderValue := "Prepare for trouble!"
secondCustomHeader := "X-Second" secondCustomHeader := "X-Second"
@ -79,25 +72,25 @@ var _ = framework.DescribeSetting("Add custom headers", func() {
h[firstCustomHeader] = firstCustomHeaderValue h[firstCustomHeader] = firstCustomHeaderValue
h[secondCustomHeader] = secondCustomHeaderValue h[secondCustomHeader] = secondCustomHeaderValue
f.CreateConfigMap("add-headers-configmap-two", h) cfgMap := "add-headers-configmap-two"
wlKey := "add-headers" f.CreateConfigMap(cfgMap, h)
wlValue := f.Namespace + "/add-headers-configmap-two"
f.UpdateNginxConfigMapData(wlKey, wlValue) f.UpdateNginxConfigMapData("add-headers", fmt.Sprintf("%v/%v", f.Namespace, cfgMap))
f.WaitForNginxConfiguration(func(server string) bool { f.WaitForNginxConfiguration(func(server string) bool {
return strings.Contains(server, fmt.Sprintf("more_set_headers \"%s: %s\";", firstCustomHeader, firstCustomHeaderValue)) && strings.Contains(server, fmt.Sprintf("more_set_headers \"%s: %s\";", secondCustomHeader, secondCustomHeaderValue)) return strings.Contains(server, fmt.Sprintf("more_set_headers \"%s: %s\";", firstCustomHeader, firstCustomHeaderValue)) &&
strings.Contains(server, fmt.Sprintf("more_set_headers \"%s: %s\";", secondCustomHeader, secondCustomHeaderValue))
}) })
resp, _, errs := gorequest.New(). resp := f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Raw()
Expect(errs).Should(BeEmpty()) assert.Equal(ginkgo.GinkgoT(), resp.Header.Get(firstCustomHeader), firstCustomHeaderValue)
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) assert.Equal(ginkgo.GinkgoT(), resp.Header.Get(secondCustomHeader), secondCustomHeaderValue)
Expect(resp.Header.Get(firstCustomHeader)).Should(ContainSubstring(firstCustomHeaderValue))
Expect(resp.Header.Get(secondCustomHeader)).Should(ContainSubstring(secondCustomHeaderValue))
}) })
}) })

View file

@ -21,9 +21,8 @@ import (
"fmt" "fmt"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
appsv1 "k8s.io/api/apps/v1" appsv1 "k8s.io/api/apps/v1"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
@ -36,7 +35,7 @@ var _ = framework.IngressNginxDescribe("[SSL] [Flag] default-ssl-certificate", f
service := framework.EchoService service := framework.EchoService
port := 80 port := 80
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeploymentWithReplicas(1)
var err error var err error
@ -44,7 +43,7 @@ var _ = framework.IngressNginxDescribe("[SSL] [Flag] default-ssl-certificate", f
[]string{"*"}, []string{"*"},
secretName, secretName,
f.Namespace) f.Namespace)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
err = framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1, err = framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1,
func(deployment *appsv1.Deployment) error { func(deployment *appsv1.Deployment) error {
@ -55,29 +54,29 @@ var _ = framework.IngressNginxDescribe("[SSL] [Flag] default-ssl-certificate", f
return err return err
}) })
Expect(err).NotTo(HaveOccurred(), "unexpected error updating ingress controller deployment flags") assert.Nil(ginkgo.GinkgoT(), err, "updating ingress controller deployment flags")
// this asserts that it configures default custom ssl certificate without an ingress at all // this asserts that it configures default custom ssl certificate without an ingress at all
framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig) framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig)
}) })
It("uses default ssl certificate for catch-all ingress", func() { ginkgo.It("uses default ssl certificate for catch-all ingress", func() {
ing := framework.NewSingleCatchAllIngress("catch-all", f.Namespace, service, port, nil) ing := framework.NewSingleCatchAllIngress("catch-all", f.Namespace, service, port, nil)
f.EnsureIngress(ing) f.EnsureIngress(ing)
By("making sure new ingress is deployed") ginkgo.By("making sure new ingress is deployed")
expectedConfig := fmt.Sprintf(`set $proxy_upstream_name "%v-%v-%v";`, f.Namespace, service, port) expectedConfig := fmt.Sprintf(`set $proxy_upstream_name "%v-%v-%v";`, f.Namespace, service, port)
f.WaitForNginxServer("_", func(cfg string) bool { f.WaitForNginxServer("_", func(cfg string) bool {
return strings.Contains(cfg, expectedConfig) return strings.Contains(cfg, expectedConfig)
}) })
By("making sure new ingress is responding") ginkgo.By("making sure new ingress is responding")
By("making sure the configured default ssl certificate is being used") ginkgo.By("making sure the configured default ssl certificate is being used")
framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig) framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig)
}) })
It("uses default ssl certificate for host based ingress when configured certificate does not match host", func() { ginkgo.It("uses default ssl certificate for host based ingress when configured certificate does not match host", func() {
host := "foo" host := "foo"
ing := f.EnsureIngress(framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, service, port, nil)) ing := f.EnsureIngress(framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, service, port, nil))
@ -85,15 +84,15 @@ var _ = framework.IngressNginxDescribe("[SSL] [Flag] default-ssl-certificate", f
[]string{"not.foo"}, []string{"not.foo"},
ing.Spec.TLS[0].SecretName, ing.Spec.TLS[0].SecretName,
ing.Namespace) ing.Namespace)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
By("making sure new ingress is deployed") ginkgo.By("making sure new ingress is deployed")
expectedConfig := fmt.Sprintf(`set $proxy_upstream_name "%v-%v-%v";`, f.Namespace, service, port) expectedConfig := fmt.Sprintf(`set $proxy_upstream_name "%v-%v-%v";`, f.Namespace, service, port)
f.WaitForNginxServer(host, func(cfg string) bool { f.WaitForNginxServer(host, func(cfg string) bool {
return strings.Contains(cfg, expectedConfig) return strings.Contains(cfg, expectedConfig)
}) })
By("making sure the configured default ssl certificate is being used") ginkgo.By("making sure the configured default ssl certificate is being used")
framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig) framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig)
}) })
}) })

View file

@ -20,10 +20,8 @@ import (
"net/http" "net/http"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
appsv1 "k8s.io/api/apps/v1" appsv1 "k8s.io/api/apps/v1"
networking "k8s.io/api/networking/v1beta1" networking "k8s.io/api/networking/v1beta1"
"k8s.io/apimachinery/pkg/util/intstr" "k8s.io/apimachinery/pkg/util/intstr"
@ -34,7 +32,7 @@ import (
var _ = framework.IngressNginxDescribe("[Flag] disable-catch-all", func() { var _ = framework.IngressNginxDescribe("[Flag] disable-catch-all", func() {
f := framework.NewDefaultFramework("disabled-catch-all") f := framework.NewDefaultFramework("disabled-catch-all")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeploymentWithReplicas(1)
err := framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1, err := framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1,
@ -46,10 +44,10 @@ var _ = framework.IngressNginxDescribe("[Flag] disable-catch-all", func() {
return err return err
}) })
Expect(err).NotTo(HaveOccurred(), "unexpected error updating ingress controller deployment flags") assert.Nil(ginkgo.GinkgoT(), err, "updating ingress controller deployment flags")
}) })
It("should ignore catch all Ingress", func() { ginkgo.It("should ignore catch all Ingress", func() {
host := "foo" host := "foo"
ing := framework.NewSingleCatchAllIngress("catch-all", f.Namespace, framework.EchoService, 80, nil) ing := framework.NewSingleCatchAllIngress("catch-all", f.Namespace, framework.EchoService, 80, nil)
@ -68,7 +66,7 @@ var _ = framework.IngressNginxDescribe("[Flag] disable-catch-all", func() {
}) })
}) })
It("should delete Ingress updated to catch-all", func() { ginkgo.It("should delete Ingress updated to catch-all", func() {
host := "foo" host := "foo"
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil) ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil)
@ -79,12 +77,11 @@ var _ = framework.IngressNginxDescribe("[Flag] disable-catch-all", func() {
return strings.Contains(server, "server_name foo") return strings.Contains(server, "server_name foo")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusOK)
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
err := framework.UpdateIngress(f.KubeClientSet, f.Namespace, host, func(ingress *networking.Ingress) error { err := framework.UpdateIngress(f.KubeClientSet, f.Namespace, host, func(ingress *networking.Ingress) error {
ingress.Spec.Rules = nil ingress.Spec.Rules = nil
@ -94,21 +91,20 @@ var _ = framework.IngressNginxDescribe("[Flag] disable-catch-all", func() {
} }
return nil return nil
}) })
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
f.WaitForNginxConfiguration(func(cfg string) bool { f.WaitForNginxConfiguration(func(cfg string) bool {
return !strings.Contains(cfg, "server_name foo") return !strings.Contains(cfg, "server_name foo")
}) })
resp, _, errs = gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusNotFound)
Expect(resp.StatusCode).Should(Equal(http.StatusNotFound))
}) })
It("should allow Ingress with both a default backend and rules", func() { ginkgo.It("should allow Ingress with both a default backend and rules", func() {
host := "foo" host := "foo"
ing := framework.NewSingleIngressWithBackendAndRules("not-catch-all", "/rulepath", host, f.Namespace, framework.EchoService, 80, framework.EchoService, 80, nil) ing := framework.NewSingleIngressWithBackendAndRules("not-catch-all", "/rulepath", host, f.Namespace, framework.EchoService, 80, framework.EchoService, 80, nil)
@ -118,13 +114,10 @@ var _ = framework.IngressNginxDescribe("[Flag] disable-catch-all", func() {
return strings.Contains(cfg, "server_name foo") return strings.Contains(cfg, "server_name foo")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK)
Expect(errs).To(BeNil())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
}) })
}) })

View file

@ -21,9 +21,8 @@ import (
"net/http" "net/http"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -33,12 +32,12 @@ var _ = framework.DescribeSetting("use-forwarded-headers", func() {
setting := "use-forwarded-headers" setting := "use-forwarded-headers"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
f.UpdateNginxConfigMapData(setting, "false") f.UpdateNginxConfigMapData(setting, "false")
}) })
It("should trust X-Forwarded headers when setting is true", func() { ginkgo.It("should trust X-Forwarded headers when setting is true", func() {
host := "forwarded-headers" host := "forwarded-headers"
f.UpdateNginxConfigMapData(setting, "true") f.UpdateNginxConfigMapData(setting, "true")
@ -51,41 +50,43 @@ var _ = framework.DescribeSetting("use-forwarded-headers", func() {
return strings.Contains(server, "server_name forwarded-headers") return strings.Contains(server, "server_name forwarded-headers")
}) })
By("ensuring single values are parsed correctly") ginkgo.By("ensuring single values are parsed correctly")
resp, body, errs := gorequest.New(). body := f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
Set("X-Forwarded-Port", "1234"). WithHeader("X-Forwarded-Port", "1234").
Set("X-Forwarded-Proto", "myproto"). WithHeader("X-Forwarded-Proto", "myproto").
Set("X-Forwarded-For", "1.2.3.4"). WithHeader("X-Forwarded-For", "1.2.3.4").
Set("X-Forwarded-Host", "myhost"). WithHeader("X-Forwarded-Host", "myhost").
End() Expect().
Status(http.StatusOK).
Body().
Raw()
Expect(errs).Should(BeEmpty()) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("host=myhost"))
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-host=myhost"))
Expect(body).Should(ContainSubstring(fmt.Sprintf("host=myhost"))) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-proto=myproto"))
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-forwarded-host=myhost"))) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-port=1234"))
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-forwarded-proto=myproto"))) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-for=1.2.3.4"))
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-forwarded-port=1234")))
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-forwarded-for=1.2.3.4")))
By("ensuring that first entry in X-Forwarded-Host is used as the best host") ginkgo.By("ensuring that first entry in X-Forwarded-Host is used as the best host")
resp, body, errs = gorequest.New(). body = f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
Set("X-Forwarded-Port", "1234"). WithHeader("X-Forwarded-Port", "1234").
Set("X-Forwarded-Proto", "myproto"). WithHeader("X-Forwarded-Proto", "myproto").
Set("X-Forwarded-For", "1.2.3.4"). WithHeader("X-Forwarded-For", "1.2.3.4").
Set("X-Forwarded-Host", "myhost.com, another.host,example.net"). WithHeader("X-Forwarded-Host", "myhost.com, another.host,example.net").
End() Expect().
Status(http.StatusOK).
Expect(errs).Should(BeEmpty()) Body().
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) Raw()
Expect(body).Should(ContainSubstring(fmt.Sprintf("host=myhost.com")))
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-forwarded-host=myhost.com")))
assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("host=myhost.com"))
assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-host=myhost.com"))
}) })
It("should not trust X-Forwarded headers when setting is false", func() {
ginkgo.It("should not trust X-Forwarded headers when setting is false", func() {
host := "forwarded-headers" host := "forwarded-headers"
f.UpdateNginxConfigMapData(setting, "false") f.UpdateNginxConfigMapData(setting, "false")
@ -97,25 +98,26 @@ var _ = framework.DescribeSetting("use-forwarded-headers", func() {
return strings.Contains(server, "server_name forwarded-headers") return strings.Contains(server, "server_name forwarded-headers")
}) })
resp, body, errs := gorequest.New(). body := f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
Set("X-Forwarded-Port", "1234"). WithHeader("X-Forwarded-Port", "1234").
Set("X-Forwarded-Proto", "myproto"). WithHeader("X-Forwarded-Proto", "myproto").
Set("X-Forwarded-For", "1.2.3.4"). WithHeader("X-Forwarded-For", "1.2.3.4").
Set("X-Forwarded-Host", "myhost"). WithHeader("X-Forwarded-Host", "myhost").
End() Expect().
Status(http.StatusOK).
Body().
Raw()
Expect(errs).Should(BeEmpty()) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("host=forwarded-headers"))
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-port=80"))
Expect(body).Should(ContainSubstring(fmt.Sprintf("host=forwarded-headers"))) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-proto=http"))
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-forwarded-port=80"))) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-original-forwarded-for=1.2.3.4"))
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-forwarded-proto=http"))) assert.NotContains(ginkgo.GinkgoT(), body, fmt.Sprintf("host=myhost"))
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-original-forwarded-for=1.2.3.4"))) assert.NotContains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-host=myhost"))
Expect(body).ShouldNot(ContainSubstring(fmt.Sprintf("host=myhost"))) assert.NotContains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-proto=myproto"))
Expect(body).ShouldNot(ContainSubstring(fmt.Sprintf("x-forwarded-host=myhost"))) assert.NotContains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-port=1234"))
Expect(body).ShouldNot(ContainSubstring(fmt.Sprintf("x-forwarded-proto=myproto"))) assert.NotContains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-for=1.2.3.4"))
Expect(body).ShouldNot(ContainSubstring(fmt.Sprintf("x-forwarded-port=1234")))
Expect(body).ShouldNot(ContainSubstring(fmt.Sprintf("x-forwarded-for=1.2.3.4")))
}) })
}) })

View file

@ -21,9 +21,8 @@ import (
"net/http" "net/http"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -32,12 +31,12 @@ var _ = framework.DescribeSetting("Geoip2", func() {
host := "geoip2" host := "geoip2"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
It("should only allow requests from specific countries", func() { ginkgo.It("should only allow requests from specific countries", func() {
Skip("GeoIP test are temporarily disabled") ginkgo.Skip("GeoIP test are temporarily disabled")
f.UpdateNginxConfigMapData("use-geoip2", "true") f.UpdateNginxConfigMapData("use-geoip2", "true")
@ -72,22 +71,20 @@ var _ = framework.DescribeSetting("Geoip2", func() {
// Should be blocked // Should be blocked
usIP := "8.8.8.8" usIP := "8.8.8.8"
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
Set("X-Forwarded-For", usIP). WithHeader("X-Forwarded-For", usIP).
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusForbidden)
Expect(resp.StatusCode).Should(Equal(http.StatusForbidden))
// Shouldn't be blocked // Shouldn't be blocked
australianIP := "1.1.1.1" australianIP := "1.1.1.1"
resp, _, errs = gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
Set("X-Forwarded-For", australianIP). WithHeader("X-Forwarded-For", australianIP).
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusOK)
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
}) })
}) })

View file

@ -20,9 +20,7 @@ import (
"net/http" "net/http"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -32,12 +30,12 @@ var _ = framework.DescribeSetting("[Security] block-*", func() {
host := "global-access-block" host := "global-access-block"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeployment()
f.EnsureIngress(framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil)) f.EnsureIngress(framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil))
}) })
It("should block CIDRs defined in the ConfigMap", func() { ginkgo.It("should block CIDRs defined in the ConfigMap", func() {
f.UpdateNginxConfigMapData("block-cidrs", "172.16.0.0/12,192.168.0.0/16,10.0.0.0/8") f.UpdateNginxConfigMapData("block-cidrs", "172.16.0.0/12,192.168.0.0/16,10.0.0.0/8")
f.WaitForNginxConfiguration( f.WaitForNginxConfiguration(
@ -47,15 +45,14 @@ var _ = framework.DescribeSetting("[Security] block-*", func() {
strings.Contains(cfg, "deny 10.0.0.0/8;") strings.Contains(cfg, "deny 10.0.0.0/8;")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusForbidden)
Expect(resp.StatusCode).Should(Equal(http.StatusForbidden))
}) })
It("should block User-Agents defined in the ConfigMap", func() { ginkgo.It("should block User-Agents defined in the ConfigMap", func() {
f.UpdateNginxConfigMapData("block-user-agents", "~*chrome\\/68\\.0\\.3440\\.106\\ safari\\/537\\.36,AlphaBot") f.UpdateNginxConfigMapData("block-user-agents", "~*chrome\\/68\\.0\\.3440\\.106\\ safari\\/537\\.36,AlphaBot")
f.WaitForNginxConfiguration( f.WaitForNginxConfiguration(
@ -65,33 +62,30 @@ var _ = framework.DescribeSetting("[Security] block-*", func() {
}) })
// Should be blocked // Should be blocked
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
Set("User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/68.0.3440.106 Safari/537.36"). WithHeader("User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/68.0.3440.106 Safari/537.36").
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusForbidden)
Expect(resp.StatusCode).Should(Equal(http.StatusForbidden))
resp, _, errs = gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
Set("User-Agent", "AlphaBot"). WithHeader("User-Agent", "AlphaBot").
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusForbidden)
Expect(resp.StatusCode).Should(Equal(http.StatusForbidden))
// Shouldn't be blocked // Shouldn't be blocked
resp, _, errs = gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
Set("User-Agent", "Mozilla/5.0 (iPhone; CPU iPhone OS 11_4_1 like Mac OS X) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/11.0 Mobile/15E148 Safari/604.1"). WithHeader("User-Agent", "Mozilla/5.0 (iPhone; CPU iPhone OS 11_4_1 like Mac OS X) AppleWebKit/605.1.15 (KHTML, like Gecko) Version/11.0 Mobile/15E148 Safari/604.1").
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusOK)
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
}) })
It("should block Referers defined in the ConfigMap", func() { ginkgo.It("should block Referers defined in the ConfigMap", func() {
f.UpdateNginxConfigMapData("block-referers", "~*example\\.com,qwerty") f.UpdateNginxConfigMapData("block-referers", "~*example\\.com,qwerty")
f.WaitForNginxConfiguration( f.WaitForNginxConfiguration(
@ -101,29 +95,26 @@ var _ = framework.DescribeSetting("[Security] block-*", func() {
}) })
// Should be blocked // Should be blocked
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
Set("Referer", "example.com"). WithHeader("Referer", "example.com").
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusForbidden)
Expect(resp.StatusCode).Should(Equal(http.StatusForbidden))
resp, _, errs = gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
Set("Referer", "qwerty"). WithHeader("Referer", "qwerty").
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusForbidden)
Expect(resp.StatusCode).Should(Equal(http.StatusForbidden))
// Shouldn't be blocked // Shouldn't be blocked
resp, _, errs = gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
Set("Referer", "qwerty123"). WithHeader("Referer", "qwerty123").
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusOK)
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
}) })
}) })

View file

@ -19,12 +19,13 @@ package settings
import ( import (
"fmt" "fmt"
"net/http" "net/http"
"time" "regexp"
"strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
networking "k8s.io/api/networking/v1beta1"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -45,106 +46,107 @@ var _ = framework.DescribeSetting("[Security] global-auth-url", func() {
enableGlobalExternalAuthAnnotation := "nginx.ingress.kubernetes.io/enable-global-auth" enableGlobalExternalAuthAnnotation := "nginx.ingress.kubernetes.io/enable-global-auth"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
f.NewHttpbinDeployment() f.NewHttpbinDeployment()
}) })
Context("when global external authentication is configured", func() { ginkgo.Context("when global external authentication is configured", func() {
BeforeEach(func() { ginkgo.BeforeEach(func() {
globalExternalAuthURL := fmt.Sprintf("http://%s.%s.svc.cluster.local:80/status/401", framework.HTTPBinService, f.Namespace) globalExternalAuthURL := fmt.Sprintf("http://%s.%s.svc.cluster.local:80/status/401", framework.HTTPBinService, f.Namespace)
By("Adding an ingress rule for /foo") ginkgo.By("Adding an ingress rule for /foo")
fooIng := framework.NewSingleIngress("foo-ingress", fooPath, host, f.Namespace, echoServiceName, 80, nil) fooIng := framework.NewSingleIngress("foo-ingress", fooPath, host, f.Namespace, echoServiceName, 80, nil)
f.EnsureIngress(fooIng) f.EnsureIngress(fooIng)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("location /foo")) return strings.Contains(server, "location /foo")
}) })
By("Adding an ingress rule for /bar") ginkgo.By("Adding an ingress rule for /bar")
barIng := framework.NewSingleIngress("bar-ingress", barPath, host, f.Namespace, echoServiceName, 80, nil) barIng := framework.NewSingleIngress("bar-ingress", barPath, host, f.Namespace, echoServiceName, 80, nil)
f.EnsureIngress(barIng) f.EnsureIngress(barIng)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("location /bar")) return strings.Contains(server, "location /bar")
}) })
By("Adding a global-auth-url to configMap") ginkgo.By("Adding a global-auth-url to configMap")
f.UpdateNginxConfigMapData(globalExternalAuthURLSetting, globalExternalAuthURL) f.UpdateNginxConfigMapData(globalExternalAuthURLSetting, globalExternalAuthURL)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring(globalExternalAuthURL)) return strings.Contains(server, globalExternalAuthURL)
}) })
}) })
It("should return status code 401 when request any protected service", func() { ginkgo.It("should return status code 401 when request any protected service", func() {
By("Sending a request to protected service /foo") ginkgo.By("Sending a request to protected service /foo")
fooResp, _, _ := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+fooPath). GET(fooPath).
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(fooResp.StatusCode).Should(Equal(http.StatusUnauthorized)) Status(http.StatusUnauthorized)
By("Sending a request to protected service /bar") ginkgo.By("Sending a request to protected service /bar")
barResp, _, _ := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+barPath). GET(barPath).
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(barResp.StatusCode).Should(Equal(http.StatusUnauthorized)) Status(http.StatusUnauthorized)
}) })
It("should return status code 200 when request whitelisted (via no-auth-locations) service and 401 when request protected service", func() { ginkgo.It("should return status code 200 when request whitelisted (via no-auth-locations) service and 401 when request protected service", func() {
By("Adding a no-auth-locations for /bar to configMap") ginkgo.By("Adding a no-auth-locations for /bar to configMap")
f.UpdateNginxConfigMapData(noAuthSetting, noAuthLocations) f.UpdateNginxConfigMapData(noAuthSetting, noAuthLocations)
By("Sending a request to protected service /foo") ginkgo.By("Sending a request to protected service /foo")
fooResp, _, _ := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+fooPath). GET(fooPath).
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(fooResp.StatusCode).Should(Equal(http.StatusUnauthorized)) Status(http.StatusUnauthorized)
By("Sending a request to whitelisted service /bar") ginkgo.By("Sending a request to whitelisted service /bar")
barResp, _, _ := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+barPath). GET(barPath).
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(barResp.StatusCode).Should(Equal(http.StatusOK)) Status(http.StatusOK)
}) })
It("should return status code 200 when request whitelisted (via ingress annotation) service and 401 when request protected service", func() { ginkgo.It("should return status code 200 when request whitelisted (via ingress annotation) service and 401 when request protected service", func() {
ginkgo.By("Adding an ingress rule for /bar with annotation enable-global-auth = false")
err := framework.UpdateIngress(f.KubeClientSet, f.Namespace, "bar-ingress", func(ingress *networking.Ingress) error {
ingress.ObjectMeta.Annotations[enableGlobalExternalAuthAnnotation] = "false"
return nil
})
assert.Nil(ginkgo.GinkgoT(), err)
By("Adding an ingress rule for /bar with annotation enable-global-auth = false")
annotations := map[string]string{
enableGlobalExternalAuthAnnotation: "false",
}
barIng := framework.NewSingleIngress("bar-ingress", barPath, host, f.Namespace, echoServiceName, 80, annotations)
f.EnsureIngress(barIng)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("location /bar")) return strings.Contains(server, "location /bar")
}) })
By("Sending a request to protected service /foo") ginkgo.By("Sending a request to protected service /foo")
fooResp, _, _ := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+fooPath). GET(fooPath).
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(fooResp.StatusCode).Should(Equal(http.StatusUnauthorized)) Status(http.StatusUnauthorized)
By("Sending a request to whitelisted service /bar") ginkgo.By("Sending a request to whitelisted service /bar")
barResp, _, _ := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+barPath). GET(barPath).
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(barResp.StatusCode).Should(Equal(http.StatusOK)) Status(http.StatusOK)
}) })
It("should still return status code 200 after auth backend is deleted using cache ", func() { ginkgo.It("should still return status code 200 after auth backend is deleted using cache ", func() {
globalExternalAuthCacheKeySetting := "global-auth-cache-key" globalExternalAuthCacheKeySetting := "global-auth-cache-key"
globalExternalAuthCacheKey := "foo" globalExternalAuthCacheKey := "foo"
@ -152,107 +154,101 @@ var _ = framework.DescribeSetting("[Security] global-auth-url", func() {
globalExternalAuthCacheDuration := "200 201 401 30m" globalExternalAuthCacheDuration := "200 201 401 30m"
globalExternalAuthURL := fmt.Sprintf("http://%s.%s.svc.cluster.local:80/status/200", framework.HTTPBinService, f.Namespace) globalExternalAuthURL := fmt.Sprintf("http://%s.%s.svc.cluster.local:80/status/200", framework.HTTPBinService, f.Namespace)
By("Adding a global-auth-cache-key to configMap") ginkgo.By("Adding a global-auth-cache-key to configMap")
f.UpdateNginxConfigMapData(globalExternalAuthCacheKeySetting, globalExternalAuthCacheKey) f.SetNginxConfigMapData(map[string]string{
f.UpdateNginxConfigMapData(globalExternalAuthCacheDurationSetting, globalExternalAuthCacheDuration) globalExternalAuthCacheKeySetting: globalExternalAuthCacheKey,
f.UpdateNginxConfigMapData(globalExternalAuthURLSetting, globalExternalAuthURL) globalExternalAuthCacheDurationSetting: globalExternalAuthCacheDuration,
globalExternalAuthURLSetting: globalExternalAuthURL,
})
cacheRegex := regexp.MustCompile(`\$cache_key.*foo`)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(MatchRegexp(`\$cache_key.*foo`)) && return cacheRegex.MatchString(server) &&
Expect(server).Should(ContainSubstring(`proxy_cache_valid 200 201 401 30m;`)) strings.Contains(server, `proxy_cache_valid 200 201 401 30m;`)
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)+barPath). GET(barPath).
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
Set("Host", host). WithBasicAuth("user", "password").
SetBasicAuth("user", "password"). Expect().
End() Status(http.StatusOK)
for _, err := range errs {
Expect(err).NotTo(HaveOccurred())
}
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
err := f.DeleteDeployment(framework.HTTPBinService) err := f.DeleteDeployment(framework.HTTPBinService)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
_, _, errs = gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET(barPath).
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
Set("Host", host). WithBasicAuth("user", "password").
SetBasicAuth("user", "password"). Expect().
End() Status(http.StatusOK)
for _, err := range errs {
Expect(err).NotTo(HaveOccurred())
}
}) })
It(`should proxy_method method when global-auth-method is configured`, func() { ginkgo.It(`should proxy_method method when global-auth-method is configured`, func() {
globalExternalAuthMethodSetting := "global-auth-method" globalExternalAuthMethodSetting := "global-auth-method"
globalExternalAuthMethod := "GET" globalExternalAuthMethod := "GET"
By("Adding a global-auth-method to configMap") ginkgo.By("Adding a global-auth-method to configMap")
f.UpdateNginxConfigMapData(globalExternalAuthMethodSetting, globalExternalAuthMethod) f.UpdateNginxConfigMapData(globalExternalAuthMethodSetting, globalExternalAuthMethod)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("proxy_method")) return strings.Contains(server, "proxy_method")
}) })
}) })
It(`should add custom error page when global-auth-signin url is configured`, func() { ginkgo.It(`should add custom error page when global-auth-signin url is configured`, func() {
globalExternalAuthSigninSetting := "global-auth-signin" globalExternalAuthSigninSetting := "global-auth-signin"
globalExternalAuthSignin := "http://foo.com/global-error-page" globalExternalAuthSignin := "http://foo.com/global-error-page"
By("Adding a global-auth-signin to configMap") ginkgo.By("Adding a global-auth-signin to configMap")
f.UpdateNginxConfigMapData(globalExternalAuthSigninSetting, globalExternalAuthSignin) f.UpdateNginxConfigMapData(globalExternalAuthSigninSetting, globalExternalAuthSignin)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("error_page 401 = ")) return strings.Contains(server, "error_page 401 = ")
}) })
}) })
It(`should add auth headers when global-auth-response-headers is configured`, func() { ginkgo.It(`should add auth headers when global-auth-response-headers is configured`, func() {
globalExternalAuthResponseHeadersSetting := "global-auth-response-headers" globalExternalAuthResponseHeadersSetting := "global-auth-response-headers"
globalExternalAuthResponseHeaders := "Foo, Bar" globalExternalAuthResponseHeaders := "Foo, Bar"
By("Adding a global-auth-response-headers to configMap") ginkgo.By("Adding a global-auth-response-headers to configMap")
f.UpdateNginxConfigMapData(globalExternalAuthResponseHeadersSetting, globalExternalAuthResponseHeaders) f.UpdateNginxConfigMapData(globalExternalAuthResponseHeadersSetting, globalExternalAuthResponseHeaders)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("auth_request_set $authHeader0 $upstream_http_foo;")) && return strings.Contains(server, "auth_request_set $authHeader0 $upstream_http_foo;") &&
Expect(server).Should(ContainSubstring("auth_request_set $authHeader1 $upstream_http_bar;")) strings.Contains(server, "auth_request_set $authHeader1 $upstream_http_bar;")
}) })
}) })
It(`should set request-redirect when global-auth-request-redirect is configured`, func() { ginkgo.It(`should set request-redirect when global-auth-request-redirect is configured`, func() {
globalExternalAuthRequestRedirectSetting := "global-auth-request-redirect" globalExternalAuthRequestRedirectSetting := "global-auth-request-redirect"
globalExternalAuthRequestRedirect := "Foo-Redirect" globalExternalAuthRequestRedirect := "Foo-Redirect"
By("Adding a global-auth-request-redirect to configMap") ginkgo.By("Adding a global-auth-request-redirect to configMap")
f.UpdateNginxConfigMapData(globalExternalAuthRequestRedirectSetting, globalExternalAuthRequestRedirect) f.UpdateNginxConfigMapData(globalExternalAuthRequestRedirectSetting, globalExternalAuthRequestRedirect)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring(globalExternalAuthRequestRedirect)) return strings.Contains(server, globalExternalAuthRequestRedirect)
}) })
}) })
It(`should set snippet when global external auth is configured`, func() { ginkgo.It(`should set snippet when global external auth is configured`, func() {
globalExternalAuthSnippetSetting := "global-auth-snippet" globalExternalAuthSnippetSetting := "global-auth-snippet"
globalExternalAuthSnippet := "proxy_set_header My-Custom-Header 42;" globalExternalAuthSnippet := "proxy_set_header My-Custom-Header 42;"
By("Adding a global-auth-snippet to configMap") ginkgo.By("Adding a global-auth-snippet to configMap")
f.UpdateNginxConfigMapData(globalExternalAuthSnippetSetting, globalExternalAuthSnippet) f.UpdateNginxConfigMapData(globalExternalAuthSnippetSetting, globalExternalAuthSnippet)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring(globalExternalAuthSnippet)) return strings.Contains(server, globalExternalAuthSnippet)
}) })
}) })

View file

@ -20,9 +20,8 @@ import (
"net/http" "net/http"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
appsv1 "k8s.io/api/apps/v1" appsv1 "k8s.io/api/apps/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
@ -33,13 +32,13 @@ import (
var _ = framework.IngressNginxDescribe("[Flag] ingress-class", func() { var _ = framework.IngressNginxDescribe("[Flag] ingress-class", func() {
f := framework.NewDefaultFramework("ingress-class") f := framework.NewDefaultFramework("ingress-class")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeploymentWithReplicas(1)
}) })
Context("Without a specific ingress-class", func() { ginkgo.Context("Without a specific ingress-class", func() {
It("should ignore Ingress with class", func() { ginkgo.It("should ignore Ingress with class", func() {
invalidHost := "foo" invalidHost := "foo"
annotations := map[string]string{ annotations := map[string]string{
class.IngressKey: "testclass", class.IngressKey: "testclass",
@ -56,24 +55,22 @@ var _ = framework.IngressNginxDescribe("[Flag] ingress-class", func() {
strings.Contains(cfg, "server_name bar") strings.Contains(cfg, "server_name bar")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", invalidHost). WithHeader("Host", invalidHost).
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusNotFound)
Expect(resp.StatusCode).Should(Equal(http.StatusNotFound))
resp, _, errs = gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", validHost). WithHeader("Host", validHost).
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusOK)
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
}) })
}) })
Context("With a specific ingress-class", func() { ginkgo.Context("With a specific ingress-class", func() {
BeforeEach(func() { ginkgo.BeforeEach(func() {
err := framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1, err := framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1,
func(deployment *appsv1.Deployment) error { func(deployment *appsv1.Deployment) error {
args := deployment.Spec.Template.Spec.Containers[0].Args args := deployment.Spec.Template.Spec.Containers[0].Args
@ -83,10 +80,10 @@ var _ = framework.IngressNginxDescribe("[Flag] ingress-class", func() {
return err return err
}) })
Expect(err).NotTo(HaveOccurred(), "unexpected error updating ingress controller deployment flags") assert.Nil(ginkgo.GinkgoT(), err, "updating ingress controller deployment flags")
}) })
It("should ignore Ingress with no class", func() { ginkgo.It("should ignore Ingress with no class", func() {
invalidHost := "bar" invalidHost := "bar"
ing := framework.NewSingleIngress(invalidHost, "/", invalidHost, f.Namespace, framework.EchoService, 80, nil) ing := framework.NewSingleIngress(invalidHost, "/", invalidHost, f.Namespace, framework.EchoService, 80, nil)
@ -107,22 +104,20 @@ var _ = framework.IngressNginxDescribe("[Flag] ingress-class", func() {
return !strings.Contains(cfg, "server_name bar") return !strings.Contains(cfg, "server_name bar")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", validHost). WithHeader("Host", validHost).
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusOK)
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
resp, _, errs = gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", invalidHost). WithHeader("Host", invalidHost).
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusNotFound)
Expect(resp.StatusCode).Should(Equal(http.StatusNotFound))
}) })
It("should delete Ingress when class is removed", func() { ginkgo.It("should delete Ingress when class is removed", func() {
host := "foo" host := "foo"
annotations := map[string]string{ annotations := map[string]string{
class.IngressKey: "testclass", class.IngressKey: "testclass",
@ -134,30 +129,28 @@ var _ = framework.IngressNginxDescribe("[Flag] ingress-class", func() {
return strings.Contains(cfg, "server_name foo") return strings.Contains(cfg, "server_name foo")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusOK)
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
ing, err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Get(host, metav1.GetOptions{}) ing, err := f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Get(host, metav1.GetOptions{})
Expect(err).To(BeNil()) assert.Nil(ginkgo.GinkgoT(), err)
delete(ing.Annotations, class.IngressKey) delete(ing.Annotations, class.IngressKey)
_, err = f.KubeClientSet.NetworkingV1beta1().Ingresses(ing.Namespace).Update(ing) _, err = f.KubeClientSet.NetworkingV1beta1().Ingresses(ing.Namespace).Update(ing)
Expect(err).To(BeNil()) assert.Nil(ginkgo.GinkgoT(), err)
f.WaitForNginxConfiguration(func(cfg string) bool { f.WaitForNginxConfiguration(func(cfg string) bool {
return !strings.Contains(cfg, "server_name foo") return !strings.Contains(cfg, "server_name foo")
}) })
resp, _, errs = gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).To(BeNil()) Status(http.StatusNotFound)
Expect(resp.StatusCode).Should(Equal(http.StatusNotFound))
}) })
}) })
}) })

View file

@ -21,10 +21,8 @@ import (
"net/http" "net/http"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
@ -36,7 +34,7 @@ var _ = framework.IngressNginxDescribe("[Flag] custom HTTP and HTTPS ports", fun
f := framework.NewDefaultFramework("forwarded-port-headers") f := framework.NewDefaultFramework("forwarded-port-headers")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
f.WaitForNginxServer("_", f.WaitForNginxServer("_",
@ -45,8 +43,8 @@ var _ = framework.IngressNginxDescribe("[Flag] custom HTTP and HTTPS ports", fun
}) })
}) })
Context("with a plain HTTP ingress", func() { ginkgo.Context("with a plain HTTP ingress", func() {
It("should set X-Forwarded-Port headers accordingly when listening on a non-default HTTP port", func() { ginkgo.It("should set X-Forwarded-Port headers accordingly when listening on a non-default HTTP port", func() {
ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil) ing := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil)
f.EnsureIngress(ing) f.EnsureIngress(ing)
@ -56,20 +54,19 @@ var _ = framework.IngressNginxDescribe("[Flag] custom HTTP and HTTPS ports", fun
return strings.Contains(server, "server_name forwarded-headers") return strings.Contains(server, "server_name forwarded-headers")
}) })
resp, body, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Expect(errs).Should(BeEmpty()) Body().
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) Contains(fmt.Sprintf("x-forwarded-port=%d", 1080))
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-forwarded-port=%d", 1080)))
}) })
}) })
Context("with a TLS enabled ingress", func() { ginkgo.Context("with a TLS enabled ingress", func() {
It("should set X-Forwarded-Port header to 443", func() { ginkgo.It("should set X-Forwarded-Port header to 443", func() {
ing := framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, nil) ing := framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, nil)
f.EnsureIngress(ing) f.EnsureIngress(ing)
@ -78,7 +75,7 @@ var _ = framework.IngressNginxDescribe("[Flag] custom HTTP and HTTPS ports", fun
ing.Spec.TLS[0].Hosts, ing.Spec.TLS[0].Hosts,
ing.Spec.TLS[0].SecretName, ing.Spec.TLS[0].SecretName,
ing.Namespace) ing.Namespace)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig) framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig)
@ -87,29 +84,29 @@ var _ = framework.IngressNginxDescribe("[Flag] custom HTTP and HTTPS ports", fun
return strings.Contains(server, "server_name forwarded-headers") return strings.Contains(server, "server_name forwarded-headers")
}) })
resp, body, errs := gorequest.New(). f.HTTPTestClientWithTLSConfig(tlsConfig).
Get(f.GetURL(framework.HTTPS)). GET("/").
TLSClientConfig(tlsConfig). WithURL(f.GetURL(framework.HTTPS)).
Set("Host", host). WithHeader("Host", host).
End() Expect().
Expect(errs).Should(BeEmpty()) Status(http.StatusOK).
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) Body().
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-forwarded-port=443"))) Contains(fmt.Sprintf("x-forwarded-port=443"))
}) })
Context("when external authentication is configured", func() { ginkgo.Context("when external authentication is configured", func() {
It("should set the X-Forwarded-Port header to 443", func() { ginkgo.It("should set the X-Forwarded-Port header to 443", func() {
f.NewHttpbinDeployment() f.NewHttpbinDeployment()
var httpbinIP string var httpbinIP string
err := framework.WaitForEndpoints(f.KubeClientSet, framework.DefaultTimeout, framework.HTTPBinService, f.Namespace, 1) err := framework.WaitForEndpoints(f.KubeClientSet, framework.DefaultTimeout, framework.HTTPBinService, f.Namespace, 1)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
e, err := f.KubeClientSet.CoreV1().Endpoints(f.Namespace).Get(framework.HTTPBinService, metav1.GetOptions{}) e, err := f.KubeClientSet.CoreV1().Endpoints(f.Namespace).Get(framework.HTTPBinService, metav1.GetOptions{})
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
httpbinIP = e.Subsets[0].Addresses[0].IP httpbinIP = e.Subsets[0].Addresses[0].IP
@ -121,30 +118,29 @@ var _ = framework.IngressNginxDescribe("[Flag] custom HTTP and HTTPS ports", fun
ing := framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, annotations) ing := framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, annotations)
f.EnsureIngress(ing) f.EnsureIngress(ing)
tlsConfig, err := framework.CreateIngressTLSSecret(f.KubeClientSet, tlsConfig, err := framework.CreateIngressTLSSecret(f.KubeClientSet,
ing.Spec.TLS[0].Hosts, ing.Spec.TLS[0].Hosts,
ing.Spec.TLS[0].SecretName, ing.Spec.TLS[0].SecretName,
ing.Namespace) ing.Namespace)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig) framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return strings.Contains(server, "server_name forwarded-headers") return strings.Contains(server, "server_name forwarded-headers")
}) })
resp, body, errs := gorequest.New().
Get(f.GetURL(framework.HTTPS)).
TLSClientConfig(tlsConfig).
Set("Host", host).
SetBasicAuth("user", "password").
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-forwarded-port=443")))
f.HTTPTestClientWithTLSConfig(tlsConfig).
GET("/").
WithURL(f.GetURL(framework.HTTPS)).
WithHeader("Host", host).
WithBasicAuth("user", "password").
Expect().
Status(http.StatusOK).
Body().
Contains(fmt.Sprintf("x-forwarded-port=443"))
}) })
}) })
}) })
}) })

View file

@ -17,45 +17,42 @@ limitations under the License.
package settings package settings
import ( import (
"fmt"
"net/http" "net/http"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeSetting("Settings - log format", func() { var _ = framework.DescribeSetting("log-format-*", func() {
f := framework.NewDefaultFramework("log-format") f := framework.NewDefaultFramework("log-format")
host := "log-format" host := "log-format"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeployment()
f.EnsureIngress(framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil)) f.EnsureIngress(framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil))
}) })
Context("Check log-format-escape-json", func() { ginkgo.Context("Check log-format-escape-json", func() {
It("should disable the log-format-escape-json by default", func() {
ginkgo.It("should disable the log-format-escape-json by default", func() {
f.WaitForNginxConfiguration( f.WaitForNginxConfiguration(
func(cfg string) bool { func(cfg string) bool {
return !strings.Contains(cfg, "log_format upstreaminfo escape=json") return !strings.Contains(cfg, "log_format upstreaminfo escape=json")
}) })
}) })
It("should enable the log-format-escape-json", func() { ginkgo.It("should enable the log-format-escape-json", func() {
f.UpdateNginxConfigMapData("log-format-escape-json", "true") f.UpdateNginxConfigMapData("log-format-escape-json", "true")
f.WaitForNginxConfiguration( f.WaitForNginxConfiguration(
func(cfg string) bool { func(cfg string) bool {
return strings.Contains(cfg, "log_format upstreaminfo escape=json") return strings.Contains(cfg, "log_format upstreaminfo escape=json")
}) })
}) })
It("should disable the log-format-escape-json", func() { ginkgo.It("should disable the log-format-escape-json", func() {
f.UpdateNginxConfigMapData("log-format-escape-json", "false") f.UpdateNginxConfigMapData("log-format-escape-json", "false")
f.WaitForNginxConfiguration( f.WaitForNginxConfiguration(
func(cfg string) bool { func(cfg string) bool {
@ -63,9 +60,10 @@ var _ = framework.DescribeSetting("Settings - log format", func() {
}) })
}) })
}) })
Context("Check log-format-upstream with log-format-escape-json", func() {
It("check log format with log-format-escape-json enabled", func() { ginkgo.Context("Check log-format-upstream with log-format-escape-json", func() {
ginkgo.It("log-format-escape-json enabled", func() {
f.SetNginxConfigMapData(map[string]string{ f.SetNginxConfigMapData(map[string]string{
"log-format-escape-json": "true", "log-format-escape-json": "true",
"log-format-upstream": "\"{\"my_header1\":\"$http_header1\", \"my_header2\":\"$http_header2\"}\"", "log-format-upstream": "\"{\"my_header1\":\"$http_header1\", \"my_header2\":\"$http_header2\"}\"",
@ -73,24 +71,22 @@ var _ = framework.DescribeSetting("Settings - log format", func() {
f.WaitForNginxConfiguration( f.WaitForNginxConfiguration(
func(cfg string) bool { func(cfg string) bool {
fmt.Sprintln(cfg)
return strings.Contains(cfg, "log_format upstreaminfo escape=json") return strings.Contains(cfg, "log_format upstreaminfo escape=json")
}) })
resp, _, errs := gorequest.New().
Get(f.GetURL(framework.HTTP)).
Set("Host", host).
AppendHeader("header1", "Here is \"header1\" with json escape").
End()
Expect(errs).Should(BeEmpty()) f.HTTPTestClient().
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) GET("/").
WithHeader("Host", host).
WithHeader("header1", `Here is "header1" with json escape`).
Expect().
Status(http.StatusOK)
logs, err := f.NginxLogs() logs, err := f.NginxLogs()
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err, "obtaining nginx logs")
Expect(logs).To(ContainSubstring(`{"my_header1":"Here is \"header1\" with json escape", "my_header2":""}`)) assert.Contains(ginkgo.GinkgoT(), logs, `{"my_header1":"Here is \"header1\" with json escape", "my_header2":""}`)
}) })
It("check log format with log-format-escape-json disabled", func() { ginkgo.It("log-format-escape-json disabled", func() {
f.SetNginxConfigMapData(map[string]string{ f.SetNginxConfigMapData(map[string]string{
"log-format-escape-json": "false", "log-format-escape-json": "false",
"log-format-upstream": "\"{\"my_header3\":\"$http_header3\", \"my_header4\":\"$http_header4\"}\"", "log-format-upstream": "\"{\"my_header3\":\"$http_header3\", \"my_header4\":\"$http_header4\"}\"",
@ -98,22 +94,19 @@ var _ = framework.DescribeSetting("Settings - log format", func() {
f.WaitForNginxConfiguration( f.WaitForNginxConfiguration(
func(cfg string) bool { func(cfg string) bool {
fmt.Sprintln(cfg)
return !strings.Contains(cfg, "log_format upstreaminfo escape=json") return !strings.Contains(cfg, "log_format upstreaminfo escape=json")
}) })
resp, _, errs := gorequest.New().
Get(f.GetURL(framework.HTTP)).
Set("Host", host).
AppendHeader("header3", "Here is \"header3\" with json escape").
End()
Expect(errs).Should(BeEmpty()) f.HTTPTestClient().
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) GET("/").
WithHeader("Host", host).
WithHeader("header3", `Here is "header3" with json escape`).
Expect().
Status(http.StatusOK)
logs, err := f.NginxLogs() logs, err := f.NginxLogs()
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err, "obtaining nginx logs")
Expect(logs).To(ContainSubstring(`{"my_header3":"Here is \x22header3\x22 with json escape", "my_header4":"-"}`)) assert.Contains(ginkgo.GinkgoT(), logs, `{"my_header3":"Here is \x22header3\x22 with json escape", "my_header4":"-"}`)
}) })
}) })
}) })

View file

@ -17,34 +17,22 @@ limitations under the License.
package settings package settings
import ( import (
. "github.com/onsi/ginkgo" "strings"
. "github.com/onsi/gomega"
"github.com/onsi/ginkgo"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.DescribeSetting("[Lua] lua-shared-dicts", func() { var _ = framework.DescribeSetting("[Lua] lua-shared-dicts", func() {
f := framework.NewDefaultFramework("lua-shared-dicts") f := framework.NewDefaultFramework("lua-shared-dicts")
host := "lua-shared-dicts"
BeforeEach(func() {
f.NewEchoDeployment()
})
It("configures lua shared dicts", func() {
ingress := framework.NewSingleIngress(host, "/", host, f.Namespace, framework.EchoService, 80, nil)
f.EnsureIngress(ingress)
ginkgo.It("configures lua shared dicts", func() {
f.UpdateNginxConfigMapData("lua-shared-dicts", "configuration_data:60,certificate_data:300, my_dict: 15 , invalid: 1a") f.UpdateNginxConfigMapData("lua-shared-dicts", "configuration_data:60,certificate_data:300, my_dict: 15 , invalid: 1a")
ngxCfg := ""
f.WaitForNginxConfiguration(func(cfg string) bool { f.WaitForNginxConfiguration(func(cfg string) bool {
ngxCfg = cfg return strings.Contains(cfg, "lua_shared_dict configuration_data 60M;") &&
return true strings.Contains(cfg, "lua_shared_dict certificate_data 20M;") &&
strings.Contains(cfg, "lua_shared_dict my_dict 15M;")
}) })
Expect(ngxCfg).Should(ContainSubstring("lua_shared_dict configuration_data 60M;"))
Expect(ngxCfg).Should(ContainSubstring("lua_shared_dict certificate_data 20M;"))
Expect(ngxCfg).Should(ContainSubstring("lua_shared_dict my_dict 15M;"))
}) })
}) })

View file

@ -19,7 +19,7 @@ package settings
import ( import (
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -28,7 +28,7 @@ var _ = framework.DescribeSetting("main-snippet", func() {
f := framework.NewDefaultFramework("main-snippet") f := framework.NewDefaultFramework("main-snippet")
mainSnippet := "main-snippet" mainSnippet := "main-snippet"
It("should add value of main-snippet setting to nginx config", func() { ginkgo.It("should add value of main-snippet setting to nginx config", func() {
expectedComment := "# main snippet" expectedComment := "# main snippet"
f.UpdateNginxConfigMapData(mainSnippet, expectedComment) f.UpdateNginxConfigMapData(mainSnippet, expectedComment)

View file

@ -19,7 +19,7 @@ package settings
import ( import (
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -27,12 +27,13 @@ import (
var _ = framework.DescribeSetting("[Security] modsecurity-snippet", func() { var _ = framework.DescribeSetting("[Security] modsecurity-snippet", func() {
f := framework.NewDefaultFramework("modsecurity-snippet") f := framework.NewDefaultFramework("modsecurity-snippet")
It("should add value of modsecurity-snippet setting to nginx config", func() { ginkgo.It("should add value of modsecurity-snippet setting to nginx config", func() {
modsecSnippet := "modsecurity-snippet"
expectedComment := "# modsecurity snippet" expectedComment := "# modsecurity snippet"
f.UpdateNginxConfigMapData("enable-modsecurity", "true") f.SetNginxConfigMapData(map[string]string{
f.UpdateNginxConfigMapData(modsecSnippet, expectedComment) "enable-modsecurity": "true",
"modsecurity-snippet": expectedComment,
})
f.WaitForNginxConfiguration( f.WaitForNginxConfiguration(
func(cfg string) bool { func(cfg string) bool {

View file

@ -19,7 +19,7 @@ package settings
import ( import (
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -28,7 +28,7 @@ var _ = framework.DescribeSetting("enable-multi-accept", func() {
multiAccept := "enable-multi-accept" multiAccept := "enable-multi-accept"
f := framework.NewDefaultFramework(multiAccept) f := framework.NewDefaultFramework(multiAccept)
It("should be enabled by default", func() { ginkgo.It("should be enabled by default", func() {
expectedDirective := "multi_accept on;" expectedDirective := "multi_accept on;"
f.WaitForNginxConfiguration( f.WaitForNginxConfiguration(
func(cfg string) bool { func(cfg string) bool {
@ -36,7 +36,7 @@ var _ = framework.DescribeSetting("enable-multi-accept", func() {
}) })
}) })
It("should be enabled when set to true", func() { ginkgo.It("should be enabled when set to true", func() {
expectedDirective := "multi_accept on;" expectedDirective := "multi_accept on;"
f.UpdateNginxConfigMapData(multiAccept, "true") f.UpdateNginxConfigMapData(multiAccept, "true")
@ -46,7 +46,7 @@ var _ = framework.DescribeSetting("enable-multi-accept", func() {
}) })
}) })
It("should be disabled when set to false", func() { ginkgo.It("should be disabled when set to false", func() {
expectedDirective := "multi_accept off;" expectedDirective := "multi_accept off;"
f.UpdateNginxConfigMapData(multiAccept, "false") f.UpdateNginxConfigMapData(multiAccept, "false")

View file

@ -20,11 +20,10 @@ import (
"fmt" "fmt"
"net/http" "net/http"
"os/exec" "os/exec"
"strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
corev1 "k8s.io/api/core/v1" corev1 "k8s.io/api/core/v1"
networking "k8s.io/api/networking/v1beta1" networking "k8s.io/api/networking/v1beta1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
@ -42,7 +41,7 @@ var _ = framework.DescribeSetting("[Security] no-auth-locations", func() {
host := "no-auth-locations" host := "no-auth-locations"
noAuthPath := "/noauth" noAuthPath := "/noauth"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
s := f.EnsureSecret(buildSecret(username, password, secretName, f.Namespace)) s := f.EnsureSecret(buildSecret(username, password, secretName, f.Namespace))
@ -53,51 +52,46 @@ var _ = framework.DescribeSetting("[Security] no-auth-locations", func() {
f.EnsureIngress(bi) f.EnsureIngress(bi)
}) })
It("should return status code 401 when accessing '/' unauthentication", func() { ginkgo.It("should return status code 401 when accessing '/' unauthentication", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("test auth")) return strings.Contains(server, "test auth")
}) })
resp, body, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusUnauthorized).
Expect(errs).Should(BeEmpty()) Body().Contains("401 Authorization Required")
Expect(resp.StatusCode).Should(Equal(http.StatusUnauthorized))
Expect(body).Should(ContainSubstring("401 Authorization Required"))
}) })
It("should return status code 200 when accessing '/' authentication", func() { ginkgo.It("should return status code 200 when accessing '/' authentication", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("test auth")) return strings.Contains(server, "test auth")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
SetBasicAuth(username, password). WithBasicAuth(username, password).
End() Expect().
Status(http.StatusOK)
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
}) })
It("should return status code 200 when accessing '/noauth' unauthenticated", func() { ginkgo.It("should return status code 200 when accessing '/noauth' unauthenticated", func() {
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
return Expect(server).Should(ContainSubstring("test auth")) return strings.Contains(server, "test auth")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(fmt.Sprintf("%s/noauth", f.GetURL(framework.HTTP))). GET("/noauth").
Set("Host", host). WithHeader("Host", host).
End() WithBasicAuth(username, password).
Expect().
Expect(errs).Should(BeEmpty()) Status(http.StatusOK)
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
}) })
}) })
@ -143,7 +137,7 @@ func buildBasicAuthIngressWithSecondPath(host, namespace, secretName, pathName s
func buildSecret(username, password, name, namespace string) *corev1.Secret { func buildSecret(username, password, name, namespace string) *corev1.Secret {
out, err := exec.Command("openssl", "passwd", "-crypt", password).CombinedOutput() out, err := exec.Command("openssl", "passwd", "-crypt", password).CombinedOutput()
Expect(err).NotTo(HaveOccurred(), "creating password") assert.Nil(ginkgo.GinkgoT(), err, "creating password")
encpass := fmt.Sprintf("%v:%s\n", username, out) encpass := fmt.Sprintf("%v:%s\n", username, out)

View file

@ -20,10 +20,8 @@ import (
"net/http" "net/http"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
appsv1 "k8s.io/api/apps/v1" appsv1 "k8s.io/api/apps/v1"
corev1 "k8s.io/api/core/v1" corev1 "k8s.io/api/core/v1"
policyv1beta1 "k8s.io/api/policy/v1beta1" policyv1beta1 "k8s.io/api/policy/v1beta1"
@ -41,16 +39,16 @@ const (
var _ = framework.IngressNginxDescribe("[Security] Pod Security Policies", func() { var _ = framework.IngressNginxDescribe("[Security] Pod Security Policies", func() {
f := framework.NewDefaultFramework("pod-security-policies") f := framework.NewDefaultFramework("pod-security-policies")
BeforeEach(func() { ginkgo.BeforeEach(func() {
psp := createPodSecurityPolicy() psp := createPodSecurityPolicy()
_, err := f.KubeClientSet.PolicyV1beta1().PodSecurityPolicies().Create(psp) _, err := f.KubeClientSet.PolicyV1beta1().PodSecurityPolicies().Create(psp)
if !k8sErrors.IsAlreadyExists(err) { if !k8sErrors.IsAlreadyExists(err) {
Expect(err).NotTo(HaveOccurred(), "creating Pod Security Policy") assert.Nil(ginkgo.GinkgoT(), err, "creating Pod Security Policy")
} }
role, err := f.KubeClientSet.RbacV1().Roles(f.Namespace).Get("nginx-ingress-controller", metav1.GetOptions{}) role, err := f.KubeClientSet.RbacV1().Roles(f.Namespace).Get("nginx-ingress-controller", metav1.GetOptions{})
Expect(err).NotTo(HaveOccurred(), "getting ingress controller cluster role") assert.Nil(ginkgo.GinkgoT(), err, "getting ingress controller cluster role")
Expect(role).NotTo(BeNil()) assert.NotNil(ginkgo.GinkgoT(), role)
role.Rules = append(role.Rules, rbacv1.PolicyRule{ role.Rules = append(role.Rules, rbacv1.PolicyRule{
APIGroups: []string{"policy"}, APIGroups: []string{"policy"},
@ -60,7 +58,7 @@ var _ = framework.IngressNginxDescribe("[Security] Pod Security Policies", func(
}) })
_, err = f.KubeClientSet.RbacV1().Roles(f.Namespace).Update(role) _, err = f.KubeClientSet.RbacV1().Roles(f.Namespace).Update(role)
Expect(err).NotTo(HaveOccurred(), "updating ingress controller cluster role to use a pod security policy") assert.Nil(ginkgo.GinkgoT(), err, "updating ingress controller cluster role to use a pod security policy")
// update the deployment just to trigger a rolling update and the use of the security policy // update the deployment just to trigger a rolling update and the use of the security policy
err = framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1, err = framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1,
@ -72,22 +70,22 @@ var _ = framework.IngressNginxDescribe("[Security] Pod Security Policies", func(
return err return err
}) })
Expect(err).NotTo(HaveOccurred(), "unexpected error updating ingress controller deployment flags") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error updating ingress controller deployment flags")
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
It("should be running with a Pod Security Policy", func() { ginkgo.It("should be running with a Pod Security Policy", func() {
f.WaitForNginxConfiguration( f.WaitForNginxConfiguration(
func(cfg string) bool { func(cfg string) bool {
return strings.Contains(cfg, "server_tokens on") return strings.Contains(cfg, "server_tokens on")
}) })
resp, _, _ := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", "foo.bar.com"). WithHeader("Host", "foo.bar.com").
End() Expect().
Expect(resp.StatusCode).Should(Equal(http.StatusNotFound)) Status(http.StatusNotFound)
}) })
}) })

View file

@ -20,10 +20,8 @@ import (
"net/http" "net/http"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
appsv1 "k8s.io/api/apps/v1" appsv1 "k8s.io/api/apps/v1"
corev1 "k8s.io/api/core/v1" corev1 "k8s.io/api/core/v1"
@ -37,16 +35,16 @@ import (
var _ = framework.IngressNginxDescribe("[Security] Pod Security Policies with volumes", func() { var _ = framework.IngressNginxDescribe("[Security] Pod Security Policies with volumes", func() {
f := framework.NewDefaultFramework("pod-security-policies-volumes") f := framework.NewDefaultFramework("pod-security-policies-volumes")
It("should be running with a Pod Security Policy", func() { ginkgo.It("should be running with a Pod Security Policy", func() {
psp := createPodSecurityPolicy() psp := createPodSecurityPolicy()
_, err := f.KubeClientSet.PolicyV1beta1().PodSecurityPolicies().Create(psp) _, err := f.KubeClientSet.PolicyV1beta1().PodSecurityPolicies().Create(psp)
if !k8sErrors.IsAlreadyExists(err) { if !k8sErrors.IsAlreadyExists(err) {
Expect(err).NotTo(HaveOccurred(), "creating Pod Security Policy") assert.Nil(ginkgo.GinkgoT(), err, "creating Pod Security Policy")
} }
role, err := f.KubeClientSet.RbacV1().Roles(f.Namespace).Get("nginx-ingress-controller", metav1.GetOptions{}) role, err := f.KubeClientSet.RbacV1().Roles(f.Namespace).Get("nginx-ingress-controller", metav1.GetOptions{})
Expect(err).NotTo(HaveOccurred(), "getting ingress controller cluster role") assert.Nil(ginkgo.GinkgoT(), err, "getting ingress controller cluster role")
Expect(role).NotTo(BeNil()) assert.NotNil(ginkgo.GinkgoT(), role)
role.Rules = append(role.Rules, rbacv1.PolicyRule{ role.Rules = append(role.Rules, rbacv1.PolicyRule{
APIGroups: []string{"policy"}, APIGroups: []string{"policy"},
@ -56,7 +54,7 @@ var _ = framework.IngressNginxDescribe("[Security] Pod Security Policies with vo
}) })
_, err = f.KubeClientSet.RbacV1().Roles(f.Namespace).Update(role) _, err = f.KubeClientSet.RbacV1().Roles(f.Namespace).Update(role)
Expect(err).NotTo(HaveOccurred(), "updating ingress controller cluster role to use a pod security policy") assert.Nil(ginkgo.GinkgoT(), err, "updating ingress controller cluster role to use a pod security policy")
err = framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1, err = framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1,
func(deployment *appsv1.Deployment) error { func(deployment *appsv1.Deployment) error {
@ -95,7 +93,7 @@ var _ = framework.IngressNginxDescribe("[Security] Pod Security Policies with vo
return err return err
}) })
Expect(err).NotTo(HaveOccurred(), "unexpected error updating ingress controller deployment") assert.Nil(ginkgo.GinkgoT(), err, "updating ingress controller deployment")
f.NewEchoDeployment() f.NewEchoDeployment()
@ -104,10 +102,10 @@ var _ = framework.IngressNginxDescribe("[Security] Pod Security Policies with vo
return strings.Contains(cfg, "server_tokens on") return strings.Contains(cfg, "server_tokens on")
}) })
resp, _, _ := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", "foo.bar.com"). WithHeader("Host", "foo.bar.com").
End() Expect().
Expect(resp.StatusCode).Should(Equal(http.StatusNotFound)) Status(http.StatusNotFound)
}) })
}) })

View file

@ -20,12 +20,8 @@ import (
"fmt" "fmt"
"net/http" "net/http"
"strings" "strings"
"time"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"github.com/parnurzeal/gorequest"
"github.com/onsi/ginkgo"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -33,11 +29,11 @@ var _ = framework.IngressNginxDescribe("Dynamic $proxy_host", func() {
test := "proxy-host" test := "proxy-host"
f := framework.NewDefaultFramework(test) f := framework.NewDefaultFramework(test)
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeployment()
}) })
It("should exist a proxy_host", func() { ginkgo.It("should exist a proxy_host", func() {
upstreamName := fmt.Sprintf("%v-%v-80", f.Namespace, framework.EchoService) upstreamName := fmt.Sprintf("%v-%v-80", f.Namespace, framework.EchoService)
annotations := map[string]string{ annotations := map[string]string{
"nginx.ingress.kubernetes.io/configuration-snippet": `more_set_headers "Custom-Header: $proxy_host"`, "nginx.ingress.kubernetes.io/configuration-snippet": `more_set_headers "Custom-Header: $proxy_host"`,
@ -50,18 +46,15 @@ var _ = framework.IngressNginxDescribe("Dynamic $proxy_host", func() {
strings.Contains(server, "set $proxy_host $proxy_upstream_name") strings.Contains(server, "set $proxy_host $proxy_upstream_name")
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", test).
Set("Host", test). Expect().
End() Status(http.StatusOK).
Header("Custom-Header").Equal(upstreamName)
Expect(len(errs)).Should(Equal(0))
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(resp.Header.Get("Custom-Header")).Should(Equal(upstreamName))
}) })
It("should exist a proxy_host using the upstream-vhost annotation value", func() { ginkgo.It("should exist a proxy_host using the upstream-vhost annotation value", func() {
upstreamName := fmt.Sprintf("%v-%v-80", f.Namespace, framework.EchoService) upstreamName := fmt.Sprintf("%v-%v-80", f.Namespace, framework.EchoService)
upstreamVHost := "different.host" upstreamVHost := "different.host"
annotations := map[string]string{ annotations := map[string]string{
@ -76,14 +69,11 @@ var _ = framework.IngressNginxDescribe("Dynamic $proxy_host", func() {
strings.Contains(server, fmt.Sprintf("set $proxy_host $proxy_upstream_name")) strings.Contains(server, fmt.Sprintf("set $proxy_host $proxy_upstream_name"))
}) })
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", test).
Set("Host", test). Expect().
End() Status(http.StatusOK).
Header("Custom-Header").Equal(upstreamName)
Expect(len(errs)).Should(Equal(0))
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(resp.Header.Get("Custom-Header")).Should(Equal(upstreamName))
}) })
}) })

View file

@ -22,8 +22,8 @@ import (
"net" "net"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -33,12 +33,12 @@ var _ = framework.DescribeSetting("use-proxy-protocol", func() {
setting := "use-proxy-protocol" setting := "use-proxy-protocol"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
f.UpdateNginxConfigMapData(setting, "false") f.UpdateNginxConfigMapData(setting, "false")
}) })
It("should respect port passed by the PROXY Protocol", func() { ginkgo.It("should respect port passed by the PROXY Protocol", func() {
host := "proxy-protocol" host := "proxy-protocol"
f.UpdateNginxConfigMapData(setting, "true") f.UpdateNginxConfigMapData(setting, "true")
@ -54,7 +54,7 @@ var _ = framework.DescribeSetting("use-proxy-protocol", func() {
ip := f.GetNginxIP() ip := f.GetNginxIP()
conn, err := net.Dial("tcp", net.JoinHostPort(ip, "80")) conn, err := net.Dial("tcp", net.JoinHostPort(ip, "80"))
Expect(err).NotTo(HaveOccurred(), "unexpected error creating connection to %s:80", ip) assert.Nil(ginkgo.GinkgoT(), err, "unexpected error creating connection to %s:80", ip)
defer conn.Close() defer conn.Close()
header := "PROXY TCP4 192.168.0.1 192.168.0.11 56324 1234\r\n" header := "PROXY TCP4 192.168.0.1 192.168.0.11 56324 1234\r\n"
@ -62,15 +62,16 @@ var _ = framework.DescribeSetting("use-proxy-protocol", func() {
conn.Write([]byte("GET / HTTP/1.1\r\nHost: proxy-protocol\r\n\r\n")) conn.Write([]byte("GET / HTTP/1.1\r\nHost: proxy-protocol\r\n\r\n"))
data, err := ioutil.ReadAll(conn) data, err := ioutil.ReadAll(conn)
Expect(err).NotTo(HaveOccurred(), "unexpected error reading connection data") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error reading connection data")
body := string(data) body := string(data)
Expect(body).Should(ContainSubstring(fmt.Sprintf("host=%v", "proxy-protocol"))) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("host=%v", "proxy-protocol"))
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-forwarded-port=1234"))) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-port=1234"))
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-forwarded-proto=http"))) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-proto=http"))
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-forwarded-for=192.168.0.1"))) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-for=192.168.0.1"))
}) })
It("should respect proto passed by the PROXY Protocol server port", func() { ginkgo.It("should respect proto passed by the PROXY Protocol server port", func() {
host := "proxy-protocol" host := "proxy-protocol"
f.UpdateNginxConfigMapData(setting, "true") f.UpdateNginxConfigMapData(setting, "true")
@ -86,7 +87,7 @@ var _ = framework.DescribeSetting("use-proxy-protocol", func() {
ip := f.GetNginxIP() ip := f.GetNginxIP()
conn, err := net.Dial("tcp", net.JoinHostPort(ip, "80")) conn, err := net.Dial("tcp", net.JoinHostPort(ip, "80"))
Expect(err).NotTo(HaveOccurred(), "unexpected error creating connection to %s:80", ip) assert.Nil(ginkgo.GinkgoT(), err, "unexpected error creating connection to %s:80", ip)
defer conn.Close() defer conn.Close()
header := "PROXY TCP4 192.168.0.1 192.168.0.11 56324 443\r\n" header := "PROXY TCP4 192.168.0.1 192.168.0.11 56324 443\r\n"
@ -94,11 +95,12 @@ var _ = framework.DescribeSetting("use-proxy-protocol", func() {
conn.Write([]byte("GET / HTTP/1.1\r\nHost: proxy-protocol\r\n\r\n")) conn.Write([]byte("GET / HTTP/1.1\r\nHost: proxy-protocol\r\n\r\n"))
data, err := ioutil.ReadAll(conn) data, err := ioutil.ReadAll(conn)
Expect(err).NotTo(HaveOccurred(), "unexpected error reading connection data") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error reading connection data")
body := string(data) body := string(data)
Expect(body).Should(ContainSubstring(fmt.Sprintf("host=%v", "proxy-protocol"))) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("host=%v", "proxy-protocol"))
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-forwarded-port=443"))) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-port=443"))
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-forwarded-proto=https"))) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-proto=https"))
Expect(body).Should(ContainSubstring(fmt.Sprintf("x-forwarded-for=192.168.0.1"))) assert.Contains(ginkgo.GinkgoT(), body, fmt.Sprintf("x-forwarded-for=192.168.0.1"))
}) })
}) })

View file

@ -19,7 +19,7 @@ package settings
import ( import (
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
networking "k8s.io/api/networking/v1beta1" networking "k8s.io/api/networking/v1beta1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
@ -31,11 +31,11 @@ var _ = framework.DescribeSetting("server-tokens", func() {
f := framework.NewDefaultFramework("server-tokens") f := framework.NewDefaultFramework("server-tokens")
serverTokens := "server-tokens" serverTokens := "server-tokens"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
It("should not exists Server header in the response", func() { ginkgo.It("should not exists Server header in the response", func() {
f.UpdateNginxConfigMapData(serverTokens, "false") f.UpdateNginxConfigMapData(serverTokens, "false")
f.EnsureIngress(framework.NewSingleIngress(serverTokens, "/", serverTokens, f.Namespace, framework.EchoService, 80, nil)) f.EnsureIngress(framework.NewSingleIngress(serverTokens, "/", serverTokens, f.Namespace, framework.EchoService, 80, nil))
@ -47,7 +47,7 @@ var _ = framework.DescribeSetting("server-tokens", func() {
}) })
}) })
It("should exists Server header in the response when is enabled", func() { ginkgo.It("should exists Server header in the response when is enabled", func() {
f.UpdateNginxConfigMapData(serverTokens, "true") f.UpdateNginxConfigMapData(serverTokens, "true")
f.EnsureIngress(&networking.Ingress{ f.EnsureIngress(&networking.Ingress{

View file

@ -21,29 +21,23 @@ import (
"fmt" "fmt"
"net/http" "net/http"
"strings" "strings"
"time"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
func noRedirectPolicyFunc(gorequest.Request, []gorequest.Request) error {
return http.ErrUseLastResponse
}
var _ = framework.DescribeSetting("[SSL] TLS protocols, ciphers and headers)", func() { var _ = framework.DescribeSetting("[SSL] TLS protocols, ciphers and headers)", func() {
f := framework.NewDefaultFramework("settings-tls") f := framework.NewDefaultFramework("settings-tls")
host := "settings-tls" host := "settings-tls"
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
f.UpdateNginxConfigMapData("use-forwarded-headers", "false") f.UpdateNginxConfigMapData("use-forwarded-headers", "false")
}) })
It("should configure TLS protocol", func() { ginkgo.It("should configure TLS protocol", func() {
sslCiphers := "ssl-ciphers" sslCiphers := "ssl-ciphers"
sslProtocols := "ssl-protocols" sslProtocols := "ssl-protocols"
@ -56,11 +50,11 @@ var _ = framework.DescribeSetting("[SSL] TLS protocols, ciphers and headers)", f
ing.Spec.TLS[0].Hosts, ing.Spec.TLS[0].Hosts,
ing.Spec.TLS[0].SecretName, ing.Spec.TLS[0].SecretName,
ing.Namespace) ing.Namespace)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig) framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig)
By("setting cipher suite") ginkgo.By("setting cipher suite")
f.UpdateNginxConfigMapData(sslCiphers, testCiphers) f.UpdateNginxConfigMapData(sslCiphers, testCiphers)
f.WaitForNginxConfiguration( f.WaitForNginxConfiguration(
@ -68,18 +62,18 @@ var _ = framework.DescribeSetting("[SSL] TLS protocols, ciphers and headers)", f
return strings.Contains(cfg, fmt.Sprintf("ssl_ciphers '%s';", testCiphers)) return strings.Contains(cfg, fmt.Sprintf("ssl_ciphers '%s';", testCiphers))
}) })
resp, _, errs := gorequest.New(). resp := f.HTTPTestClientWithTLSConfig(tlsConfig).
Get(f.GetURL(framework.HTTPS)). GET("/").
TLSClientConfig(tlsConfig). WithURL(f.GetURL(framework.HTTPS)).
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Raw()
Expect(errs).Should(BeEmpty()) assert.Equal(ginkgo.GinkgoT(), int(resp.TLS.Version), tls.VersionTLS12)
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) assert.Equal(ginkgo.GinkgoT(), resp.TLS.CipherSuite, tls.TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384)
Expect(resp.TLS.Version).Should(BeNumerically("==", tls.VersionTLS12))
Expect(resp.TLS.CipherSuite).Should(BeNumerically("==", tls.TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384))
By("enforcing TLS v1.0") ginkgo.By("enforcing TLS v1.0")
f.UpdateNginxConfigMapData(sslProtocols, "TLSv1") f.UpdateNginxConfigMapData(sslProtocols, "TLSv1")
f.WaitForNginxConfiguration( f.WaitForNginxConfiguration(
@ -87,19 +81,19 @@ var _ = framework.DescribeSetting("[SSL] TLS protocols, ciphers and headers)", f
return strings.Contains(cfg, "ssl_protocols TLSv1;") return strings.Contains(cfg, "ssl_protocols TLSv1;")
}) })
resp, _, errs = gorequest.New(). resp = f.HTTPTestClientWithTLSConfig(tlsConfig).
Get(f.GetURL(framework.HTTPS)). GET("/").
TLSClientConfig(tlsConfig). WithURL(f.GetURL(framework.HTTPS)).
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Raw()
Expect(errs).Should(BeEmpty()) assert.Equal(ginkgo.GinkgoT(), int(resp.TLS.Version), tls.VersionTLS10)
Expect(resp.StatusCode).Should(Equal(http.StatusOK)) assert.Equal(ginkgo.GinkgoT(), resp.TLS.CipherSuite, tls.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA)
Expect(resp.TLS.Version).Should(BeNumerically("==", tls.VersionTLS10))
Expect(resp.TLS.CipherSuite).Should(BeNumerically("==", tls.TLS_ECDHE_RSA_WITH_AES_256_CBC_SHA))
}) })
It("should configure HSTS policy header", func() { ginkgo.It("should configure HSTS policy header", func() {
hstsMaxAge := "hsts-max-age" hstsMaxAge := "hsts-max-age"
hstsIncludeSubdomains := "hsts-include-subdomains" hstsIncludeSubdomains := "hsts-include-subdomains"
hstsPreload := "hsts-preload" hstsPreload := "hsts-preload"
@ -109,85 +103,75 @@ var _ = framework.DescribeSetting("[SSL] TLS protocols, ciphers and headers)", f
ing.Spec.TLS[0].Hosts, ing.Spec.TLS[0].Hosts,
ing.Spec.TLS[0].SecretName, ing.Spec.TLS[0].SecretName,
ing.Namespace) ing.Namespace)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig) framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig)
By("setting max-age parameter") ginkgo.By("setting max-age parameter")
f.UpdateNginxConfigMapData(hstsMaxAge, "86400") f.UpdateNginxConfigMapData(hstsMaxAge, "86400")
resp, _, errs := gorequest.New(). f.HTTPTestClientWithTLSConfig(tlsConfig).
Get(f.GetURL(framework.HTTPS)). GET("/").
TLSClientConfig(tlsConfig). WithURL(f.GetURL(framework.HTTPS)).
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Header("Strict-Transport-Security").Equal("max-age=86400; includeSubDomains")
Expect(errs).Should(BeEmpty()) ginkgo.By("setting includeSubDomains parameter")
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(resp.Header.Get("Strict-Transport-Security")).Should(Equal("max-age=86400; includeSubDomains"))
By("setting includeSubDomains parameter")
f.UpdateNginxConfigMapData(hstsIncludeSubdomains, "false") f.UpdateNginxConfigMapData(hstsIncludeSubdomains, "false")
resp, _, errs = gorequest.New(). f.HTTPTestClientWithTLSConfig(tlsConfig).
Get(f.GetURL(framework.HTTPS)). GET("/").
TLSClientConfig(tlsConfig). WithURL(f.GetURL(framework.HTTPS)).
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Header("Strict-Transport-Security").Equal("max-age=86400")
Expect(errs).Should(BeEmpty()) ginkgo.By("setting preload parameter")
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(resp.Header.Get("Strict-Transport-Security")).Should(Equal("max-age=86400"))
By("setting preload parameter")
f.UpdateNginxConfigMapData(hstsPreload, "true") f.UpdateNginxConfigMapData(hstsPreload, "true")
resp, _, errs = gorequest.New(). f.HTTPTestClientWithTLSConfig(tlsConfig).
Get(f.GetURL(framework.HTTPS)). GET("/").
TLSClientConfig(tlsConfig). WithURL(f.GetURL(framework.HTTPS)).
Set("Host", host). WithHeader("Host", host).
End() Expect().
Status(http.StatusOK).
Header("Strict-Transport-Security").Equal("max-age=86400; preload")
Expect(errs).Should(BeEmpty()) ginkgo.By("overriding what's set from the upstream")
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
Expect(resp.Header.Get("Strict-Transport-Security")).Should(Equal("max-age=86400; preload"))
By("overriding what's set from the upstream")
// we can not use gorequest here because it flattens the duplicate headers // we can not use gorequest here because it flattens the duplicate headers
// and specifically in case of Strict-Transport-Security it ignore extra headers // and specifically in case of Strict-Transport-Security it ignore extra headers
// intead of concatenating, rightfully. And I don't know of any API it provides for getting raw headers. // intead of concatenating, rightfully. And I don't know of any API it provides for getting raw headers.
curlCmd := fmt.Sprintf("curl -I -k --fail --silent --resolve settings-tls:443:127.0.0.1 https://settings-tls/%v", "?hsts=true") curlCmd := fmt.Sprintf("curl -I -k --fail --silent --resolve settings-tls:443:127.0.0.1 https://settings-tls/%v", "?hsts=true")
output, err := f.ExecIngressPod(curlCmd) output, err := f.ExecIngressPod(curlCmd)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
Expect(output).Should(ContainSubstring("strict-transport-security: max-age=86400; preload")) assert.Contains(ginkgo.GinkgoT(), output, "strict-transport-security: max-age=86400; preload")
// this is what the upstream sets // this is what the upstream sets
Expect(output).ShouldNot(ContainSubstring("strict-transport-security: max-age=3600; preload")) assert.NotContains(ginkgo.GinkgoT(), output, "strict-transport-security: max-age=3600; preload")
}) })
It("should not use ports during the HTTP to HTTPS redirection", func() { ginkgo.It("should not use ports during the HTTP to HTTPS redirection", func() {
ing := f.EnsureIngress(framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, nil)) ing := f.EnsureIngress(framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, nil))
tlsConfig, err := framework.CreateIngressTLSSecret(f.KubeClientSet, tlsConfig, err := framework.CreateIngressTLSSecret(f.KubeClientSet,
ing.Spec.TLS[0].Hosts, ing.Spec.TLS[0].Hosts,
ing.Spec.TLS[0].SecretName, ing.Spec.TLS[0].SecretName,
ing.Namespace) ing.Namespace)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig) framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig)
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
RedirectPolicy(noRedirectPolicyFunc). Expect().
Set("Host", host). Status(http.StatusPermanentRedirect).
End() Header("Location").Equal(fmt.Sprintf("https://%v/", host))
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusPermanentRedirect))
Expect(resp.Header.Get("Location")).Should(Equal(fmt.Sprintf("https://%v/", host)))
}) })
It("should not use ports or X-Forwarded-Host during the HTTP to HTTPS redirection", func() { ginkgo.It("should not use ports or X-Forwarded-Host during the HTTP to HTTPS redirection", func() {
f.UpdateNginxConfigMapData("use-forwarded-headers", "true") f.UpdateNginxConfigMapData("use-forwarded-headers", "true")
ing := f.EnsureIngress(framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, nil)) ing := f.EnsureIngress(framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, nil))
@ -195,20 +179,16 @@ var _ = framework.DescribeSetting("[SSL] TLS protocols, ciphers and headers)", f
ing.Spec.TLS[0].Hosts, ing.Spec.TLS[0].Hosts,
ing.Spec.TLS[0].SecretName, ing.Spec.TLS[0].SecretName,
ing.Namespace) ing.Namespace)
Expect(err).NotTo(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig) framework.WaitForTLS(f.GetURL(framework.HTTPS), tlsConfig)
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Retry(10, 1*time.Second, http.StatusNotFound). WithHeader("Host", host).
RedirectPolicy(noRedirectPolicyFunc). WithHeader("X-Forwarded-Host", "example.com:80").
Set("Host", host). Expect().
Set("X-Forwarded-Host", "example.com:80"). Status(http.StatusPermanentRedirect).
End() Header("Location").Equal("https://example.com/")
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusPermanentRedirect))
Expect(resp.Header.Get("Location")).Should(Equal("https://example.com/"))
}) })
}) })

View file

@ -20,9 +20,8 @@ import (
"net/http" "net/http"
"strings" "strings"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
@ -30,11 +29,11 @@ import (
var _ = framework.IngressNginxDescribe("[SSL] redirect to HTTPS", func() { var _ = framework.IngressNginxDescribe("[SSL] redirect to HTTPS", func() {
f := framework.NewDefaultFramework("sslredirect") f := framework.NewDefaultFramework("sslredirect")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
It("should redirect from HTTP to HTTPS when secret is missing", func() { ginkgo.It("should redirect from HTTP to HTTPS when secret is missing", func() {
host := "redirect.com" host := "redirect.com"
_ = f.EnsureIngress(framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, nil)) _ = f.EnsureIngress(framework.NewSingleIngressWithTLS(host, "/", host, []string{host}, f.Namespace, framework.EchoService, 80, nil))
@ -46,23 +45,15 @@ var _ = framework.IngressNginxDescribe("[SSL] redirect to HTTPS", func() {
strings.Contains(server, "listen 80") strings.Contains(server, "listen 80")
}) })
log, err := f.NginxLogs() logs, err := f.NginxLogs()
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err, "obtaining nginx logs")
Expect(log).ToNot(BeEmpty()) assert.NotEmpty(ginkgo.GinkgoT(), logs)
resp, _, errs := gorequest.New(). f.HTTPTestClient().
Get(f.GetURL(framework.HTTP)). GET("/").
Set("Host", host). WithHeader("Host", host).
RedirectPolicy(func(_ gorequest.Request, _ []gorequest.Request) error { Expect().
return http.ErrUseLastResponse Status(http.StatusPermanentRedirect).
}). Header("Location").Equal("https://redirect.com/")
End()
Expect(errs).Should(BeEmpty())
Expect(resp.StatusCode).Should(Equal(http.StatusPermanentRedirect))
location, err := (*http.Response)(resp).Location()
Expect(err).Should(BeNil())
Expect(location.String()).Should(Equal("https://redirect.com/"))
}) })
}) })

View file

@ -23,10 +23,8 @@ import (
"strings" "strings"
"time" "time"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
"github.com/parnurzeal/gorequest"
v1 "k8s.io/api/core/v1" v1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
@ -35,11 +33,11 @@ import (
var _ = framework.IngressNginxDescribe("[SSL] secret update", func() { var _ = framework.IngressNginxDescribe("[SSL] secret update", func() {
f := framework.NewDefaultFramework("ssl") f := framework.NewDefaultFramework("ssl")
BeforeEach(func() { ginkgo.BeforeEach(func() {
f.NewEchoDeployment() f.NewEchoDeployment()
}) })
It("should not appear references to secret updates not used in ingress rules", func() { ginkgo.It("should not appear references to secret updates not used in ingress rules", func() {
host := "ssl-update" host := "ssl-update"
dummySecret := f.EnsureSecret(&v1.Secret{ dummySecret := f.EnsureSecret(&v1.Secret{
@ -57,7 +55,9 @@ var _ = framework.IngressNginxDescribe("[SSL] secret update", func() {
ing.Spec.TLS[0].Hosts, ing.Spec.TLS[0].Hosts,
ing.Spec.TLS[0].SecretName, ing.Spec.TLS[0].SecretName,
ing.Namespace) ing.Namespace)
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err)
time.Sleep(5 * time.Second)
f.WaitForNginxServer(host, f.WaitForNginxServer(host,
func(server string) bool { func(server string) bool {
@ -66,19 +66,20 @@ var _ = framework.IngressNginxDescribe("[SSL] secret update", func() {
}) })
log, err := f.NginxLogs() log, err := f.NginxLogs()
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err, "obtaining nginx logs")
Expect(log).ToNot(BeEmpty()) assert.NotContains(ginkgo.GinkgoT(), log, fmt.Sprintf("starting syncing of secret %v/dummy", f.Namespace))
Expect(log).ToNot(ContainSubstring(fmt.Sprintf("starting syncing of secret %v/dummy", f.Namespace)))
time.Sleep(5 * time.Second) time.Sleep(5 * time.Second)
dummySecret.Data["some-key"] = []byte("some value") dummySecret.Data["some-key"] = []byte("some value")
f.KubeClientSet.CoreV1().Secrets(f.Namespace).Update(dummySecret) f.KubeClientSet.CoreV1().Secrets(f.Namespace).Update(dummySecret)
time.Sleep(5 * time.Second)
Expect(log).ToNot(ContainSubstring(fmt.Sprintf("starting syncing of secret %v/dummy", f.Namespace))) assert.NotContains(ginkgo.GinkgoT(), log, fmt.Sprintf("starting syncing of secret %v/dummy", f.Namespace))
Expect(log).ToNot(ContainSubstring(fmt.Sprintf("error obtaining PEM from secret %v/dummy", f.Namespace))) assert.NotContains(ginkgo.GinkgoT(), log, fmt.Sprintf("error obtaining PEM from secret %v/dummy", f.Namespace))
}) })
It("should return the fake SSL certificate if the secret is invalid", func() { ginkgo.It("should return the fake SSL certificate if the secret is invalid", func() {
host := "invalid-ssl" host := "invalid-ssl"
// create a secret without cert or key // create a secret without cert or key
@ -97,25 +98,29 @@ var _ = framework.IngressNginxDescribe("[SSL] secret update", func() {
strings.Contains(server, "listen 443") strings.Contains(server, "listen 443")
}) })
req := gorequest.New() resp := f.HTTPTestClientWithTLSConfig(&tls.Config{ServerName: host, InsecureSkipVerify: true}).
resp, _, errs := req. GET("/").
Get(f.GetURL(framework.HTTPS)). WithURL(f.GetURL(framework.HTTPS)).
TLSClientConfig(&tls.Config{ServerName: host, InsecureSkipVerify: true}). WithHeader("Host", host).
Set("Host", host). Expect().
End() Status(http.StatusOK).
Expect(errs).Should(BeEmpty()) Raw()
Expect(resp.StatusCode).Should(Equal(http.StatusOK))
// check the returned secret is the fake one // check the returned secret is the fake one
cert := resp.TLS.PeerCertificates[0] cert := resp.TLS.PeerCertificates[0]
Expect(cert.DNSNames[0]).Should(Equal("ingress.local"))
Expect(cert.Subject.Organization[0]).Should(Equal("Acme Co")) assert.Equal(ginkgo.GinkgoT(), len(resp.TLS.PeerCertificates), 1)
Expect(cert.Subject.CommonName).Should(Equal("Kubernetes Ingress Controller Fake Certificate")) for _, pc := range resp.TLS.PeerCertificates {
assert.Equal(ginkgo.GinkgoT(), pc.Issuer.CommonName, "Kubernetes Ingress Controller Fake Certificate")
}
assert.Equal(ginkgo.GinkgoT(), cert.DNSNames[0], "ingress.local")
assert.Equal(ginkgo.GinkgoT(), cert.Subject.Organization[0], "Acme Co")
assert.Equal(ginkgo.GinkgoT(), cert.Subject.CommonName, "Kubernetes Ingress Controller Fake Certificate")
// verify the log contains a warning about invalid certificate // verify the log contains a warning about invalid certificate
log, err := f.NginxLogs() logs, err := f.NginxLogs()
Expect(err).ToNot(HaveOccurred()) assert.Nil(ginkgo.GinkgoT(), err, "obtaining nginx logs")
Expect(log).ToNot(BeEmpty()) assert.Contains(ginkgo.GinkgoT(), logs, fmt.Sprintf("%v/invalid-ssl\" contains no keypair or CA certificate", f.Namespace))
Expect(log).To(ContainSubstring(fmt.Sprintf("%v/invalid-ssl\" contains no keypair or CA certificate", f.Namespace)))
}) })
}) })

View file

@ -23,8 +23,8 @@ import (
"strings" "strings"
"time" "time"
. "github.com/onsi/ginkgo" "github.com/onsi/ginkgo"
. "github.com/onsi/gomega" "github.com/stretchr/testify/assert"
appsv1 "k8s.io/api/apps/v1" appsv1 "k8s.io/api/apps/v1"
apiv1 "k8s.io/api/core/v1" apiv1 "k8s.io/api/core/v1"
@ -39,9 +39,9 @@ var _ = framework.IngressNginxDescribe("[Status] status update", func() {
host := "status-update" host := "status-update"
address := getHostIP() address := getHostIP()
It("should update status field after client-go reconnection", func() { ginkgo.It("should update status field after client-go reconnection", func() {
port, cmd, err := f.KubectlProxy(0) port, cmd, err := f.KubectlProxy(0)
Expect(err).NotTo(HaveOccurred(), "unexpected error starting kubectl proxy") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error starting kubectl proxy")
err = framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1, err = framework.UpdateDeployment(f.KubeClientSet, f.Namespace, "nginx-ingress-controller", 1,
func(deployment *appsv1.Deployment) error { func(deployment *appsv1.Deployment) error {
@ -67,7 +67,7 @@ var _ = framework.IngressNginxDescribe("[Status] status update", func() {
_, err := f.KubeClientSet.AppsV1().Deployments(f.Namespace).Update(deployment) _, err := f.KubeClientSet.AppsV1().Deployments(f.Namespace).Update(deployment)
return err return err
}) })
Expect(err).NotTo(HaveOccurred(), "unexpected error updating ingress controller deployment flags") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error updating ingress controller deployment flags")
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeploymentWithReplicas(1)
@ -82,27 +82,27 @@ var _ = framework.IngressNginxDescribe("[Status] status update", func() {
time.Sleep(30 * time.Second) time.Sleep(30 * time.Second)
err = cmd.Process.Kill() err = cmd.Process.Kill()
Expect(err).NotTo(HaveOccurred(), "unexpected error terminating kubectl proxy") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error terminating kubectl proxy")
ing, err = f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Get(host, metav1.GetOptions{}) ing, err = f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).Get(host, metav1.GetOptions{})
Expect(err).NotTo(HaveOccurred(), "unexpected error getting %s/%v Ingress", f.Namespace, host) assert.Nil(ginkgo.GinkgoT(), err, "unexpected error getting %s/%v Ingress", f.Namespace, host)
ing.Status.LoadBalancer.Ingress = []apiv1.LoadBalancerIngress{} ing.Status.LoadBalancer.Ingress = []apiv1.LoadBalancerIngress{}
_, err = f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).UpdateStatus(ing) _, err = f.KubeClientSet.NetworkingV1beta1().Ingresses(f.Namespace).UpdateStatus(ing)
Expect(err).NotTo(HaveOccurred(), "unexpected error cleaning Ingress status") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error cleaning Ingress status")
time.Sleep(10 * time.Second) time.Sleep(10 * time.Second)
err = f.KubeClientSet.CoreV1(). err = f.KubeClientSet.CoreV1().
ConfigMaps(f.Namespace). ConfigMaps(f.Namespace).
Delete("ingress-controller-leader-nginx", &metav1.DeleteOptions{}) Delete("ingress-controller-leader-nginx", &metav1.DeleteOptions{})
Expect(err).NotTo(HaveOccurred(), "unexpected error deleting leader election configmap") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error deleting leader election configmap")
_, cmd, err = f.KubectlProxy(port) _, cmd, err = f.KubectlProxy(port)
Expect(err).NotTo(HaveOccurred(), "unexpected error starting kubectl proxy") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error starting kubectl proxy")
defer func() { defer func() {
if cmd != nil { if cmd != nil {
err := cmd.Process.Kill() err := cmd.Process.Kill()
Expect(err).NotTo(HaveOccurred(), "unexpected error terminating kubectl proxy") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error terminating kubectl proxy")
} }
}() }()
@ -118,8 +118,8 @@ var _ = framework.IngressNginxDescribe("[Status] status update", func() {
return true, nil return true, nil
}) })
Expect(err).NotTo(HaveOccurred(), "unexpected error waiting for ingress status") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error waiting for ingress status")
Expect(ing.Status.LoadBalancer.Ingress).Should(Equal([]apiv1.LoadBalancerIngress{ assert.Equal(ginkgo.GinkgoT(), ing.Status.LoadBalancer.Ingress, ([]apiv1.LoadBalancerIngress{
{IP: "1.1.0.0"}, {IP: "1.1.0.0"},
})) }))
}) })

View file

@ -20,32 +20,30 @@ import (
"context" "context"
"fmt" "fmt"
"net" "net"
"net/http"
"strings" "strings"
"github.com/parnurzeal/gorequest" "github.com/onsi/ginkgo"
"github.com/stretchr/testify/assert"
corev1 "k8s.io/api/core/v1" corev1 "k8s.io/api/core/v1"
metav1 "k8s.io/apimachinery/pkg/apis/meta/v1" metav1 "k8s.io/apimachinery/pkg/apis/meta/v1"
"k8s.io/apimachinery/pkg/util/intstr" "k8s.io/apimachinery/pkg/util/intstr"
. "github.com/onsi/ginkgo"
. "github.com/onsi/gomega"
"k8s.io/ingress-nginx/test/e2e/framework" "k8s.io/ingress-nginx/test/e2e/framework"
) )
var _ = framework.IngressNginxDescribe("[TCP] tcp-services", func() { var _ = framework.IngressNginxDescribe("[TCP] tcp-services", func() {
f := framework.NewDefaultFramework("tcp") f := framework.NewDefaultFramework("tcp")
It("should expose a TCP service", func() { ginkgo.It("should expose a TCP service", func() {
f.NewEchoDeploymentWithReplicas(1) f.NewEchoDeploymentWithReplicas(1)
config, err := f.KubeClientSet. config, err := f.KubeClientSet.
CoreV1(). CoreV1().
ConfigMaps(f.Namespace). ConfigMaps(f.Namespace).
Get("tcp-services", metav1.GetOptions{}) Get("tcp-services", metav1.GetOptions{})
Expect(err).To(BeNil(), "unexpected error obtaining tcp-services configmap") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error obtaining tcp-services configmap")
Expect(config).NotTo(BeNil(), "expected a configmap but none returned") assert.NotNil(ginkgo.GinkgoT(), config, "expected a configmap but none returned")
if config.Data == nil { if config.Data == nil {
config.Data = map[string]string{} config.Data = map[string]string{}
@ -57,14 +55,14 @@ var _ = framework.IngressNginxDescribe("[TCP] tcp-services", func() {
CoreV1(). CoreV1().
ConfigMaps(f.Namespace). ConfigMaps(f.Namespace).
Update(config) Update(config)
Expect(err).NotTo(HaveOccurred(), "unexpected error updating configmap") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error updating configmap")
svc, err := f.KubeClientSet. svc, err := f.KubeClientSet.
CoreV1(). CoreV1().
Services(f.Namespace). Services(f.Namespace).
Get("nginx-ingress-controller", metav1.GetOptions{}) Get("nginx-ingress-controller", metav1.GetOptions{})
Expect(err).To(BeNil(), "unexpected error obtaining ingress-nginx service") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error obtaining ingress-nginx service")
Expect(svc).NotTo(BeNil(), "expected a service but none returned") assert.NotNil(ginkgo.GinkgoT(), svc, "expected a service but none returned")
svc.Spec.Ports = append(svc.Spec.Ports, corev1.ServicePort{ svc.Spec.Ports = append(svc.Spec.Ports, corev1.ServicePort{
Name: framework.EchoService, Name: framework.EchoService,
@ -75,7 +73,7 @@ var _ = framework.IngressNginxDescribe("[TCP] tcp-services", func() {
CoreV1(). CoreV1().
Services(f.Namespace). Services(f.Namespace).
Update(svc) Update(svc)
Expect(err).NotTo(HaveOccurred(), "unexpected error updating service") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error updating service")
f.WaitForNginxConfiguration( f.WaitForNginxConfiguration(
func(cfg string) bool { func(cfg string) bool {
@ -83,14 +81,15 @@ var _ = framework.IngressNginxDescribe("[TCP] tcp-services", func() {
}) })
ip := f.GetNginxIP() ip := f.GetNginxIP()
resp, _, errs := gorequest.New().
Get(fmt.Sprintf("http://%v:8080", ip)). f.HTTPTestClient().
End() GET("/").
Expect(errs).Should(BeEmpty()) WithURL(fmt.Sprintf("http://%v:8080", ip)).
Expect(resp.StatusCode).Should(Equal(200)) Expect().
Status(http.StatusOK)
}) })
It("should expose an ExternalName TCP service", func() { ginkgo.It("should expose an ExternalName TCP service", func() {
// Setup: // Setup:
// - Create an external name service for DNS lookups on port 5353. Point it to google's DNS server // - Create an external name service for DNS lookups on port 5353. Point it to google's DNS server
// - Expose port 5353 on the nginx ingress NodePort service to open a hole for this test // - Expose port 5353 on the nginx ingress NodePort service to open a hole for this test
@ -122,8 +121,8 @@ var _ = framework.IngressNginxDescribe("[TCP] tcp-services", func() {
CoreV1(). CoreV1().
Services(f.Namespace). Services(f.Namespace).
Get("nginx-ingress-controller", metav1.GetOptions{}) Get("nginx-ingress-controller", metav1.GetOptions{})
Expect(err).To(BeNil(), "unexpected error obtaining ingress-nginx service") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error obtaining ingress-nginx service")
Expect(svc).NotTo(BeNil(), "expected a service but none returned") assert.NotNil(ginkgo.GinkgoT(), svc, "expected a service but none returned")
svc.Spec.Ports = append(svc.Spec.Ports, corev1.ServicePort{ svc.Spec.Ports = append(svc.Spec.Ports, corev1.ServicePort{
Name: "dns-svc", Name: "dns-svc",
@ -134,15 +133,15 @@ var _ = framework.IngressNginxDescribe("[TCP] tcp-services", func() {
CoreV1(). CoreV1().
Services(f.Namespace). Services(f.Namespace).
Update(svc) Update(svc)
Expect(err).NotTo(HaveOccurred(), "unexpected error updating service") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error updating service")
// Update the TCP configmap to link port 5353 to the DNS external name service // Update the TCP configmap to link port 5353 to the DNS external name service
config, err := f.KubeClientSet. config, err := f.KubeClientSet.
CoreV1(). CoreV1().
ConfigMaps(f.Namespace). ConfigMaps(f.Namespace).
Get("tcp-services", metav1.GetOptions{}) Get("tcp-services", metav1.GetOptions{})
Expect(err).To(BeNil(), "unexpected error obtaining tcp-services configmap") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error obtaining tcp-services configmap")
Expect(config).NotTo(BeNil(), "expected a configmap but none returned") assert.NotNil(ginkgo.GinkgoT(), config, "expected a configmap but none returned")
if config.Data == nil { if config.Data == nil {
config.Data = map[string]string{} config.Data = map[string]string{}
@ -154,7 +153,7 @@ var _ = framework.IngressNginxDescribe("[TCP] tcp-services", func() {
CoreV1(). CoreV1().
ConfigMaps(f.Namespace). ConfigMaps(f.Namespace).
Update(config) Update(config)
Expect(err).NotTo(HaveOccurred(), "unexpected error updating configmap") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error updating configmap")
// Validate that the generated nginx config contains the expected `proxy_upstream_name` value // Validate that the generated nginx config contains the expected `proxy_upstream_name` value
f.WaitForNginxConfiguration( f.WaitForNginxConfiguration(
@ -172,8 +171,7 @@ var _ = framework.IngressNginxDescribe("[TCP] tcp-services", func() {
}, },
} }
ips, err := resolver.LookupHost(context.Background(), "google-public-dns-b.google.com") ips, err := resolver.LookupHost(context.Background(), "google-public-dns-b.google.com")
Expect(err).NotTo(HaveOccurred(), "unexpected error from DNS resolver") assert.Nil(ginkgo.GinkgoT(), err, "unexpected error from DNS resolver")
Expect(ips).Should(ContainElement("8.8.4.4")) assert.Contains(ginkgo.GinkgoT(), ips, "8.8.4.4")
}) })
}) })