前言:

最近做一个地图展示页面,业务初期没什么问题,运行一阵后报错:

Error during serialization or deserialization using the JSON JavaScriptSerializer.
The length of the string exceeds the value set on the maxJsonLength property.

Google 了一下,原来是由于业务数据的增多, ajax 后台返回时报错,参考网上的方法,在返回时设置一下 MaxJsonLength

            var jsonResult = Json(jsonString);
jsonResult.MaxJsonLength = int.MaxValue;
return jsonResult;

报错的问题是解决了,可还有一个问题就是页面加载时间过长。为了地图展示的效果,不能进行数据分页。

期间尝试了很多方法,记录如下:

 列表与地图同步:

页面的布局是左边显示数据列表,右边显示 GoogleMap 。刚开始拼列表的 html 和地图的初始化、加载是在同一个方法里面执行的,这样的效果就是列表和地图同时显示,由于地图的初始化、加载比较耗时,就想让列表先显示,地图初始化完后再显示。也就是列表显示和地图初始化同步执行,改后代码:

                    if(pageData.length>0){
SetListHtml(1);
$("#loadGif").hide();
setTimeout(function () {SetMap();}, 0);
}
else{
$("#loadGif").hide();
}
 存储过程和缓存:

列表与地图同步可以让用户的体验好一些,但是页面加载时间还是过长,于是就把后台取数据改成存储过程、把一些不是经常改变的数据做成缓存。在做缓存的过程中,由于不是经常改变的数据有时也会改变,因此缓存依赖要设成 SqlCacheDependency 。具体方法网上有很多。

        public DataTable GetCacheGpsBoundary()
{
string cacheKey = "dtCustomerBoundary";
DataTable dtCustomerBoundary = (DataTable)HttpRuntime.Cache.Get(cacheKey);
if (dtCustomerBoundary == null)
{
log.Debug("dtCustomerBoundary从数据库中获取");
dtCustomerBoundary = new DataTable();
string sql = "";
SqlCacheDependency sqlCacheDependency = null;
string connectionString = ConfigurationManager.AppSettings[""];
using (SqlConnection cn = new SqlConnection(connectionString))
{
using (SqlCommand cmd = cn.CreateCommand())
{
cn.Open();
cmd.CommandText = sql;
sqlCacheDependency = new SqlCacheDependency(cmd);
//当有DML操作时,onChange事件会接收来自Sql Server通过sq_DispatcherProc存储过程发送给应用程序的消息。
using (SqlDataAdapter adapter = new SqlDataAdapter()) //查询数据
{
adapter.SelectCommand = cmd;
adapter.Fill(dtCustomerBoundary);
}
}
}
HttpContext.Current.Cache.Insert(cacheKey, dtCustomerBoundary, sqlCacheDependency);
}
else
{
log.Debug("dtCustomerBoundary从缓存中获取");
}
return dtCustomerBoundary;
}
 GZip压缩:

存储过程和缓存在本机测试的确加快了页面加载速度,可是发布到服务器后页面加载速度还是不理想。想分析具体原因在哪里,在网上找到一个工具:

HttpWatch Basic 9.2
Copyright: Copyright 2002 -2014 Simtec Limited
Version: 9.2.6

先看下图例颜色的意义:

我理解 Wait 就是服务器执行用时, Receive 就是传输用时。

没有加存储过程和缓存:

再来看下改成存储过程和加缓存后

最后是启用 GZip 后的图

通过 HttpWatch 我们可以看出压缩后数据的大小 853424 ,为压缩前 4309641 的 19.80% 、用时也由 8.623 缩短到 3.119 ,由于服务器当前资源、网络情况等每次时间会有所不同。

启用 GZip 压缩后,服务器和客户端 CPU 负担会加大,但对页面加载速度效果还是很明显的,刚开始通过 HttpWatch 看出是由于传输数据过大使页面加载时间过长时,就想到要用压缩,可在后台 ajax 方法中对返回的 Json 字符串 采用 GZipStream 压缩后,在前台 JavaScript 一直找不到好的方法去解压,尝试了很多加解压算法 Zlib、LZString 等等,加解压的时间都太长了,没什么效果。

看了 单程列车博客上 .NET MVC 简单实现GZIP  后在后台添加一个 Filter 就可以实现服务端 gzip 压缩,客户端会自动解压,客户端 ajax 时可能要加一句

headers: { "Accept-Encoding" : "gzip" } ,其实我觉得 ajax 就是异步的去打开某一网页。

 总结:

分析、看清问题,找到问题真实原因,才有可能找到好的解决方法;

刚开始想在取数据这块优化,看 sql 的执行计划看的一头雾水,今年要买些数据库优化方法的书补补;

对 JavaScript、HTTP、C#、MVC、SQL 等等掌握的是否系统、全面在综合运用时起着决定性的作用

解决一个问题的时候还是很高兴的。

 参考:

http://stackoverflow.com/questions/5692836/maxjsonlength-exception-in-asp-net-mvc-during-javascriptserializer

http://www.cnblogs.com/zhaojingjing/archive/2011/01/20/1940357.html

http://www.cnblogs.com/willick/p/3331520.html

HTTP权威指南

最新文章

  1. [NOIP2011] 聪明的质检员(二分答案)
  2. Visual studio 2013安装
  3. shell学习笔记1
  4. ubuntu中磁盘挂载与卸载
  5. mybatis + postgresql 遇到的问题
  6. 学渣上手 LaTeX 完成毕业论文
  7. 微信JS-SDK 接口调用与 php 遇到的坑
  8. java.lang.ClassCastException: org.springframework.web.filter.CharacterEncodingFilter cannot be cast to javax.servlet.Filter
  9. 菜鸟的jQuery源码学习笔记(二)
  10. [译]Java 设计模式之命令
  11. CentOS配置本地yum源
  12. mysql数据库内容相关操作
  13. Linux搭建SVN环境
  14. 使用while和read命令读取文件内容
  15. 每日英语:Got a Case of the Mondays? Blame the Sunday Blues
  16. Java堆外内存管理
  17. python3异常处理 try
  18. No.11 selenium学习之路之浏览器大小
  19. bootstrap-table 分页增删改查之一(分页)
  20. MVC4中control的增删改查

热门文章

  1. 一个厂区宿舍管理后台密码爆破 - selenium版
  2. 【redis】配置优化及从库优先级
  3. $forceUpdate和this.$set('userInfo',name,'小红');
  4. windows搭建minikube环境学习Kubernates
  5. #Cisco——配置链路聚合
  6. JavaScript 静态方法
  7. 092_Schema获取表字段的方式
  8. Linux系统Shell脚本第一章:Shell脚本基础及时间同步
  9. TypeScript的super
  10. 如何将视频作为Windows桌面动态壁纸,两步就可以搞定!