Javascript Model-View-Controller example

21 Comments

When I first got into Javascript, it wasn’t obvious to me how best to use the language to do a simple model-view-controller.

I’ve heard of backbone, spine, and some other javascript mvc frameworks, but I just wanted to start with something really simple. My friend Jonas came up with a good example showing how our thinking has evolved after building some stuff.

Option 1: Prototype

In the prototype method you define your functions using the javascript prototype construct and then make use of ‘this’ and ‘self’ to make sure you are calling your methods with the right javascript context.

This is how we first stared doing simple mvc.

FormModel_literal.js

var FormModel = function(){};

FormModel.prototype.getInputText = function(){
   return $('#inputtext').val();
};

FormModel.prototype.setInputText = function(value){
   $('#inputtext').val(value);
};

FormController_prototype.js

var FormController = function(pModel){

    this.model = pModel || new FormModel();
    
    this.fill_clicked = function(){
        this.model.setInputText('Hello World');
    };

    this.clear_clicked = function(){
        this.model.setInputText('');
    }
};

FormController.prototype.init = function(){

    var self = this;

    $('#fillbutton').click(function(){ self.fill_clicked(); });
    $('#clearbutton').click(function(){ self.clear_clicked(); });
};

FormController.prototype.getModel = function(){
    return this.model;
};

It’s nice. It works. You don’t need to worry about state (it’s all in the model). But you do need to watch context (this, that, and self) and it’s easy to get wrong if you aren’t careful.

Option 2: Literal method

In the literal method, you use the javascript literal construct to keep most internal methods private, and then only expose those you want publicly consumed in the return statement.

FormModel_literal.js

var FormModel = function(){

    function getInputText(){
       return $('#inputtext').val();
    }

    function setInputText(value){
       $('#inputtext').val(value);
    }

    return {
        getInputText : getInputText,
        setInputText : setInputText
    }
};

FormController_literal.js

var FormController = function(pModel){

    var model = pModel || new FormModel();

    function fill_clicked(){
        model.setInputText('Hello World');
    }

    function clear_clicked(){
        model.setInputText('');
    }

    function init(){

        $('#fillbutton').click(function(){ fill_clicked(); });
        $('#clearbutton').click(function(){ clear_clicked(); });
    }

    return {
        init: init,
        model : model
    };
};

I think it’s elegant and nice. And I didn’t even know you could use a return statement like that in Javascript.

The advantage of this method is you don’t have to worry so much about getting the context wrong (this, that and self) as it’s all in the same context.

And it’s just easier on the eyes for me as it more closely resembles the classical OO model I am used to in Java and C#.

You can hook these up in view a test page as follows:

<html>

    <head>
        <script type="text/javascript" src="jquery-1.6.1.min.js"></script>

        <!-- Using function returning an Object literal (my preference) -->
        <script type="text/javascript" src="js/controllers/FormController_literal.js"></script>
        <script type="text/javascript" src="js/models/FormModel_literal.js"></script>

        <!-- Using Prototype -->
        <!--<script type="text/javascript" src="js/controllers/FormController_prototype.js" ></script>-->
        <!--<script type="text/javascript" src="js/models/FormModel_prototype.js"></script>-->

        <script type="text/javascript">

            $(document).ready(function() {
                new FormController().init();
            });

        </script>

    </head>

    <body>
        <input type="text" id="inputtext" name="inputtext" value="" />
        <input type="button" id="fillbutton" value="Fill with Text"/>
        <input type="button" id="clearbutton" value="Clear"/>
    </body>

</html>

So while both methods will work, we are currently leaning towards option 2 (the literal method).

It just seems cleaner, less stuff to worry about, and it looks good. Of course being relatively new to hard core javascript, and still looking for better ways, we reserve the right to change our minds tomorrow.

If you have any tips, better ideas, or feedback, we’d love to hear them.

Update:
Nice write up along similar lines from Ola Bini.

Advertisements

How to return Json data from MVC controller

5 Comments

