istio.io/istio@v0.0.0-20240520182934-d79c90f27776/tests/integration/security/remote_jwks/remote_jwks_test.go (about)

     1  //go:build integ
     2  // +build integ
     3  
     4  // Copyright Istio Authors
     5  //
     6  // Licensed under the Apache License, Version 2.0 (the "License");
     7  // you may not use this file except in compliance with the License.
     8  // You may obtain a copy of the License at
     9  //
    10  //     http://www.apache.org/licenses/LICENSE-2.0
    11  //
    12  // Unless required by applicable law or agreed to in writing, software
    13  // distributed under the License is distributed on an "AS IS" BASIS,
    14  // WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
    15  // See the License for the specific language governing permissions and
    16  // limitations under the License.
    17  
    18  package remotejwks
    19  
    20  import (
    21  	"net/http"
    22  	"strings"
    23  	"testing"
    24  
    25  	"istio.io/istio/pkg/http/headers"
    26  	"istio.io/istio/pkg/test/framework"
    27  	"istio.io/istio/pkg/test/framework/components/echo"
    28  	"istio.io/istio/pkg/test/framework/components/echo/check"
    29  	"istio.io/istio/pkg/test/framework/components/echo/echotest"
    30  	"istio.io/istio/pkg/test/framework/resource/config/apply"
    31  	"istio.io/istio/tests/common/jwt"
    32  	"istio.io/istio/tests/integration/security/util"
    33  )
    34  
    35  // TestRemoteJwks tests always delegate Envoy to fetch http jwks server.
    36  func TestRemoteJwks(t *testing.T) {
    37  	payload1 := strings.Split(jwt.TokenIssuer1, ".")[1]
    38  	framework.NewTest(t).
    39  		Run(func(t framework.TestContext) {
    40  			ns := apps.EchoNamespace.Namespace
    41  
    42  			cases := []struct {
    43  				name          string
    44  				policyFile    string
    45  				delay         string
    46  				timeout       string
    47  				customizeCall func(t framework.TestContext, from echo.Instance, opts *echo.CallOptions)
    48  			}{
    49  				{
    50  					name:       "remote-jwks-without-service-entry",
    51  					policyFile: "./testdata/requestauthn-no-se.yaml.tmpl",
    52  					customizeCall: func(t framework.TestContext, from echo.Instance, opts *echo.CallOptions) {
    53  						opts.HTTP.Path = "/valid-token-forward-remote-jwks"
    54  						opts.HTTP.Headers = headers.New().WithAuthz(jwt.TokenIssuer1).Build()
    55  						opts.Check = check.And(
    56  							check.NotOK(),
    57  							check.Status(http.StatusUnauthorized))
    58  					},
    59  				},
    60  				{
    61  					name:       "remote-jwks-with-service-entry",
    62  					policyFile: "./testdata/requestauthn-with-se.yaml.tmpl",
    63  					customizeCall: func(t framework.TestContext, from echo.Instance, opts *echo.CallOptions) {
    64  						opts.HTTP.Path = "/valid-token-forward-remote-jwks"
    65  						opts.HTTP.Headers = headers.New().WithAuthz(jwt.TokenIssuer1).Build()
    66  						opts.Check = check.And(
    67  							check.OK(),
    68  							check.ReachedTargetClusters(t),
    69  							check.RequestHeaders(map[string]string{
    70  								headers.Authorization: "Bearer " + jwt.TokenIssuer1,
    71  								"X-Test-Payload":      payload1,
    72  							}))
    73  					},
    74  				},
    75  				{
    76  					name:       "remote-jwks-with-service-entry",
    77  					policyFile: "./testdata/requestauthn-with-se-timeout.yaml.tmpl",
    78  					timeout:    "10ms",
    79  					delay:      "30ms",
    80  					customizeCall: func(t framework.TestContext, from echo.Instance, opts *echo.CallOptions) {
    81  						opts.HTTP.Path = "/valid-token-forward-remote-jwks"
    82  						opts.HTTP.Headers = headers.New().WithAuthz(jwt.TokenIssuer1).Build()
    83  						opts.Check = check.And(
    84  							check.NotOK(),
    85  							check.Status(http.StatusUnauthorized),
    86  						)
    87  					},
    88  				},
    89  			}
    90  
    91  			for _, c := range cases {
    92  				t.NewSubTest(c.name).Run(func(t framework.TestContext) {
    93  					echotest.New(t, apps.All.Instances()).
    94  						SetupForDestination(func(t framework.TestContext, to echo.Target) error {
    95  							args := map[string]string{
    96  								"Namespace": ns.Name(),
    97  								"dst":       to.Config().Service,
    98  								"delay":     c.delay,
    99  								"timeout":   c.timeout,
   100  							}
   101  							return t.ConfigIstio().EvalFile(ns.Name(), args, c.policyFile).Apply(apply.Wait)
   102  						}).
   103  						FromMatch(
   104  							// TODO(JimmyCYJ): enable VM for all test cases.
   105  							util.SourceMatcher(ns, true)).
   106  						ConditionallyTo(echotest.ReachableDestinations).
   107  						ToMatch(util.DestMatcher(ns, true)).
   108  						Run(func(t framework.TestContext, from echo.Instance, to echo.Target) {
   109  							opts := echo.CallOptions{
   110  								To: to,
   111  								Port: echo.Port{
   112  									Name: "http",
   113  								},
   114  							}
   115  
   116  							c.customizeCall(t, from, &opts)
   117  
   118  							from.CallOrFail(t, opts)
   119  						})
   120  				})
   121  			}
   122  		})
   123  }