Short Walks – 406 Error While Creating a .Net Core Api

I’m afraid this is another of those: “What has AddMvc()” ever done for us posts.  Today, I was creating a brand new .Net Core 2.1 Api and, instead of calling AddMvc in ConfigureServices, I instead used AddMvcCore:

public void ConfigureServices(IServiceCollection services)
{
    services.AddMvcCore();

When I tried to access the API, I got a 406 error.  The fix is very simple (and one that using AddMvc() does for you:

public void ConfigureServices(IServiceCollection services)
{
    services.AddMvcCore()
            .AddJsonFormatters();

Unity Lifetime Manager

If you’ve ever used an IoC container, you’ll know that one of their benefits and burdens is that they abstract away from you the hassle of managing your dependencies. Just declare your interfaces as constructor parameters and then register those dependencies at startup, and the IoC container will propogate your class. Your registration may look like this:

    container.RegisterType<IMyService, MyService>();

But what about when your class has state? For example, what if I have this sort of thing:

    container.RegisterType<IMyData, MyData>();

Here we’re using unity, but it appears that the default behaviour for most IoC containers is transient – that is, they are created each time they are resolved. This is important, not just because you will lose data that you thought you had (in fact that’s one of the better scenarios – because it’s obvious that it’s not behaving how you expect), but because if you’re caching results of queries and so forth, you might find your application is going back for data that you thought it already had. Here’s an example, using Unity, that proves this:

static void Main(string[] args)
{
    var container = new UnityContainer();
 
    container.RegisterType<IMyService, MyService>();
    container.RegisterType<IMyData, MyData>();
 
    container.Resolve<IMyData>().Test = "testing";
    container.Resolve<IMyService>().TestFunction();
 
    Console.ReadLine();
}

The service class might look like this:

public interface IMyService
{
    void TestFunction();
}
 
public class MyService : IMyService
{
    private readonly IMyData myData;
 
    public MyService(IMyData myData)
    {
        this.myData = myData;
    }
 
    public void TestFunction()
    {
        Console.WriteLine($"Test Data: {myData.Test}");
    }
}

And the data class:

public interface IMyData
{
    string Test { get; set; }
}
public class MyData : IMyData
{
    public string Test { get; set; }
}

If you run that, you’ll see that the output is:

Test Data: 

Different IoC containers have slightly different life times – in fact, in the .Net Core IoC, you have to now explicitly register as Singleton, Transient or Scoped. In Unity, you can do something like this:

static void Main(string[] args)
{
    var container = new UnityContainer();
 
    container.RegisterType<IMyService, MyService>(new ContainerControlledLifetimeManager());
    container.RegisterType<IMyData, MyData>(new ContainerControlledLifetimeManager());
 
    container.Resolve<IMyData>().Test = "testing";
    container.Resolve<IMyService>().TestFunction();
 
    Console.ReadLine();
}

Creating a Basic Web Site from an Asp.Net Core Empty Project

I recently wanted to do a very quick proof of concept, regarding the use of setInterval versus setTimeout after reading that setTimeout was referable if you were calling the same function very rapidly. I thought I’d note down my journey from File -> New Project to having the POC running so that next time, I don’t have to re-lookup the various parts.

File -> New Project

If you create a brand new Asp.Net Core 2.1 project, select empty project, and then run the generated code, you’ll see this:

This is generated by a line in Startup.cs:

app.Run(async (context) =>
{
    await context.Response.WriteAsync("Hello World!");
});

The target here is to get to a situation where the blank app is serving an HTML page with some attached Javascript as fast as possible. Here, I’ve got exactly three steps.

Step 1 – Create the HTML File

The application can only serve static files (HTML is considered a static file) from the wwwroot folder. The internal structure of this folder doesn’t matter, but that’s where your file must go:

The contents of this file are as follows:

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8" />
    <title></title>
</head>
<body>
    <p>test</p>
</body>
</html>

This won’t actually do anything yet, because by default, Asp.Net Core does not serve static files, nor does it know the enormous significance of naming something “Index”.

Step 2 – Configure Asp.Net

Startup.cs is where all the magic happens; this is what it looks like out of the box:

public class Startup
{
    // This method gets called by the runtime. Use this method to add services to the container.
    // For more information on how to configure your application, visit https://go.microsoft.com/fwlink/?LinkID=398940
    public void ConfigureServices(IServiceCollection services)
    {
        
    }
 
    // This method gets called by the runtime. Use this method to configure the HTTP request pipeline.
    public void Configure(IApplicationBuilder app, IHostingEnvironment env)
    {
        if (env.IsDevelopment())
        {
            app.UseDeveloperExceptionPage();
        }
 
        app.Run(async (context) =>
        {
            await context.Response.WriteAsync("Hello World!");
        });
    }
}

The `context.Response.WriteAsync` goes, and instead we tell Asp.Net Core to serve static files, and the call to `UseDefaultFiles` means that it will search for Index or Default files. It’s also worth pointing out that the order of these matters:

public void Configure(IApplicationBuilder app, IHostingEnvironment env)
{
    if (env.IsDevelopment())
    {
        app.UseDeveloperExceptionPage();
    }
            
    app.UseDefaultFiles();
    app.UseStaticFiles();                                    
}

Now it loads the Index.html. So technically it was only two steps – although we haven’t referenced any Javascript yet.

Step 3 – Adding the javascript… and let’s do something funky

Change the HTML to give the paragraph an ID and an absolute position. Also, reference the file site.js:

<!DOCTYPE html>
<html>
<head>
    <meta charset="utf-8" />
    <title></title>
    <script src="site.js"></script>
</head>
<body>
    <p id="testElement" style="position:absolute">test</p>
</body>
</html>

Obviously, without adding site.js, nothing will happen (it also needs to be in wwwroot):

The Javascript code for that new file is here:

var divxPos = 0;
 
window.onload = function () {
    runCode();
};
 
function runCode() {
    var test = document.getElementById("testElement");    
    test.style.left = divxPos++ + 'px';    
 
    setTimeout(() => runCode(), 50);
};

If you run it, you’ll find the text running away with itself!

.Net Client Side Libraries

In this post, I introduced (to me) a new method of installing client side Javascript libraries for a .Net Web Application.

In this follow-up, I’m going to cover how this can be used in conjunction with npm in order to simply move the files into the correct location. Note that this is a new tool in Visual Studio, and you’ll need VS 15.8.0 or higher for it to work. Let’s start by creating an empty .Net Core Web App. Once you’ve done so, you’re app probably looks like this:

Now you’ll need to launch a bash or powershell console:

npm init
npm install jquery

Refresh your project and show all files:

As you can see, you now have a node_modules directory. The problem is that the files need to be under wwwroot. Obviously, you could copy it, but let’s try the client side manager:

In the resultant dialog, select File System; navigate to the JQuery directory and select the files that you want:

Now refresh the project again and let’s see what we have:

This actually translates to a JSON file; libman.json looks like this:

{
  "version": "1.0",
  "defaultProvider": "filesystem",
  "libraries": [
    {
      "library": "node_modules\\jquery\\dist\\",
      "destination": "wwwroot/lib/dist/",
      "files": [
        "jquery.min.js"
      ]
    }
  ]
}

Abusing the system

Okay – so that’s very nice; but now that we have a system that will copy files from wherever into wherever (the rule is that you have to go deeper in the files structure – so you couldn’t copy that file back again) then we, presumably, could use this for other things. For example, have you ever had a file (an image or something) that you need to include in your project:

Obviously, c:\tmp above could just as easily be \\shareddrive\images.

To be clear, I’m unsure whether this is abusing the system, or it was meant for this exact thing. It is possible that this type of usage may become unsupported in future (so you’ve been warned).

Installing Client Side Libraries in Asp.Net Core

As a relative newcomer to the web front-end, one thing that always surprised me was how many moving parts you need to get something running. This is probably true elsewhere (i.e. in back-end development, and desktop development) but we just do a better job of hiding it. In the past, people writing web-pages have always has an uneasy relationship with Microsoft. Maybe it started in the late nineties when, in order to win the battle of the browsers with Netscape, Microsoft started giving its product away. Since then IE became more and more bloated, as it had to support 10 years worth of old technology, and people have had to ensure it still worked on IE 6 and 7.

But now things are different, Microsoft is a rebranded company and nobody hates them anymore… and when you create a brand new Asp.Net Core 2.1 project, you can use npm to install client side packages, use them in your web page and it all just works – end of the post.

Except that hasn’t happened. In fact, the client side package management for the web seems (to me) to be in a bit of a mess – especially where Microsoft is concerned.

Create a brand new Asp.Net Core 2.1 MVC project from the template and it comes with jquery, supplied by bower; except Microsoft aren’t continuing support for bower anymore.

So, use NuGet to install your package?

Nope – not on .Net Core!

So, use npm – that’s still supported?

Yep – here’s the Asp.Net Signal R client side package installed using npm:

Okay, so it puts it in ‘node_modules’ – I can reference the library directly from there, right?

Nope – it needs to be in wwwroot\lib.

Errr – so I copy it across manually?

You can. Although that’s kind of the problem that package managers were invented to solve.

I can create a gulp task to take the files out of the downloaded directory and place them into the lib directory!

Yes – yes, you can. Although now you have a gulp task, and an npm restore, all so that you can include one or two files in your project. This all just seems too hard!

LibMan

Introducing LibMan. It isn’t a Package Manager; but it might just be the correct answer to the question: “Why the hell is this whole thing so difficult – I only want one file!”

Here is the context menu for the in the lib folder after v15.8 (this has been available in preview for a while):

That gives you the following dialog:

This is amazing, I can pick the library that I want, and where I want it to go! I can also select specific files that I want – this almost feels like a sensible way to manage client side packages. Click install and bang:

You can see what it’s done by either selecting “Manage Client Side Packages…” from the solution context menu:

Alternatively, you can just have a look at the libman.json file (they both do the same thing as of 15.8.7, which makes me wonder whether “Manage Client Side Packages…” will do something different one day – the ellipses kind of give it away).

And There’s More…

There’s a CLI for it (which seemed to balk a bit when I tried to install it via NuGet), and you can use this as a replacement for Gulp to copy files around, by just selecting “File System” as the source (although this sort of solves that problem further down the tree).

References

https://docs.microsoft.com/en-us/aspnet/core/client-side/bower?view=aspnetcore-2.1

https://blogs.msdn.microsoft.com/webdev/2018/08/22/libman-cli-released/

https://blogs.msdn.microsoft.com/webdev/2018/08/31/library-manager-release-in-15-8/

Short Walks – Navigating in ReactJs

When you start using the React sample templates, one thing that you’ll notice is the navigation menu; it tends to look like this:

<div className='navbar-collapse collapse'>
    <ul className='nav navbar-nav'>
        <li>
            <NavLink to={ '/' } exact activeClassName='active'>
                <span className='glyphicon glyphicon-home'></span> Home
            </NavLink>
        </li>

After messing around for a while, you’ll probably think: now I need to navigate somewhere from within the code of the tsx/jsx file. Turns out you need to use `.push()`:

import { NavLink } from 'react-router-dom';

. . .

doSomething()
.then(output => {
    this.props.history.push('/timbuktu');
});

Not exactly intuitive. And even less intuitive is if you want to go back. You’re thinking it must be `.pop()`? So was I; it’s actually:

import { NavLink } from 'react-router-dom';

. . .

doSomething()
.then(output => {
    this.props.history.goBack();
});

Fixing CSRF Vulnerability

One way that your web-site might be vulnerable to an attack is via Cross Site Request Forgery (CSRF or XSRF).

If you’ve ever been logged into a web-site – say Twitter for example – and you open a separate tab, then type in a twitter account, for example: https://www.twitter.com/paul_michaels, you’ll notice that when the site opens, it opens already logged in for you – which is very helpful. Imagine having to re-log-in every single time you wanted to view a tweet or a profile.

Okay, now imagine that, instead of typing that into the browser, you click the link above – try it! What – it didn’t take you to Twitter, but it took you to the home page of this blog? In fact, that’s exactly how a CSRF attack would work in practice. If you were already logged into that site, the link could have executed a CSRF attack.

Cross Site Request Forgery works on the premise that the victim of the attack is actually logged into a given website with valid credentials, and the attacker knows the exact format of a valid request. So, for example, I can take you to my Twitter profile, because the format of that is well known. Nobody, least of all Twitter themselves, want you to have to mess around logging in again.

But what about if you want to actually post a Tweet? Here’s the Url that gets called:

It’s a little difficult to demonstrate, because Twitter operates over HTTPS, so the traffic is encrypted, but the gist is that, even if I managed to create a site that copied this message exactly, the Tweet would not get created. Let’s have a look at replicating such an attack.

To Reproduce

Your first step is to create a really bog standard web site – the default MVC template will do. It might also help to demonstrate if you don’t use HTTPS.

Launch the web-site with F12 tools and make a given request. For example, click the “Contact” link on the default site. Make a note of the URL and the form data for the request:

Leave the app running and logged in.

Now Attack

Create a new web app with the following code:

<h1>Run CSRF Attack on MyApp</h1>
<form action="https://localhost:12312/SendLoadsOfMoney" method="post">
    <input type="hidden" name="values" 
           value="{'BankName': 'Big Bank', 'Amount': '1234.12' }">
    <input type="submit" value="Attack Now!">
</form>

Obviously, don’t use that code – otherwise you’ll cause over a thousand pounds to be transferred from my account to yours! Replace the URL with whatever the URL from the above site was, and the values with whatever values were behind your grey box above. You can use POST or GET or whatever else you like. What you’ll notice is that clicking your button interacts with the site you created in the same way as it would if you were on your site. The “SendLoadsOfMoney” is obviously an example that takes it to the extremes, but the principle is correct.

Fix

To fix this in MVC is very easy.

Add:

[ValidateAntiForgeryToken]

If you add this to the controller method, you should start seeing this error:

The required anti-forgery cookie “__RequestVerificationToken” is not present.

Your calling code might look like this:

<form action="Test" method="post">
    <input type="submit" value="Test3">
</form>

The next step is to add a call into the client; for example:

<form action="Test" method="post">
    @Html.AntiForgeryToken()
    <input type="submit" value="Test3">
</form>

So far, so good. This works for Asp.Net Mvc Core and Framework, but not for ApiControllers! The decorator [ValidateAntiForgeryToken] has no effect on an ApiController out of the box (and worse, you’ll never know it without launching a specific attack on your ApiController). So what can you do?

One option is to implement a custom token as described here. I would treat this as a specific case for ApiControllers only, though.

References

https://github.com/zaproxy/zaproxy/wiki/Downloads

https://www.owasp.org/index.php/OWASP_Testing_Project

https://www.owasp.org/index.php/Cross-Site_Request_Forgery_(CSRF)_Prevention_Cheat_Sheet

https://docs.microsoft.com/en-us/aspnet/core/security/anti-request-forgery?view=aspnetcore-2.1

https://www.devexpress.com/Support/Center/Question/Details/KA18920/how-to-use-antiforgerytoken-during-devexpress-callbacks

Microsoft Chat Bot Framework – Up And Running

Some time ago (think early to mid-nineties), I used to run a BBS. One Christmas, I logged onto another BBS based in Manchester, and they had a “Santa Chat”. I tried it for a while, and was so impressed by it, that I decided to write my own; it was basically the gift that kept giving: you put this thing on your BBS (basically an Eliza clone) and it records the responses of the unsuspecting users to a text file (or log).

These days there are laws against recording such things, but those were simpler times, and once they realised the joke, everyone was happy, and life went on (albeit at 14.4k bps).

A few years ago, I decided to relive my youth, and wrote an app for the Windows Store – this one didn’t keep logs, although I imagine, had I added a “Post Log to Facebook” button, it probably would have got some use. It has since removed by MS in their wisdom. There was very little difference between it and Eliza.

Now, Microsoft seem to have jumped on this bandwagon, and they have released a framework for developing such apps. Clearly their efforts were just a copy of mine… well, anyway, this is a quick foray into the world of a chat bot.

You’re first step, in Azure, is to set-up a Web-App bot:

This will actually create a fully working bot in two or three clicks; select “Test in Web Chat” if you don’t believe me:

Okay – it doesn’t do much – but what it does do is fully working! You can download the code for this if you like:

The code doesn’t look too daunting when you download it:

In fact, looking inside MessagesController, it appears to be a simple API controller. In fact, the controller selects a dialog to use, and the dialog is the magic class that essentially controls all the… err… dialog. The default is called “EchoDialog”.

For the purposes of this demo, we can change the part we want using the web browser; select Online Code Editor:

The bit we’re interested in for the purpose of this is the EchoDialog. Let’s try changing the text that gets sent back a little; replace the test in MessageReceivedAsync with this:

public async Task MessageReceivedAsync(IDialogContext context, IAwaitable<IMessageActivity> argument)
{
    var message = await argument;
 
    if (message.Text == "reset")
    {
        PromptDialog.Confirm(
            context,
            AfterResetAsync,
            "Are you sure you want to reset the count?",
            "Didn't get that!",
            promptStyle: PromptStyle.Auto);
    }
    else
    {
        if (message == "test")
        {
            await context.PostAsync("Testing 1, 2, 3...");
        }
        else
        {
            await context.PostAsync($"{this.count++}: You said {message.Text}");
        }
        context.Wait(MessageReceivedAsync);
    }
}

So, we are checking the input, and where it’s “test”, we’ll return a slightly different response. You’ll need to build this; select the “Open Console” button down the left hand side of the screen and type “build”:

When it’s done, open up your test again and see what happens:

Remember that the bot itself is exposed as an API, so you can put this directly into your own code.

References

https://blogs.msdn.microsoft.com/uk_faculty_connection/2017/09/08/how-to-build-a-chat-bot-using-azure-bot-service-and-train-it-with-luis/

https://github.com/Microsoft/BotFramework-Emulator

Set-up a new Asp.Net Core 2.1 Project with Docker

Until recently, I’ve pretty much managed to avoid the container revolution. However, as the tools are becoming much more integrated, and the technology much more pervasive, I thought I’d document my journey into the world of containers.

As far as I can tell, the battle between types of containers and orchestrators is now over, and the VHS has emerged as Docker and Kubernetes; at least, MS, Google and Amazon seem to think so.

Docker – from step 0

Let’s follow the process through from nothing; the first step is to visit the Docker Store here.

Once you’re there, you’ll need to pick a username and sign in. After this, you can download Docker for Windows:

Once downloaded, run it, and you’ll see this bizarre screen, that seemingly lives in your way:

You can just close this: docker actually lives in your system tray. Right click there and select Settings:

Share your drive that you’re planning to run your Asp.Net Core code from.

By default, docker installs with a Linux bias, so the next step is to switch to Windows Containers (again in the right-click context menu):

Finally, some code…

Okay, Docker is now primed and ready to run a container. Let’s create our new project:

After you okay this, you’ll notice that there’s a new “Add Docker Support” in the create Project dialogue:

Once you create this (and persuade your browser and Docker that you’re not too bothered about certificates for the minute) it should run out of the box:

To prove it’s running, open Power Shell and type:

 docker ps

Or, to take the more brute force approach by just restarting docker and have a look at VS:

References

https://stackify.com/azure-container-instances/

https://docs.microsoft.com/en-us/aspnet/core/host-and-deploy/docker/visual-studio-tools-for-docker?view=aspnetcore-2.1

Unit Testing With Entity Framework and Entity Framework Core 2.1

Entity Framework Core 2.1 comes with a nifty little feature: an In Memory Database setting. What this means, is that with a single option setting, your tests can interact directly with the database (or at least EF’s impression of the database) but not actually touch any physical database. In other words, you can write unit tests for data access; an example:

// Arrange
DbContextOptions<ApplicationDbContext> options = new DbContextOptionsBuilder<ApplicationDbContext>()
    .UseInMemoryDatabase(Guid.NewGuid().ToString())
    .EnableSensitiveDataLogging()                
    .Options;

using (var context = new ApplicationDbContext(options))
{
    context.Database.EnsureDeleted();
	ResourceCategory resourceCategory = new ResourceCategory()
    {
        Name = "TestCategory"
    }
};
 
// Act
_applicationDbContext.ResourceCategories.Add(resourceCategory);
_applicationDbContext.SaveChanges();
	
 
// Assert                
Assert.Equal("TestCategory", context.ResourceCategories.First().Name);               

To just quickly explain what this is doing: we have a DbContext called ApplicationDbContext and we’re building a set of options on top of that context. We’re then instantiating the context and cleaning the in memory database. Finally, we’re adding a new piece of data to the context and then asserting that it has been added.

Told you it was nifty.

But what about if you’re still using Entity Framework 6?

Glad you asked.

Out of the box, EF does not come with this kind of functionality; however, I recently came across (and contributed) to a NuGet library that provides just such a facility. It provides a wrapper for both Moq and Nsubstitute. The GitHub Repo is here.