// AJAX: Called by the JqGrid control
public ActionResult Grid(JqGridSearchCriteria criteria)
{

 var draftJson = new {
      total = 1,
      page = 1,
      records = 1,
      rows = new[]
      {
       new{
          id = 8,
          cell = new[]
          {
          "data1",
          "data2",
          "9/13/2010",
          }
          }
     },
};

   return Json(draftJson, JsonRequestBehavior.AllowGet);
}

Silverlight Model-View-Presenter (MVP) example

2 Comments

The Model-View-Presenter is a great pattern for breaking apart separations of concerns in your applications.

The model holds your data and services.
The view holds your user interface controls and interactions.
The the presenter coordinates things behind the scenes.

It’s nice because it keep your business logic out the UI and it makes testing a lot easier as you can focus on just one layer of the application at a time.

Having used MVP a lot in ASP.NET applications, I wanted to see what it would look like in Silverlight and coded up this quick example for reference.

Let’s now see how MVP handles someone entering new user information on a page and hitting the save button.

The View

The view is our gateway into getting and controlling what the user sees on the screen.

UserAdminView.xaml

<UserControl x:Class="MVP1.View.UserAdminView" ...  d:DesignHeight="300" d:DesignWidth="400">
    
    <Grid x:Name="LayoutRoot" Background="White">

        <ListBox ScrollViewer.VerticalScrollBarVisibility="Disabled">

            <TextBlock Text="Username"/>
            <TextBox Name="userNameTextBox" Width="100" Height="25" />
            <TextBlock Text="Roles" />

            <StackPanel Orientation="Horizontal">
                <CheckBox Name="RequestorCheckBox"  />
                <TextBlock Text="Requestor"/>
            </StackPanel>

            <StackPanel Orientation="Horizontal">
                <CheckBox Name="ApproverCheckBox"  />
                <TextBlock Text="Approver"/>
            </StackPanel>

            <Button Name="SaveButton" Content="Save" Click="SaveButtonClicked"/>
            <TextBlock Name="Message" Foreground="Green" Text="Success" Visibility="Collapsed"/>

         </ListBox>
    </Grid>
</UserControl>

When the user hits the save button we need to know what the users name is and what roles they are going to be assigned. To do that we might define a view interface that looks like this:

IUserAdminView.cs

    public interface IUserAdminView
    {
        string ReadName();
        IList ReadRoles();
        void DisplayMessage(string userName);
    }

… and gets implemented like this:

UserAdminView.xaml.cs

    public partial class UserAdminView : IUserAdminView
    {
        private readonly UserAdminPresenter presenter;

        public UserAdminView()
        {
            InitializeComponent();
            presenter = new UserAdminPresenter(this, new UserRepository());
        }

        public string ReadName()
        {
            return userNameTextBox.Text;
        }

        public IList<string> ReadRoles()
        {
            IList<string> roles = new List<string>();
            if (RequestorCheckBox.IsChecked == true)
                roles.Add("Requestor");
            if (ApproverCheckBox.IsChecked == true)
                roles.Add("Approver");
            return roles;
        }

        public void DisplayMessage(string userName)
        {
            Message.Visibility = Visibility.Visible;
            Message.Text = string.Format("{0} was successfully added.", userName);
        }

        private void SaveButtonClicked(object sender, RoutedEventArgs e)
        {
            presenter.HandleAddUser();
        }
    }

ReadName(), ReadRoles() and DisplayMessage() interact directly with the view and do pretty much what you’d expect.

The SaveButtonClicked event hanlder however is a bit different.

       private void SaveButtonClicked(object sender, RoutedEventArgs e)
        {
            presenter.HandleAddUser();
        }

Because the view isn’t really in a position to handle saving the user, it passes this request off to the presenter who can (he’s got the view for reading data and the model for saving it).

But before we get into that guy let’s take a quick look at the model.

The Model

 public interface IUserRepository
    {
        void AddUser(string username);
        void UpdateUserRoles(string username, IList<string> roles);
    }

The Model often goes by more than one name. Some call it the Service layer. My friends like Task. Here I’ve called it IUserRepository because all we’re going to do is save the user to the database.

