Seamlessly adds a swagger to WebApi projects! Combines ApiExplorer and swagger/swagger-ui to provide a rich discovery and documentation experience to your API consumers.
In addition to it's Swagger generator, Swashbuckle also contains an embedded version of swagger-ui which it will automatically serve up once Swashbuckle is installed. This means little or no maintenance for discovery and documentation of your service, allowing you to focus on building an awesome API!
And that's not all ...
Once you have a Web API that can describe itself in Swagger, you've opened the treasure chest of Swagger-based tools including a client generator that can be targetted to a wide range of popular platforms. See swagger-codegen for more details.
Swashbuckle Core Features:
- Auto-generated Swagger 1.2
- Seamless integration of swagger-ui
- Reflection-based type/model descriptions ... including support for polymorphic types
- Extensibility hooks for customizing the generated spec
- Extensibility hooks for customizing the swagger-ui
- Out-of-the-box support for leveraging Xml comments
*Swashbuckle 4.0
As of version 4.0, Swashbuckle has no dependency on ASP.Net MVC. As a result, it's now available to both IIS hosted and self-hosted Web API's. However, this introduces several (relatively) trivial breaking changes. Checkout the transition guide if you're upgrading from a prior version.
If youre service is hosted in IIS, you can start exposing Swagger docs and a corresponding Swagger UI by simply installing the following Nuget package:
Install-Package Swashbuckle
This will add a reference to Swashbuckle.Core, which contains the generator and embedded swagger-ui. It will also install a bootstrapper (App_Start/SwaggerConfig.cs) that initiates Swashbuckle on app start-up using WeActivatorEx. Once installed, you should be able to browse the following raw docs and UI endpoints:
swagger/api-docs
swagger
If youre service is self-hosted, you need to install Swashbuckle.Core directly ...
Install-Package Swashbuckle.Core
And then manually apply the one-liner to initiate Swashbuckle before starting the server:
var config = new HttpSelfHostConfiguration("http://localhost:8080");
Swashbuckle.Bootstrapper.Init(config);
Troubleshooting??? I thought this was all supposed to be "seamless"? OK you've called me out! Things shouldn't go wrong, but if they do, take a look at the troubleshooting steps for inspiration.
Swashbuckle automatically generates a Swagger spec and UI based off the WebApi ApiExplorer. The out-of-the-box generator caters for the majority of WebApi implementations but also includes some extensibility points for application-specific needs ..
You can customize the auto-generated spec by applying the following config options at App startup ...
SwaggerSpecConfig.Customize(c =>
{
c.ResolveTargetVersionUsing((req) => "2.0");
c.IgnoreObsoleteActions();
c.ResolveVersionSupportUsing((apiDesc, version) => GetVersionByAttribute(apiDesc) == version)
c.GroupDeclarationsBy(RootResourceName)
c.MapType<MySerializeableType>(() => new DataType { Type = "string" });
c.PolymorphicType<Product>(pc => pc
.DiscriminateBy(p => p.Type)
.SubType<Book>()
.SubType<Album>()
.SubType<Service>(sc => sc
.SubType<Shipping>()
.SubType<Packaging>()));
c.OperationFilter<AddStandardResponseCodes>();
c.OperationFilter<AddAuthorizationResponseCodes>();
c.IncludeXmlComments(GetXmlCommentsPath());
});
You can use this option to indicate the current version of your API.
It may also be used in conjuction with the ResolveVersionSupportUsing to implement a UI that can switch between service versions. For example, something in the Swagger request (maybe a query param) could indicate the target version. Then you can provide a lambda for ResolveVersionSupportUsing that takes an ApiDescription and target version and determines if the action should be included in the Swagger spec for that version.
Set this option if you'd like to exclude any WebApi actions decorated with the System.ObsoleteAttribute from your swagger spec and UI
This option accepts a lambda as a strategy for grouping actions into ApiDeclarations. The default implementation groups by controller name.
This allows you to override the default DataType generation for a given Type. It's intended for the use-case when you have a class that is serialized to a primitive JSON type.
The Swagger spec provides a way to describe polymorphic models with subTypes and discriminator properties. Swashbuckle currently requires these to be explicitly configured. Later versions may include a feature to scan assemblies but in the meantime you can use the fluent "PolymorphicType" method to guide you.
This will generate an additional complex model for each sub-type and bind them to the base model via the subTypes property:
"Product": {
"id": "Product",
"type": "object",
"properties": {
"Id": {
"type": "integer",
"format": "int32"
},
"Price": {
"type": "number",
"format": "double"
}
"Type": {
"type": "string",
}
},
"required": [],
"subTypes": [ "Book", "Album", "Service" ],
"discriminator": "Type"
}
*Note: The Swagger Spec is typically ahead of swagger-ui and so the latter doesn't currently have support for displaying polymorphic types.
This is similar to the OperationFilter option. It provides a way to customize the generated DataType/Model for complex Types in your API. Model filters implement the following interface:
public interface IModelFilter
{
void Apply(DataType model, DataTypeRegistry dataTypeRegistry, Type type);
}
This provides a way to customize Operation descriptions by applying one or more filters after initial generation. For example:
A filter that enhances the spec with standard response code descriptions ...
public class AddStandardResponseCodes : IOperationFilter
{
public void Apply(Operation operation, DataTypeRegistry dataTypeRegistry, ApiDescription apiDescription)
{
operation.ResponseMessages.Add(new ResponseMessage
{
Code = (int)HttpStatusCode.OK,
Message = "It's all good!"
});
operation.ResponseMessages.Add(new ResponseMessage
{
Code = (int)HttpStatusCode.InternalServerError,
Message = "Somethings up!"
});
}
}
Or, a filter that adds an authorization response description to actions that are decorated with the AuthorizeAttribute ...
public class AddAuthorizationResponseCodes : IOperationFilter
{
public void Apply(Operation operation, DataTypeRegistry dataTypeRegistry, ApiDescription apiDescription)
{
if (apiDescription.ActionDescriptor.GetFilters().OfType<AuthorizeAttribute>().Any())
{
operation.ResponseMessages.Add(new ResponseMessage
{
Code = (int)HttpStatusCode.Unauthorized,
Message = "Authentication required"
});
}
}
}
The filter interface is relatively simple. In most cases, you just inspect the apiDescription and then modify the corresponding operation accordingly. If you're customizing DataType descriptions for the operation and need to register new Models for the underlying ApiDeclaration, you can use the provided dataTypeRegistry.
If you annonate Controllers and API Types with Xml Comments, you can use this option to incorporate those comments into the generated spec and UI. The Xml tags are mapped to Swagger properties as follows:
- Action summary -> Operation.Summary
- Action remarks -> Operation.Notes
- Parameter summary -> Operation.Parameters[name].Description
- Type summary -> DataType.Descripton
- Property summary -> DataType.Properties[name].Description
The Swagger UI supports a number of options to customize it's appearance and behavior. See the documentation for a detailed description.
All of these options are exposed through Swashbuckle configuration ...
SwaggerUiConfig.Customize(c =>
{
c.SupportHeaderParams = true;
c.DocExpansion = DocExpansion.List;
c.SupportedSubmitMethods = new[] {HttpMethod.Get, HttpMethod.Post, HttpMethod.Put, HttpMethod.Head};
c.InjectJavaScript(typeof (SwaggerConfig).Assembly, "Swashbuckle.TestApp.SwaggerExtensions.onComplete.js");
c.InjectStylesheet(typeof(SwaggerConfig).Assembly, "Swashbuckle.TestApp.SwaggerExtensions.customStyles.css");
});
The InjectJavaScript and InjectStylesheet options allow custom JavaScript or CSS to be injected into the UI once it's loaded.
To do this, the file(s) MUST be added to your project as an "Embedded Resource". After that, you can inject them by specifying the containing Assembly and resource name as shown above.
What's the resource name?: When you add an embedded resource (Right-click in Solution Explorer -> Properties -> Build Action), it is assigned the following resource name by default:
<Project Default Namespace>.<Escaped Folder Path>.<File Name>
So, if your app's default namespace is "Swashbuckle.TestApp", and you have a custom script - "SwaggerExtensions/onComplete.js", then it will be assigned the following resource name at build time:
"Swashbuckle.TestApp.SwaggerExtensions.onComplete.js"
If you're upgrading from a version prior to 4.0, the following information will help make the upgrade as seamless as possible
Because Swashbuckle 4.0 has no dependency on ASP.Net MVC, the approach to bootstrapping is a little different. The upgrade should install a bootstrapper (App_Start/SwaggerConfig.cs) that is invoked on app start-up using WeActivatorEx. If you're unable to access the Swagger content after upgrading, check out the bootstrap troubleshooting steps.
- SwaggerSpecConfig and SwaggerUiConfig classes have moved namespace from Swashbuckle.Models to Swashbuckle.Application.
- ApiVersion has been replaced with a method - ResolveTargetVersionUsing that accepts a lambda.
- IgnoreObsoleteActions has been converted to a method.
- IOperationFilter interface has moved namespace from Swashbuckle.Models to Swashbuckle.Swagger
- It's signature has also been simplified - see the Extensibility section for more details
- Some of the Swagger types have been renamed to better reflect terminology used in the Swagger Spec
- the "Spec" suffix has been removed from several of the class names, e.g. OperationSpec is now called Operation
- The ModelSpec class has been renamed to DataType as it describes both primitive and complex data types (Models).
In previous versions this was left up to the app - typically with a custom implementation of the WebApi's IDocumentationProvider and an IOperationFilter that parses the XML into the relevant Swagger properties . Version 4.0 supports this out-of-the-box and so both of these artifacts can be removed from your app. See the Extensibilty section for details on including Xml Comments.
As of version 4.0, Swashbuckle has no dependency on ASP.Net MVC and so, routes are no longer wired up through an MVC Area. Instead, the Swashbuckle package will install a bootstrapper (App_Start/SwaggerConfig.cs) that is invoked on app start-up using WeActivatorEx. You should ensure that this file exists and is annotated with the following assembly attribute:
[assembly: PreApplicationStartMethod(.....)]
In addition, the referenced static method should contain the following line to initiate Swashbuckle:
Swashbuckle.Bootstrapper.Init(GlobalConfiguration.Configuration);
The swagger-ui is a single page application (SPA) consisting of html, JavaScript and CSS. To serve up these files (.html, .js and .css), you're web server must execute the ASP.NET Routing Module on all requests (as opposed to just extensionless URL's). If the setting for this is not present in your Web.config, you'll need to add it manually:
<system.webServer>
<modules runAllManagedModulesForAllRequests="true" />
<!-- Other web server settings -->
</system.webServer>
If you see the following error message in the Swagger UI ...
Unable to read api '.....' from path ..... (server returned undefined)
It's likely because something went wrong during the spec generation. You can dig a little deeper by browsing to the path in question. When you do this, you may see the following error message:
Failed to generate Swagger models with unique Id's. Do you have multiple API types with the same class name?
This is by design and will occur if one or more of your API types have conflicting class names - e.g. Namespace1.Customer, Namespace2.Customer etc. Actually, the class names need only be unique within a given ApiDeclaration, the scope if which is customizeable via the GroupDeclarationsBy option described below.
VS 2103 ships with a new feature - Browser Link that improves the web development workflow by setting up a channel between the IDE and pages being previewed in a local browser. It does this by dynamically injecting JavaScript into your files.
Although this JavaScript SHOULD have no affect on your production code, it appears to be breaking the swagger-ui.
I hope to find a permanent fix but in the meantime, you'll need to workaround this isuse by disabling the feature in your web.config:
<appSettings>
<add key="vs:EnableBrowserLink" value="false"/>
</appSettings>< appSettings>
Prior to version 4.0, Swashbuckle wires up it's routes as an MVC Area. In MVC projects, all Areas are usually registered at application startup. If the code to do this is not present in your Global.asax.cs, you'll need to add it manually:
protected void Application_Start()
{
// Other boot-strapping ...
AreaRegistration.RegisterAllAreas();
}