UPDATE: This post is a out of date. We recently released the Release Candidate for ASP.NET MVC 3.
Feels like just yesterday that we released ASP.NET MVC 2 to the world and here I am already talking about an early preview. In a way, we’re right on schedule. It was almost exactly a year ago that we released Preview 1 of ASP.NET MVC 2.
Today I’m happy to announce that ASP.NET MVC 3 Preview 1 is available for download. Give it a try out and let us know what you think. Some key notes before you give it a whirl:
- ASP.NET MVC 3 Preview 1 tooling requires Visual Studio 2010
- ASP.NET MVC 3 Preview 1 runtime requires the ASP.NET 4 runtime
As usual, to find out what’s in this release, check out the release notes. Also at the recent MVCConf, a virtual conference about ASP.NET MVC, I recorded a talk that provided a sneak peek at ASP.NET MVC 3 Preview 1. The audio quality isn’t great, but I do demo some of the key new features so be sure to check it out.
So what’s in this release that I’m excited about? Here’s a small sampling:
- Razor View Engine which ScottGu wrote about recently. Note that for Preview 1, we only support the C# version (CSHTML). IN later previews, we will add support for the VB.NET version (VBHTML). Also, Intellisense support for Razor syntax in Visual Studio 2010 will be released later.
- Dependency Injection hooks using service locator interface. Brad Wilson should have a few blog posts on this over the next few days.
- Support for .NET 4 Data Annotation and Validation attributes.
- Add View dialog support for multiple view engines including custom view engines.
- Global Action Filters
In the next few days you should see more details about each of these areas start to show up in various blog posts. I’ll try to keep this blog post updated with relevant blog posts so you can find them all. Enjoy!
Related
I wanted to confirm something about how to upload a file or set of files with ASP.NET MVC and the first search result for the phrase “uploading a file with asp.net mvc” is Scott Hanselman’s blog post on the topic.
His blog post is very thorough and helps provide a great understanding of what’s happening under the hood. The only complaint I have is that the code could be much simpler since we’ve made improvements to the ASP.NET MVC 2. I write this blog post in the quixotic hopes of knocking his post from the #1 spot.
Uploading a single file
Let’s start with the view. Here’s a form that will post back to the current action.
<form action="" method="post" enctype="multipart/form-data">
<label for="file">Filename:</label>
<input type="file" name="file" id="file" />
<input type="submit" />
</form>
Here’s the action method that this view will post to which saves the file into a directory in the App_Data folder named “uploads”.
[HttpPost]
public ActionResult Index(HttpPostedFileBase file) {
if (file.ContentLength > 0) {
var fileName = Path.GetFileName(file.FileName);
var path = Path.Combine(Server.MapPath("~/App_Data/uploads"), fileName);
file.SaveAs(path);
}
return RedirectToAction("Index");
}
Notice that the argument to the action method is an instance of HttpPostedFileBase. ASP.NET MVC 2 introduces a new value providers feature which I’ve covered before.
Whereas model binders are used to bind incoming data to an object model, value providers provide an abstraction for the incoming data itself.
In this case, there’s a default value provider called the HttpFileCollectionValueProvider which supplies the uploaded files to the model binder.Also notice that the argument name, file, is the same name as the name of the file input. This is important for the model binder to match up the uploaded file to the action method argument.
Uploading multiple files
In this scenario, we want to upload a set of files. We can simply have multiple file inputs all with the same name.
<form action="" method="post" enctype="multipart/form-data">
<label for="file1">Filename:</label>
<input type="file" name="files" id="file1" />
<label for="file2">Filename:</label>
<input type="file" name="files" id="file2" />
<input type="submit" />
</form>
Now, we just tweak our controller action to accept an IEnumerable of HttpPostedFileBase instances. Once again, notice that the argument name matches the name of the file inputs.
[HttpPost]
public ActionResult Index(IEnumerable<HttpPostedFileBase> files) {
foreach (var file in files) {
if (file.ContentLength > 0) {
var fileName = Path.GetFileName(file.FileName);
var path = Path.Combine(Server.MapPath("~/App_Data/uploads"), fileName);
file.SaveAs(path);
}
}
return RedirectToAction("Index");
}
Yes, it’s that easy. :)
UPDATE: Check out my Razor View Syntax Quick Reference for a nice quick reference to Razor.
There’s an old saying, “Good things come to those who wait.” I remember when I first joined the ASP.NET MVC project, I (and many customers) wanted to include a new streamlined custom view engine. Unfortunately at the time, it wasn’t in the card since we had higher priority features to implement.
Well the time for a new view engine has finally come as announced by Scott Guthrie in this very detailed blog post.
While I’m very excited about the new streamlined syntax, there’s a lot under the hood I’m also excited about.
Andrew Nurse, who writes the parser for the Razor syntax, provides more under-the-hood details in this blog post. Our plan for the next version of ASP.NET MVC is to make this the new default view engine, but for backwards compatibility we’ll keep the existing WebForm based view engine.
As part of that work, we’re also focusing on making sure ASP.NET MVC tooling supports any view engine. In ScottGu’s blog post, if you look carefully, you’ll see Spark listed in the view engines drop down in the Add View dialog. We’ll make sure it’s trivially easy to add Spark, Haml, whatever, to an ASP.NET MVC project. :)
Going back to Razor, one benefit that I look forward to is that unlike an ASPX page, it’s possible to fully compile a CSHTML page without requiring the ASP.NET pipeline. So while you can allow views to be compiled via the ASP.NET runtime, it may be possible to fully compile a site using T4 for example. A lot of cool options are opened up by a cleanly implemented parser.
In the past several months, our team has been working with other teams around the company to take a more holistic view of the challenges developing web applications. ScottGu recently blogged about the results of some of this work:
- SQLCE 4 – Medium trust x-copy deployable database for ASP.NET.
- IIS Express – A replacement for Cassini that does the right thing.
The good news is there’s a lot more coming! In some cases, we had to knock some heads together (our heads and the heads of other teams) to drive focus on what developers really want and need rather than too much pie in the sky architectural astronomy.
I look forward to talking more about what I’ve been working on when the time is right. :)