首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >NSwag多文档端点

NSwag多文档端点
EN

Stack Overflow用户
提问于 2017-07-21 13:26:51
回答 3查看 5.4K关注 0票数 3

有可能有多个文档端点,比如在swashbuckle中吗?

代码语言:javascript
复制
options.SwaggerEndpoint("/swagger/v1/swagger.json", "API v1");
options.SwaggerEndpoint("/swagger/v2/swagger.json", "API v2");

如果是,如何装饰api调用,使一些属于一个版本,一些属于另一个版本?

根据瑞科·苏特的建议,我所做的就是这样的:

ApiVersionAttribute.cs

代码语言:javascript
复制
public class ApiVersionAttribute:Attribute
    {
        private List<string> _versions = new List<string>();

        public List<string> Versions { get { return _versions; } }

        public ApiVersionAttribute(string version) {
            Versions.Add(version);
        }
    }

MyApiVersionProcessor.cs

代码语言:javascript
复制
        public string Version { get; set; }

        public MyApiVersionProcessor(string version)
        {
            this.Version = version;
        }

        public new Task<bool> ProcessAsync(OperationProcessorContext context)
        {
            bool returnValue = true;

            var versionAttributes = context.MethodInfo.GetCustomAttributes()
                .Concat(context.MethodInfo.DeclaringType.GetTypeInfo().GetCustomAttributes())
                .Where(a => a.GetType()
                                .IsAssignableTo("MapToApiVersionAttribute", TypeNameStyle.Name) 
                            || a.GetType()
                                .IsAssignableTo("ApiVersionAttribute", TypeNameStyle.Name)
                       )
                .Select(a => (dynamic)a)
                .ToArray();

            var versionAttribute = versionAttributes.FirstOrDefault();

            if (null == versionAttribute)
            {
                returnValue = false;
            }
            else
            {
                if (ObjectExtensions.HasProperty(versionAttribute, "Versions")
                    && Version.Equals(versionAttribute.Versions[0].ToString()))
                {
                    ReplaceApiVersionInPath(context.OperationDescription, versionAttribute.Versions);
                }
                else {
                    returnValue = false;
                }
            }

            return Task.FromResult(returnValue);
        }

        private void ReplaceApiVersionInPath(SwaggerOperationDescription operationDescription,
            dynamic versions)
        {
            operationDescription.Path = operationDescription.Path.Replace("{version:apiVersion}",
                versions[0].ToString());
        }
    }

在我的Global.asax里

代码语言:javascript
复制
                // NSwag
                // https://github.com/RSuter/NSwag/wiki/OwinGlobalAsax#integration                
                app.UseSwaggerUi(typeof(WebApiApplication).Assembly, new SwaggerUiSettings
                {                       
                    //TypeNameGenerator = new MyTypeNameGenerator(),
                    MiddlewareBasePath = "/swagger",
                    SwaggerRoute = "/swagger/v1/swagger.json",
                    Version = "1.0.0.0",
                    // https://github.com/RSuter/NSwag/wiki/Middlewares
                    OperationProcessors =
                    {
                        new MyApiVersionProcessor("v1")
                    },
                    PostProcess = document =>
                    {                        
                        document.BasePath = "/";
                        document.Produces
                            = new List<string> { "application/json"
                                                , "text/json"
                                                , "text/html"
                                                , "plain/text"
                                                , "application/xml"};
                        document.Consumes
                            = document.Produces;
                        document.Info.Title = "Document V1";                     
                    }

                });

                app.UseSwaggerUi(typeof(WebApiApplication).Assembly, new SwaggerUiSettings
                {
                    //TypeNameGenerator = new MyTypeNameGenerator(),
                    MiddlewareBasePath = "/swagger",
                    SwaggerRoute = "/swagger/v2/swagger.json",
                    Version = "2.0.0.0",
                    OperationProcessors =
                    {
                        new MyApiVersionProcessor("v2")
                    },
                    PostProcess = document =>
                    {
                        document.BasePath = "/";
                        document.Produces
                            = new List<string> { "application/json"
                                                , "text/json"
                                                , "text/html"};
                        document.Consumes
                            = document.Produces;
                        document.Info.Title = "Document V2";
                    }

                });

并用我的控制器的方法

代码语言:javascript
复制
[ApiVersion("v2")]

[ApiVersion("v1")]

等。

EN

回答 3

Stack Overflow用户

