Christian Weiss

thoughts on web development and IT security

Introducing the ASP.NET MVC “Feature Folders” Project Structure

What’s the problem with the default ASP.NET MVC folder structure?

Which of these requirements is more common?

  • Change something in every view, controller or model of your project
  • Add a new field to your model X, show this field to the user, make it editable, the value must be validated against some fancy rules, …

I guess we are on the same page if we see the second one as more common. I would go as far as to say that if you have the first requirement you’re either working on a major relaunch or you’re not using layout pages, css, abstract classes, [insert random reusability gadget here] correctly.

By default, the ASP.NET MVC project structure advices you to keep every concept in its own area – you therefore might end up with a structure like this:

  • Content
    • CustomerImages
      • AnIconSpecialToCustomers.png
    • Customers.css
  • Controllers
    • CustomersController.cs
  • Models
    • Customer.cs
  • Repositories
    • CustomerRepository.cs
  • Scripts
    • Customers.js
  • Views
    • Customers
      • Create.cshtml
      • Index.cshtm
  • ViewModels
    • Customers
      • IndexViewModel.cs
      • CreateViewModel.cs

As soon as you have more than 3 controllers, this becomes hard to navigate. ASP.NET MVC’s solution for having a better structure is to use “Areas”, however in my opinion they do not solve the problem I’m talking about. To complete the second requirement I’ve mentioned, you still have to navigate through many folders, because most probably, you don’t have a distinct views-guy, a distinct model-guy, a distinct controller-guy, … in your company. It’s a lot more common that e.g. only one or two people are working on all of these mentioned files.

Grouping files by feature

When I’m talking about a feature, I understand it as a sum of files that are needed to create a user benefit. Therefore, with structuring files by feature, the project structure could look like this:

  • Customers
    • Images
      • AnIconSpecialToCustomers.png
    • Create.cshtml
    • CreateViewModel.cs
    • Customer.cs
    • CustomerRepository.cs
    • Customers.css
    • Customers.js
    • CustomersController.cs
    • Index.cshtml
    • IndexViewModel.cs

Think again of our second requirement and of some of the advantages with this structure:

  • You immediately get an overview about how the feature might be implemented.
  • You immediately see which files might be affected by the requirement. You don’t have to check every concept folder to see if there even is a corresponding file. (there might not be a js-file for every feature, …)
  • Every affected file is in one folder. The required navigation in the Solution Explorer is kept to a minimum.
  • In your source control system, you can look at the entire change history of this feature on one folder.
  • If you have to implement a new similar feature, you can copy this one folder and use it as a starting point

Why is there a M in ASP.NET MVC?

I would like to make an exception of my previous structure: It’s important to understand that the ASP.NET MVC framework itself (System.Web.Mvc) does NOT give you any built-in support for “models”. If you require persistent data, you are allowed to use whatever technology you want (Entity Framework, NHibernate, raw ADO.NET, …). Yes, the project templates by default already reference Entity Framework, but again, this is a separate library and ASP.NET MVC has no dependency on it.

In my opinion this is a very good thing! The traditional three-tier architecture (data, business logic, presentation) still is one of the most important concepts for structuring software systems. ASP.NET MVC clearly targets the presentation tier and shouldn’t cover responsibilities from other tiers.

For this reason, we have to move the files “Customer.cs” and “CustomerRepository.cs” into a separate library. However, everything else in our folder belongs to the presentation layer.

What’s next?

I plan to do follow-up posts that address the challenges and also possible solutions for this structure, so stay tuned!

Moving my BlogEngine.NET blog to Microsoft Azure

I thought, after 5 years since my last post it might be time to write a new one! But that’s not so easy! When you login to the backend after such a long time, everything feels just wrong: The design is ugly, the blog engine is outdated, I’m not sure if my hosting provider still is the best choice for me and I don’t like my domain anymore! So, instead of just writing a post about something, I decided to change all of these things first and tell you about this process!

Get a running BlogEngine.NET instance within minutes

I was always interested in Windows Azure Microsoft Azure but never really had the time to do something useful with it. Therefore I decided to take this opportunity and move my blog to it. I already had access to the Azure Management Portal, so I didn’t have to go through some registration process. Since I also wanted to update my blog to the latest version of BlogEngine.NET I decided to start with a new installation and migrate my data afterwards (moving data from 6 posts is not so hard Smiley). Luckily, with Azure’s Gallery, it’s extremely easy to setup an instance of BlogEngine.Net. I just followed these instructions: http://blogs.msdn.com/b/webdev/archive/2012/10/12/blogengine-net-and-windows-azure-web-sites.aspx

After that, I just had to go through a quick export/import process to move my data from my old blog to the new one. I started with a “free” web site but quickly scaled it up to a “shared” one because I wanted the site to be running on my custom domain.