This example doesn’t actually talk to any databases, but if it did that code would go here (or a more likely some backend webservice):

public class UserRepository: IUserRepository
    {
        public void AddUser(string username)
        {
            // add user to the database
        }

        public void UpdateUserRoles(string username, IList roles)
        {
            // update the user roles
        }
    }

That’s it for the model. It just does the actual work of whatever we want to do and is usually called from the presenter.

The Presenter

 public class UserAdminPresenter
    {
        private IUserAdminView view;
        private IUserRepository repos;

        public UserAdminPresenter(IUserAdminView view, IUserRepository repos)
        {
            this.view = view;
            this.repos = repos;
        }

        public void HandleAddUser()
        {
            string userName = view.ReadName();
            IList<string> roles = view.ReadRoles();

            if (!string.IsNullOrEmpty(userName))
            {
                repos.AddUser(userName);
                repos.UpdateUserRoles(userName, roles);
                view.DisplayMessage(userName);
            }
        }
}

The presenter is where we bring it all together. We use our view to get the data and the model to save it. It coordinates whatever is going on in your view.

In this case there’s only one thing we’re doing. Adding a user. So when the Save button gets pressed our view passes control over to the presenter and it goes about using the view and model to do just that.

        public void HandleAddUser()
        {
            string userName = view.ReadName();
            IList<string> roles = view.ReadRoles();

            if (!string.IsNullOrEmpty(userName))
            {
                repos.AddUser(userName);
                repos.UpdateUserRoles(userName, roles);
                view.DisplayMessage(userName);
            }
        }

That’s it. That’s all there is to MVP.

How is this different from any other MVP implementation?

Not much.

Any differences will usually be in platform. The stateless (request/response) nature of the web means web events come at HTTP Posts. In Silverlight they come as .NET WPF events.

Other than that they are pretty much the same.

How is this different from MVC?

It’s not really that much different. Thick client MVC implementations, in my experience, use a lot of eventing for communication. I don’t like that.

I find heavy eventing hard to follow and difficult to debug. So much happens behind the scenes it can be hard to see where you are in the program. This isn’t an MVC problem. It’s more an implementation style (see last post for an example of heavy eventing).

What I like about MVP (and MVC implementations like Rails and MVC.NET) is the simple request response enforced by statelessness of HTTP. Fire event, something happens, update controls.

If I can maintain that simplicity my Silverlight applications (less rather than more events) I will usually go for that.

What about MVVM?

That’s on my todo list next. I want to try the data binding that comes with that and see how that compares to MVC and MVP.

Stay tuned.

In the meantime, here’s an article to get you started on MVVM.

You can download the source here for this example here SilverLight-MPV.doc (rename *.doc to *.zip – wordpress limitation).

Silverlight Model-View-Controller (MVC) example

8 Comments

I recently started playing with Silverlight again, and wanted to share one way of doing MVC.

To keep things simple, I created an app that basically updates one textbox when you start typing something in the other (salary calculates taxes).

Let’s first go through the code at a high-level, and then walk through what actually happens sequentially behind the scenes.

Step 1: Define your model.

    public interface ICalculatorModel
    {
        double Salary { get; set; }
        double Taxes { get; set; }

        event EventHandler<CalculatorEventArgs> TaxesChanged;
    }

In MVC our model defines our data. Here we are saying we’ve got two pieces of information we are interested in (salary and taxes) and an event to notify people when one of these values change.

Here’s what the actual model looks like.

public class CalculatorModel : ICalculatorModel
    {
        private double salary;
        private double taxes;
        public readonly double TAX_RATE = 0.3d;

        public double Salary
        {
            get { return salary; }
            set
            {
                if (value == this.salary) return;
                salary = value;
                Taxes = salary*TAX_RATE;
            }
        }

        public double Taxes
        {
            get { return taxes; }
            set
            {
                if (value == this.taxes) return;
                taxes = value;
                OnTaxesChanged(new CalculatorEventArgs(this));
            }
        }

        public event EventHandler<CalculatorEventArgs> TaxesChanged;

        protected void OnTaxesChanged(CalculatorEventArgs e)
        {
            if (TaxesChanged != null)
                TaxesChanged(this, e); // fire event
        }
    }

