无法在 swagger 中为 Azure Function 传递正确的参数

问题描述 投票:0回答:1

我有一个可以验证地址的 Azure 函数。我添加了 Swagger,但似乎无法使其工作。当我传递正确的 JSON 参数时,它总是会导致错误的请求。我是否缺少一些东西来让招摇发挥作用?谢谢

[FunctionName("ValidateAddress")]
public async Task<IActionResult> Run(
     [HttpTrigger(AuthorizationLevel.Function, "post", Route = null)] HttpRequest req,
     ILogger log)
{
     // Read the request body
     string requestBody = await new StreamReader(req.Body).ReadToEndAsync();
     var data = JsonConvert.DeserializeObject<RequestData>(requestBody);

     // Validate input
     if (data == null)
     {
         return new BadRequestObjectResult("Invalid request body");
     }

     var result = await _addressValidationBusinessLogic.GetAddressResult(data);

     // Prepare the response
     return new OkObjectResult(result);
}

public class RequestData
{
    public Address Address { get; set; }
    public bool TaxPurpose { get; set; }
}

 public class Address
 {
     private static readonly string Separator = Environment.NewLine;

     public string StreetLine1 { get; set; }
     public string StreetLine2 { get; set; }
     public string City { get; set; }
     public string State { get; set; }
     public string PostalCode { get; set; }
     public string CountyName { get; set; }
     public string Country { get; set; }
 }

大摇大摆:

enter image description here

我将此 JSON 作为参数传递。但它始终是一个错误的请求,因为字符串请求正文始终为空。我也尝试过传递 string 和 int ,它是一样的。

{
  "Address": {
    "StreetLine1": "123 Main St",
    "StreetLine2": "",
    "City": "City",
    "State": "State",
    "PostalCode": "12345",
    "CountyName": "",
    "Country": "Country"
  },
  "TaxPurpose": true
}

添加启动项

[assembly: FunctionsStartup(typeof(AddressValidation.Startup))]
namespace AddressValidation
{
    public class Startup : FunctionsStartup
    {
        public override void Configure(IFunctionsHostBuilder builder)
        {
            builder.Services.AddHttpClient();

            var configuration = BuildConfiguration(builder.GetContext().ApplicationRootPath);
            builder.Services.AddAppConfiguration(configuration);

            builder.Services.AddScoped<AddressValidationBusinessLogic>();
            builder.Services.AddScoped<GoogleAddressValidator>();
            builder.Services.AddScoped<VertexAddressValidator>();

            builder.AddSwashBuckle(Assembly.GetExecutingAssembly(), opts => {
                opts.AddCodeParameter = true;
                opts.Documents = new[] {
                    new SwaggerDocument {
                        Name = "v1",
                            Title = "Swagger document",
                            Description = "Integrate Swagger UI With Azure Functions",
                            Version = "v1"
                    }
                };
                opts.ConfigureSwaggerGen = x => {
                    x.OperationFilter<SetContentTypeOperationFilter>();
                    x.CustomOperationIds(apiDesc => {
                        return apiDesc.TryGetMethodInfo(out MethodInfo mInfo) ? mInfo.Name : default(System.Guid).ToString();
                    });
                };
            });
        }

        private IConfiguration BuildConfiguration(string applicationRootPath)
        {
            var config =
                new ConfigurationBuilder()
                    .SetBasePath(applicationRootPath)
                    .AddJsonFile("appsettings.local.json", optional: true, reloadOnChange: true)
                    .AddEnvironmentVariables()
                    .Build();

            return config;
        }

        public class SetContentTypeOperationFilter : IOperationFilter
        {
            public void Apply(OpenApiOperation operation, OperationFilterContext context)
            {
                // Check if the operation consumes JSON
                if (operation.RequestBody?.Content?.ContainsKey("application/json") == true)
                {
                    // Set the Content-Type header to 'application/json'
                    operation.RequestBody.Content["application/json"].Schema.Properties["Content-Type"] = new OpenApiSchema
                    {
                        Type = "string",
                        Default = new OpenApiString("application/json")
                    };
                }
            }
        }
    }
}
c# azure-functions swagger swagger-ui
1个回答
0
投票

无法在 swagger 中为 Azure Function 传递正确的参数

下面是对我有用的代码

函数1.cs:

