diff --git a/src/Authoring/Configs/CorsConfig.cs b/src/Authoring/Configs/CorsConfig.cs index b98c9b0c..f459436c 100644 --- a/src/Authoring/Configs/CorsConfig.cs +++ b/src/Authoring/Configs/CorsConfig.cs @@ -24,7 +24,7 @@ public record CorsConfig /// Policy expressions are allowed. /// [ExpressionAllowed] - public string? TerminateUnmatchedRequest { get; init; } + public bool? TerminateUnmatchedRequest { get; init; } /// /// List of origins allowed to make cross-origin calls to your API.
diff --git a/test/Test.Core/Compiling/CorsTests.cs b/test/Test.Core/Compiling/CorsTests.cs index 4dd9cdcc..b73d90af 100644 --- a/test/Test.Core/Compiling/CorsTests.cs +++ b/test/Test.Core/Compiling/CorsTests.cs @@ -14,10 +14,10 @@ public class PolicyDocument : IDocument { public void Inbound(IInboundContext context) { context.Cors(new CorsConfig() - { - AllowedOrigins = ["contoso.com"], - AllowedHeaders = ["accept"], - }); + { + AllowedOrigins = ["contoso.com"], + AllowedHeaders = ["accept"], + }); } } """, @@ -44,10 +44,10 @@ public class PolicyDocument : IDocument { public void Inbound(IInboundContext context) { context.Cors(new CorsConfig() - { - AllowedOrigins = ["contoso.com", "fabrikam.com"], - AllowedHeaders = ["accept"], - }); + { + AllowedOrigins = ["contoso.com", "fabrikam.com"], + AllowedHeaders = ["accept"], + }); } } """, @@ -67,6 +67,37 @@ public void Inbound(IInboundContext context) { """, DisplayName = "Should compile cors policy with multiple origins" + )] + [DataRow( + """ + [Document] + public class PolicyDocument : IDocument + { + public void Inbound(IInboundContext context) { + context.Cors(new CorsConfig() + { + AllowedOrigins = [GetCorsOrigin(context.ExpressionContext)], + AllowedHeaders = ["accept"], + }); + } + string GetCorsOrigin(IExpressionContext context) => (string)context.Variables["CorsOrigin"]; + } + """, + """ + + + + + @((string)context.Variables["CorsOrigin"]) + + +
accept
+
+
+
+
+ """, + DisplayName = "Should allow origin from an expression" )] [DataRow( """ @@ -75,10 +106,10 @@ public class PolicyDocument : IDocument { public void Inbound(IInboundContext context) { context.Cors(new CorsConfig() - { - AllowedOrigins = ["contoso.com"], - AllowedHeaders = ["accept", "content-type"], - }); + { + AllowedOrigins = ["contoso.com"], + AllowedHeaders = ["accept", "content-type"], + }); } } """, @@ -106,11 +137,11 @@ public class PolicyDocument : IDocument { public void Inbound(IInboundContext context) { context.Cors(new CorsConfig() - { - AllowCredentials = true, - AllowedOrigins = ["contoso.com"], - AllowedHeaders = ["accept"], - }); + { + AllowCredentials = true, + AllowedOrigins = ["contoso.com"], + AllowedHeaders = ["accept"], + }); } } """, @@ -137,11 +168,11 @@ public class PolicyDocument : IDocument { public void Inbound(IInboundContext context) { context.Cors(new CorsConfig() - { - AllowedOrigins = ["contoso.com"], - AllowedHeaders = ["accept"], - AllowedMethods = ["PUT", "DELETE"], - }); + { + AllowedOrigins = ["contoso.com"], + AllowedHeaders = ["accept"], + AllowedMethods = ["PUT", "DELETE"], + }); } } """, @@ -172,12 +203,12 @@ public class PolicyDocument : IDocument { public void Inbound(IInboundContext context) { context.Cors(new CorsConfig() - { - AllowedOrigins = ["contoso.com"], - AllowedHeaders = ["accept"], - AllowedMethods = ["PUT", "DELETE"], - PreflightResultMaxAge = 100, - }); + { + AllowedOrigins = ["contoso.com"], + AllowedHeaders = ["accept"], + AllowedMethods = ["PUT", "DELETE"], + PreflightResultMaxAge = 100, + }); } } """, @@ -200,6 +231,44 @@ public void Inbound(IInboundContext context) { """, DisplayName = "Should compile cors policy with allow methods and preflight result max age" + )] + [DataRow( + """ + [Document] + public class PolicyDocument : IDocument + { + public void Inbound(IInboundContext context) { + context.Cors(new CorsConfig() + { + AllowedOrigins = ["contoso.com"], + AllowedHeaders = ["accept"], + AllowedMethods = ["PUT", "DELETE"], + PreflightResultMaxAge = 100, + PreflightResultMaxAge = GetPreflightResultMaxAge(context.ExpressionContext), + }); + } + int GetPreflightResultMaxAge(IExpressionContext context) => (int)context.Variables["PreflightResultMaxAge"]; + } + """, + """ + + + + + contoso.com + + +
accept
+
+ + PUT + DELETE + +
+
+
+ """, + DisplayName = "Should compile cors policy with allow methods and preflight result max age from expression" )] [DataRow( """ @@ -208,11 +277,11 @@ public class PolicyDocument : IDocument { public void Inbound(IInboundContext context) { context.Cors(new CorsConfig() - { - AllowedOrigins = ["contoso.com"], - AllowedHeaders = ["accept"], - ExposeHeaders = ["accept", "content-type"], - }); + { + AllowedOrigins = ["contoso.com"], + AllowedHeaders = ["accept"], + ExposeHeaders = ["accept", "content-type"], + }); } } """, @@ -236,6 +305,100 @@ public void Inbound(IInboundContext context) { """, DisplayName = "Should compile cors policy with expose headers" )] + [DataRow( + """ + [Document] + public class PolicyDocument : IDocument + { + public void Inbound(IInboundContext context) { + context.Cors(new CorsConfig() + { + AllowedOrigins = ["contoso.com"], + AllowedHeaders = ["accept"], + TerminateUnmatchedRequest = true, + }); + } + } + """, + """ + + + + + contoso.com + + +
accept
+
+
+
+
+ """, + DisplayName = "Should compile cors policy with terminate unmatched request explicitly enabled" + )] + [DataRow( + """ + [Document] + public class PolicyDocument : IDocument + { + public void Inbound(IInboundContext context) { + context.Cors(new CorsConfig() + { + AllowedOrigins = ["contoso.com"], + AllowedHeaders = ["accept"], + TerminateUnmatchedRequest = false, + }); + } + } + """, + """ + + + + + contoso.com + + +
accept
+
+
+
+
+ """, + DisplayName = "Should compile cors policy with terminate unmatched request disabled" + )] + [DataRow( + """ + [Document] + public class PolicyDocument : IDocument + { + public void Inbound(IInboundContext context) { + context.Cors(new CorsConfig() + { + AllowedOrigins = ["contoso.com"], + AllowedHeaders = ["accept"], + TerminateUnmatchedRequest = GetTerminateUnmatchedRequest(context.ExpressionContext), + }); + } + bool GetTerminateUnmatchedRequest(IExpressionContext context) => (bool)context.Variables["TerminateUnmatchedRequest"]; + } + """, + """ + + + + + contoso.com + + +
accept
+
+
+
+
+ """, + DisplayName = "Should compile cors policy with terminate unmatched request from expression" + )] public void ShouldCompileCorsPolicy(string code, string expectedXml) { code.CompileDocument().Should().BeSuccessful().And.DocumentEquivalentTo(expectedXml);