Deployment with Git and the App_Data folder

The default template of BlogEngine.NET 2.9 is quite nice, however I wanted to make some minor changes. Sounds like a good opportunity to test another great feature of Microsoft Azure: Git deployment.

According to this tutorial, I setup a Git repository for my web site within the Azure portal and cloned the repository to my notebook. Again, this was very straightforward and worked immediately. This also has the advantage that you now have a backup of your remote files on your home network.

But there’s one important thing to take care of when you use Git deployment with BlogEngine.NET. BlogEngine.NET by default stores data in files within the App_Data folder. This is quite nice since you don’t have to pay for a SQL Server database! However, if you use Git deployment it overwrites this folder, since it’s now under source control. Therefore I added the “App_Data” folder to the .gitignore file. Unfortunately, the deployment still did overwrite changes. I guess this happened, because on the server, the App_Data folder was still a part of the git folder.

To overcome this, I tried a different way: First, I copied my local App_Data folder to some backup directory on my notebook. Then I removed the .gitignore file and really deleted the App_Data folder from my local and remote repository (so if you do this as well, please note that you will have a downtime!). After that, I manually copied the App_Data folder back to Azure with FTP. As a last step, I re-created the .gitignore file with the App_Data-exclusion and also moved the App_Data folder back on my machine.

As a result, the “App_Data” folder is no longer monitored by Git and will not be touched when Azure does a deployment. Of course, whenever you need a up-to-date version of your App_Data folder on your PC for development purposes, you have to manually download it from Azure.

Some warnings about this:

  • I’m pretty sure this is not the best way to handle this. As far as I know, you shouldn’t store user generated content on your server but instead use an Azure Storage account for it. Having user files on your server has several disadvantages: you can’t scale out your servers, you don’t have any replication or backups and so on.
  • I’m not sure if the current deployment behavior, which does not touch untracked folders will stay that way forever. I wouldn’t be surprised if they do a real sync someday because actually, the git repository should be 100% consistent with the web folder.

This means, I do not recommend this for anything else than completely uncritical things! If you want to do this, make sure you regularly backup your App_Data folder by e.g. doing a scheduled FTP download every day.

For this blog, I’m fine with those risks for now but if I happen to need a storage account anyway or if I will blog more in the future I will definitely move the data to a storage account.

Meet me @ BASTA! Spring 2009

Hello everyone!

Next week, I will attend the biggest German .NET conference “BASTA! Spring 2009”. Feel free to contact me, if you’d like to chat with me “offline” there!

What’s next on my blog?

I’m working on an ASP.Net MVC application right now and I plan to post about some of the techniques I’ve used, so expect to read from me after the conference!

Thanks for reading,
Christian Weiss

Testable and reusable cookie access with ASP.Net MVC RC

All good things come in threes, so I’m writing another post about how to access cookie or sessions. I got inspired by a comment from Chris Marisic, who suggested to use a more testable way for this stuff!

Previous posts about this topic:

Intro

Using static wrapper properties is a quick and easy way, but you can’t unit test them because they access HttpContext.Current directly. This time I will show you, how you can build a fully unit testable and strongly typed way to access your cookies. As there has been Christmas time 2 days ago (ASP.Net MVC RC1 was released *g*) I’m using the latest MVC bits for my example!

A Reusable Cookie Container

The cookie container is responsible for getting values out of and into the cookie collections. It does not know which concrete values I’m using in my application! This is implemented in a different level, so you can use this class for all of your applications!

In my implementation it’s possible to store “objects” in cookies. I’ve implemented it this way because I don’t want to convert all my DateTime, int, … cookies every time! But I also don’t want someone to save Lists or any other complex types, so my SetValue() method validates the type of the value and throws an exception, if it’s not a value type or nullable value type. That’s a little type checking, but I think it is worth it because cookies are set quite rarely!

Here’s the interface:

public interface ICookieContainer
{
    bool Exists(string key);
    
    string GetValue(string key);
    T GetValue<T>(string key);
    
    void SetValue(string key, object value, DateTime expires);
}

I will just show the fundamental code here. If you want to see the whole implementation, please take a look at the code sample. (see bottom)

As you can see below, I’ve used the abstracted versions of HttpRequest and HttpResponse, which you get, if you use ASP.Net MVC. That’s just one of thousand things I love about ASP.Net MVC. These classes can be used easily in unit tests. Notice that everything can be injected here. There’s no direct access to HttpContext.Current!

public class CookieContainer : ICookieContainer
{
    private readonly HttpRequestBase _request;
    private readonly HttpResponseBase _response;

    public CookieContainer(HttpRequestBase request, HttpResponseBase response)
    {
        // "Check" is a helper class, I've got from the "Kigg" project
        Check.IsNotNull(request, "request");
        Check.IsNotNull(response, "response");

        _request = request;
        _response = response;
    }