It basically sets values for it’s properties, and fires off an event when someone changes the Taxes property value (this is the event our view registers for so it knows when to update it’s value on the screen).

Step 2: Define your view.

  public partial class CalculatorView : Page
    {
        private ICalculatorModel model;
        private ICalculatorController controller;

        public CalculatorView()
        {
            InitializeComponent();
        }

        public void SetModel(ICalculatorModel calculatorModel)
        {
            model = calculatorModel;
            SalaryTextBox.TextChanged += SalaryTextBoxChanged;
            model.TaxesChanged += ModelTaxesChanged;
        }

        private void ModelTaxesChanged(object sender, CalculatorEventArgs e)
        {
            TaxesTextBox.Text = e.Taxes.ToString();
        }

        private void SalaryTextBoxChanged(object sender, TextChangedEventArgs e)
        {
            controller.SetSalary(Double.Parse(SalaryTextBox.Text));
        }

        public void SetController(ICalculatorController calculatorController)
        {
            controller = calculatorController;
        }
    }

The view fires events off (letting models and controllers know when something interesting has happened). And it registers for events it is interested in (so it knows when to update itself).

In this example we are interested in two events:

  1. When does the SalaryTextBox text change.
  2. SalaryTextBox.TextChanged += SalaryTextBoxChanged;
    
  3. When does our model Taxes value change.
  4. model.TaxesChanged += ModelTaxesChanged;
    

Let’s now take a look at the controller.

Step 3: Hooking up the controller.

    public class CalculatorController : ICalculatorController
    {
        private CalculatorView view;
        private ICalculatorModel model;

        public CalculatorController(CalculatorView view, ICalculatorModel model)
        {
            this.view = view;
            this.model = model;

            view.SetModel(model);
            view.SetController(this);
        }

        public void SetSalary(double salary)
        {
            model.Salary = salary;
        }

        public void SetTaxes(double taxes)
        {
            model.Taxes = taxes;
        }
    }

The controller basically just coordinates things between the model and the view.
Here it passes on the setting of model values to the model itself (which then fires events telling people the model is changed).

But actual hookup for the controller occurs in the MainPage.xaml.cs code behind.

    public partial class MainPage : UserControl
    {
        public MainPage()
        {
            InitializeComponent();
            ICalculatorModel model = new CalculatorModel();
            ICalculatorController controller = new CalculatorController(view, model);
        }
    }

That’s it for setup. Now let’s see how this all actually works.

Step 4: Let the events fly.

Because we have registered for the SalaryTextBox.TextChanged and model.TaxesChanged events in our view …

 public partial class CalculatorView : Page
    {
        public void SetModel(ICalculatorModel calculatorModel)
        {
            ...
            SalaryTextBox.TextChanged += SalaryTextBoxChanged;
            model.TaxesChanged += ModelTaxesChanged;
            ...
        }
}

when someone starts typing in the salary textbox

 public partial class CalculatorView : Page
    {
        private void SalaryTextBoxChanged(object sender, TextChangedEventArgs e)
        {
            controller.SetSalary(Double.Parse(SalaryTextBox.Text));
        }
}

our controller gets notified which passes the message onto our model

    public class CalculatorModel : ICalculatorModel
    {
        public double Salary
        {
             ...
            set
            {
                if (value == this.salary) return;
                salary = value;
                Taxes = salary*TAX_RATE;
            }
        }

        public double Taxes
        {
            ...
            set
            {
                if (value == this.taxes) return;
                taxes = value;
                OnTaxesChanged(new CalculatorEventArgs(this));
            }
        }
}

