我一直在研究和研究并尝试优化我使用asp.net C#用户控件构建的应用程序(它最终将转移到MVC / Angular / Razor,但是现在它必须保持为用户控件)。
在我的本地计算机上,我的平均页面生成时间约为150 - 500毫秒。哪个很好。一旦它上升到服务器,加载时间气球到600 - 1200毫秒。一旦考虑了下载速度,响应时间,延迟等等,客户就会看到1.5s-2.2s的DOM就绪页面。我的目标是在.7 - 1.2s DOM就绪区域进行这些时间。
以下是本地主机上的页面加载时间细分:
Page PreInit: 0 | 0
BindData: 58 | 58
Content Page Loaded: 2 | 60
Master Page Fixed: 0 | 60
Binding Child: 150 | 210
Bind Data Completed: 0 | 210
Page Rendered: 74 | 284
这是在服务器上加载的完全相同的页面:
Page PreInit: 0 | 0
BindData: 401 | 401
Content Page Loaded: 8 | 409
Master Page Fixed: 0 | 409
Binding Child: 108 | 517
Bind Data Completed: 0 | 517
Page Rendered: 356 | 873
我得知我的LINQ to SQL调用正在减慢BindData()函数的速度,我愿意接受340ms的速度减慢,因为服务器运行的网站超过15个。我不打算增加更多。
困扰我的是从BindData()函数结束到Page_PreRenderComplete事件的时间。与生产服务器上的356ms加载时间相比,我们有74ms的加载时间。令我感到困惑的是,将页面转换为HTML需要花费5倍的时间。
任何帮助都会非常感激。谢谢!
作为一个注释,我的本地主机通过IIS运行,指向127.0.0.1的网站。两台服务器(本地和生产)都运行IIS 7.5。我的应用程序的发行版本有debug =“false”,两者都设置为在ASP.net 4.6.1中运行
完整的ASPX页面代码
请原谅秒表的东西。这就是我可以弄清楚减速发生的位置。
public partial class Page_Content : BasePage
{
public string loadTime = "<pre>";
public decimal elapsed = 0;
public System.Diagnostics.Stopwatch timer = new System.Diagnostics.Stopwatch();
protected void Page_PreInit(object sender, EventArgs e)
{
timer.Start();
loadTime += String.Format("{0, 25}: {1, 4} | {2, 4}<br />", "Page PreInit", timer.ElapsedMilliseconds - elapsed, timer.ElapsedMilliseconds);
elapsed = timer.ElapsedMilliseconds;
}
protected void Page_PreRenderComplete(object sender, EventArgs e)
{
timer.Stop();
loadTime += String.Format("{0, 25}: {1, 4} | {2, 4}<br />", "Page Rendered", timer.ElapsedMilliseconds - elapsed, timer.ElapsedMilliseconds);
elapsed = timer.ElapsedMilliseconds;
lblTime.Text = loadTime + "</pre>";
}
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
BindData();
}
protected void BindData()
{
loadTime += String.Format("{0, 25}: {1, 4} | {2, 4}<br />", "BindData", timer.ElapsedMilliseconds - elapsed, timer.ElapsedMilliseconds);
elapsed = timer.ElapsedMilliseconds;
string imgURL = "";
string mobileURL = "";
var cp = contentService.GetContentPage(cpName, true, false);
if (cp != null)
{
loadTime += String.Format("{0, 25}: {1, 4} | {2, 4}<br />", "Content Page Loaded", timer.ElapsedMilliseconds - elapsed, timer.ElapsedMilliseconds);
elapsed = timer.ElapsedMilliseconds;
var _master = (CMS.Master)this.Master;
if (_master != null)
_master.SetPageClass(String.Format("content-page page-{0}", cp.Name));
loadTime += String.Format("{0, 25}: {1, 4} | {2, 4}<br />", "Master Page Fixed", timer.ElapsedMilliseconds - elapsed, timer.ElapsedMilliseconds);
elapsed = timer.ElapsedMilliseconds;
ctrlContent.item = cp;
ctrlContent.OverWriteSEO = true;
ctrlContent.BindData();
loadTime += String.Format("{0, 25}: {1, 4} | {2, 4}<br />", "Binding Child", timer.ElapsedMilliseconds - elapsed, timer.ElapsedMilliseconds);
elapsed = timer.ElapsedMilliseconds;
if (settingService.GetSettingValueByNameBool("Media.ContentPiece.ShowHeaderImage", false))
{
if (cp.ImageID.HasValue)
{
imgURL = pictureService.GetPictureUrl(cp.ImageID.Value, settingService.GetSettingValueByNameInt("Media.Carousel.ImageSize", 1000));
mobileURL = pictureService.GetPictureUrl(cp.ImageID.Value, settingService.GetSettingValueByNameInt("Media.Carousel.Mobile.ImageSize", 768));
}
loadTime += String.Format("{0, 25}: {1, 4} | {2, 4}<br />", "Pictures Loaded", timer.ElapsedMilliseconds - elapsed, timer.ElapsedMilliseconds);
elapsed = timer.ElapsedMilliseconds;
if (!string.IsNullOrEmpty(imgURL))
{
pnlMainImage.Visible = true;
pnlMainImage.Attributes.Add("style", String.Format("background-image: url('{0}')", imgURL));
pnlMainMobile.Visible = true;
pnlMainMobile.Attributes.Add("style", String.Format("background-image: url('{0}')", mobileURL));
pnlPageHeader.CssClass = "image-header-adjust inner-bound";
}
}
loadTime += String.Format("{0, 25}: {1, 4} | {2, 4}<br />", "Bind Data Completed", timer.ElapsedMilliseconds - elapsed, timer.ElapsedMilliseconds);
elapsed = timer.ElapsedMilliseconds;
}
else
Response.Redirect("~/");
}
public string cpName
{
get
{
return globalService.QueryString("ID");
}
}
}
更新
在检查后做了一些修改后,感谢@ sh1rts,我发现有一些不必要的数据库往返行程。我已经最小化了这些,并获得了显着的改进。但是,似乎leach显然是应用程序将LINQ转换为SQL并从数据库返回集合所花费的时间。我假设这意味着我的生产数据库返回的值比我的dev DB慢。任何有关优化该连接的帮助都将受到赞赏。
这是新时代(平均.8s - 1.2s到DOM-Ready)
Page PreInit: 0 | 0
Bind Data Fired: 298 | 298
Content Page Loaded: 7 | 305
Binding User Control: 11 | 316
Bind Data Completed: 0 | 316
Page Rendered: 151 | 467