0

I am working on API versioning on .Net Core 3.1. The issue is that we are consuming an external nuget package that will apply different versions on different API versions. For example, for API Version 1.0, I need to use V2.0 of this nuget package; for API Version 2.0, I need to use V3.0 of this nuget package.

So if I use the strategy this way: https://dev.to/99darshan/restful-web-api-versioning-with-asp-net-core-1e8g by spliting the controller classes in the same project, then it would force all of my API versions with the same nuget package versions.

I was wondering what's the better way to do API versioning in my scenario?

superninja
  • 3,114
  • 7
  • 30
  • 63
  • 1
    Which kind of Nuget Package you want to install in your application? Based on my experience, for the different version of Nuget Package, might be they are not compatible or the latest version of Nuget Package should try to maximize backward compatibility. So, generally we could only install one version of the package in our application, you could check it. – Zhi Lv Feb 02 '21 at 05:34
  • It's an internal nuget package in my company, and it is currently not backward compatible :( – superninja Feb 02 '21 at 22:40
  • 1
    use reflection. https://stackoverflow.com/questions/5916855/using-multiple-versions-of-the-same-dll – Power Mouse Feb 23 '21 at 19:16
  • 1
    multiple versions same dll nuget: https://stackoverflow.com/questions/34802007/using-two-different-versions-of-same-the-nuget-package – Power Mouse Feb 23 '21 at 19:20

1 Answers1

0

As long the features you are using are functionally compatible (typically by source code), then the NuGet package versions do not need to match. You did not specifically say, but I get the impression you are defining API versions by applying attributes and that is the only surface area used by the code and libraries that define the corresponding controllers.

You're describing a typical setup for plug-in or composition based API applications. Assuming that is correct, then the NuGet package version is only interesting to the host application (e.g. the hosting server code). The host application that runs the server must use a version of the NuGet package that is greater than or equal to the highest version used by any of the other referenced assemblies. The rest is handled by .NET, not NuGet. Modern .NET projects enable automatic binding redirects; typically without any developer configuration. This means that if your controller libraries are an array of say version 1.0, 2.0, and 3.0 and the host references 3.0, then all libraries ultimately use 3.0 at runtime. The only caveat to this is that all libraries must target the same runtime. For example, you cannot make a mix of full .NET Framework and .NET 5.0 (formerly .NET Core) work together. As long as the runtimes are aligned, you should not have any problem getting everything aligned; regardless, of NuGet package or assembly version.

There are also, at least, two other solutions to this problem.

  1. Use Conventions - API Versioning provides a fluent interface for defining API versions by convention. It was designed to solve the exact problems of applying API version metadata to controllers defined in another library. This configuration would likely be defined in the host application. You can also define your conventions so you don't have to define every version individually. The VersionByNamespaceConvention uses this approach to derive a single API version by the containing .NET namespace.
  2. Use Custom Metadata - Contrary to popular belief, API Versioning does not care about attributes. It provides some attributes as a simple, out-of-the-box way to apply metadata, but it's not a hard requirement. It only cares about IApiVersionProvider. This means that you can easily roll your own attributes and then plug it into API Versioning by implementing IApiVersionProvider or IControllerConvention. This would allow you to create metadata library, with .NET Standard if necessary, that will likely never change and you can subsequently add to the versioning configuration.

#2 is a more advanced scenario. I'm not aware of any existing examples that would demonstrate all of that end-to-end, but if you choose that path and have questions, I can push you in the right direction.

Chris Martinez
  • 3,185
  • 12
  • 28