回答已采纳

发布于 2017-07-25 10:58:52

您可以定义两次app.UseSwagger并实现一个自定义操作处理器,它只根据您的需要过滤所需的api操作(即,在第一个调用中,您应该过滤所有版本的x,在第二个版本中,应该过滤y的所有版本)。

当前默认添加的ApiVersionProcessor仅用第一个声明版本替换路由路径中的版本占位符。我认为我们应该扩展这个处理器,这样您就可以排除版本,并且插入正确的版本。

顺便说一句:我是NSwag的作者。

票数 3
EN

Stack Overflow用户

发布于 2019-10-11 18:09:52

现在有一个开箱即用的解决方案。我为ASP.NET WebAPI Owin提出了它,我想它在ASP.NET核心中应该非常类似。

First:您需要安装ASP.NET API版本控制(GitHub努基特)

第二个:您需要用所需的路线和版本来修饰您的操作方法。例如:

代码语言:javascript
复制
[Route("api/v{version:apiVersion}/get1")]
[ApiVersion("1")]

public IEnumerable<string> Get1()
{           
   return new string[] { "value1", "value2" };
}

[Route("api/v{version:apiVersion}/get2")]
[ApiVersion("2")]

public IEnumerable<string> Get2()
{           
   return new string[] { "value1", "value2" };
}

第三版:您必须将所需的配置添加到Startup.cs文件中,1)为每个API版本生成一个单独的OpenAPI规范文件(要求NSwag通过Swagger显示指定文件)

代码语言:javascript
复制
public class Startup
{
    [Obsolete]
    public void Configuration(IAppBuilder app)
    {
        var config = new HttpConfiguration();

        // register versioning
        config.MapHttpAttributeRoutes(new DefaultInlineConstraintResolver
        {
            ConstraintMap = { ["apiVersion"] = typeof(ApiVersionRouteConstraint) }
        });

        config.AddApiVersioning(options =>
        {
            // reporting api versions will return the headers "api-supported-versions" and "api-deprecated-versions"
            options.ReportApiVersions = true;

            // automatically applies an api version based on the name of the defining controller's namespace
            options.Conventions.Add(new VersionByNamespaceConvention());
        });

        // generate OpenAPI Sepecification for each version and assign a route to it

        var assembly = typeof(Startup).Assembly;

        app.UseSwagger(assembly ,s =>
        {
            s.GeneratorSettings.OperationProcessors.TryGet<ApiVersionProcessor>().IncludedVersions = new[] { "1" };
            s.GeneratorSettings.SchemaType = SchemaType.OpenApi3;
            s.DocumentPath = "/swagger/v1.0.json";
        });

        app.UseSwagger(assembly , s =>
        {
            s.GeneratorSettings.OperationProcessors.TryGet<ApiVersionProcessor>().IncludedVersions = new[] { "2" };
            s.GeneratorSettings.SchemaType = SchemaType.OpenApi3;

            s.DocumentPath = "/swagger/v2.0.json";
        });

        // integrate Swagger-UI with the generated OpenAPI files generated before.
        _ = app.UseSwaggerUi3(assembly , s =>
          {
              s.SwaggerRoutes.Add(new SwaggerUi3Route("Version 1", "/swagger/v1.0.json"));
              s.SwaggerRoutes.Add(new SwaggerUi3Route("Version 2", "/swagger/v2.0.json"));

              s.GeneratorSettings.Title = "My API";
              s.GeneratorSettings.Description = "API functionalities.";
          });

        app.UseWebApi(config);

        config.EnsureInitialized();
    }
}

转到Swagger页面。你会看到:

  1. 右上角有一个放置框,允许您选择版本。
  2. 对于每个API版本,只列出了相关的操作方法。
票数 3
EN

Stack Overflow用户

发布于 2021-02-17 15:30:54

我们遇到了这个问题,但我们打算采取相反的办法。

  1. 卷起傲慢的文件
  2. 翻找它,然后根据标签分割它
  3. 为每个标记创建本地swagger文档
  4. 针对每个新创建的swagger文档运行nswag

这样,我们就不必仅仅因为客户机需要其他东西就改变服务器。

(如果我们成功将更新:D)

编辑:因此,我成功地将模式分解为多个模式,每个控制器一个模式,并通过nswag生成新文件。不是最漂亮的代码,但它有效..。如果有人感兴趣,可以在github上发布

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/45238908

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档