Now when the model sets it’s salary, it’s actually doing two things. First it sets the value of the salary if it’s changed, secondly it sets the Taxes property down below which in turn fires the OnTaxesChanged changed event:

    public class CalculatorModel : ICalculatorModel
    {
        protected void OnTaxesChanged(CalculatorEventArgs e)
        {
            if (TaxesChanged != null)
                TaxesChanged(this, e);
        }

This is how our Taxes textbox gets update. Because we registered for this event way back in our view, when it gets fired our Taxes textbox gets updated.

    public partial class CalculatorView : Page
    {
        private void ModelTaxesChanged(object sender, CalculatorEventArgs e)
        {
            TaxesTextBox.Text = e.Taxes.ToString();
        }

Phew!

That’s a lot of work to update one textbox based on the contents of another, but you could see how if you had a complicated UI, the benefits of separating the model from the view would start to pay off.

It jury is still out for me on how best to use MVC in Silverlight. Coming from a web background, all this eventing can get pretty confusing (the statelessness of the HTTP is nice).

But this is a start. I’ll post more when I get a chance to play with some other models like Model-View-Presenter.

You can download and play with source SilverLight-MVC here.

Note: WordPress doesn’t allow *.zip files so rename the *.doc to *.zip when you download.

You’ll need Visual Studios 2010 with Silverlight4.

In the mean time, here are some others Silverlight model view examples:

  1. Another MVC example.
  2. Model-View-Presenter example.
  3. Model-View-ViewModel example.

Getting started with Watin, NUnit, and MVC.NET

2 Comments

Watin is a web application testing framework handy for writing high-level smoke screen tests against your .NET web application.

The website has a decent getting started section but I ran into one gotcha (really just a missing dll) and wanted to show you how to get it up and running quickly and easily using NUnit on a simple MVC.NET application.

Step 1: Download Watin

You can download Watin from the main website or just click here and download the lastest Watin 2.x release candidate.

Step 2: Create an empty web application.

For this example I created an empty ‘ASP.NET MVC2 Web Application’ and then added a ‘Class Library’ project to hold my Watin unit tests.

Step 3: Add references.

To run the Watin tests you need two dlls:

  • Watin.Core.dll
  • Interop.SHDocVw.dll

Add these (as well as nunit.framework.dll) to your unit test class library.

Step 4: Create config file to set thread state

Because Internet Explorer is not thread safe, we need to configure NUnit to run in single thread state mode (more details on why here).

Add a ‘Application Configuration File’ (i.e. App.config) to your unit test dll

and paste the following into your configuration file:

<?xml version="1.0" encoding="utf-8" ?>
<configuration>
  <configSections>
   <sectionGroup name="NUnit">
    <section name="TestRunner" type="System.Configuration.NameValueSectionHandler"/>
   </sectionGroup>
  </configSections>
  <NUnit>
   <TestRunner>
    <!-- Valid values are STA,MTA. Others ignored. -->
    <add key="ApartmentState" value="STA" />
   </TestRunner>
  </NUnit>
</configuration>

Step 5: Write your test(s)

The Watin Getting Started section has a simple example to get you going.

using NUnit.Framework;
using WatiN.Core;

namespace tests
{
    [TestFixture]
    public class WatinTest
    {
        [Test]
        public void HelloGoogle()
        {
            // Open a new Internet Explorer window and
            // goto the google website.
            IE ie = new IE("http://www.google.com");

            // Find the search text field and type Watin in it.
            ie.TextField(Find.ByName("q")).TypeText("WatiN");

            // Click the Google search button.
            ie.Button(Find.ByValue("Google Search")).Click();

            // Uncomment the following line if you want to close
            // Internet Explorer and the console window immediately.
            //ie.Close();
        }
    }
}

When you run this test, your default browser should pop-up, enter ‘Watin’ in the search box, and then click the search button.

To run a test against your MVC.NET application, you need to start your webserver. Hit F5 to run your application, note the URL it starts up on (i.e. http://localhost:1110), and then edit the test below so it looks something like this:

        [Test]
        public void HelloMVC()
        {
            IE ie = new IE("http://localhost:1110");
            Assert.IsTrue(ie.Text.Contains("My MVC Application"));
        }

Congratulations! You’ve just written your first Watin test.

Next week we will dive deeper and look more closely at some specific Watin controls and how they work.

%d bloggers like this: