ASP.NET 4.5 和 Visual Studio 2012 的新增功能

本文档介绍 ASP.NET 4.5 中引入的新功能和增强功能。 它还介绍了在 Visual Studio 2012 中对 Web 开发进行的改进。 本文档最初于 2012 年 2 月 29 日发布。

ASP.NET Core运行时和框架

异步读取和写入 HTTP 请求和响应

ASP.NET 4 引入了使用 HttpRequest.GetBufferlessInputStream 方法将 HTTP 请求实体作为流读取的功能。 此方法提供对请求实体的流式访问。 但是,它以同步方式执行,这会在请求期间绑定线程。

ASP.NET 4.5 支持在 HTTP 请求实体上异步读取流,以及异步刷新。 ASP.NET 4.5 还支持对 HTTP 请求实体进行双重缓冲,从而更轻松地与下游 HTTP 处理程序(如 .aspx 页处理程序和 ASP.NET MVC 控制器)集成。

HttpRequest 处理的改进

ASP.NET 4.5 从 HttpRequest.GetBufferlessInputStream 返回的流引用支持同步和异步读取方法。 从 GetBufferlessInputStream 返回的 Stream 对象现在同时实现 BeginRead 和 EndRead 方法。 使用异步 Stream 方法,可以异步读取分块形式的请求实体,而 ASP.NET 在异步读取循环的每次迭代之间释放当前线程。

ASP.NET 4.5 还添加了一个用于以缓冲方式读取请求实体的配套方法: HttpRequest.GetBufferedInputStream。 此新重载的工作方式类似于 GetBufferlessInputStream,支持同步读取和异步读取。 但是,在读取时, GetBufferedInputStream 还会将实体字节复制到 ASP.NET 内部缓冲区中,以便下游模块和处理程序仍可访问请求实体。 例如,如果管道中的某些上游代码已使用 GetBufferedInputStream 读取请求实体,则仍然可以使用 HttpRequest.FormHttpRequest.Files。 这样,便可以对请求执行异步处理 (,例如,将大型文件上传到数据库) 流式处理,但之后仍运行 .aspx 页和 MVC ASP.NET 控制器。

异步刷新响应

当客户端距离较远或具有低带宽连接时,向 HTTP 客户端发送响应可能需要相当长的时间。 通常,ASP.NET 会缓冲响应字节,因为它们是由应用程序创建的。 然后,ASP.NET 在请求处理结束时对累积的缓冲区执行单个发送操作。

如果缓冲响应较大 (例如,将大型文件流式传输到客户端) ,则必须定期调用 HttpResponse.Flush 以将缓冲输出发送到客户端并控制内存使用情况。 但是,由于 Flush 是同步调用,因此迭代调用 Flush 在可能长时间运行的请求期间仍会占用线程。

ASP.NET 4.5 添加了对使用 HttpResponse 类的 BeginFlushEndFlush 方法异步执行刷新的支持。 使用这些方法,可以创建异步模块和异步处理程序,以增量方式将数据发送到客户端,而无需将操作系统线程绑定到客户端。 在 BeginFlushEndFlush 调用之间,ASP.NET 释放当前线程。 这大大减少了支持长时间运行的 HTTP 下载所需的活动线程总数。

支持 await基于任务的 异步模块和处理程序

.NET Framework 4 引入了称为任务的异步编程概念。 任务由 System.Threading.Tasks 命名空间中的 Task 类型和相关类型表示。 .NET Framework 4.5 基于此版本构建,具有编译器增强功能,使使用 Task 对象变得简单。 在 .NET Framework 4.5 中,编译器支持两个新关键字:awaitasyncawait 关键字 (keyword) 是语法简写,用于指示一段代码应异步等待其他一段代码。 异步关键字 (keyword) 表示可用于将方法标记为基于任务的异步方法的提示。

awaitasyncTask 对象的组合使你在 .NET 4.5 中编写异步代码变得更加容易。 ASP.NET 4.5 通过新的 API 支持这些简化,这些 API 允许使用新的编译器增强功能编写异步 HTTP 模块和异步 HTTP 处理程序。

异步 HTTP 模块

假设你想要在返回 Task 对象的方法中执行异步工作。 下面的代码示例定义了一个异步方法,该方法进行异步调用以下载 Microsoft 主页。 请注意,在方法签名中使用异步关键字 (keyword) ,以及对 DownloadStringTaskAsync 的await 调用。

private async Task
ScrapeHtmlPage(object caller, EventArgs e)
{
    WebClient wc = new WebClient();
    var result = await wc.DownloadStringTaskAsync("http://www.microsoft.com");
    // Do something with the result
}

这就是你需要编写的全部内容 - .NET Framework将在等待下载完成时自动处理展开调用堆栈,以及在下载完成后自动还原调用堆栈。

现在,假设你想要在异步 ASP.NET HTTP 模块中使用此异步方法。 ASP.NET 4.5 包括一个帮助程序方法 (EventHandlerTaskAsyncHelper) ,以及一个新的委托类型 (TaskEventHandler) ,可用于将基于任务的异步方法与 ASP.NET HTTP 管道公开的旧异步编程模型集成。 此示例演示如何:

public void Init(HttpApplication
context)
 {
   // Wrap the Task-based method so that it can be used with 
   // the older async programming model.
   EventHandlerTaskAsyncHelper helper = 
       new EventHandlerTaskAsyncHelper(ScrapeHtmlPage);
 
   // The helper object makes it easy to extract Begin/End methods out of
   // a method that returns a Task object. The ASP.NET pipeline calls the 
   // Begin and End methods to start and complete calls on asynchronous 
   // HTTP modules.
   context.AddOnPostAuthorizeRequestAsync(
       helper.BeginEventHandler, helper.EndEventHandler);
}

异步 HTTP 处理程序

在 ASP.NET 中编写异步处理程序的传统方法是实现 IHttpAsyncHandler 接口。 ASP.NET 4.5 引入了可从中派生的 HttpTaskAsyncHandler 异步基类型,这使得编写异步处理程序更加容易。

HttpTaskAsyncHandler 类型是抽象的,需要重写 ProcessRequestAsync 方法。 在内部 ASP.NET 负责将返回签名 (ProcessRequestAsyncTask 对象) 与 ASP.NET 管道使用的较旧的异步编程模型集成。

以下示例演示如何使用 Taskawait 作为异步 HTTP 处理程序实现的一部分:

public class MyAsyncHandler : HttpTaskAsyncHandler
{
    // ...
     
    // ASP.NET automatically takes care of integrating the Task based override
    // with the ASP.NET pipeline.
    public override async Task ProcessRequestAsync(HttpContext context)
    {
        WebClient wc = new WebClient();
        var result = await 
           wc.DownloadStringTaskAsync("http://www.microsoft.com");
        // Do something with the result
    }
}

新的 ASP.NET 请求验证功能

默认情况下,ASP.NET 执行请求验证 , 它会检查请求以在字段、标头、Cookie 等中查找标记或脚本。 如果检测到任何异常,ASP.NET 将引发异常。 这充当防范潜在跨站点脚本攻击的第一道防线。

ASP.NET 4.5 可以轻松有选择地读取未经验证的请求数据。 ASP.NET 4.5 还集成了常用的 AntiXSS 库,该库以前是外部库。

开发人员经常要求能够有选择地关闭其应用程序的请求验证。 例如,如果你的应用程序是论坛软件,你可能希望允许用户提交 HTML 格式的论坛帖子和评论,但仍要确保请求验证正在检查所有其他内容。

