diff --git a/src/NSwag.CodeGeneration.CSharp.Tests/CSharpClientSettingsTests.cs b/src/NSwag.CodeGeneration.CSharp.Tests/CSharpClientSettingsTests.cs index 05350c01f..b859c1bca 100644 --- a/src/NSwag.CodeGeneration.CSharp.Tests/CSharpClientSettingsTests.cs +++ b/src/NSwag.CodeGeneration.CSharp.Tests/CSharpClientSettingsTests.cs @@ -175,6 +175,29 @@ public async Task When_client_base_interface_is_not_specified_then_client_interf Assert.Contains("public partial interface IFooClient\n", code); } + [Fact] + public async Task When_client_base_interface_is_not_specified_then_client_interface_should_have_no_base_interface_and_has_correct_access_modifier() + { + // Arrange + var swaggerGenerator = new WebApiOpenApiDocumentGenerator(new WebApiOpenApiDocumentGeneratorSettings + { + SchemaSettings = new NewtonsoftJsonSchemaGeneratorSettings() + }); + + var document = await swaggerGenerator.GenerateForControllerAsync(); + var generator = new CSharpClientGenerator(document, new CSharpClientGeneratorSettings + { + GenerateClientInterfaces = true, + ClientInterfaceAccessModifier = "internal" + }); + + // Act + var code = generator.GenerateFile(); + + // Assert + Assert.Contains("internal partial interface IFooClient\n", code); + } + [Fact] public async Task When_client_base_interface_is_specified_then_client_interface_extends_it() { @@ -198,6 +221,30 @@ public async Task When_client_base_interface_is_specified_then_client_interface_ Assert.Contains("public partial interface IFooClient : IClientBase", code); } + [Fact] + public async Task When_client_base_interface_is_specified_with_access_modifier_then_client_interface_extends_it_and_has_correct_access_modifier() + { + // Arrange + var swaggerGenerator = new WebApiOpenApiDocumentGenerator(new WebApiOpenApiDocumentGeneratorSettings + { + SchemaSettings = new NewtonsoftJsonSchemaGeneratorSettings() + }); + + var document = await swaggerGenerator.GenerateForControllerAsync(); + var generator = new CSharpClientGenerator(document, new CSharpClientGeneratorSettings + { + GenerateClientInterfaces = true, + ClientBaseInterface = "IClientBase", + ClientInterfaceAccessModifier = "internal" + }); + + // Act + var code = generator.GenerateFile(); + + // Assert + Assert.Contains("internal partial interface IFooClient : IClientBase", code); + } + [Fact] public async Task When_client_class_generation_is_enabled_and_suppressed_then_client_class_is_not_generated() { diff --git a/src/NSwag.CodeGeneration.CSharp/CSharpClientGeneratorSettings.cs b/src/NSwag.CodeGeneration.CSharp/CSharpClientGeneratorSettings.cs index efe684aa9..cbe18c2c2 100644 --- a/src/NSwag.CodeGeneration.CSharp/CSharpClientGeneratorSettings.cs +++ b/src/NSwag.CodeGeneration.CSharp/CSharpClientGeneratorSettings.cs @@ -19,6 +19,7 @@ public CSharpClientGeneratorSettings() GenerateExceptionClasses = true; ExceptionClass = "ApiException"; ClientClassAccessModifier = "public"; + ClientInterfaceAccessModifier = "public"; UseBaseUrl = true; HttpClientType = "System.Net.Http.HttpClient"; WrapDtoExceptions = true; @@ -70,6 +71,9 @@ public CSharpClientGeneratorSettings() /// Gets or sets the client class access modifier (default: public). public string ClientClassAccessModifier { get; set; } + /// Gets or sets the client interface access modifier (default: public). + public string ClientInterfaceAccessModifier { get; set; } + /// Gets or sets a value indicating whether to use and expose the base URL (default: true). public bool UseBaseUrl { get; set; } diff --git a/src/NSwag.CodeGeneration.CSharp/Models/CSharpClientTemplateModel.cs b/src/NSwag.CodeGeneration.CSharp/Models/CSharpClientTemplateModel.cs index e73787d16..37eb12e2e 100644 --- a/src/NSwag.CodeGeneration.CSharp/Models/CSharpClientTemplateModel.cs +++ b/src/NSwag.CodeGeneration.CSharp/Models/CSharpClientTemplateModel.cs @@ -122,6 +122,9 @@ public CSharpClientTemplateModel( /// Gets or sets the client class access modifier. public string ClientClassAccessModifier => _settings.ClientClassAccessModifier; + /// Gets or sets the client interface access modifier. + public string ClientInterfaceAccessModifier => _settings.ClientInterfaceAccessModifier; + /// Gets the operations. public IEnumerable Operations { get; } diff --git a/src/NSwag.CodeGeneration.CSharp/Templates/Client.Interface.liquid b/src/NSwag.CodeGeneration.CSharp/Templates/Client.Interface.liquid index 8fbb51e45..c1d63ef4d 100644 --- a/src/NSwag.CodeGeneration.CSharp/Templates/Client.Interface.liquid +++ b/src/NSwag.CodeGeneration.CSharp/Templates/Client.Interface.liquid @@ -1,6 +1,6 @@ {% template Client.Interface.Annotations %} [System.CodeDom.Compiler.GeneratedCode("NSwag", "{{ ToolchainVersion }}")] -public partial interface I{{ Class }}{% if HasClientBaseInterface %} : {{ ClientBaseInterface }}{% endif %} +{{ ClientInterfaceAccessModifier }} partial interface I{{ Class }}{% if HasClientBaseInterface %} : {{ ClientBaseInterface }}{% endif %} { {% template Client.Interface.Body %} {% for operation in InterfaceOperations -%} diff --git a/src/NSwag.Commands/Commands/CodeGeneration/OpenApiToCSharpClientCommand.cs b/src/NSwag.Commands/Commands/CodeGeneration/OpenApiToCSharpClientCommand.cs index fcb02cd5b..ee6781ef4 100644 --- a/src/NSwag.Commands/Commands/CodeGeneration/OpenApiToCSharpClientCommand.cs +++ b/src/NSwag.Commands/Commands/CodeGeneration/OpenApiToCSharpClientCommand.cs @@ -185,11 +185,16 @@ public string ClientClassAccessModifier set { Settings.ClientClassAccessModifier = value; } } + [Argument(Name = "TypeAccessModifier", IsRequired = false, Description = "The DTO class/enum access modifier (default: public).")] public string TypeAccessModifier { get { return Settings.CSharpGeneratorSettings.TypeAccessModifier; } - set { Settings.CSharpGeneratorSettings.TypeAccessModifier = value; } + set + { + Settings.CSharpGeneratorSettings.TypeAccessModifier = value; + Settings.ClientInterfaceAccessModifier = value; + } } [Argument(Name = "PropertySetterAccessModifier", IsRequired = false, Description = "The access modifier of property setters (default: '').")]