    public string GetValue(string key)
    {
        Check.IsNotEmpty(key, "key");

        HttpCookie cookie = _request.Cookies[key];
        return cookie != null ? cookie.Value : null;
    }

    public void SetValue(string key, object value, DateTime expires)
    {
        Check.IsNotEmpty(key, "key");

        string strValue = CheckAndConvertValue(value);

        HttpCookie cookie = new HttpCookie(key, strValue) {Expires = expires};
        _response.Cookies.Set(cookie);
    }
    
    // ... see code sample for full implementation
}

Here’s a sample unit tests that proves the testability of this code. I use Moq as my mocking framework.

public static class Mocks
{
    public static Mock<HttpRequestBase> HttpRequest()
    {
        var httpRequest = new Mock<HttpRequestBase>();
        httpRequest.Setup(x => x.Cookies).Returns(new HttpCookieCollection());
        return httpRequest;
    }

    public static Mock<HttpResponseBase> HttpResponse()
    {
        var httpResponse = new Mock<HttpResponseBase>();
        httpResponse.Setup(x => x.Cookies).Returns(new HttpCookieCollection());
        return httpResponse;
    }
}

// This method is from my CookieContainerTests class

[TestMethod]
public void SetValue_UpdatesExistingCookie()
{
    // Arrange
    const string cookieName = "myCookie";
    const string cookieValue = "myValue";
    DateTime cookieExpires = new DateTime(2009, 1, 1, 0, 0, 0);

    var httpRequest = Mocks.HttpRequest();
    var httpResponse = Mocks.HttpResponse();
    var cookieContainer = new CookieContainer(httpRequest.Object, httpResponse.Object);
    
    httpResponse.Object.Cookies.Add(new HttpCookie(cookieName, "oldValue"));

        // Act
    _cookieContainer.SetValue(cookieName, cookieValue, cookieExpires);

    // Assert
    HttpCookie cookie = httpResponse.Object.Cookies["myCookie"];
    Assert.IsNotNull(cookie);
    Assert.AreEqual(cookie.Name, cookieName);
    Assert.AreEqual(cookie.Value, cookieValue);
    Assert.AreEqual(cookie.Expires, cookieExpires);
}

That’s it! Now you have a testable and reusable cookie container!

How to use it in your application

It’s really easy to integrate this into your app! Just create an interface that defines all your application-specific properties you want to save in cookies and a concrete implementation of this interface that interacts with the cookie container.

public interface IAppCookies
{
    string UserEmail { get; set; }
    DateTime? LastVisit { get; set; }
}

public class AppCookies : IAppCookies
{
    private readonly ICookieContainer _cookieContainer;

    public AppCookies(ICookieContainer cookieContainer)
    {
        _cookieContainer = cookieContainer;
    }

    public string UserEmail
    {
        get { return _cookieContainer.GetValue("UserEmail"); }
        set { _cookieContainer.SetValue("UserEmail", value, DateTime.Now.AddDays(10)); }
    }

    public DateTime? LastVisit
    {
        get { return _cookieContainer.GetValue<DateTime?>("LastVisit"); }
        set { _cookieContainer.SetValue("LastVisit", value, DateTime.Now.AddDays(10)); }
    }
}

You can now inject this IAppCookies interface to your MVC Controller:

public class HomeController : Controller
{
    private readonly IAppCookies _cookies;

    public HomeController(IAppCookies cookies)
    {
        _cookies = cookies;
    }

    public ActionResult Index()
    {
        DateTime currentTime = DateTime.Now;

        IndexViewModel viewModel = new IndexViewModel
        {
            CurrentTime = currentTime,
            LastVisit = (_cookies.LastVisit ?? currentTime),
            UserEmail = _cookies.UserEmail
        };

        _cookies.LastVisit = currentTime;

        return View(viewModel);
    }

    public class IndexViewModel
    {
        public string UserEmail { get; set; }
        public DateTime LastVisit { get; set; }
        public DateTime CurrentTime { get; set; }
    }
}

Wow, you’re still reading :-)

That’s all I want to show here! If you want to see more about how the IOC is set up (I’m using StructureMap) or anything else, take a look at the full code:

I looking forward to hearing your feedback on this!

Thanks for reading,
Christian Weiss

Use wrappers to access your cookies, sessions, …

As described in my previous post, I will give you some more details about how you can access your cookies in a type-safe and easy way!

Update: Read the follow up post

The simplest way to do this is by using a little wrapper class like this one:

using System;
using System.Globalization;
using System.Web;

namespace CookieWrapper.Web
{
    public static class MyCookies
    {
        public static string UserEmail
        {
            get { return GetValue("UserEmail"); }
            set { SetValue("UserEmail", value, DateTime.Now.AddDays(10)); }
        }