ASP.NET 4.5 引入了两项功能,使你可以轻松地选择性地使用未经验证的输入:延迟 (“惰性”) 请求验证和访问未经验证的请求数据。

延迟 (“延迟”) 请求验证

在 ASP.NET 4.5 中,默认情况下,所有请求数据都受请求验证的约束。 但是,可以将应用程序配置为延迟请求验证,直到实际访问请求数据。 (这有时称为延迟请求验证,具体取决于某些数据方案的延迟加载等术语。) 可以通过在 httpRUntime 元素中将 requestValidationMode 属性设置为 4.5,将应用程序配置为在 Web.config 文件中使用延迟验证,如以下示例所示:

<httpRuntime requestValidationMode="4.5" ... />

当请求验证模式设置为 4.5 时,仅针对特定请求值触发请求验证,并且仅在代码访问该值时触发。 例如,如果代码获取 Request.Form[“forum_post”] 的值,则仅对表单集合中的该元素调用请求验证。 不会验证 Form 集合中的其他元素。 在以前版本的 ASP.NET 中,当访问集合中的任何元素时,会针对整个请求集合触发请求验证。 新行为使不同的应用程序组件能够更轻松地查看不同的请求数据片段,而无需在其他部分触发请求验证。

对未经验证的请求的支持

仅延迟请求验证并不能解决有选择地绕过请求验证的问题。 对 Request.Form[“forum_post”] 的调用仍然触发该特定请求值的请求验证。 但是,你可能希望在不触发验证的情况下访问此字段,因为你希望允许在该字段中添加标记。

为了允许这样做,ASP.NET 4.5 现在支持对请求数据的未经验证的访问。 ASP.NET 4.5 在 HttpRequest 类中包含新的 Unvalidated 集合属性。 此集合提供对请求数据的所有常见值(如 FormQueryStringCookie 和Url)的访问。

使用论坛示例,为了能够读取未经验证的请求数据,首先需要将应用程序配置为使用新的请求验证模式:

<httpRuntime requestValidationMode="4.5" ...
/>

然后,可以使用 HttpRequest.Unvalidated 属性读取未验证的表单值:

var s = context.Request.Unvalidated.Form["forum_post"];

警告

安全性 - 谨慎使用未经验证的请求数据! ASP.NET 4.5 添加了未验证的请求属性和集合,以便更轻松地访问非常具体的未验证请求数据。 但是,仍必须对原始请求数据执行自定义验证,以确保不会向用户呈现危险文本。

AntiXSS 库

由于 Microsoft AntiXSS 库的普及,ASP.NET 4.5 现在包含该库 4.0 版本中的核心编码例程。

编码例程由新的 System.Web.Security.AntiXss 命名空间中的 AntiXssEncoder 类型实现。 可以通过调用类型中实现的任何静态编码方法,直接使用 AntiXssEncoder 类型。 但是,使用新的反 XSS 例程的最简单方法是将 ASP.NET 应用程序配置为默认使用 AntiXssEncoder 类。 为此,请将以下属性添加到 Web.config 文件:

<httpRuntime ...
  encoderType="System.Web.Security.AntiXss.AntiXssEncoder,System.Web, Version=4.0.0.0, Culture=neutral, PublicKeyToken=b03f5f7f11d50a3a" />

encoderType 属性设置为使用 AntiXssEncoder 类型时,ASP.NET 中的所有输出编码都自动使用新的编码例程。

以下是已合并到 ASP.NET 4.5 中的外部 AntiXSS 库的部分:

  • HtmlEncodeHtmlFormUrlEncodeHtmlAttributeEncode
  • XmlAttributeEncodeXmlEncode
  • UrlEncodeUrlPathEncode (新)
  • CssEncode

支持 WebSocket 协议

WebSocket 协议是基于标准的网络协议,用于定义如何通过 HTTP 在客户端和服务器之间建立安全的实时双向通信。 Microsoft 已与 IETF 和 W3C 标准机构合作,帮助定义协议。 WebSocket 协议不受任何客户端 (而不仅仅是浏览器) 的支持,Microsoft 投入大量资源在客户端和移动操作系统上支持 WebSocket 协议。

使用 WebSocket 协议,可以更轻松地在客户端和服务器之间创建长时间运行的数据传输。 例如,编写聊天应用程序要容易得多,因为可以在客户端和服务器之间建立真正的长期连接。 无需使用定期轮询或 HTTP 长轮询等解决方法来模拟套接字的行为。

ASP.NET 4.5 和 IIS 8 包括低级别的 WebSocket 支持,使 ASP.NET 开发人员能够使用托管 API 在 WebSocket 对象上异步读取和写入字符串和二进制数据。 对于 ASP.NET 4.5,有一个新的 System.Web.WebSocket 命名空间,其中包含用于处理 WebSocket 协议的类型。

浏览器客户端通过创建 DOM WebSocket 对象来建立 WebSocket 连接,该对象指向 ASP.NET 应用程序中的 URL,如以下示例所示:

socket = new WebSocket("ws://contoso.com/MyWebSocketApplication.ashx");

可以使用任何类型的模块或处理程序在 ASP.NET 中创建 WebSocket 终结点。 在前面的示例中,使用了 .ashx 文件,因为 .ashx 文件是创建处理程序的一种快速方法。

根据 WebSocket 协议,ASP.NET 应用程序通过指示应将请求从 HTTP GET 请求升级到 WebSocket 请求来接受客户端的 WebSocket 请求。 下面是一个示例:

