.NET Core – The uShip Blog https://ushipblogsubd.wpengine.com Mon, 24 Mar 2025 18:28:59 +0000 en-US hourly 1 https://wordpress.org/?v=6.8.2 Visual Studio+ReSharper-level Productivity in VSCode https://ushipblogsubd.wpengine.com/shipping-code/visual-studioresharper-level-productivity-in-vscode/ https://ushipblogsubd.wpengine.com/shipping-code/visual-studioresharper-level-productivity-in-vscode/#comments Tue, 06 Sep 2016 14:18:04 +0000 https://ushipblogsubd.wpengine.com/?p=6350 Update 2017-05-22: This post originally written for a project.json .NET Core project. It has been edited for a .csproj .NET Core project. Visual Studio Code (aka VSCode) is a lightweight text editor from Microsoft. Many people think just because it is a “text-editor”, they will be missing the features they are used to from an... Read More

The post Visual Studio+ReSharper-level Productivity in VSCode appeared first on The uShip Blog.

]]>
Update 2017-05-22: This post originally written for a project.json .NET Core project. It has been edited for a .csproj .NET Core project.

Visual Studio Code (aka VSCode) is a lightweight text editor from Microsoft. Many people think just because it is a “text-editor”, they will be missing the features they are used to from an IDE like Visual Studio. With the proper configuration, VSCode can be a very powerful tool.

Setup

VSCode by default doesn’t come with the tools necessary to build .NET Core projects. The following setup will be necessary to get the editor, compiler, and extension necessary to get you closer to an IDE experience.

To install an extension, open the Command Palette (cmd+shift+p), remove the >, and run ext install csharp.

Note: While this tutorial is cross-platform , all given commands are using Mac OS X key bindings. For Windows and Linux, replace cmd with ctrl.

Key Bindings

Command Palette

The most important key binding in VSCode is cmd+shift+p, which brings up the Command Palette, similar to Sublime Text. Why is it so important? Hitting those keys brings up a search box that allows you to start typing a command like “ext” for “Extensions: Install Extensions” or “build” for “Tasks: Run Build Task”.

Shell

