Skip to content

Commit 61190da

Browse files
committed
Update OIDC timeout test, add errors timeout test, add VirtualServer test that checks OIDC timeout nginx conf values
1 parent 8da33ae commit 61190da

File tree

2 files changed

+293
-10
lines changed

2 files changed

+293
-10
lines changed

internal/configs/configmaps_test.go

Lines changed: 125 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -394,30 +394,145 @@ func TestParseConfigMapOIDC(t *testing.T) {
394394
},
395395
}
396396

397+
nginxPlus := true
398+
hasAppProtect := false
399+
hasAppProtectDos := false
400+
hasTLSPassthrough := false
401+
directiveAutoadjustEnabled := false
402+
397403
for _, test := range tests {
398404
t.Run(test.msg, func(t *testing.T) {
399-
cfgParams := NewDefaultConfigParams(context.Background(), true)
400-
401-
err := parseConfigMapOIDC(nil, test.configMap, cfgParams, makeEventLogger())
402-
if err != nil {
403-
t.Errorf("parseConfigMapOIDC() returned unexpected error: %v", err)
405+
result, configOk := ParseConfigMap(context.Background(), test.configMap, nginxPlus, hasAppProtect, hasAppProtectDos, hasTLSPassthrough, directiveAutoadjustEnabled, makeEventLogger())
406+
if !configOk {
407+
t.Error("want configOk true, got configOk false")
404408
}
405409

406410
// Check only the specific fields that are set in the test expectation
407411
if test.want.PKCETimeout != "" {
408-
assert.Equal(t, test.want.PKCETimeout, cfgParams.OIDC.PKCETimeout)
412+
assert.Equal(t, test.want.PKCETimeout, result.OIDC.PKCETimeout)
409413
}
410414
if test.want.IDTokenTimeout != "" {
411-
assert.Equal(t, test.want.IDTokenTimeout, cfgParams.OIDC.IDTokenTimeout)
415+
assert.Equal(t, test.want.IDTokenTimeout, result.OIDC.IDTokenTimeout)
412416
}
413417
if test.want.AccessTimeout != "" {
414-
assert.Equal(t, test.want.AccessTimeout, cfgParams.OIDC.AccessTimeout)
418+
assert.Equal(t, test.want.AccessTimeout, result.OIDC.AccessTimeout)
415419
}
416420
if test.want.RefreshTimeout != "" {
417-
assert.Equal(t, test.want.RefreshTimeout, cfgParams.OIDC.RefreshTimeout)
421+
assert.Equal(t, test.want.RefreshTimeout, result.OIDC.RefreshTimeout)
418422
}
419423
if test.want.SIDSTimeout != "" {
420-
assert.Equal(t, test.want.SIDSTimeout, cfgParams.OIDC.SIDSTimeout)
424+
assert.Equal(t, test.want.SIDSTimeout, result.OIDC.SIDSTimeout)
425+
}
426+
})
427+
}
428+
}
429+
430+
func TestParseConfigMapOIDCErrors(t *testing.T) {
431+
t.Parallel()
432+
tests := []struct {
433+
configMap *v1.ConfigMap
434+
expectedErr bool
435+
msg string
436+
}{
437+
{
438+
configMap: &v1.ConfigMap{
439+
Data: map[string]string{
440+
"oidc-pkce-timeout": "invalid-time",
441+
},
442+
},
443+
expectedErr: true,
444+
msg: "invalid PKCE timeout format",
445+
},
446+
{
447+
configMap: &v1.ConfigMap{
448+
Data: map[string]string{
449+
"oidc-id-tokens-timeout": "abc123",
450+
},
451+
},
452+
expectedErr: true,
453+
msg: "invalid ID token timeout format",
454+
},
455+
{
456+
configMap: &v1.ConfigMap{
457+
Data: map[string]string{
458+
"oidc-access-tokens-timeout": "5x",
459+
},
460+
},
461+
expectedErr: true,
462+
msg: "invalid access token timeout format",
463+
},
464+
{
465+
configMap: &v1.ConfigMap{
466+
Data: map[string]string{
467+
"oidc-refresh-tokens-timeout": "",
468+
},
469+
},
470+
expectedErr: true,
471+
msg: "empty refresh token timeout",
472+
},
473+
{
474+
configMap: &v1.ConfigMap{
475+
Data: map[string]string{
476+
"oidc-sids-timeout": " ",
477+
},
478+
},
479+
expectedErr: true,
480+
msg: "whitespace-only SIDS timeout",
481+
},
482+
{
483+
configMap: &v1.ConfigMap{
484+
Data: map[string]string{
485+
"oidc-pkce-timeout": "-5m",
486+
},
487+
},
488+
expectedErr: true,
489+
msg: "negative PKCE timeout",
490+
},
491+
{
492+
configMap: &v1.ConfigMap{
493+
Data: map[string]string{
494+
"oidc-id-tokens-timeout": "1.5h",
495+
},
496+
},
497+
expectedErr: true,
498+
msg: "decimal in ID token timeout",
499+
},
500+
{
501+
configMap: &v1.ConfigMap{
502+
Data: map[string]string{
503+
"oidc-access-tokens-timeout": "5minutes",
504+
},
505+
},
506+
expectedErr: true,
507+
msg: "invalid time unit format",
508+
},
509+
510+
{
511+
configMap: &v1.ConfigMap{
512+
Data: map[string]string{
513+
"oidc-sids-timeout": "5s 10m",
514+
},
515+
},
516+
expectedErr: true,
517+
msg: "multiple time values without proper format",
518+
},
519+
}
520+
521+
nginxPlus := true
522+
hasAppProtect := false
523+
hasAppProtectDos := false
524+
hasTLSPassthrough := false
525+
directiveAutoadjustEnabled := false
526+
527+
for _, test := range tests {
528+
t.Run(test.msg, func(t *testing.T) {
529+
_, configOk := ParseConfigMap(context.Background(), test.configMap, nginxPlus, hasAppProtect, hasAppProtectDos, hasTLSPassthrough, directiveAutoadjustEnabled, makeEventLogger())
530+
531+
if test.expectedErr && configOk {
532+
t.Errorf("want configOk false, got configOk true for %s", test.msg)
533+
}
534+
if !test.expectedErr && !configOk {
535+
t.Errorf("want configOk true, got configOk false for %s", test.msg)
421536
}
422537
})
423538
}

internal/configs/virtualserver_test.go

Lines changed: 168 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,7 @@ import (
1313

1414
"github.com/google/go-cmp/cmp"
1515
"github.com/google/go-cmp/cmp/cmpopts"
16+
"github.com/nginx/kubernetes-ingress/internal/configs/version1"
1617
"github.com/nginx/kubernetes-ingress/internal/configs/version2"
1718
"github.com/nginx/kubernetes-ingress/internal/k8s/secrets"
1819
nl "github.com/nginx/kubernetes-ingress/internal/logger"
@@ -24,6 +25,7 @@ import (
2425
meta_v1 "k8s.io/apimachinery/pkg/apis/meta/v1"
2526
"k8s.io/apimachinery/pkg/runtime"
2627
"k8s.io/apimachinery/pkg/util/intstr"
28+
"k8s.io/client-go/tools/record"
2729
)
2830

2931
func createPointerFromBool(b bool) *bool {
@@ -21963,6 +21965,105 @@ func TestGenerateTimeWithDefault(t *testing.T) {
2196321965
}
2196421966
}
2196521967

21968+
// TestOIDCTimeoutInMainConfig verifies that OIDC timeout values from ConfigMap appear in generated nginx.conf
21969+
func TestOIDCTimeoutInMainConfig(t *testing.T) {
21970+
t.Parallel()
21971+
21972+
tests := []struct {
21973+
name string
21974+
configMapData map[string]string
21975+
expectedTimeouts map[string]string
21976+
expectedDirectives []string
21977+
}{
21978+
{
21979+
name: "default timeouts",
21980+
configMapData: map[string]string{
21981+
"zone-sync": "true",
21982+
},
21983+
expectedTimeouts: map[string]string{
21984+
"PKCETimeout": "90s",
21985+
"IDTokenTimeout": "1h",
21986+
"AccessTimeout": "1h",
21987+
"RefreshTimeout": "8h",
21988+
"SIDSTimeout": "8h",
21989+
},
21990+
expectedDirectives: []string{
21991+
"keyval_zone zone=oidc_pkce:128K timeout=90s sync;",
21992+
"keyval_zone zone=oidc_id_tokens:1M timeout=1h sync;",
21993+
"keyval_zone zone=oidc_access_tokens:1M timeout=1h sync;",
21994+
"keyval_zone zone=refresh_tokens:1M timeout=8h sync;",
21995+
"keyval_zone zone=oidc_sids:1M timeout=8h sync;",
21996+
"include oidc/oidc_common.conf;",
21997+
},
21998+
},
21999+
{
22000+
name: "custom timeouts",
22001+
configMapData: map[string]string{
22002+
"zone-sync": "true",
22003+
"oidc-pkce-timeout": "2m",
22004+
"oidc-id-tokens-timeout": "2h",
22005+
"oidc-access-tokens-timeout": "30m",
22006+
"oidc-refresh-tokens-timeout": "1h",
22007+
"oidc-sids-timeout": "120s",
22008+
},
22009+
expectedTimeouts: map[string]string{
22010+
"PKCETimeout": "2m",
22011+
"IDTokenTimeout": "2h",
22012+
"AccessTimeout": "30m",
22013+
"RefreshTimeout": "1h",
22014+
"SIDSTimeout": "120s",
22015+
},
22016+
expectedDirectives: []string{
22017+
"keyval_zone zone=oidc_pkce:128K timeout=2m sync;",
22018+
"keyval_zone zone=oidc_id_tokens:1M timeout=2h sync;",
22019+
"keyval_zone zone=oidc_access_tokens:1M timeout=30m sync;",
22020+
"keyval_zone zone=refresh_tokens:1M timeout=1h sync;",
22021+
"keyval_zone zone=oidc_sids:1M timeout=120s sync;",
22022+
"include oidc/oidc_common.conf;",
22023+
},
22024+
},
22025+
}
22026+
22027+
for _, test := range tests {
22028+
t.Run(test.name, func(t *testing.T) {
22029+
// Parse ConfigMap
22030+
configMap := &api_v1.ConfigMap{Data: test.configMapData}
22031+
configParams, configOk := ParseConfigMap(context.Background(), configMap, true, false, false, false, false, record.NewFakeRecorder(1024))
22032+
if !configOk {
22033+
t.Error("expected configOk true, got configOk false ")
22034+
}
22035+
22036+
vsc := newVirtualServerConfigurator(&baseCfgParams, false, false, &StaticConfigParams{}, false, &fakeBV)
22037+
_, warnings := vsc.GenerateVirtualServerConfig(&virtualServerExWithOIDCTimeout, nil, nil)
22038+
if len(warnings) != 0 {
22039+
t.Errorf("Unexpected warnings: %v", warnings)
22040+
}
22041+
22042+
mainConfig := GenerateNginxMainConfig(&StaticConfigParams{}, configParams, &MGMTConfigParams{})
22043+
mainConfig.OIDC.Enable = true
22044+
22045+
templateExecutor, err := version1.NewTemplateExecutor("version1/nginx-plus.tmpl", "version1/nginx-plus.ingress.tmpl")
22046+
if err != nil {
22047+
t.Fatalf("Failed to create template executor: %v", err)
22048+
}
22049+
22050+
nginxConfigContent, err := templateExecutor.ExecuteMainConfigTemplate(mainConfig)
22051+
if err != nil {
22052+
t.Fatalf("Failed to execute template: %v", err)
22053+
}
22054+
22055+
configString := string(nginxConfigContent)
22056+
t.Logf("Generated nginx.conf snippet:\n%s", configString)
22057+
22058+
for _, directive := range test.expectedDirectives {
22059+
if !strings.Contains(configString, directive) {
22060+
t.Errorf("Expected directive not found: %s", directive)
22061+
}
22062+
}
22063+
})
22064+
}
22065+
}
22066+
2196622067
var (
2196722068
l = slog.New(nic_glog.New(io.Discard, &nic_glog.Options{Level: levels.LevelInfo}))
2196822069
ctx = nl.ContextWithLogger(context.Background(), l)
@@ -21977,6 +22078,73 @@ var (
2197722078
RealIPRecursive: true,
2197822079
}
2197922080

22081+
virtualServerExWithOIDCTimeout = VirtualServerEx{
22082+
VirtualServer: &conf_v1.VirtualServer{
22083+
ObjectMeta: meta_v1.ObjectMeta{
22084+
Name: "oidc-app",
22085+
Namespace: "default",
22086+
},
22087+
Spec: conf_v1.VirtualServerSpec{
22088+
Host: "app.example.com",
22089+
Upstreams: []conf_v1.Upstream{
22090+
{
22091+
Name: "app",
22092+
Service: "app-svc",
22093+
Port: 80,
22094+
},
22095+
},
22096+
Routes: []conf_v1.Route{
22097+
{
22098+
Path: "/",
22099+
Policies: []conf_v1.PolicyReference{
22100+
{
22101+
Name: "oidc-policy",
22102+
Namespace: "default",
22103+
},
22104+
},
22105+
Action: &conf_v1.Action{
22106+
Pass: "app",
22107+
},
22108+
},
22109+
},
22110+
},
22111+
},
22112+
Policies: map[string]*conf_v1.Policy{
22113+
"default/oidc-policy": {
22114+
ObjectMeta: meta_v1.ObjectMeta{
22115+
Name: "oidc-policy",
22116+
Namespace: "default",
22117+
},
22118+
Spec: conf_v1.PolicySpec{
22119+
OIDC: &conf_v1.OIDC{
22120+
AuthEndpoint: "https://auth.example.com/auth",
22121+
TokenEndpoint: "https://auth.example.com/token",
22122+
JWKSURI: "https://auth.example.com/jwks",
22123+
ClientID: "test-client-id",
22124+
ClientSecret: "oidc-secret",
22125+
Scope: "openid profile email",
22126+
RedirectURI: "/redirect",
22127+
ZoneSyncLeeway: createPointerFromInt(20),
22128+
AccessTokenEnable: true,
22129+
EndSessionEndpoint: "https://auth.example.com/logout",
22130+
PostLogoutRedirectURI: "/_logout",
22131+
},
22132+
},
22133+
},
22134+
},
22135+
SecretRefs: map[string]*secrets.SecretReference{
22136+
"default/oidc-secret": {
22137+
Secret: &api_v1.Secret{
22138+
Type: secrets.SecretTypeOIDC,
22139+
Data: map[string][]byte{
22140+
"client-secret": []byte("super-secret-value"),
22141+
},
22142+
},
22143+
Path: "/etc/nginx/secrets/default_oidc-secret",
22144+
},
22145+
},
22146+
}
22147+
2198022148
virtualServerExWithGunzipOn = VirtualServerEx{
2198122149
VirtualServer: &conf_v1.VirtualServer{
2198222150
ObjectMeta: meta_v1.ObjectMeta{

0 commit comments

Comments
 (0)