Microsoft Visual Studio 2005 Web Project System: What Is It and Why Did We Do It?
Product Unit Manager, Web.NET
Microsoft Visual Studio 2005
Microsoft ASP.NET 2.0
Summary: Describes the new Web project system used by Microsoft Visual Studio 2005, describes the motivation for the changes, and gives some background on the features it provides. (14 printed pages)
Note This article originally appeared on Scott's blog. Join in the discussion here.
There has been a lot of online discussion lately about the new Web project system that is being introduced with Microsoft Visual Studio 2005. My goal with this post is to explain a little more about what it is, and provide some background as to the features it provides and the motivation we had in introducing it.
Web projects are used when building Microsoft ASP.NET applications inside Visual Studio 2005. They can be used either stand-alone—where everything within an application lives inside a single project—or together with class library, data, Web service, unit-test, and/or any other project supported by Visual Studio as part of a solution. They fully support references and project build-ordering within a Visual Studio solution—you set these up and manage these cross-project relationships using a .sln solution file, just like you do today with Microsoft Visual Studio 2003 (for example, you might have three to four class library projects that build class library assemblies that are then consumed and used by the Web project).
When you are ready to "publish" a Web solution, you can use the new Publish command on the Build menu to compile and generate a deployable directory structure for a Web server. This is logically equivalent to the user workflow steps taken with a Windows Forms client application project in Visual Studio 2005 (except its Publish option generates a client "Click-Once" package instead of Web site). You can also automate Web project build operations, using the new MSBuild system for command-line and automated build server scenarios.
The new Visual Studio 2005 Web project support provides a number of new feature enhancements over Microsoft Visual Studio .NET 2002 and Microsoft Visual Studio .NET 2003. A few of the big improvements that we think developers will like are:
No More FrontPage Server Extension Requirement
Unlike previous releases of Visual Studio, Visual Studio 2005 no longer requires developers to use or have FPSE (FrontPage Server Extensions) installed in order to create or build Web projects.
You can now browse, create, and open local IIS applications and vdirs without FPSE on the box; instead, we now have support for Visual Studio 2005 to directly use the IIS metabase configuration store to attach and identify sites/apps/vdirs and associated physical path bindings. You can also edit and open Web projects directly off of the file-system, or access them remotely over FTP.
FPSE is still fully supported for those who want it. But, if you are in the camp that doesn't want it (which, based on feedback, is 95 percent + of you), your _vti_ directories will be a thing of the past.
Built-in Development Web Server (No IIS Requirement & Debug as Normal User)
In addition to providing full support for developing and testing Web projects on IIS, Visual Studio 2005 also includes a built-in development Web server that ships in the box. This test Web server is ideal for doing development when IIS is either not installed, or your IT policy limits desktop deployment of it.
This Web server only handles local requests, for security reasons (so people can't access your application remotely while you are developing it), and it automatically shuts down when you close your Web projects. It also supports developers' debugging applications running within it while running under a non-admin "normal user" account. Once you've built your application using it, you can then upgrade the Web to either run under IIS locally, or deploy the application to a remote server to test and verify. There is also now a new built-in Copy Web Wizard that can help with copying your Web to a remote server (it supports FTP and FPSE as copying protocols too).
Obviously, we also fully support building Web projects against IIS directly. (Note: This is required when you are building a solution with nested vdirs and subapplications.)
More Flexible File Management and Better Cross-Tool Collaboration Support
Web projects have a few unique characteristics that often differentiate them from other types of application projects:
- Web projects are almost always built using a variety of very different tools in parallel. Images are worked on using tools such as Photoshop, Illustrator, and FireWorks. CSS and .aspx/.htm content layout is worked on using DreamWeaver or FrontPage. Code is worked on using Visual Studio. A tremendous amount of integration and collaboration goes on between these different types of resources. Although sometimes the same person performs all of these tasks, typically, for larger projects, they are split up across multiple people working together.
One of the big complaints we hear with Visual Studio 2002/2003 is how hard it is to manage these cross-tool workflows—especially given that non-Visual Studio tools do not work with FPSE and do not integrate at all with Visual Studio project files. For example, a designer might update a CSS file in a Web project to use a new background image, and add the new image to an images directory under the Web project, using his or her image editing tool. If the Web developer using Visual Studio .NET 2003 does not coordinate this change by updating his or her project file to remove the old image and add the new image to the project file manifest, then they will find that things work fine during development, but will fail in production, because the new image will not be copied/deployed when the Web project is built to a new location.
- Web projects are also unique in that the file layout of pages, images, CSS stylesheets, Flash SWF files, and other items within a Web application are directly surfaced to end-users accessing the running Web app with a browser. File layouts are almost always hierarchical, and a great deal of attention and work is done when coming up with this organization. The number of files and project items within a typical Web site can easily climb into the hundreds or thousands. One of the complaints we hear with Visual Studio 2002/2003 is how hard it is to manage this within the IDE—especially when source control is used, and it is necessary to check out and then check in a common project file every-time a file layout is changed or a file is added/renamed/deleted.
To better support both of these scenarios, Visual Studio 2005 Web projects no longer store a list of all files in a central Web project manifest file. Instead, the content and layout of the Web project are directly inferred from the file layout and file contents of the Web project folder. Additions/deletions/movements of files and folders within the Web project do not require updating one central project file that is a single point of contention. This means you can easily use any non-Visual Studio tool that directly works off the file-system with your Web project, and that when running under source control, you do not need to lock and update the project file anytime you move or make a file change.
The project layout under the Solution Explorer for Web projects has also been changed to show a file-system view of the Web project. This ensures that developers always see a 100 percent accurate view of what the exact file layout and content of their Web projects look like (something not true with Visual Studio 2003).
Note We no longer show the references tree underneath the root Web project node, because it is not represented in the file-system; instead, you pull up the references list for the project from the project's Property page (right-click the project in the Solution Explorer to quickly go there), and you can add a new reference to a project directly using the Add Reference menu or shortcut menu item.
Web projects obviously fully support source control. If you move or rename a file in a project under source control, Visual Studio 2005 will move and rename the item appropriately with the source control depot (preserving history), without requiring you to exclusively check out/check in a project manifest to update it as well.
Better Support for Building Much Larger Web Projects
We've heard complaints from developers who work on large Web projects with Visual Studio 2003 that the IDE and workflow environment doesn't scale well to handle lots and lots of files and content. Opening a large Web site can sometimes take minutes, and re-building and running it can often take a very long time when you make a change.
With Visual Studio 2005, we've tried to significantly improve this scalability to handle hundreds and thousands of items within a Web project. As an example, on my local desktop machine (a P4 3Ghz) I just tested opening up with Visual Studio 2005 a local Web project that contains 9,000 files (5,000 .aspx pages and 4,000 images—distributed across 36 directories, each containing 250 items). It opened with Visual Studio 2005 in under 3 seconds. I could then open up, and immediately begin editing, any of the .aspx pages in any directory, without any pauses or delays. This is several orders of magnitude faster than any previous version of Visual Studio (where it would take minutes for a project of this size to even open).
Doing a first-time clean build of this 9,000 item Web site takes about 42 seconds on my machine (about the same time as Visual Studio 2003). What is cool, though, is that after building the Web project once, I can now open any of the 5,000 pages, make a change to the code in the page, rebuild it, and immediately run and test it in less than 2 seconds from the moment I hit CTRL+F5.
There were a couple of architectural changes that we made to facilitate this. One of the biggest changes was that we've moved away from compiling everything in a Web project into a single DLL (which is the only mode that Visual Studio .NET 2002 and Visual Studio .NET 2003 support). Instead, we now partition the Web project into multiple, more granular assemblies.
All non-code-behind classes, datasets, Web services, and other non-UI code that live in the Web project are by default now compiled into one common assembly. Pages and user controls are then compiled into separate, more granular assemblies (by default, each directory in the Web project is compiled into a separate assembly). Note that the Web project can also obviously reference other class library projects as part of a solution too (these work just the same as today, and would compile into their own project's assembly).
The big advantage of this more granular model is that the entire Web site does not need to be recompiled on every change; instead, the scope of compilation can be easily calculated based on what changed and what the down-level build dependencies of the change were, and only the affected pieces need to be rebuilt.
Visual Studio 2005 developers also now have more options in their Build menu. They can force building the entire solution (including the current Web project and all other projects in the solution), they can build/rebuild just the Web project, or they can now also choose to use the new Build Page command, and build/rebuild just the current page they are working on (and any dependent resources, such as user controls, that it is using that have also changed). This provides a great way to quickly validate local changes you've made to a few files, without having to do a full build. For C# developers who don't have the background compile capability of VB, it also provides a super convenient way to update intellisense, without having to do a full rebuild.
The F5 and CTRL+F5 "run" options can also be configured by the developer to choose what level of compilation error checking should occur when these keystrokes are used to launch a Web app. The default continues to be compile all changed pages in the Web site—although a useful configuration option when dealing with large Web apps is to compile just the pages/resources you are currently working on (this would allow me to open a 9,000 file Web app in 3 seconds, and then compile and run any page within it in about 2 seconds—and avoid the first time hit of compiling everything else).
Deeper and More Accurate Error Checking and Validation at Build-Time
Errors found at compile/build-time are infinitely easier to identify and fix than ones hit at runtime. One of our goals with Visual Studio 2005 and ASP.NET 2.0 was to increase the depth of checking we provide at build-time in Visual Studio 2005, and to provide a more accurate view of what will happen with the Web app at runtime than with Visual Studio 2003-built apps.
Today, with Visual Studio 2003 and ASP.NET 1.1, developers actually use two different build-environments (typically without realizing this). One of these is Visual Studio .NET 2003, which compiles and builds the code-behind files within the Web project using one set of settings (stored in a .proj file) and produces a .dll stored in the \bin directory. The other build-system is ASP.NET 1.1, which at runtime will then use a different build system to parse and compile controls, markup, and code within .aspx files that derive from the compiled code-behind classes, and which then saves the output of these compilations into a separate temporary folder on the server. The build-settings of the ASP.NET compilation system, and the subsequent load-time behavior of the code-behind .dll that Visual Studio produces, are stored in the application's root Web.config file.
The fact that these two systems are completely different today can be confusing, and can often lead to errors that are missed entirely by Visual Studio at compile-time—but that cause Web apps to blow up at runtime. A few common issues we often hear complaints about are:
- A developer renames the ID of a control in the .aspx file, but doesn't update the field reference in their code-behind. When they build in Visual Studio 2003, they don't see any compile-time errors—but at runtime, they get a null-reference exception (because there is a mismatch between the .aspx and code-behind).
- A developer has a typo on a server control definition in the .aspx (wrong attribute, incorrect attribute value, misclosed server control tag, data-binding expression error, template error, and so on). When they build in Visual Studio 2003, they don't see any compile errors—but at runtime, they get a parse-time error.
- A developer has an error in their Web.config file (either bad syntax or an illegal value). When they build in Visual Studio 2003, they don't see any compile errors—but at runtime, they get a configuration error.
- A developer builds a Web project. After testing it and thinking it is done, they switch the project from debug mode to release mode and compile, assuming that the deployed project is now running optimized. They forget that the <compilation debug="true"> section in their Web.config is the true switch to control whether the app runs under debug mode, and that Visual Studio configures this to be true by default and never changes it. Their app ends up running slowly, and has different behavior than it should (error handling paths are different, .aspx compilation is much slower and inefficient, and so on).
- Discrepancies between the values in the <assemblies> section in Web.config and the references in Visual Studio can cause assemblies to be incorrectly loaded or to not be found.
With Visual Studio 2005 and ASP.NET 2.0 we decided to merge the ASP.NET and Visual Studio Web project build-systems into one common compilation architecture, with one shared place to store compilation settings for a Web project. Among other benefits, this now means that all five of the above issues will now generate compile-time errors when building Web projects in Visual Studio (both in the IDE and through the command-line with MSBuild), instead of only being caught by testing at runtime.
It also means that we can do much deeper design-time integration inside Visual Studio itself—so that things such as master pages, user controls, themes, and other resources that have previously been "dynamically compiled" by ASP.NET only at runtime can now be compiled and used within Visual Studio as well (for example, this means you now get both WYSIWYG and intellisense support for user controls, master pages, and skin resources). It also allows us to get full intellisense of code+content within .aspx pages—so <script runat=server> blocks, <%# %> databinding blocks, and other syntactical elements inside ASP.NET pages are now fully supported inside the Visual Studio editor.
We choose to store the unified compilation and build settings (release/debug, assembly references, namespace imports, warning levels, and so on) within the <compilation> section of the application's Web.config (where all of these settings already existed in ASP.NET 1.1). Because this file is relative to the Web project root, it allows the Web project to be easily included in multiple .sln solutions within Visual Studio.
In addition to providing richer compilation and runtime validation within Web projects, we have also added new accessibility compliance validation in Visual Studio 2005 (to allow developers to check for Section 508 and WCAG compliance). This accessibility checking can be run manually (there is a button on the toolbar and a menu item to configure and run it), or developers can also configure their Web projects to automatically run the accessibility checker each time a Web project build occurs.
More Flexible and Iterative Web Development Experience
We've tried to optimize the workflow behavior within Visual Studio 2005, to enable a more iterative and flexible Web editing model. Several of these optimizations are a direct result of the changes we've made in the Web project system, and include:
- The ability to make quick tactical changes to your Web projects in Visual Studio 2005 and immediately "save and refresh" to see the changes. With Visual Studio 2002 and Visual Studio 2003, developers were always required to recompile and rebuild their projects to see the affect of any changes within their Web apps. Visual Studio 2005 obviously fully supports this as well (as mentioned earlier, you can "Build Solution," "Build Web," and "Build Page" to compile and verify that there are no errors at any granularity).
We also then support an "on demand" compilation workflow, where a user can just save the code-behind or class file they are editing, and immediately hit refresh in the browser (no explicit recompile or rebuild required). ASP.NET will then on-demand recompile only the changed resources and apply them to that request—allowing you to immediately see the difference. This is ideal for making quick surgical changes (one or two liners, where you are confident you have it right and just want to immediately see the changes). We think this feature merges the best features of dynamic languages/scripting (rapid development) with the best features of strongly typed compiled languages (better error checking and performance).
- The ability to both edit and add code while the debugger is attached. With Visual Studio 2002 and Visual Studio 2003, attaching and detaching the debugger can often be cumbersome and time consuming (especially when it nukes the process on detach). When the debugger is attached, developers are not allowed to make any changes to the running Web application or Web project.
With Visual Studio 2005, we now allow a workflow where developers can launch a Web project under the debugger, try out and step through a request to identify an issue, and then—without closing or detaching the debugger—add methods, classes, and pages, and change code in the project, click Save, and then click Refresh in the browser to immediately step through things in the debugger again. This is supported for both VB and C#, and enables much richer editing support than the "edit and continue" support in client projects (where only code-inside methods can be changed—and method, parameter, and class signatures can't be changed). I personally have found it useful to keep the debugger attached for 1 to 2 hours at a time, while I work on pages and classes and develop the entire Web with the ability to step through things at anytime.
Richer Web Deployment Options
Visual Studio 2005 and ASP.NET 2.0 now support several additional deployment options for Web projects not previously available with Visual Studio .NET 2003. These include:
- The optional ability to completely compile a Web project, including compiling all .aspx, .ascx, and .master file content (allowing you to compile and then remove the HTML and ASP.NET server control markup code, and optionally even remove the .aspx and .ascx files themselves and just ship the .dll assemblies). There are a couple of benefits with this feature: 1) It allows you to ship a totally "locked-down" deployment package for enterprise deployment environments. 2) It allows you to better protect your intellectual property from customers if you don't want them to see or change your markup. 3) It eliminates all runtime ASP.NET compilation steps, avoiding the first-time performance hit when a page is first accessed and the .aspx markup is compiled, and enabling much better application startup time and working set usage. This last benefit can be particularly noticeable with large applications, and provides a big performance improvement over Visual Studio .NET 2003-built apps today.
- The ability to support "patching" of deployed assemblies within a site, and allowing you to overwrite some (but not all) of the compiled code-behind binaries on your deployment server, without having to change all of the DLLs. This is enabled using the "fixed names" option within the new Web build-system, and is particularly useful with user control libraries where you might only want to reissue a binary for one or two controls in a library, and not have to update the code-behind dll used for all of them.
Note that, in addition to supporting complete compilation, we also obviously continue to support a model where only the code-behind is compiled and the .aspx markup is left for later customization. We also now support a fully dynamic compilation model, where everything (including code-behind and classes) is dynamically compiled on the production server (this is useful for small site and hobbyist scenarios).
Web Project Build Automation Support
Visual Studio 2005 and ASP.NET 2.0 now have richer support for command-line level build automation, and can also be integrated and automated using the new MSBuild system being introduced in Visual Studio 2005.
ASP.NET 2.0 ships with a new command-line compiler (aspnet_compiler.exe) that provides full support for compiling and building ASP.NET projects (with or without Visual Studio installed). It supports all of the new build and deployment options mentioned in Web projects earlier (optional compilation of .aspx content, updatable assemblies, and so on), and provides deep error warnings and detections when compiling Web applications.
The aspnet_compiler.exe utility can be invoked stand-alone, or used within the context of a MSBuild project file. MSBuild provides a very rich framework for automating and constructing build and environment rules. Some examples of how you could use this for Web projects are: support building and then copying user-control libraries from multiple Web projects into a Web site as a prebuild step; compiling your Web projects; code-signing output; producing both release and debug builds in separate directories for each automated build you kick off; kicking off automated unit tests; sending out code-coverage reports, and so on.
MSBuild can be directly run from the command-line (it ships as part of the .NET Framework redist setup, so no Visual Studio is required on your build-server). If you pass it a .sln file that has Web projects contained within it, these can be built and deployed as part of the solution by MSBuild, and provide basic build-option support.
Unfortunately, we don't have direct MSBuild IDE support to launch MSBuild workflows in the Web project IDE—so you can't add a MSBuild file into a solution with only a single Web project and directly kick it off in the IDE. (Note: C++ projects also don't support this either in Visual Studio 2005.)
What you can do, though, with Visual Studio 2005 Web projects, in order to get equivalent functionality, is to add a "build helper project" that lives next to your Web project in the same Visual Studio solution. This "build helper project" is just an empty class library project, but can contain custom build/configured MSBuild scripts where you can specifically script custom build actions for both your Web project and overall solution (for example, as part of a single script, you could compile multiple user-control library projects, merge them into a Web application project, compile and publish it, run a post-grep utility over it to make sure only production deployment connection strings are being used in the Web.config file, encrypt any necessary Web.config files, and so on). You can then kick off these builds/actions by building the "build helper project" either in the IDE or directly from the command-line. This isn't as elegant as attaching all of these build scripts to the Web project directly, but it enables the same functionality—and provides a lot more power than what was available in Visual Studio .NET 2003.
Going forward, we are looking to add more integration support with MSBuild in the next Visual Studio Orcas release—there is a lot of cool stuff we will be able to do with it. In the meantime, we are also planning to post some samples on the Web of additional MSBuild tasks (with source code, so you can see and tweak them) that show how to enable both common and advanced scenarios with Web projects.
Visual Studio Team System Integration
One of the biggest things in Visual Studio 2005 is the introduction of the Visual Studio Team System products, and the advanced development support they provide. These features are fully integrated with the Web project system, and allow developers building Web projects to take advantage of lots of new capabilities. A few of the big new features that touch a little on the Web project system include:
- Ability to develop unit tests for both classes and Web UI within a Web project (allowing functional ASP.NET UI validation within test projects). Visual Studio Team System includes a built-in Web replay tool that captures interactions between a browser and the server, and allows easy automation and validation of behavior.
- Ability to measure and precisely quantify the percentage of code exercised by tests (what we often call code coverage). A Web developer can build a Web project, build lots of tests to exercise its functionality, and then run those tests and get a report detailing that "74 percent of the lines of code in the Web project were executed during the tests," as well as a precise breakdown of what parts of the code-base were not exercised because boundary and use cases weren't good enough.
- Ability to load-test Web projects to measure RPS (requests per second) throughput, average latency, memory usage, and dozens of other metrics.
- Ability to profile code execution of Web projects and analyze the percentage of time spent where within a Web project, as well as memory allocations and usage.
- Ability to automate and kick off regular or nightly builds using the new Build Server capabilities. Tests can automatically be run as part of this to verify and report build quality.
And a whole lot more...
Visit http://lab.msdn.microsoft.com/teamsystem/default.aspx for more details on Visual Studio Team System.
Sharepoint Server Support
We've done a lot of work to integrate ASP.NET 2.0 with the next release of Sharepoint that ships with Microsoft Office 12 next year. The new version is built entirely using the new features of ASP.NET 2.0: Webparts, master pages, themes, site navigation, membership, roles, personalization, localization, data controls, and so on.
One of our goals with Visual Studio is to enable great tool support for building Sharepoint solutions. Today, with Visual Studio 2003, this is fairly limited (you can pretty much only create a Webpart control as a class library). One of the design goals of the new Visual Studio 2005 Web project system was to enable great Sharepoint support, and enable directly opening and debugging Sharepoint solutions. Going forward, we will support creating and editing new pages in running Sharepoint servers, adding code-behind logic to pages, creating application logic, customizing workflow, building and adding new Webpart controls, and debugging the finished solution.
As the above sections hopefully spell out, there is a heck of a lot of new functionality provided with the Visual Studio 2005 Web project system. We think this functionality not only adds a lot of new features to take advantage of, but also addresses a lot of the key pain-points about which we've heard feedback from customers using Visual Studio .NET 2003 today.
So what are the downsides to it? Well, we really hope there aren't a lot.... Several people have expressed concerns about some important features missing from the project system in Beta1 and Beta2. As I mentioned in my earlier blog post, though, these features will be in the final release.
The only current Visual Studio .NET 2003 feature I know of that is not directly supported in the Visual Studio 2005 Web project system is the lack of pre-build/post-build events defined directly in the Web project itself. As I mentioned above in the "Web Project Build Automation Support" section, you can add a "build helper project" into your solution to get back this equivalent functionality, as well as to get much, much richer build customization support than Visual Studio 2003 provided using the new MSBuild capabilities. This extra step is a little more inconvenient than embedding directly in the Web project, even though it does provide much more power. We will be publishing a whitepaper before the final release that walks through the steps of how to set it up and take advantage of it to help make its usage and benefits more discoverable.
Because there have been a number of changes to both the Web project syste, and lots of other parts of Visual Studio, it is also going to take a little time for current developers to learn all the new capabilities, how to take full advantage of them, and sometimes how to map and evaluate the new capabilities to existing solutions (and in some cases workarounds) they might be using today to achieve similar results.
It would be great if people could post here questions, or suggestions for additional blog entries or MSDN whitepapers that you'd like to see come out between now and the final release that cover either "How do I do [insert scenario]?" or "Is there a better way now to handle [insert scenario]?" I'll then follow-up on these, and either post new blog entries on them or get whitepapers written that go into more detail.
Here are a few I've already been asked about that we are planning to cover:
- Best techniques for reusing user control libraries in multiple Web apps with Visual Studio 2005.
- Best techniques for building a single Web site that is partitioned into multiple nested/isolated vdirs and applications with Visual Studio 2005.
- Best techniques for using MSBuild and "builder helper projects" with Web projects in Visual Studio 2005.
- Best techniques for upgrading from Visual Studio .NET 2003 to Visual Studio 2005, and what project system considerations you should keep in mind.
Hope this helps provide some more information about the new project system, as well as clear up some confusion about what it is.
About the author
Scott Guthrie co-founded the ASP.NET Team, and leads the design team responsible for architecting the product. His individual contributions include: ASP.NET Web Forms Page Architecture, ASP.NET Web Services Infrastructure, ASP.NET Compilation System, ASP.NET Distributed Session State Infrastructure, ASP.NET Deployment Architecture, ASP.NET Reliability System, and the ASP.NET HTTP Runtime Architecture. Prior to ASP.NET, Scott was a member of the IIS and Windows NT development teams.