HttpContext.Current.AcceptWebSocketRequest(// WebSocket delegate goes here)

AcceptWebSocketRequest 方法接受函数委托,因为 ASP.NET 展开当前 HTTP 请求,然后将控制权转移到函数委托。 从概念上讲,此方法类似于使用 System.Threading.Thread 的方式,在 System.Threading.Thread 中定义执行后台工作的线程启动委托。

ASP.NET 且客户端成功完成 WebSockets 握手后,ASP.NET 调用委托,WebSockets 应用程序将开始运行。 下面的代码示例演示了一个简单的回显应用程序,该应用程序使用 ASP.NET 中的内置 WebSocket 支持:

public async Task MyWebSocket(AspNetWebSocketContext context)
{
    WebSocket socket = context.WebSocket;
    while (true)
    {
        ArraySegment<byte> buffer = new ArraySegment<byte>(new byte[1024]);

        // Asynchronously wait for a message to arrive from a client
        WebSocketReceiveResult result = 
           await socket.ReceiveAsync(buffer, CancellationToken.None);

        // If the socket is still open, echo the message back to the client
        if (socket.State == WebSocketState.Open)
        {
           string userMessage = Encoding.UTF8.GetString(buffer.Array, 0,
               result.Count);
           userMessage = "You sent: " + userMessage + " at " + 
               DateTime.Now.ToLongTimeString();
           buffer = new ArraySegment<byte>(Encoding.UTF8.GetBytes(userMessage));

           // Asynchronously send a message to the client
           await socket.SendAsync(buffer, WebSocketMessageType.Text,
               true, CancellationToken.None);
        }
        else { break; }
    }
}

.NET 4.5 中对 await 关键字 (keyword) 和基于任务的异步操作的支持自然适合编写 WebSocket 应用程序。 该代码示例演示 WebSocket 请求在 ASP.NET 内完全异步运行。 应用程序通过调用 await 套接字异步等待从客户端发送消息 。ReceiveAsync。 同样,可以通过调用 await 套接字将异步消息发送到客户端 。SendAsync

在浏览器中,应用程序通过 onmessage 函数接收 WebSocket 消息。 若要从浏览器发送消息,请调用 WebSocket DOM 类型的 send 方法,如以下示例所示:

// Receive a string message from the server.
socket.onmessage = function(msg)
{
    document.getElementById("serverData").innerHTML = msg.data; 
};
// Send a string message from the browser.
socket.send(document.getElementById("msgText"));

将来,我们可能会发布此功能的更新,以抽象化此版本中 WebSockets 应用程序所需的一些低级别编码。

捆绑和缩小

捆绑使你可以将单个 JavaScript 和 CSS 文件合并到一个捆绑包中,这些捆绑包可以像对待单个文件一样进行处理。 缩小通过删除空格和其他不需要的字符来压缩 JavaScript 和 CSS 文件。 这些功能适用于 Web Forms、ASP.NET MVC 和网页。

捆绑包是使用 Bundle 类或其子类之一 ScriptBundle 和 StyleBundle 创建的。 配置捆绑包的实例后,只需将捆绑包添加到全局 BundleCollection 实例,即可将其提供给传入请求。 在默认模板中,捆绑包配置在 BundleConfig 文件中执行。 此默认配置为模板使用的所有核心脚本和 css 文件创建捆绑包。

使用几个可能的帮助程序方法之一从视图中引用捆绑包。 为了支持在调试与发布模式下为捆绑包呈现不同的标记,ScriptBundle 和 StyleBundle 类具有帮助程序方法 Render。 处于调试模式时,Render 将为捆绑包中的每个资源生成标记。 处于发布模式时,Render 将为整个捆绑包生成单个标记元素。 通过在 web.config 中修改编译元素的 debug 属性,可以在调试和发布模式之间切换,如下所示:

<system.web>
 <compilation targetframework="4.5" debug="true" />
 ...</system.web>

此外,可以通过 BundleTable.EnableOptimizations 属性直接设置启用或禁用优化。

BundleTable.EnableOptimizations = true;

捆绑文件时,首先按字母顺序对文件进行排序, (解决方案资源管理器) 中的显示方式。 然后组织它们,以便首先加载已知库及其自定义扩展 (,例如 jQuery、MooTools 和 Dojo) 。 例如,如上所示的 Scripts 文件夹捆绑的最终顺序为:

  1. jquery-1.6.2.js
  2. jquery-ui.js
  3. jquery.tools.js
  4. a.js

CSS 文件也按字母顺序排序,然后重新组织,以便 reset.css 和 normalize.css 先于任何其他文件。 上面所示的 Styles 文件夹捆绑的最终排序如下:

  1. reset.css
  2. content.css
  3. forms.css
  4. globals.css
  5. menu.css
  6. styles.css

Web 托管的性能改进

.NET Framework 4.5 和 Windows 8 引入了可帮助大幅提升 Web 服务器工作负载性能的功能。 这包括将启动时间和使用 ASP.NET 的 Web 托管网站的内存占用量减少高达 35% () 。

关键性能因素

理想情况下,所有网站都应处于活动状态并在内存中,以确保每当请求出现时快速响应下一个请求。 可能影响网站响应能力的因素包括:

  • 应用池回收后网站重启所需的时间。 这是在站点程序集不再位于内存中时为站点启动 Web 服务器进程所需的时间。 (平台程序集仍在内存中,因为它们由其他站点使用。) 这种情况称为“冷站点,暖框架启动”或只是“冷站点启动”。
  • 站点占用的内存量。 此术语为“每站点内存消耗”或“非共享工作集”。

新的性能改进侧重于这两个因素。

新性能功能的要求

新功能的要求可分为以下类别:

  • .NET Framework 4 上运行的改进。
  • 需要 .NET Framework 4.5 但可在任何版本的 Windows 上运行的改进。
  • 仅在 Windows 8 上运行的 .NET Framework 4.5 时可用的改进。

性能随你能够启用的每个改进级别而提高。

.NET Framework 4.5 的一些改进利用了适用于其他方案的更广泛的性能功能。

共享通用程序集

要求:.NET Framework 4 和 Visual Studio 11 开发人员预览版 SDK

服务器上的不同站点通常使用相同的帮助程序程序集 (例如,来自初学者工具包或示例应用程序) 的程序集。 每个站点在其 Bin 目录中都有其自己的这些程序集的副本。 尽管程序集的对象代码相同,但它们在物理上是独立的程序集,因此必须在冷站点启动期间单独读取每个程序集,并单独保存在内存中。

新的互插功能解决了这种低效问题,减少了 RAM 要求和加载时间。 Interning 允许 Windows 在文件系统中保留每个程序集的单个副本,并将站点 Bin 文件夹中的各个程序集替换为指向单个副本的符号链接。 如果单个站点需要程序集的不同版本,则符号链接将替换为程序集的新版本,并且只有该站点受到影响。

使用符号链接共享程序集需要一个名为 aspnet_intern.exe 的新工具,该工具可用于创建和管理实习生程序集的存储。 它作为 Visual Studio 11 开发人员预览版 SDK 的一部分提供。 但是, (,它将在仅安装 .NET Framework 4 的系统上工作,前提是你已安装了最新的 update.)

为了确保所有符合条件的程序集都已被拘留,可以定期运行aspnet_intern.exe (,例如,每周一次作为计划任务) 运行。 典型用途如下:

aspnet_intern -mode exec -sourcedir
"C:\Windows\Microsoft.NET\Framework\v4.0.30319\Temporary ASP.NET Files" -interndir C:\ASPNETCommonAssemblies

若要查看所有选项,请运行不带参数的工具。

使用多核 JIT 编译加快启动速度

要求:.NET Framework 4.5

对于冷站点启动,不仅必须从磁盘读取程序集,而且站点必须经过 JIT 编译。 对于复杂站点,这会增加显著延迟。 .NET Framework 4.5 中的一种新的常规用途技术通过跨可用处理器核心分布 JIT 编译来减少这些延迟。 它通过使用之前启动站点期间收集的信息,尽可能多地尽早执行此操作。 此功能由 System.Runtime.ProfileOptimization.StartProfile 方法实现。

ASP.NET 中默认启用使用多个核心的 JIT 编译,因此无需执行任何操作即可利用此功能。 如果要禁用此功能,请在 Web.config 文件中进行以下设置:

<configuration>
  <!-- ... -->
  <system.web>
<compilation profileGuidedOptimizations="None"  />
  <!-- ... -->

优化垃圾回收以优化内存

要求:.NET Framework 4.5

站点运行后,使用垃圾回收器 (GC) 堆可能是其内存消耗的一个重要因素。 与任何垃圾回收器一样,.NET Framework GC 在 CPU 时间 (频率和回收) 和内存消耗的重要性之间进行权衡, (用于新的、已释放或可自由) 对象的额外空间。 对于以前的版本,我们提供了有关如何配置 GC 以实现适当平衡 (的指导,例如,请参阅 ASP.NET 2.0/3.5 共享托管配置) 。

对于 .NET Framework 4.5,可以使用工作负载定义的配置设置(而不是多个独立设置),该设置支持以前建议的所有 GC 设置,以及为每站点工作集提供额外性能的新优化。

若要启用 GC 内存优化,请将以下设置添加到 Windows\Microsoft.NET\Framework\v4.0.30319\aspnet.config 文件:

<configuration>
  <!-- ... -->
  <runtime>
<performanceScenario value="HighDensityWebHosting"  />
  <!-- ... -->

(如果你熟悉前面有关更改aspnet.config的指南,请注意,此设置将替换旧设置,例如,无需设置 gcServer、gcConcurrent 等。无需删除旧设置。)

Web 应用程序的预提取

要求:.NET Framework 4.5 在 Windows 8 上运行

对于多个版本,Windows 包含一种称为 预取器 的技术,可降低应用程序启动的磁盘读取成本。 由于冷启动主要是客户端应用程序的问题,因此此技术尚未包含在 Windows Server 中,Windows Server 仅包括对服务器至关重要的组件。 预提取现已在最新版本的 Windows Server 中提供,可在其中优化单个网站的启动。

对于 Windows Server,默认情况下不启用预提取器。 若要为高密度 Web 托管启用和配置预提取器,请在命令行中运行以下命令集:

sc config sysmain start=auto
reg add "HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Control\Session Manager\Memory Management\PrefetchParameters" /v EnablePrefetcher /t REG_DWORD /d 2 /f
reg add "HKEY_LOCAL_MACHINE\Software\Microsoft\Windows NT\CurrentVersion\Prefetcher" /v MaxPrefetchFiles /t REG_DWORD /d 8192 /f
net start sysmain

然后,若要将预提取器与 ASP.NET 应用程序集成,请将以下内容添加到 Web.config 文件:

<configuration>
  <!-- ... -->
  <system.web>
<compilation enablePrefetchOptimization="true" />
  <!-- ... -->

ASP.NET Web 窗体

强类型化数据控件

在 ASP.NET 4.5 中,Web Forms包含一些处理数据的改进。 第一个改进是强类型数据控件。 对于以前版本的 ASP.NET 中的Web Forms控件,可以使用 Eval 和数据绑定表达式显示数据绑定值:

<ul>
<asp:Repeater runat="server" ID="customers">
       <ItemTemplate>
           <li>
               First Name: <%# Eval("FirstName")%><br />
               Last Name: <%# Eval("LastName")%><br />
           </li>
       </ItemTemplate>
</asp:Repeater>
</ul>

对于双向数据绑定,请使用 绑定

<asp:FormView runat="server" ID="editCustomer">
<EditItemTemplate>
       <div>
           <asp:Label runat="server" AssociatedControlID="firstName">
               First Name:</asp:Label>
           <asp:TextBox ID="firstName" runat="server"
               Text='<%#Bind("FirstName") %>' />
       </div>
       <div>
           <asp:Label runat="server" AssociatedControlID="lastName">
               First Name:</asp:Label>
           <asp:TextBox ID="lastName" runat="server"
               Text='<%#
Bind("LastName") %>' />
       </div>
       <asp:Button runat="server" CommandName="Update"/>
</EditItemTemplate>
</asp:FormView>

在运行时,这些调用使用反射读取指定成员的值,然后在标记中显示结果。 此方法可以轻松针对任意未调整的数据进行数据绑定。

但是,此类数据绑定表达式不支持成员名称的 IntelliSense、导航 ((如转到定义) )或编译时检查这些名称等功能。

为了解决此问题,ASP.NET 4.5 添加了声明控件绑定到的数据的数据类型的功能。 使用新的 ItemType 属性执行此操作。 设置此属性时,两个新的类型化变量在数据绑定表达式的范围内可用: ItemBindItem。 由于变量是强类型,因此可以获得 Visual Studio 开发体验的全部优势。

对于双向数据绑定表达式,请使用 BindItem 变量:

<asp:FormView runat="server" ID="editCustomer">
<EditItemTemplate>
       <div>
           <asp:Label runat="server" AssociatedControlID="firstName">
               First Name:</asp:Label>
           <asp:TextBox ID="firstName" runat="server"  
               Text='<%#BindItem.FirstName %>' />
       </div>
       <div>
           <asp:Label runat="server" AssociatedControlID="lastName">
               First Name:</asp:Label>
           <asp:TextBox ID="lastName" runat="server" 
               Text='<%#BindItem.LastName %>' />
       </div>
       <asp:Button runat="server" CommandName="Update"/>
</EditItemTemplate>
</asp:FormView>

ASP.NET Web Forms框架中支持数据绑定的大多数控件都已更新为支持 ItemType 属性。

模型绑定

模型绑定扩展 ASP.NET Web Forms控件中的数据绑定,以处理以代码为中心的数据访问。 它结合了 ObjectDataSource 控件和 MVC 中模型绑定 ASP.NET 的概念。

选择数据

若要配置数据控件以使用模型绑定来选择数据,请将控件的 SelectMethod 属性设置为页面代码中方法的名称。 数据控件在页面生命周期中的适当时间调用 方法,并自动绑定返回的数据。 无需显式调用 DataBind 方法。

在以下示例中, GridView 控件配置为使用名为 GetCategories 的方法:

<asp:GridView ID="categoriesGrid"
runat="server"
ItemType="WebApplication1.Model.Category"
SelectMethod="GetCategories" AutoGenerateColumns="false">
<Columns>
       <asp:BoundField DataField="CategoryID" HeaderText="ID" />
       <asp:BoundField DataField="CategoryName" HeaderText="Name" />
       <asp:BoundField DataField="Description" HeaderText="Description" />
       <asp:TemplateField HeaderText="# of Products">
           <ItemTemplate><%# Item.Products.Count %></ItemTemplate>
       </asp:TemplateField>
</Columns>
</asp:GridView>

在页面的代码中创建 GetCategories 方法。 对于简单的选择操作,该方法不需要任何参数,应返回 IEnumerableIQueryable 对象。 如果新的 ItemType 属性设置为 (启用强类型数据绑定表达式(如) 前面的 强类型数据控件 中所述),则应返回这些接口的泛型版本- IEnumerable<T>IQueryable<T>T 参数与ItemType 属性的类型匹配, (例如 IQueryable<Category>) 。

以下示例演示 GetCategories 方法的代码。 此示例将 Entity Framework Code First 模型与 Northwind 示例数据库一起使用。 该代码确保查询通过 Include 方法返回每个类别的相关产品的详细信息。 (这可确保标记中的 TemplateField 元素显示每个类别中的产品计数,而无需 n+1 select.)

public IQueryable<Category>
GetCategories()
{
    var db = new Northwind();
    return db.Categories.Include(c => c.Products);
}

页面运行时, GridView 控件会自动调用 GetCategories 方法,并使用配置的字段呈现返回的数据:

显示按类别列出的食物列表的网格视图的屏幕截图。有八种食物类别。

由于 select 方法返回 IQueryable 对象, 因此 GridView 控件可以在执行查询之前对其进行进一步操作。 例如, GridView 控件可以在执行返回的 IQueryable 对象之前添加用于排序和分页的查询表达式,以便这些操作由基础 LINQ 提供程序执行。 在这种情况下,Entity Framework 将确保在数据库中执行这些操作。

以下示例演示修改为允许排序和分页的 GridView 控件:

<asp:GridView ID="categoriesGrid"
runat="server"
AutoGenerateColumns="false"
AllowSorting="true" AllowPaging="true" PageSize="5"
ItemType="WebApplication1.Model.Category" DataKeyNames="CategoryID"
SelectMethod="GetCategories"
UpdateMethod="UpdateCategory">
<Columns>
       <asp:BoundField DataField="CategoryID" HeaderText="ID" SortExpression="CategoryID" />
       <asp:BoundField DataField="CategoryName" HeaderText="Name" SortExpression="CategoryName" />
       <asp:BoundField DataField="Description" HeaderText="Description" />
       <asp:TemplateField HeaderText="# of Products">
           <ItemTemplate><%# Item.Products.Count %></ItemTemplate>
       </asp:TemplateField>
</Columns>
<EmptyDataTemplate>No categories found with a product count of 
      <%# minProductsCount.SelectedValue %></EmptyDataTemplate>
</asp:GridView>

现在,当页面运行时,控件可以确保仅显示数据的当前页,并按所选列排序:

显示按类别列出的食物列表的网格视图的屏幕截图。有三类,糖果,调味品和饮料。

若要筛选返回的数据,必须将参数添加到 select 方法。 这些参数将在运行时由模型绑定填充,你可以在返回数据之前使用它们来更改查询。

例如,假设你想要让用户通过在查询字符串中输入关键字 (keyword) 来筛选产品。 可以将参数添加到 方法,并更新代码以使用参数值:

public IQueryable<Product>
GetProducts(string keyword)
{
    IQueryable<Product> query = _db.Products;
     
    if (!String.IsNullOrWhiteSpace(keyword))
    {
        query = query.Where(p => p.ProductName.Contains(keyword));
    }
    return query;
}

如果为关键字 (keyword) 提供值,则此代码包含 Where 表达式,然后返回查询结果。

值提供程序

前面的示例没有具体说明 关键字 (keyword) 参数的值来自何处。 若要指示此信息,可以使用参数属性。 对于此示例,可以使用 System.Web.ModelBinding 命名空间中的 QueryStringAttribute 类:

public IQueryable<Product>
GetProducts([QueryString]string keyword)
{
    IQueryable<Product> query = _db.Products;
     
    if (!String.IsNullOrWhiteSpace(keyword))
    {
        query = query.Where(p => p.ProductName.Contains(keyword));
    }
    return query;
}

这会指示模型绑定尝试在运行时将查询字符串中的值绑定到 关键字 (keyword) 参数。 (这可能涉及执行类型转换,但在这种情况下不执行。) 如果无法提供值并且类型不可为 null,则会引发异常。

这些方法的值源称为值提供程序,指示要使用的值提供程序的参数属性称为值提供程序属性。 Web Forms将包括Web Forms应用程序中所有典型用户输入源的值提供程序和相应属性,例如查询字符串、Cookie、窗体值、控件、视图状态、会话状态和配置文件属性。 还可以编写自定义值提供程序。

默认情况下,参数名称用作键,以在值提供程序集合中查找值。 在示例中,代码将查找名为 关键字 (keyword) (的查询字符串值,例如 ~/default.aspx?关键字 (keyword) =chef) 。 可以通过将自定义键作为参数传递给参数属性来指定该键。 例如,若要使用名为 q 的查询字符串变量的值,可以执行以下操作:

public IQueryable<Product>
GetProducts([QueryString("q")]string keyword)
{
    IQueryable<Product> query = _db.Products;

    if (!String.IsNullOrWhiteSpace(keyword))
    {
       query = query.Where(p => p.ProductName.Contains(keyword));
    }
    return query;
}

如果此方法位于页面的代码中,则用户可以使用查询字符串传递关键字 (keyword) 来筛选结果:

显示“我的 A S P dot Net 应用程序”页上的浏览器的屏幕截图。卡琼食品列出了两个变量。

模型绑定完成许多需要手动编码的任务:读取值、检查 null 值、尝试将其转换为适当的类型、检查转换是否成功,最后在查询中使用值。 模型绑定会导致代码少得多,并且能够在整个应用程序中重复使用该功能。

按控件中的值进行筛选

假设你想要扩展该示例,让用户从下拉列表中选择一个筛选器值。 将以下下拉列表添加到标记,并将其配置为使用 SelectMethod 属性从另一个方法获取其数据:

<asp:Label runat="server" AssociatedControlID="categories"
Text="Select a category to show products for: " />
<asp:DropDownList runat="server" ID="categories"
SelectMethod="GetCategories" AppendDataBoundItems="true"
DataTextField="CategoryName" DataValueField="CategoryID"
AutoPostBack="true">
  <asp:ListItem Value="" Text="- all -" />
</asp:DropDownList>

通常,还将向 GridView 控件添加 EmptyDataTemplate 元素,以便在找不到匹配产品时控件将显示一条消息:

<asp:GridView ID="productsGrid"
runat="server" DataKeyNames="ProductID"
AllowPaging="true" AllowSorting="true" AutoGenerateColumns="false"
SelectMethod="GetProducts" >
<Columns>
       <asp:BoundField DataField="ProductID" HeaderText="ID" />
       <asp:BoundField DataField="ProductName" HeaderText="Name"				  
            SortExpression="ProductName" />
       <asp:BoundField DataField="UnitPrice" HeaderText="Unit Price" 
            SortExpression="UnitPrice" />
       <asp:BoundField DataField="UnitsInStock" HeaderText="# in Stock" 
            SortExpression="UnitsInStock" />
</Columns>
<EmptyDataTemplate>
        No products matching the filter criteria were found</EmptyDataTemplate>
</asp:GridView>

在页面代码中,为下拉列表添加新的 select 方法:

public IQueryable<Category>
GetCategories()
{
    return _db.Categories;
}

最后,更新 GetProducts select 方法以采用包含下拉列表中所选类别 ID 的新参数:

public IQueryable<Product>
GetProducts(
[QueryString("q")] string keyword,
[Control("categories")] int? categoryId)
{
    IQueryable<Product> query = _db.Products;
     
    if (!String.IsNullOrWhiteSpace(keyword))
    {
        query = query.Where(p => p.ProductName.Contains(keyword));
    }
    if (categoryId.HasValue && categoryId > 0)
    {
        query = query.Where(p => p.CategoryID == categoryId);
    }
    return query;
}

现在,当页面运行时,用户可以从下拉列表中选择一个类别, GridView 控件会自动重新绑定以显示筛选的数据。 这是可能的,因为模型绑定跟踪所选方法的参数值,并检测回发后是否更改了任何参数值。 如果是这样,模型绑定将强制关联的数据控件重新绑定到数据。

显示按 ID、名称、单价和库存编号列出的糖果列表的网格视图的屏幕截图。

HTML 编码Data-Binding表达式

现在可以对数据绑定表达式的结果进行 HTML 编码。 在标记数据绑定表达式的 %# 前缀末尾 <添加冒号 (:) :

<asp:TemplateField HeaderText="Name">
<ItemTemplate><%#: Item.Products.Name %></ItemTemplate>
</asp:TemplateField>

不显眼的验证

现在可以将内置验证程序控件配置为对客户端验证逻辑使用不显眼的 JavaScript。 这大大减少了在页面标记中内联呈现的 JavaScript 数量,并减小了整体页面大小。 可以通过以下任一方式为验证程序控件配置不显眼的 JavaScript:

  • 通过向 Web.config 文件中的 <appSettings> 元素添加以下设置,全局:

    <add name="ValidationSettings:UnobtrusiveValidationMode" value="WebForms" />
    
  • 全局通过将静态 System.Web.UI.ValidationSettings.UnobtrusiveValidationMode 属性设置为 UnobtrusiveValidationMode.WebForms (通常在 Global.asax 文件) 的 Application_Start 方法中。

  • 通过将 Page 类的新 UnobtrusiveValidationMode 属性设置为 UnobtrusiveValidationMode.WebForms,单独针对页面。

HTML5 汇报

对Web Forms服务器控件进行了一些改进,以利用 HTML5 的新功能:

  • TextBox 控件的 TextMode 属性已更新为支持新的 HTML5 输入类型,如电子邮件日期时间等。
  • FileUpload 控件现在支持从支持此 HTML5 功能的浏览器上传多个文件。
  • 验证程序控件现在支持验证 HTML5 输入元素。
  • 具有表示 URL 的属性的新 HTML5 元素现在支持 runat=“server”。 因此,可以使用 URL 路径中的 ASP.NET 约定(如 ~ 运算符)来表示应用程序根 (例如 video <runat=“server” src=“~/myVideo.wmv” />) 。
  • UpdatePanel 控件已修复,支持发布 HTML5 输入字段。

ASP.NET MVC 4

ASP.NET MVC 4 Beta 现在包含在 Visual Studio 11 Beta 版中。 ASP.NET MVC 是一个框架,用于利用模型-视图-控制器 (MVC) 模式开发高度可测试和可维护的 Web 应用程序。 ASP.NET MVC 4 可以轻松地为移动 Web 生成应用程序,并包括 ASP.NET Web API,这有助于生成可访问任何设备的 HTTP 服务。 有关详细信息,请参阅 ASP.NET MVC 4 发行说明

ASP.NET 网页 2

新功能包括:

  • 新的和更新的网站模板。
  • 使用验证帮助程序添加服务器端和客户端 验证
  • 使用资产管理器注册脚本的功能。
  • 使用 OAuth 和 OpenID 启用从 Facebook 和其他站点登录。
  • 使用地图帮助程序添加 地图
  • 并行运行网页应用程序。
  • 为移动设备呈现页面。

有关这些功能和整页代码示例的详细信息,请参阅 网页 2 Beta 版中的热门功能

Visual Web Developer 11 Beta

本部分提供有关 Visual Web Developer 11 Beta 和 Visual Studio 2012 候选版本中 Web 开发改进的信息。

Visual Studio 2010 和 Visual Studio 2012 候选版本之间的项目共享 (Project 兼容性)

在 Visual Studio 2012 候选发布之前,在较新版本的 Visual Studio 中打开现有项目会启动转换向导。 这强制将项目和解决方案的内容 (资产) 升级到不向后兼容的新格式。 因此,转换后,无法在旧版 Visual Studio 中打开项目。

许多客户告诉我们,这不是正确的方法。 在 Visual Studio 11 Beta 中,我们现在支持使用 Visual Studio 2010 SP1 共享项目和解决方案。 这意味着,如果在 Visual Studio 2012 候选发布版中打开 2010 项目,仍可在 Visual Studio 2010 SP1 中打开该项目。

注意

Visual Studio 2010 SP1 和 Visual Studio 2012 候选发布之间不能共享几种类型的项目。 其中包括一些较旧的项目 (,例如 ASP.NET MVC 2 项目) 或用于特殊用途 (的项目,如设置项目) 。

首次在 Visual Studio 11 Beta 中打开 Visual Studio 2010 SP1 Web 项目时,以下属性将添加到项目文件:

  • FileUpgradeFlags
  • UpgradeBackupLocation
  • OldToolsVersion
  • VisualStudioVersion
  • VSToolsPath

升级项目文件的进程使用 FileUpgradeFlags、UpgradeBackupLocation 和 OldToolsVersion。 它们对在 Visual Studio 2010 中使用项目没有任何影响。

VisualStudioVersion 是 MSBuild 4.5 使用的新属性,用于指示当前项目的 Visual Studio 版本。 由于 MSBuild 4.0 中不存在此属性, (Visual Studio 2010 SP1 使用的 MSBuild 版本) ,因此我们将默认值注入项目文件。

VSToolsPath 属性用于确定要从 MSBuildExtensionsPath32 设置表示的路径导入的正确 .targets 文件。

还有一些与 Import 元素相关的更改。 为了支持 Visual Studio 的两个版本之间的兼容性,需要进行这些更改。

注意

如果在两台不同计算机上的 Visual Studio 2010 SP1 和 Visual Studio 11 Beta 之间共享项目,并且该项目在 App_Data 文件夹中包含本地数据库,则必须确保在两台计算机上安装数据库使用的SQL Server版本。

ASP.NET 4.5 网站模板中的配置更改

对使用 Visual Studio 2012 候选版本中的网站模板创建的网站的默认 Web.config 文件进行了以下更改:

  • 在 元素中<httpRuntime>encoderType,属性现在默认设置为使用添加到 ASP.NET 的 AntiXSS 类型。 有关详细信息,请参阅 AntiXSS 库
  • 此外, <httpRuntime> 在 元素中 requestValidationMode , 属性设置为“4.5”。 这意味着,默认情况下,请求验证配置为使用延迟 (“延迟”) 验证。 有关详细信息,请参阅 新的 ASP.NET 请求验证功能
  • <modules><system.webServer> 元素不包含 runAllManagedModulesForAllRequests 属性。 (其默认值为 false.) 这意味着,如果使用的是尚未更新为 SP1 的 IIS 7 版本,则可能在新站点中遇到路由问题。 有关详细信息,请参阅 IIS 7 中用于 ASP.NET 路由的本机支持

这些更改不会影响现有应用程序。 但是,它们可能表示现有网站与使用新模板为 ASP.NET 4.5 创建的新网站之间的行为差异。

IIS 7 中用于 ASP.NET 路由的本机支持

这不是对 ASP.NET 的更改,而是新网站项目的模板更改,如果你使用的是尚未应用 SP1 更新的 IIS 7 版本,可能会对你产生影响。

在 ASP.NET 中,可以将以下配置设置添加到应用程序,以支持路由:

<configuration>
  <system.webServer>
<modules runAllManagedModulesForAllRequests="true">
     <!-- more -->
</modules>
  </system.webServer>
</configuration>

runAllManagedModulesForAllRequests 为 true 时,即使 URL 上没有 .aspx.mvc 或类似的扩展,类似 URL http://mysite/myapp/home 也会转到 ASP.NET。

对 IIS 7 进行的更新使 runAllManagedModulesForAllRequests 设置变得不必要,并支持本机 ASP.NET 路由。 (有关更新的信息,请参阅Microsoft 支持部门文章提供更新,使某些 IIS 7.0 或 IIS 7.5 处理程序能够处理其 URL 不以句点结尾的请求。)

如果网站在 IIS 7 上运行并且 IIS 已更新,则无需将 runAllManagedModulesForAllRequests 设置为 true。 事实上,不建议将其设置为 true,因为这会增加请求的不必要的处理开销。 如果此设置为 true,则所有请求(包括 针对.htm.jpg和其他静态文件的请求)也会通过 ASP.NET 请求管道。

如果使用 Visual Studio 2012 RC 中提供的模板创建新的 ASP.NET 4.5 网站,则网站的配置不包括 runAllManagedModulesForAllRequests 设置。 这意味着默认情况下,该设置为 false。

如果随后在未安装 SP1 的 Windows 7 上运行网站,IIS 7 将不会包含所需的更新。 因此,路由将不起作用,你将看到错误。 如果遇到路由不起作用的问题,可以执行以下操作之一:

  • 将 Windows 7 更新到 SP1,这将将更新添加到 IIS 7。
  • 安装前面列出的Microsoft 支持部门文章中所述的更新。
  • 在该网站的Web.config文件中,将 runAllManagedModulesForAllRequests 设置为 true。 请注意,这会为请求增加一些开销。

HTML 编辑器

智能任务

在“设计”视图中,服务器控件的复杂属性通常具有关联的对话框和向导,以便于对其进行设置。 例如,可以使用特殊对话框将数据源添加到 Repeater 控件或向 GridView 控件添加列。

但是,对于复杂属性,此类 UI 帮助在“源”视图中不可用。 因此,Visual Studio 11 引入了“源”视图的智能任务。 智能任务是 C# 和 Visual Basic 编辑器中常用功能的上下文感知快捷方式。

对于 ASP.NET Web Forms控件,当插入点位于 元素内时,智能任务在服务器标记上显示为小字形:

当插入点位于 元素内时,显示服务器标记作为小字形的屏幕截图。

单击字形或按 Ctrl+时,智能任务将展开。 (点) ,就像在代码编辑器中一样。 然后,它显示与“设计”视图中的“智能任务”类似的快捷方式。

显示“网格视图任务”窗口的屏幕截图。

例如,上图中的智能任务显示了 GridView 任务选项。 如果选择“编辑列”,将显示以下对话框:

显示“字段”对话框的屏幕截图。

填充对话框中设置可在设计视图中设置的相同属性。 单击“确定”时,控件的标记将更新为新设置:

显示使用新设置更新的控件标记的屏幕截图。

WAI-ARIA 支持

编写可访问的网站变得越来越重要。 WAI-ARIA 辅助功能标准定义了开发人员应如何编写可访问的网站。 Visual Studio 现在完全支持此标准。

例如, 角色 属性现在具有完整的 IntelliSense:

显示列表中突出显示为 Role 属性的菜单项的屏幕截图。

WAI-ARIA 标准还引入了前缀为 aria 的属性 ,使你可以向 HTML5 文档添加语义。 Visual Studio 还完全支持以下 aria- 属性:

显示 aria 属性的屏幕截图。在属性列表中选择“Aria 删除效果”。显示已选择副本的 aria drop 效果属性的屏幕截图。

新的 HTML5 代码片段

为了更快、更轻松地编写常用的 HTML5 标记,Visual Studio 包含许多代码片段。 视频片段就是一个示例:

显示选中的 Visual Studio 视频片段的屏幕截图。

若要调用代码片段,请在 IntelliSense 中选择元素时按 Tab 两次:

显示 IntelliSense 中选择的元素“文件”的屏幕截图。

这会生成一个可以自定义的代码片段。

提取到用户控件

在大型网页中,最好将各个部分移动到用户控件中。 这种形式的重构有助于提高页面的可读性,并可以简化页面结构。

为简化此操作,在源视图中编辑Web Forms页面时,现在可以选择页面中的文本,右键单击它,然后选择“提取到用户控件”:

显示上下文菜单中选中“提取到用户控件”的屏幕截图。

特性中代码 Nugget 的 IntelliSense

Visual Studio 始终为任何页面或控件中的服务器端代码块提供 IntelliSense。 现在,Visual Studio 还包含用于 HTML 属性中的代码块的 IntelliSense。

显示列表中选择了“查询字符串”的屏幕截图。

这样可以更轻松地创建数据绑定表达式:

显示已选中“Java 脚本字符串编码”的屏幕截图。

重命名开始或结束标记时自动重命名匹配的标记

例如,如果将 HTML 元素重命名为 (,则将 div 标记更改为 标头 标记) ,则相应的开始或结束标记也会实时更改。

显示开始和结束标记实时更改的屏幕截图。突出显示了 Heade 一词。

这有助于避免忘记更改结束标记或更改错误标记的错误。

事件处理程序生成

Visual Studio 现在在“源”视图中包含功能,可帮助你编写事件处理程序并手动绑定它们。 如果在“源”视图中编辑事件名称,IntelliSense 将显示 <“创建新事件>”,这将在页面的代码中创建具有正确签名的事件处理程序:

显示“源视图”中插入点处的“创建新事件”的屏幕截图。

默认情况下,事件处理程序将使用 控件的 ID 用作事件处理方法的名称:

显示控件的 ID 的屏幕截图,表示事件处理方法的名称。

在本例中,生成的事件处理程序将如下所示 (C#) :

显示 C sharp 生成的事件处理程序的屏幕截图。

智能缩进

在空 HTML 元素内按 Enter 时,编辑器会将插入点放在正确的位置:

显示两个 H T M L 元素之间的插入点的屏幕截图。

如果在此位置按 Enter,则结束标记将向下移动并缩进以匹配开始标记。 插入点也缩进:

显示结束标记向下移动并缩进以匹配开始标记的屏幕截图。插入点也缩进。

自动减少语句完成

Visual Studio 中的 IntelliSense 列表现在根据键入的内容筛选,以便仅显示相关选项:

显示 IntelliSense 列表中选择的单词映射的屏幕截图。

IntelliSense 还基于 IntelliSense 列表中各个单词的标题大小写进行筛选。 例如,如果键入“dl”,将显示 dl 和 asp:DataList:

显示已选择 d l 的屏幕截图,因为它已键入。

此功能可更快地获取已知元素的语句补全。

JavaScript 编辑器

Visual Studio 2012 候选版本中的 JavaScript 编辑器是全新的,它极大地改进了在 Visual Studio 中使用 JavaScript 的体验。

代码大纲显示

现在会自动为所有函数创建大纲区域,从而折叠与当前焦点无关的文件部分。

大括号匹配

将插入点放在左大括号或右大括号上时,编辑器会突出显示匹配的插入点。

转到定义

使用“转到定义”命令,可以跳转到函数或变量的源。

ECMAScript5 支持

编辑器支持 ECMAScript5 中的新语法和 API,ECMAScript5 是描述 JavaScript 语言的最新版本的标准。

DOM IntelliSense

针对 DOM API 的 IntelliSense 已得到改进,支持许多新的 HTML5 API,包括 querySelector、DOM 存储、跨文档消息传递和 画布。 DOM IntelliSense 现在由单个简单的 JavaScript 文件驱动,而不是由本机类型库定义驱动。 这使得扩展或替换变得容易。

VSDOC 签名重载

现在,可以使用新的 <签名> 元素为 JavaScript 函数的单独重载声明详细的 IntelliSense 注释,如以下示例所示:

function GetOrSet(key, value) {
/// <signature>
///	 <summary>Gets the value</summary>
///	 <param name="key" type="String">The key to get the value for</param>
///	 <returns type="String" />
/// </signature>
/// <signature>
///	 <summary>Sets the value</summary>
///	 <param name="key" type="String">The key to set the value for</param>
///	 <param name="value" type="String">The value to set</param>
///	 <returns type="MyLib" />
/// </signature>
    if (value) {
        values[key] = value;
        return this;
    } else {
        return values[key];
    }
}

隐式引用

现在可以将 JavaScript 文件添加到中央列表,该列表将隐式包含在任何给定 JavaScript 文件或块引用的文件列表中,这意味着你将获得 IntelliSense 的内容。 例如,可以将 jQuery 文件添加到文件中心列表,并且无论是否使用 /// <reference />) 显式引用 jQuery 函数,你都可以在任何 JavaScript 文件块中 (获取 jQuery 函数的 IntelliSense。

CSS 编辑器

自动减少语句完成

CSS 的 IntelliSense 列表现在根据所选架构支持的 CSS 属性和值进行筛选。

显示键入 radiu 时,在 C S 的 IntelliSense 列表中选择了边框半径的屏幕截图。

IntelliSense 还支持游戏大小写搜索:

屏幕截图显示了在 f w 之后选择的字体粗细。

分层缩进

CSS 编辑器使用缩进来显示分层规则,从而概述了级联规则的逻辑组织方式。 在以下示例中,选择器#list是列表的级联子级,因此是缩进的。

显示缩进列表示例的屏幕截图。

以下示例演示更复杂的继承:

显示其他变量列表的屏幕截图。

规则的缩进由其父规则决定。 默认情况下启用分层缩进,但你可以禁用它“选项”对话框 (“工具”,菜单栏中的“选项”) :

显示“选项”对话框的屏幕截图。选中分层缩进。

CSS 黑客支持

对数百个真实 CSS 文件的分析表明,CSS 黑客非常常见,现在 Visual Studio 支持最常用的攻击。 此支持包括 IntelliSense 和验证star (*) 和下划线 (_) 属性黑客:

显示列表中所选高度的屏幕截图。

还支持典型的选择器黑客,因此即使在应用分层缩进时也能保持。 用于面向 Internet Explorer 7 的典型选择器黑客是,在选择器前面添加 *:first-child + html。 使用该规则将维护分层缩进:

显示典型选择器黑客示例的屏幕截图。

特定于供应商的架构 (-moz-, -webkit)

CSS3 引入了许多由不同浏览器在不同时间实现的属性。 以前,这迫使开发人员使用特定于供应商的语法为特定浏览器编写代码。 这些特定于浏览器的属性现在包含在 IntelliSense 中。

显示 IntelliSense 中选择了 m s 自动换行的屏幕截图。

注释和取消注释支持

现在,可以使用在代码编辑器中使用的相同快捷方式来注释和取消注释 CSS 规则, (Ctrl+K,C 注释,Ctrl+K,取消注释) 。

颜色选取器

在早期版本的 Visual Studio 中,颜色相关属性的 IntelliSense 由命名颜色值的下拉列表组成。 该列表已替换为功能齐全的颜色选取器。

输入颜色值时,将自动显示颜色选取器,并显示以前使用的颜色列表,后跟默认调色板。 可以使用鼠标或键盘选择颜色。

显示以前使用的颜色列表的屏幕截图,后跟默认调色板。

可以将列表展开为完整的颜色选取器。 通过选取器,可以在移动不透明度滑块时自动将任何颜色转换为 RGBA 来控制 alpha 通道:

显示颜色选取器在移动不透明度滑块时自动将任何颜色转换为 R G B A 的屏幕截图。

代码片段

CSS 编辑器中的代码片段可以更轻松、更快地创建跨浏览器样式。 许多需要特定于浏览器的设置的 CSS3 属性现在已滚动到代码片段中。

显示 C S S 编辑器中的代码片段的屏幕截图。选择了“轻松退出”的单词。

CSS 代码片段通过键入显示 IntelliSense 列表的 at-symbol (@) 来支持 CSS3 媒体查询) 等高级 (方案。

显示在 IntelliSense 列表中选择的媒体处的屏幕截图。

选择 @media 值并按 Tab 时,CSS 编辑器将插入以下代码片段:

显示选择了 1024 p x 的代码片段的屏幕截图。

与代码片段一样,可以创建自己的 CSS 代码片段。

自定义区域

命名代码区域(已在代码编辑器中提供)现在可用于 CSS 编辑。 这使你可以轻松地对相关的样式块进行分组。

显示代码编辑器的屏幕截图。使用的样式块用于区域菜单。

折叠区域时,它会显示区域的名称:

显示菜单区域折叠的屏幕截图。

Page Inspector

Page Inspector是一种工具,用于在 Visual Studio IDE 中呈现 html、Web Forms、ASP.NET MVC 或网页) (网页,并可用于检查源代码和生成的输出。 对于 ASP.NET 页,Page Inspector可以确定哪个服务器端代码生成了呈现给浏览器的 HTML 标记。

显示 Visual Studio 代码的屏幕截图。右窗格包含源代码,左窗格呈现网页。

有关Page Inspector的详细信息,请参阅以下教程:

发布

发布配置文件

在 Visual Studio 2010 中,Web 应用程序项目的发布信息不存储在版本控制中,并且不用于与他人共享。 在 Visual Studio 2012 候选发布中,发布配置文件的格式已更改。 它已成为团队项目,现在可以轻松地从基于 MSBuild 的生成中利用。 生成配置信息位于“发布”对话框中,因此你可以在发布前轻松切换生成配置。

发布配置文件存储在 PublishProfiles 文件夹中。 文件夹的位置取决于所使用的编程语言:

  • C#:Properties\PublishProfiles
  • Visual Basic:我的项目\PublishProfiles

每个配置文件都是一个 MSBuild 文件。 在发布期间,此文件将导入到项目的 MSBuild 文件中。 在 Visual Studio 2010 中,如果要对发布或打包过程进行更改,则必须将自定义项放在名为 ProjectName.wpp.targets 的文件中。 这仍受支持,但现在可以将自定义项放在发布配置文件本身中。 这样,自定义项将仅用于该配置文件。

现在还可以利用 MSBuild 中的发布配置文件。 为此,请在生成项目时使用以下命令:

msbuild.exe project.csproj /t:WebPublish /p:PublishProfile=ProfileName

project.csproj 值是项目的路径,ProfileName 是要发布的配置文件的名称。 或者,可以传入发布配置文件的完整路径,而不是传递 PublishProfile 属性的配置文件名称。

ASP.NET 预编译和合并

对于 Web 应用程序项目,Visual Studio 2012 候选发布版在“包/发布 Web 属性”页上添加了一个选项,用于在发布或打包项目时预编译和合并网站内容。 若要查看这些选项,请右键单击解决方案资源管理器中的项目,选择“属性”,然后选择“包/发布 Web”属性页。 下图显示了“发布前预编译此应用程序”选项。

屏幕截图显示若要查看“包/发布 Web 属性”页的选项,请右键单击解决方案资源管理器中的项目,选择“属性”,然后选择“包/发布 Web”属性页。

选择此选项后,每当发布或打包 Web 应用程序时,Visual Studio 都预编译应用程序。 如果要控制站点的预编译方式或程序集的合并方式,请单击“高级”按钮配置这些选项。

IIS Express

用于在 Visual Studio 中测试 Web 项目的默认 Web 服务器现在IIS Express。 Visual Studio 开发服务器仍然是开发过程中本地 Web 服务器的一个选项,但IIS Express现在是推荐的服务器。 在 Visual Studio 11 Beta 中使用 IIS Express 的体验与在 Visual Studio 2010 SP1 中使用它非常相似。

免责声明

这是一份初稿,并可能在本文所述软件最终商业发布之前进行大幅更改。

本文档中包含的信息代表 Microsoft Corporation 在发布之日对所讨论问题的当前观点。 由于 Microsoft 必须响应不断变化的市场条件,因此不应将其解释为 Microsoft 作出的承诺,并且 Microsoft 无法保证在发布日期之后提供的任何信息的准确性。

本白皮书仅用于提供信息。 MICROSOFT 对本文档中的信息不做任何明示、暗示或法定的担保。

用户有责任遵守所有适用的版权法/著作权法。 在不限制版权所辖权利的前提下,未经 Microsoft Corporation 的明确书面许可,本文档的任何部分不得被复制、存储或引进检索系统,或者以任何形式、任何方式(电子、机械、影印、录音等)或为任何目的进行传播。

Microsoft 可能拥有本文档所涵盖主题的专利、专利申请、商标、版权或其他知识产权。 除非 Microsoft 提供了明确的书面许可协议,否则提供本文档并不意味着赋予您这些专利、商标、版权或其他知识产权的任何许可。

除非另有说明,否则此处描述的示例公司、组织、产品、域名、电子邮件地址、徽标、人员、地点和事件都是虚构的,不应与任何真实的公司、组织、产品、域名、电子邮件地址、徽标、人员、地点或事件关联,也不应推断。

(C) 2012 Microsoft Corporation。 保留所有权利。

Microsoft 和 Windows 是 Microsoft Corporation 在美国和/或其他国家/地区的注册商标或商标。

此处提到的真实公司和产品的名称可能是其各自所有者的商标。