You will frequently need to run shell commands within VSCode. ctrl+` toggles an in-editor shell.

ReSharper Bindings

Where would each of us be without alt+enter, ReSharper’s quick fix and context actions key binding? Just because you don’t have ReSharper doesn’t mean your life is over (even though some people might think that). Common ReSharper operations are supported in VSCode, and these operations can be bound to custom key bindings, which allows us to roughly mirror the ReSharper plugin in VSCode. The below are the most common ReSharper key bindings I use. You can use the Command Palette to search for “Preferences: Open Keyboard Shortcuts”.

[
	{ "key": "alt+enter",                 "command": "editor.action.quickFix",
                                     "when": "editorTextFocus" },
	{ "key": "cmd+b",               "command": "editor.action.goToDeclaration",
                                     "when": "editorTextFocus" },
	{ "key": "alt+f7",               "command": "editor.action.referenceSearch.trigger",
                                     "when": "editorTextFocus" },
	{ "key": "cmd+shift+alt+n",                 "command": "workbench.action.showAllSymbols" },
	{ "key": "cmd+n",                 "command": "workbench.action.quickOpen" },
	{ "key": "cmd+shift+n",                 "command": "workbench.action.quickOpen" },			
	{ "key": "cmd+f12",			"command": "workbench.action.gotoSymbol"},
	{ "key": "cmd+t l", 			"command": "workbench.action.tasks.test"},

	{ "key": "cmd+p",			"command": "editor.action.triggerParameterHints"}
]
Command ReSharper VSCode default
Quick Fix alt+enter cmd+.
Go to anything cmd+n cmd+p
Go to symbol cmd+shift+alt+n cmd+t
Go to declaration cmd+b f12
Go to file cmd+n cmd+p
Go to file member cmd+f12 shift+cmd+o
Parameter info cmd+p shift+cmd+space
Find usages alt+f7 shift+f12
Run all tests cmd+t l N/A

VSCode key bindings reference: https://code.visualstudio.com/docs/customization/keybindings
ReSharper key bindings reference: https://www.jetbrains.com/resharper/docs/ReSharper_DefaultKeymap_IDEAscheme.pdf

Building and Debugging .NET Core Applications

This is it. The moment you’ve been waiting for. Using VSCode as an IDE.

Creating a .NET Core Project

VSCode doesn’t have a UI to create new projects, since it is file and folder based. However, we can use the in-editor shell to create a project after creating a folder.

mkdir my_project
code my_project

Note that the above requires code to be in your path. You can do this via searching “PATH” in the Command Palette.

Once we are in VSCode, run the following in the in-editor shell to create a new .NET Core command line project

dotnet new
# Run `dotnet new -h` to see your available options.
# Some templates that are available: Console (the default), Web (ASP.NET Core MVC), Lib (class library), xunittest and nunittest (XUnit and NUnit test projects)

You might see: “Required assets to build and debug are missing from your project. Add them?” Select “Yes”.

Building and Debugging

The building and debugging key bindings are the typical bindings from Visual Studio.

To debug, set a breakpoint and hit F5. It’s really that easy!

NuGet

Now that we are able to debug a .NET Core application, let’s walk through the common task of adding a NuGet dependency.

VSCode doesn’t come with a NuGet client by default, so let’s install one via ext install vscode-nuget-package-manager.

To install a NuGet package:

  • Open the Command Palette and search for “NuGet Package Manager: Add Package” and hit enter
  • Enter a search term and hit enter (e.g. “json”)
  • Select a package from the list and hit enter (e.g. “Newtonsoft.Json”)
  • Select a version from the list and hit enter (e.g. 9.0.1)
  • Select a project to add the reference to
  • Run dotnet restore in the in-editor shell as prompted by the NuGet extension

Alternatively, you can use the dotnet NuGet commands directly:

dotnet add path/to/your_project package Example.Package -v 1.0

Be aware that not all NuGet packages are compatible with .NET Core. See this awesome list of packages that support .NET Core. Hint: your favorite packages are probably there.

Testing

“The code is not done until the tests run” – A person

Now that we have a .NET Core project with a NuGet package reference, let’s add a test.

Set up

We need to install the following NuGet packages:

  • NUnit
  • NUnit3TestAdapter, at least version 3.8.0-alpha1

The following will have to be added to .vscode/tasks.json:

{
	"taskName": "test",
	"args": [],
	"isTestCommand": true,
	"problemMatcher": "$msCompile"
}

Note: You may be able to run dotnet new -t xunittest or dotnet new -t nunittest depending on what version of dotnet you have installed. The bleeding edge can be installed from the GitHub page.

Running the Test

Now we can add the simplest failing test:

using NUnit.Framework;

[TestFixture]
public class ProgramTests
{
	[Test]
	public void Should_fail()
	{
		Assert.Fail("This is a failure!");
	}
}

Now when we hit cmd+t l, our test will fail!

Debugging the Test

If you prefer to use xUnit (see: dotnet-test-xunit) you can easily run or debug the test by simply selecting the corresponding option in the editor. Unfortunately, debugging with NUnit isn’t quite as simple yet, and currently requires a convoluted process. See this GitHub issue that addresses this.

Conclusion

VSCode out-of-the-box won’t give you everything you need to be fully productive with .NET Core, but with some setup you should be up and running in no time. Do you have any VSCode tips and tricks of your own that I didn’t mention? Please comment below and share.

Summary of Setup

[amp-cta id=’8486′]

The post Visual Studio+ReSharper-level Productivity in VSCode appeared first on The uShip Blog.

]]>
https://ushipblogsubd.wpengine.com/shipping-code/visual-studioresharper-level-productivity-in-vscode/feed/ 3
Self-hosting a .NET API: Choosing between OWIN with ASP.NET Web API and ASP.NET Core MVC 1.0 https://ushipblogsubd.wpengine.com/shipping-code/self-hosting-a-net-api-choosing-between-owin-with-asp-net-web-api-and-asp-net-core-mvc-1-0/ https://ushipblogsubd.wpengine.com/shipping-code/self-hosting-a-net-api-choosing-between-owin-with-asp-net-web-api-and-asp-net-core-mvc-1-0/#comments Fri, 29 Apr 2016 08:08:21 +0000 https://ushipblogsubd.wpengine.com/?p=4328 Intro At uShip, our monolithic web application and the services supporting it are written in ASP.NET MVC, Web API, and hosted on IIS . We have begun the journey of transitioning to microservices. One of the important decisions we had to make early on was the choice of hosting model for our microservice APIs. We... Read More

The post Self-hosting a .NET API: Choosing between OWIN with ASP.NET Web API and ASP.NET Core MVC 1.0 appeared first on The uShip Blog.

]]>
Intro

At uShip, our monolithic web application and the services supporting it are written in ASP.NET MVC, Web API, and hosted on IIS . We have begun the journey of transitioning to microservices. One of the important decisions we had to make early on was the choice of hosting model for our microservice APIs. We opted for a self-hosted solution, where we didn’t have to depend on the existence of IIS on a machine, instead allowing the application to create an instance of an HTTP server within its own process. Self-hosting also opens up the possibility for future Linux deployments. We invested a bit of time investigating OWIN and the new ASP.NET Core offering. Here’s what we found.

OWIN vs ASP.NET Core MVC 1.0

OWIN

OWIN is a specification that describes how web servers and web applications interact that has been around for quite a while. One can build applications on top of OWIN which removes the dependency on IIS, allowing self-hosting. Once the application is self-hosted, wrapping it in a Windows service allows Windows to help manage the application’s lifecycle.

ASP.NET Core MVC 1.0

ASP.NET Core MVC 1.0 (the framework formally known as ASP.NET 5 MVC 6) is a new web framework by Microsoft. It is not a successor to ASP.NET Web API 2.2 or MVC 5, the web frameworks built for .NET Framework 4.6 (the latest version of the full .NET Framework). Rather, it is an alternative web framework that one can use if their code can run on .NET Core, a re-imaging of the .NET Framework that includes a subset of the full .NET Framework and is cross platform. Web applications built with ASP.NET Core can be run on Kestrel, an HTTP server built for ASP.NET Core that will allow you to self-host your application.

The below are some of our reasons we chose self-hosting with OWIN instead of with Kestrel and ASP.NET Core:

  • Stability. The ASP.NET Core ecosystem as a whole is not yet stable. At time of writing ASP.NET Core is on RC1, but we have seen code interface changes, project file changes, major tooling changes, and so on. The bleeding edge is too bloody for us to be productive in a codebase our size.
  • Seamless upgrade. .NET Framework 4.6 is the natural upgrade path for us. Our software is more than 10 years old, and we have invested lots of time in learning various libraries, and have significant use of them throughout the entire codebase. A lot of these libraries (e.g,. NHibernate) are not yet compatible ASP.NET Core.
  • Maturity. Nothing beats software that has stood the test of time in production. Along with reliability, there is also a plethora of online documentation for OWIN and tutorials by people that have already run into the problems that we will inevitably run into.

The below will help you implement your own OWIN self-hosted application. While the implementation is OWIN-specific, the overall idea of self-hosting is very similar and will be much easier to port to ASP.NET Core than an IIS deployment would be.

Terms To Be Familiar With

Below are some terms that you should be familiar with before moving on to the implementation

  • OWIN: Open Web Interface for .NET. Acts as an adapter between web servers and web applications. This is a specification, not an implementation.
  • Middleware: “plugins” for OWIN. Similar to an IHttpModule in IIS. If using Web API, these middlewares run before and after the ASP.NET pipeline finishes.
  • Katana: Microsoft’s implementation of OWIN, a collection of NuGet packages for developing OWIN applications. A breakdown of the NuGet packages and their purposes are shown in the following diagram.
    katana-nuget-map
  • Topshelf: An opinionated framework for easily developing Windows services.

Self-hosted Web API Hello, World! Windows service with OWIN and Topshelf

Note: All code is available on GitHub.

  • In Visual Studio, create a new Console Application project called “OwinHelloWorld”
  • Install the Microsoft.AspNet.WebApi.OwinSelfHost NuGet package
  • Install the Topshelf NuGet package
  • Add the following code:
    using Microsoft.Owin.Hosting;
    using Owin;
    using System;
    using System.Web.Http;
    using Topshelf;
    
    namespace OwinHelloWorld
    {
        public class Program
        {
            public static int Main(string[] args)
            {
                return (int) HostFactory.Run(x =>
                {
                    x.Service<OwinService>(s =>
                    {
                        s.ConstructUsing(() => new OwinService());
                        s.WhenStarted(service => service.Start());
                        s.WhenStopped(service => service.Stop());
                    });
                });
            }
        }
    
        public class OwinService
        {
            private IDisposable _webApp;
    
            public void Start()
            {
                _webApp = WebApp.Start<StartOwin>("http://localhost:9000");
            }
    
            public void Stop()
            {
                _webApp.Dispose();
            }
        }
    
        public class StartOwin
        {
            public void Configuration(IAppBuilder appBuilder)
            {
                var config = new HttpConfiguration();
                config.Routes.MapHttpRoute(
                    name: "DefaultApi",
                    routeTemplate: "api/{controller}/{id}",
                    defaults: new { id = RouteParameter.Optional }
                    );
    
                appBuilder.UseWebApi(config);
            }
        }
    
        public class HelloWorldController : ApiController
        {
            public string Get()
            {
                return "Hello, World!";
            }
        }
    }
  • Run the application one of the following ways:
    • Hit F5 in Visual Studio to debug
    • Run the exe to run the application as a regular process. The exe is usually located in SolutionRoot/SelfHostDemo/bin/Debug/SelfHostDemo.exe
    • Manage the application as a Windows service
      # Install and start the Windows service
      SelfHostDemo.exe install start
      
      # Stop and uninstall the Windows service
      SelfHostDemo.exe stop uninstall
  • Hit http://localhost:9000/api/helloworld in your browser

Gotchas Encountered While Switching from IIS to a Self-hosted Model

It would be a bad to assume that you can simply port over your IIS-based codebase into a self-hosted model. The below are some gotchas that you may run into.

    • HttpContext.Current: This will be null. HttpContext is IIS based and will not be set when self-hosting with OWIN.. If you have any code that relies on HttpContext, HttpRequest, or HttpResponse, it will have to be rewritten to handle an HttpRequestMessage or HttpResponseMessage, the HTTP types provided by Web API. Fortunately, we still have access to CallContext provided by ASP.NET. This class can be used to provide per-request static semantics. We have written an OWIN Middleware that gives us the request scope behavior of HttpContext.Current using CallContext:
      using Microsoft.Owin;
      using System.Runtime.Remoting.Messaging;
      using System.Threading.Tasks;
      
      namespace OwinHelloWorld
      {
          /// <summary>
          /// Sets the current <see cref="IOwinContext"/> for later access via <see cref="OwinCallContext.Current"/>.
          /// Inspiration: https://github.com/neuecc/OwinRequestScopeContext
          /// </summary>
          public class OwinContextMiddleware : OwinMiddleware
          {
              public OwinContextMiddleware(OwinMiddleware next) : base(next)
              {
              }
      
              public override async Task Invoke(IOwinContext context)
              {
                  try
                  {
                      OwinCallContext.Set(context);
                      await Next.Invoke(context);
                  }
                  finally 
                  {
                      OwinCallContext.Remove(context);
                  }
              }
          }
      
          /// <summary>
          /// Helper class for setting and accessing the current <see cref="IOwinContext"/>
          /// </summary>
          public class OwinCallContext
          {
              private const string OwinContextKey = "owin.IOwinContext";
      
              public static IOwinContext Current
              {
                  get { return (IOwinContext) CallContext.LogicalGetData(OwinContextKey); }
              }
      
              public static void Set(IOwinContext context)
              {
                  CallContext.LogicalSetData(OwinContextKey, context);
              }
      
              public static void Remove(IOwinContext context)
              {
                  CallContext.FreeNamedDataSlot(OwinContextKey);
              }
          }
      }
    • HttpRequestMessage.Content.ReadAsStreamAsync().Result: IIS let’s you read the request stream multiple times, but by default OWIN does not, not does it let you reset the stream after reading it once. A common reason people need to read the stream twice is to log the incoming request before the input body is deserialized by the framework. We have written an OWIN Middleware that copies the request stream into an in-memory buffer to get around this:
      using Microsoft.Owin;
      using System.IO;
      using System.Threading.Tasks;
      
      namespace OwinHelloWorld
      {
          /// <summary>
          /// Buffers the request stream to allow for reading multiple times.
          /// The Katana (OWIN implementation) implementation of request streams
          /// is different than that of IIS.
          /// </summary>
          public class RequestBufferingMiddleware : OwinMiddleware
          {
              public RequestBufferingMiddleware(OwinMiddleware next)
                  : base(next)
              {
              }
      
              // Explanation of why this is necessary: http://stackoverflow.com/a/25607448/4780595
              // Implementation inspiration: http://stackoverflow.com/a/26216511/4780595
              public override Task Invoke(IOwinContext context)
              {
                  var requestStream = context.Request.Body;
                  var requestMemoryBuffer = new MemoryStream();
                  requestStream.CopyTo(requestMemoryBuffer);
                  requestMemoryBuffer.Seek(0, SeekOrigin.Begin);
      
                  context.Request.Body = requestMemoryBuffer;
      
                  return Next.Invoke(context);
              }
          }
      }
    • IIS-specific modules: When investigating the switch from IIS to self-hosted, we discovered we relied on ISAPI_Rewrite, an IIS module that rewrites URLs ala Apache’s .htaccess. If we wanted to keep such behavior, we would need to either write an OWIN middleware that does the same thing, or somehow get a reverse proxy to do it.

What the future holds

Once the ASP.NET Core MVC 1.0 ecosystem stabilizes, it may be a suitable alternative to building OWIN applications for most. But for now, writing a self-hosted application using OWIN might be the best choice for a pre-existing codebase. If you are one of the lucky few who is in a greenfield project, it is definitely worth building your application with Core in mind for an easy upgrade. For help on determining if your software can be ported to Core, see ApiPort.

[amp-cta id=’8510′]

The post Self-hosting a .NET API: Choosing between OWIN with ASP.NET Web API and ASP.NET Core MVC 1.0 appeared first on The uShip Blog.

]]>
https://ushipblogsubd.wpengine.com/shipping-code/self-hosting-a-net-api-choosing-between-owin-with-asp-net-web-api-and-asp-net-core-mvc-1-0/feed/ 16