New Blog, now .NET Core, Docker and Linux powered - and soon to be open-sourced

Posted on Saturday, 26 Nov 2016

A little while ago I concluded that my blog was looking a bit long in the tooth and decided that since I'm looking at .NET Core, what better opportunity to put it through its paces than by rewriting my blog using it.

I won't go into too much detail as how the blog is built as it's nothing anyone wouldn't have seen before, but as someone that likes to read about people's experiencing building things, I thought I'd break down how it's built and what I learned whilst doing it.

Here's an overview of some of the technology I've used:

  • .NET Core / ASP.NET Core MVC
  • MediatR
  • Azure SQL
  • Dapper
  • Redis
  • Google Authentication
  • Docker
  • Nginx
  • Ubuntu

.NET Core / ASP.NET Core MVC

Having been following the development of .NET Core, I thought I'd wait until things stabilised before I started migrating. Unfortunately I didn't wait long enough and had to go through the the pain many developers experiences with breaking changes.

I also ran into various issues such as waiting for libraries to migrate to .NET Standard, and other problems such as RSS feed generation for which no .NET Standard libraries exist, primarily because System.ServiceModel.Syndication is not .NET Core compatible just yet. None of these are deal breakers, with work arounds out there, but none-the-less tripped me up along the way. That said, whilst running into these issues I did keep reminding myself that this is what happens when you start building with frameworks and libraries still in beta - so no hard feelings.

In fact, I've been extremely impressed with the direction and features in ASP.NET Core and look forward to building more with it moving forward.

MediatR

I've never been a fan of the typical N-teir approach to building an application primarily because it encourages you to split your application into various horizontal slices (generally UI, Business Logic and Data Access), which often leads of a ridged design filled with lots of very large mixed concerns. Instead I prefer breaking my application up into vertical slices based on features, such as Blog, Pages, Admin etc.

MediatR helps me do this and at the same time allows you to model your application's commands and queries, turning a HTTP request into a pipeline to which you handle and return a response. This has an added effect of keeping your controllers nice and skinny as the only responsibility of the Controller is to pass the request into MediatR's pipeline.

Below is a simplified example of what a controller looks like, forming the request then delegating it to the appropriate handler:

// Admin Controller
public class BlogAdminController {

    private readonly IMediator _mediator;

    public BlogAdminController(IMediator mediator)
    {
        _mediator = mediator;
    }

    [Route("/admin/blog/edit/{id:int}")]
    public IActionResult Edit(BlogPostEdit.Query query)
    {
        BlogPostEdit.Response model = _mediator.Send(query);

        return View(model);
    }
}
public class BlogPostEdit
{
    public class Query : IRequest<Response>
    {
        public int Id { get; set; }
    }

    public class BlogPostEditRequestHandler : IRequestHandler<Query, Response>
    {
        private readonly IBlogAdminStorage _storage;

        public BlogPostEditRequestHandler(IBlogAdminStorage storage)
        {
            _storage = storage;
        }

        public Response Handle(Query request)
        {
            var blogPost = _storage.GetBlogPost(request.Id);
            if (blogPost == null)
                throw new RecordNotFoundException(string.Format("Blog post Id {0} not found", request.Id.ToString()));

            return new Response
            {
                BlogPostEditModel = blogPost
            };
        }
    }

    public class Response
    {
        public BlogPostEditModel BlogPostEditModel { get; set; }
    }
}

A powerful feature of MediatR's pipelining approach is you can start to use the decorator pattern to handle cross-cutting concerns like caching, logging and even validation.

If you're interested in reading more about MediatR then I'd highly recommend Jimmy Bogard's video on favouring slices rather than layers, where he covers MediatR and its architectural benefits.

Google Authentication

I wanted to keep login simple, and not have to worry about storing passwords. With this in mind I decided to go with Google Authentication for logging in, which I cover in my Social authentication via Google in ASP.NET Core MVC post.

Docker, Ubuntu and Redis

Having read loads on Docker but never having played with it, migrating my blog to .NET Core seemed like a perfect opportunity to get stuck into Docker to see what all the fuss was about.

Having been using Docker for a couple of months now I'm completely sold on how it changes the deployment and development landscape.

This isn't the right post to go into too much detail about Docker, but no doubt you're aware of roughly what it does by now and if you're considering taking it for a spin to see what it can do for you then I would highly recommend it.

Docker's made configuring my application to run on Ubuntu with Redis and Nginx an absolute breeze. No longer do I have to spin up individual services and packing website up and deploy it. Now I simply have to publish an image to a repository, pull it down to my host and run docker-compose up.

Don't get me wrong, Docker's certainly not the golden bullet that some say it is, but it's definitely going to make your life easier in most cases.

Open-sourcing the blog

I redeveloped the blog in mind of open-sourcing it, so once I've finished tidying it up I'll put it up on my GitHub account so you can download it and give it a try for yourself. It's no Orchard CMS, but it'll do the job for me - and potentially you.

Back