        public static DateTime? LastVisit
        {
            get
            {
                string strDate = GetValue("LastVisit");
                if (String.IsNullOrEmpty(strDate))
                    return null;
                return DateTime.Parse(strDate, CultureInfo.InvariantCulture);
            }
            set
            {
                string strDate = value.HasValue ? value.Value.ToString(CultureInfo.InvariantCulture) : null;
                SetValue("LastVisit", strDate, DateTime.Now.AddDays(10));
            }
        }

        private static string GetValue(string key)
        {
            HttpCookie cookie = HttpContext.Current.Request.Cookies[key];
            if (cookie != null)
                return cookie.Value;
            return null;
        }

        private static void SetValue(string key, string value, DateTime expires)
        {
            HttpContext.Current.Response.Cookies[key].Value = value;
            HttpContext.Current.Response.Cookies[key].Expires = expires;
        }
    }
}

All you have to do is create a static property for every cookie that you would like to work with. As you can see you also have the Expires-times administrated in one single place!

Now you can access the values as seen below and you don’t have to worry about the cookie implementation-details in every place.

tbLastVisit.Text = MyCookies.UserEmail;
MyCookies.LastVisit = DateTime.Now; 

Of course, you can also use this same approach for working with session data or any other key-based collection.

Thanks for reading,
Christian Weiss

Don’t use Response.Cookies[string] to check if a cookie exists!

Update: Follow Up Posts

The short explanation, if you don’t like to read the entire story

If you use code like “if (Response.Cookies[“mycookie”] != null) { … }”, ASP.Net automatically generates a new cookie with the name “mycookie” in the background and overwrites your old cookie! Always use the Request.Cookies-Collection to read cookies!

The long explanation and some useful advices at the end

You can access the Cookies-Collection in two different places in ASP.Net:

  • Request.Cookies gives you the cookies that are sent from the browser to your server.
  • With Response.Cookies, you can send cookies from your server to the browser.

Storing cookies

To make your life easier (or harder, as you will see later), ASP.Net gives you the possibility to add a cookie to the browser this way:

Response.Cookies["mycookie"].Value = "some value"; 
Response.Cookies["mycookie"].Expires = DateTime.Now.AddDays(10);

As you can see here, the .net framework automatically generates the HttpCookie instance with the name “mycookie” in the background and adds it to the collection.

Sending cookies to the browser this way is perfectly fine.

Reading Cookies

The important thing you have to know when reading cookies is, that the Response.Cookies collection is empty at the beginning of every request. The cookie with the name “mycookie” can only be found in the Request.Cookies-Collection!

If you use the following line to check the cookie, a new cookie with the name “mycookie” and an empty value gets added to the Response.Cookies Collection and this overwrites your old cookie! (See framework code above!)

if (Response.Cookies["mycookie"] != null) 
{ 
    // This automatically overwrites the existing cookie with an empty value!!! 
}

The correct way to access cookies is by using the Request.Cookies-Collection:

if (Request.Cookies["mycookie"] != null) 
{ 
    // This is fine 
}

So remember the following rules

  • To read cookies, ALWAYS use the Request.Cookies-Collection
  • Only use the Response.Cookies to set or change cookies

How can I make it better and more beautiful?

Accessing the Request.Cookies or Response.Cookies collection directly is lame! You can’t easily test this code and you don’t have all the other cool stuff like type safety and IntelliSense for the keys.

I will write a follow-up post right after this one with an detailed example on how you can do it better!

Thanks for reading,
Christian Weiss

I’d like to announce … myself!

I don’t know why, but due to some reasons, you stumbled upon this page! I’m happy to announce, that this page is going to be my attempt to make the world a better place for you – at least if you are a Microsoft .Net developer and if you – like me – love to learn new things!

“WTF? Yet another blog about programming?”

If that’s what you are thinking right now, then my answer is “Maybe! But hopefully not!”. I will give my best to provide you with high quality information and if it saves you some hours then it served its purpose!

What can you expect from this blog?

I’m a web developer and software architect. The things I like working with are constantly changing, as I really like to dive into new technologies! Currently I’m learning a lot about ASP.Net MVC and all the ALT.Net topics, so these will be the first topics I’m going to write about.

Your English is crap! Stop hurting my eyes!

I’m from Austria and I speak German (with some crazy dialect)! That means, English is not my first language! This blog is a great opportunity for me to get my hands dirty and just improve my English knowledge! Please feel free to write comments and correct me, if you have found some disastrous mistakes.

Stop talking, start writing!

That’s enough said for my first post! Hopefully, I’ve awaken your interest a little bit and you will visit my page again. Expect to reading from me soon!

Thanks for reading,
Christian Weiss