From 99f1da009b091769a6be5332bb28771849a2ccba Mon Sep 17 00:00:00 2001 From: Furkan Senharputlu Date: Fri, 22 Dec 2023 18:34:51 +0300 Subject: [PATCH] [TT-10868] Implement OAS api level response header transformation (#5905) Parent: https://tyktech.atlassian.net/browse/TT-4851 Subtask: https://tyktech.atlassian.net/browse/TT-10868 --- apidef/migration.go | 10 ++++++++ apidef/oas/middleware.go | 31 ++++++++++++++++++++++++ apidef/oas/oas_test.go | 4 +-- apidef/oas/schema/x-tyk-api-gateway.json | 3 +++ apidef/oas/schema/x-tyk-gateway.md | 5 ++++ 5 files changed, 50 insertions(+), 3 deletions(-) diff --git a/apidef/migration.go b/apidef/migration.go index 80fe0ca228a9..d09d8b56593b 100644 --- a/apidef/migration.go +++ b/apidef/migration.go @@ -247,10 +247,12 @@ func (a *APIDefinition) Migrate() (versions []APIDefinition, err error) { a.MigrateEndpointMeta() a.MigrateCachePlugin() a.migrateGlobalHeaders() + a.migrateGlobalResponseHeaders() for i := 0; i < len(versions); i++ { versions[i].MigrateEndpointMeta() versions[i].MigrateCachePlugin() versions[i].migrateGlobalHeaders() + versions[i].migrateGlobalResponseHeaders() } return versions, nil @@ -321,6 +323,14 @@ func (a *APIDefinition) migrateGlobalHeaders() { } } +func (a *APIDefinition) migrateGlobalResponseHeaders() { + vInfo := a.VersionData.Versions[""] + if len(vInfo.GlobalResponseHeaders) == 0 && len(vInfo.GlobalResponseHeadersRemove) == 0 { + vInfo.GlobalResponseHeadersDisabled = true + a.VersionData.Versions[""] = vInfo + } +} + func (a *APIDefinition) MigrateCachePlugin() { vInfo := a.VersionData.Versions[""] list := vInfo.ExtendedPaths.Cached diff --git a/apidef/oas/middleware.go b/apidef/oas/middleware.go index c82c99997804..572d86302aad 100644 --- a/apidef/oas/middleware.go +++ b/apidef/oas/middleware.go @@ -73,6 +73,10 @@ type Global struct { // TransformRequestHeaders contains the configurations related to API level request header transformation. // Tyk classic API definition: `global_headers`/`global_headers_remove`. TransformRequestHeaders *TransformHeaders `bson:"transformRequestHeaders,omitempty" json:"transformRequestHeaders,omitempty"` + + // TransformResponseHeaders contains the configurations related to API level response header transformation. + // Tyk classic API definition: `global_response_headers`/`global_response_headers_remove`. + TransformResponseHeaders *TransformHeaders `bson:"transformResponseHeaders,omitempty" json:"transformResponseHeaders,omitempty"` } // Fill fills *Global from apidef.APIDefinition. @@ -153,6 +157,19 @@ func (g *Global) Fill(api apidef.APIDefinition) { if ShouldOmit(g.TransformRequestHeaders) { g.TransformRequestHeaders = nil } + + if g.TransformResponseHeaders == nil { + g.TransformResponseHeaders = &TransformHeaders{} + } + + g.TransformResponseHeaders.Fill(apidef.HeaderInjectionMeta{ + Disabled: vInfo.GlobalResponseHeadersDisabled, + AddHeaders: vInfo.GlobalResponseHeaders, + DeleteHeaders: vInfo.GlobalResponseHeadersRemove, + }) + if ShouldOmit(g.TransformResponseHeaders) { + g.TransformResponseHeaders = nil + } } // ExtractTo extracts *Global into *apidef.APIDefinition. @@ -230,6 +247,16 @@ func (g *Global) ExtractTo(api *apidef.APIDefinition) { var headerMeta apidef.HeaderInjectionMeta g.TransformRequestHeaders.ExtractTo(&headerMeta) + if g.TransformResponseHeaders == nil { + g.TransformResponseHeaders = &TransformHeaders{} + defer func() { + g.TransformResponseHeaders = nil + }() + } + + var resHeaderMeta apidef.HeaderInjectionMeta + g.TransformResponseHeaders.ExtractTo(&resHeaderMeta) + if len(api.VersionData.Versions) == 0 { api.VersionData.Versions = map[string]apidef.VersionInfo{ Main: {}, @@ -240,6 +267,10 @@ func (g *Global) ExtractTo(api *apidef.APIDefinition) { vInfo.GlobalHeadersDisabled = headerMeta.Disabled vInfo.GlobalHeaders = headerMeta.AddHeaders vInfo.GlobalHeadersRemove = headerMeta.DeleteHeaders + + vInfo.GlobalResponseHeadersDisabled = resHeaderMeta.Disabled + vInfo.GlobalResponseHeaders = resHeaderMeta.AddHeaders + vInfo.GlobalResponseHeadersRemove = resHeaderMeta.DeleteHeaders api.VersionData.Versions[Main] = vInfo } diff --git a/apidef/oas/oas_test.go b/apidef/oas/oas_test.go index 78148a653f43..e6e965c7b6d1 100644 --- a/apidef/oas/oas_test.go +++ b/apidef/oas/oas_test.go @@ -169,6 +169,7 @@ func TestOAS_ExtractTo_ResetAPIDefinition(t *testing.T) { vInfo.Paths.BlackList = nil vInfo.OverrideTarget = "" vInfo.GlobalHeadersDisabled = false + vInfo.GlobalResponseHeadersDisabled = false vInfo.UseExtendedPaths = false vInfo.ExtendedPaths.MockResponse = nil vInfo.ExtendedPaths.Cached = nil @@ -245,9 +246,6 @@ func TestOAS_ExtractTo_ResetAPIDefinition(t *testing.T) { "APIDefinition.VersionData.Versions[0].ExtendedPaths.PersistGraphQL[0].Method", "APIDefinition.VersionData.Versions[0].ExtendedPaths.PersistGraphQL[0].Operation", "APIDefinition.VersionData.Versions[0].ExtendedPaths.PersistGraphQL[0].Variables[0]", - "APIDefinition.VersionData.Versions[0].GlobalResponseHeaders[0]", - "APIDefinition.VersionData.Versions[0].GlobalResponseHeadersRemove[0]", - "APIDefinition.VersionData.Versions[0].GlobalResponseHeadersDisabled", "APIDefinition.VersionData.Versions[0].IgnoreEndpointCase", "APIDefinition.VersionData.Versions[0].GlobalSizeLimit", "APIDefinition.UptimeTests.CheckList[0].CheckURL", diff --git a/apidef/oas/schema/x-tyk-api-gateway.json b/apidef/oas/schema/x-tyk-api-gateway.json index c81781db9ff2..58ef4778aac0 100644 --- a/apidef/oas/schema/x-tyk-api-gateway.json +++ b/apidef/oas/schema/x-tyk-api-gateway.json @@ -497,6 +497,9 @@ }, "transformRequestHeaders": { "$ref": "#/definitions/X-Tyk-TransformHeaders" + }, + "transformResponseHeaders": { + "$ref": "#/definitions/X-Tyk-TransformHeaders" } } }, diff --git a/apidef/oas/schema/x-tyk-gateway.md b/apidef/oas/schema/x-tyk-gateway.md index f7688f6727e5..ed9ff133cf3b 100644 --- a/apidef/oas/schema/x-tyk-gateway.md +++ b/apidef/oas/schema/x-tyk-gateway.md @@ -670,6 +670,11 @@ TransformRequestHeaders contains the configurations related to API level request Tyk classic API definition: `global_headers`/`global_headers_remove`. +**Field: `transformResponseHeaders` ([TransformHeaders](#transformheaders))** +TransformResponseHeaders contains the configurations related to API level response header transformation. + +Tyk classic API definition: `global_response_headers`/`global_response_headers_remove`. + ### **PluginConfig**