Microsoft gets serious about WebAssembly

Compiled code running at near-native speeds in the browser is getting the .NET touch.

It’s not hard to see why Microsoft is investing in WebAssembly. It’s a technology that scratches many different itches. It delivers apps to users, adds rich user interfaces to web applications, and even provides a way to manage and update edge devices. By building on widely distributed web technologies and supporting familiar programming languages, it’s a way to run compiled binaries anywhere that you can run a JavaScript engine.

Microsoft has had plenty of experience with common language runtimes like WebAssembly’s. After all, .NET’s own CLR has been around for more than two decades now and has become the foundation for its open source reinvention, while supporting many different languages from a managed C++ implementation to the stalwart C# and Visual Basic and the functional F#. So, it wasn’t hard to provide tools for .NET’s Roslyn compiler to target the WebAssembly byte code rather than the .NET CLR’s.

Blazor WebAssembly tools in Visual Studio

The initial Blazor experiment built on the ASP.NET Core tooling to deliver WebAssembly code using familiar development tools and techniques. Now Blazor and WebAssembly are supported targets for C# development in Visual Studio. If you have a recent version of Visual Studio 2019 installed, start by creating a new project, and then choose to build a Blazor WebAssembly app. This will set up the scaffolding for a Blazor application, with an optional ASP.NET Core host, using either .NET Core 3.1 or .NET 5.0. I’d recommend .NET Core 5.0 for new development, but if you want long-term support you may prefer to choose the .NET Core 3.1 option.

Blazor WebAssembly apps can be delivered as Progressive Web Apps (PWAs) or used as front ends for ASP.NET Core applications. This last option is attractive, especially if you’ve used technologies like Silverlight in the past, as it gives you a set of rich user interfaces for a web application. Unlike Silverlight or Flash, Blazor doesn’t require risky browser plug-ins; everything is managed by the browser and its JavaScript engine (including security and application isolation).

The Visual Studio scaffolding is enough to get you started, providing a WebAssembly host for your code. You can then add controls as needed, using either the standard WinUI controls or working with third-party tools. Popular control vendors such as Infragistics have Blazor implementations of familiar controls with versions for both WebAssembly and server-side Blazor. Third-party controls like these let you build much more complex UIs, similar to those you’d use in a standard desktop application.

Once you’ve built a WebAssembly application you need to get it to your users. The Visual Studio tool gives you some options, but you need to either provide a complete web app for the ASP.NET Core option or use something like the Windows Store to deliver a WebAssembly PWA.

Using WebAssembly in Azure Static Web Apps

One option is to use the Azure Static Web Apps tool to deliver new code to a host URL each time you push a new build through GitHub. Code in a PWA or in a webpage may well be dynamic, but it’s not dynamically generated by a server. By building a Blazor app as a single page application, you can use standard switch and routing techniques to handle its different URLs, with a fallback route to ensure that any other URLs automatically resolve to the index view.

Azure Static Web Apps use GitHub to host your code, so Microsoft provides a GitHub repository with the files you need to build your first Blazor app. Start by using the provided template to set up your own repository, adding the main branch to your own account. You can then clone it to a local machine for editing in your choice of development tools. Once you’ve set that up, in Azure follow the usual route to create a Static Web App and connect it to your new GitHub repository. You can then deploy the sample code to Azure and test your app’s website. You can find the site URL in the Azure Portal.

With local code on your development system, you can open it in your choice of development tool, using either built-in Git tools or a Git client to push updates to your GitHub repository. It’s best to work in a local development branch, using pull requests to update the main branch. Once you’re happy with your code, accept the pull request and Azure Static Web Apps will use a GitHub Action to push a new build of both your site and your Blazor WebAssembly code to Azure. If you reload the site or a hosted PWA, you’ll automatically see any changes.

This approach makes a lot of sense as a way of transparently updating WebAssembly apps. Users will automatically be presented with a new version the next time they open the app’s URL, with no need to seek updates. At the same time, you don’t need to build an update infrastructure. A Blazor PWA delivered as an Azure Static Web App will look like a desktop app to a user, one that will always be up to date.

Taking advantage of WebView2 for WebAssembly

One interesting aspect of the recent Project Reunion 0.5 release is its production-ready support for the first WinUI 3 components, including the Chromium-based WebView2 control. This includes the same JavaScript engine as Microsoft’s Edge browser, and that brings along its WebAssembly support. You can use it to host Blazor and other WebAssembly frameworks, running web-delivered controls while using JavaScript interop tools to link your WebAssembly UI to local code via WinUI.

This approach makes it easier to update application logic out of band from standard updates. By refreshing the Blazor code, you can deliver updates without having to distribute a whole new release to users. This approach can work well when you’re having to respond to a rapidly changing regulatory environment, for example updating a realty app for new local taxes as soon as they’ve been approved, or calculating tariffs and other import duties while customs rules are still in flux.

Rapid changes aren’t the only reason to embed WebAssembly in an application. You can use it with WebView2 to A/B test new UI features, delivering different static content with Blazor components to different groups of users, experimentally verifying new application features before moving to standard WinUI components in a final release.

Going further

As we’ve seen with experiments like krustlets, Microsoft’s WebAssembly ambitions go much further than apps that can run hosted in any browser. It was an early adopter of the standalone WASI, the WebAssembly System Interface. This takes the WebAssembly runtime and decouples it from its browser host, providing a lightweight JVM host for compiled code. If WebAssembly in the browser gave you a near-native environment for what might have previously been JavaScript, WASI applies the same decoupling to Node.js, letting you run near-native binaries on a standalone JVM.

That has definite advantages for managing updates to small-form-factor IoT devices, where a WASI-enabled JavaScript runtime and simple firmware can keep a device’s software in sync with a cloud-hosted or locally hosted repository. Devices can download updated applications as they are available, and because WASI is a standard specification, software can be developed and tested using basic simulators with digital twins.

WebAssembly’s flexibility is key to much of its utility. Initially we’ll see it used as a Flash or Silverlight replacement, providing a way to host rich controls on ASP.NET Core web apps. Experience gained here will allow us to host those new experiences in desktop apps using WebView2 before we use them as PWAs delivered via Static Web Apps. There’s a lot to like about Microsoft’s measured and tool-driven approach to WebAssembly, and its rapid maturity means it’s time to start building your own Blazor-driven experiments.

Copyright © 2021 IDG Communications, Inc.