让我通过调查情况来澄清这一点,假设您有这样的看法;
@renderSection("Header")
@using (var context = SetUpSomeContext()) {
<div>
Some content here
@RenderBody();
</div>
}
@renderSection("Footer")
我们假设 razor 按照您期望的顺序执行页面,如果我们声明我们的视图会发生什么?
@{
Layout = null;
}
<div>@SomethingThatDependsOnContextBeingSetUp()</div>
在执行@RenderBody()之前,Razor 不会知道该视图是否需要布局页面。此外,它会推断它无缘无故渲染了布局页面,这是不合理的。所以这不是实际发生的情况。
当请求发出时,Razor 首先执行视图的主体是很自然的。如果您的视图未像我的演示 Razor 中那样指定布局,则仅呈现该页面的输出并停在那里。如果视图在执行视图后在您的代码中指定了布局,它将控制权传递给布局页面。(布局页面从自上而下)所以布局页面剩下的只是内容放置。当它看到@RenderBody()时,它只放置您已经执行的视图的输出。
对于部分;当您的视图主体执行时,它们不会被执行,在您的视图将控制权传递给布局页面后,布局页面会按照声明的顺序显式调用您的部分的执行。
另请注意,您在视图正文中指定了页面标题,并且它在布局标题标记(ViewBag.Title)中呈现。执行视图正文后,在视图正文中声明的所有变量都可以在布局页面中使用。
Sum:渲染顺序是从上到下,但执行顺序不同。
对于您的情况:“SomethingThatDependsOnContextBeingSetUp 在 SetUpSomeContext 之前执行并失败”。就像我说的,这是 Razor 执行周期的自然行为,视图主体在布局页面执行之前执行。当你让它成为部分时; 首先执行视图主体,但在布局页面之前不执行部分。视图主体将控制权传递给布局页面,布局页面开始从上到下渲染,如果看到@RenderSection,则调用部分的执行。因此在这种情况下执行 SetUpSomeContext在SomethingThatDependsOnContextBeingSetUp执行之前。