using System.Net;
using System.Threading.Tasks;
using System.Web.Helpers;
using Microsoft.AspNetCore.Http;
using Microsoft.AspNetCore.Mvc;
using Microsoft.Azure.WebJobs;
using Microsoft.Azure.WebJobs.Extensions.Http;
using Microsoft.Azure.WebJobs.Extensions.OpenApi.Core.Attributes;
using Microsoft.Azure.WebJobs.Extensions.OpenApi.Core.Enums;
using Microsoft.Extensions.Logging;
using Microsoft.OpenApi.Models;
using Newtonsoft.Json;

namespace FunctionApp153
{
    public class Function1
    {
        private readonly ILogger<Function1> _logger;

        public class RithwikAdress
        {
            public string StreetLine1 { get; set; }
            public string StreetLine2 { get; set; }
            public string City { get; set; }
            public string State { get; set; }
            public string PostalCode { get; set; }
            public string CountyName { get; set; }
            public string Country { get; set; }
        }

        public class RithReqBody
        {
            public RithwikAdress Address { get; set; }
            public bool? TaxPurpose { get; set; } 
        }

        public Function1(ILogger<Function1> log)
        {
            _logger = log;
        }

        [FunctionName("Function1")]
        [OpenApiOperation(operationId: "Run", tags: new[] { "name" })]
        [OpenApiSecurity("function_key", SecuritySchemeType.ApiKey, Name = "code", In = OpenApiSecurityLocationType.Query)]
        [OpenApiParameter(name: "JSON", In = ParameterLocation.Query, Required = true, Type = typeof(Json), Description = "Hello Rithwk Bojja, The **JSON** parameter")]
        [OpenApiResponseWithBody(statusCode: HttpStatusCode.OK, contentType: "text/plain", bodyType: typeof(string), Description = "The OK response")]
        public async Task<IActionResult> Run(
            [HttpTrigger(AuthorizationLevel.Function, "get", "post", Route = null)] HttpRequest req)
        {
            _logger.LogInformation("C# HTTP trigger function processed a request.");

            string nameJson = req.Query["JSON"];
            string JSON = string.Empty;
            RithReqBody data = null;
           
            data = JsonConvert.DeserializeObject<RithReqBody>(nameJson);
            _logger.LogInformation($"Hello Rithwik, The Deserilaized data: {JsonConvert.SerializeObject(data)}");
            string rithaddress = data?.Address?.StreetLine1 ?? "Unknown";
            string rithcity = data?.Address?.City ?? "Unknown";
            string rithstate = data?.Address?.State ?? "Unknown";
            string rithpostalCode = data?.Address?.PostalCode ?? "Unknown";
            string rithcountry = data?.Address?.Country ?? "Unknown";
            bool? taxPurpose = data?.TaxPurpose;
            string rithtax = taxPurpose.HasValue ? taxPurpose.Value.ToString() : "Unknown";
            string rithout = $"Hello Rithwik Bojja. This HTTP triggered function executed successfully.\nAddress: {rithaddress}, {rithcity}, {rithstate}, {rithpostalCode}, {rithcountry}. Tax Purpose: {rithtax}";
            return new OkObjectResult(rithout);
        }
    }
}

未使用此功能的任何启动。

csproj:

<Project Sdk="Microsoft.NET.Sdk">
  <PropertyGroup>
    <TargetFramework>net6.0</TargetFramework>
    <AzureFunctionsVersion>v4</AzureFunctionsVersion>
  </PropertyGroup>
  <ItemGroup>
    <PackageReference Include="Microsoft.AspNet.WebPages" Version="3.3.0" />
    <PackageReference Include="Microsoft.Azure.WebJobs.Extensions.OpenApi" Version="1.0.0" />
    <PackageReference Include="Microsoft.NET.Sdk.Functions" Version="4.2.0" />
  </ItemGroup>
  <ItemGroup>
    <None Update="host.json">
      <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
    </None>
    <None Update="local.settings.json">
      <CopyToOutputDirectory>PreserveNewest</CopyToOutputDirectory>
      <CopyToPublishDirectory>Never</CopyToPublishDirectory>
    </None>
  </ItemGroup>
</Project>

输出:

输入为:

{
  "Address": {
    "StreetLine1": "Bojja Road",
    "StreetLine2": " Rithwik Lane",
    "City": "Hyderabad",
    "State": "Telangana",
    "PostalCode": "12345",
    "CountyName": "Miya",
    "Country": "India"
  },
  "TaxPurpose": true
}

enter image description here

© www.soinside.com 2019 - 2024. All rights reserved.