`
foxty
  • 浏览: 137160 次
  • 性别: Icon_minigender_1
  • 来自: 深圳
社区版块
存档分类
最新评论

[原创]Ajax和LazyLoad的冲突

阅读更多
  如果你的项目中同时使用了ajax和orm工具,那你就应该注意这篇文章,或许你也碰到过这个问题。

  乍一看标题,或许很多人都很迷糊,ajax和orm的lazyload有什么关系,那里来的冲突?是啊,乍一看,一个是前端,一个是后端,基本没有关系的,怎么就有了冲突。如果你使用了remote call调用服务器端方法,并且得到返回的po的时候,就很有可能出现这种问题。

  先看看lazyload的含义,lazyload是为了防止n+1问题同时节省资源的一种做法,比如,我有一张用户表(user),一张订单表(order),一张货物表(item), user和order是1:N的关系,order和item假设1:1的关系。当我们使用orm工具的时候,一般可能会这么定义, user对象中存在一个由order对象组成的Set或List,而order和item之间还各存在一个Item和Orer对象。正常情况下,取得一个user对象的时候,如果不需要相关的order信息,只要不去显示访问order列表的get方法,orm工具是不会去加载和当前user对象关联的order列表的。当我们要这些order信息的时候,仅仅访问其get(Java) 方法或者其属性(.Net),orm工具会自动的帮我们加载这些对象。

  但是不幸的是,如果你通过ajax的remotecall来得到一个User对象,那么你的lazyload就会失控了。我们知道现在的 ajax框架都是支持remotecall的(据我所知),它的一个好处就是客户端js可以直接访问服务器端方法,并且ajax框架能够以一种协议将服务器端返回的po对象转换成js对象。那么在回到刚才所提到的User对象,当通过remotecall得到一个User对象的时候,ajax框架会遍历User对象的get方法或者属性同时生成一个纯js的object,,在遍历的过程中,它会把加载该user的ordet列表,order关联Item,Item也被加载了。Lazyload就会在你意向不到的情况下失效了。

  如果你对象中存在树的结构,那么这里就会无限制的一直加载下去,直到把整棵树全部加载完毕,而且可能你还根本不知道会有这个问题。正是今天碰到这个奇怪并隐讳的问题,花费了我几个小时的时间,才真正的找出根本原因。

  建议大家在使用ajax的同时尽量少使用这种方式,尽量使用更新局部页面的办法,而不是通过remotecall获得po,动态生成dom。有一个解决的办法就是,把需要lazyload的属性以及访问方法都设置成private,另外通过其他方法来调用。这样就能避免转换对象的时候导致你的lazyload失效。
分享到:
评论
28 楼 nihongye 2007-05-11  
sorphi 写道
>>如果产生json有更简洁有效的方式,不需要xml-to-json那当然更好了。在这方面我是个新手,请多指点哦

我大概比你还新,去看看

http://www.iteye.com/topic/78243


谢谢推荐,我说的是在服务端如何更好的object to json。
27 楼 sorphi 2007-05-11  
>>如果产生json有更简洁有效的方式,不需要xml-to-json那当然更好了。在这方面我是个新手,请多指点哦

我大概比你还新,去看看

http://www.iteye.com/topic/78243
26 楼 nihongye 2007-05-11  
sorphi 写道
nihongye 写道
我们使用webwork action处理请求,然后返回velocityXML result type(使用velocity生成xml)。如果客户端组件需要json格式.再加上xml to json的拦截器


为什么不根据需要返回不同的格式,而要使用昂贵的chain filter呢?

不知道ajax是否可以设置http header,action根据accept content type 来选择输出不同的格式。



再回复顶楼的原帖,如果不使用open session in view,不知道ajax的remote call时如何会导致lazyload失效(lazy load exception不发生)。或者说我对这个ajax框架如何使用OSIV感到迷惑,remote call不应该利用到OSIV机制才对啊


因为用脚本产生xml很方便。昂贵的chain filter?多了一层xml-to-json,对于我们的应用应该是不昂贵的。
如果产生json有更简洁有效的方式,不需要xml-to-json那当然更好了。在这方面我是个新手,请多指点哦
25 楼 sorphi 2007-05-11  
nihongye 写道
我们使用webwork action处理请求,然后返回velocityXML result type(使用velocity生成xml)。如果客户端组件需要json格式.再加上xml to json的拦截器


为什么不根据需要返回不同的格式,而要使用昂贵的chain filter呢?

不知道ajax是否可以设置http header,action根据accept content type 来选择输出不同的格式。



再回复顶楼的原帖,如果不使用open session in view,不知道ajax的remote call时如何会导致lazyload失效(lazy load exception不发生)。或者说我对这个ajax框架如何使用OSIV感到迷惑,remote call不应该利用到OSIV机制才对啊
24 楼 huangpengxiao 2007-05-11  
什么AJAX框架?
23 楼 nihongye 2007-05-11  
我们使用webwork action处理请求,然后返回velocityXML result type(使用velocity生成xml)。如果客户端组件需要json格式.再加上xml to json的拦截器
22 楼 hexiaodong 2007-05-11  
我的建议是,把裁剪工作放在web层,毕竟是由web层来负责展示的,所以它更清楚该取哪些属性,哪些关联对象。所以lazyload要用,opensessioninview也要开启。
21 楼 JJYAO 2007-05-10  
这不是Ajax的问题,而是Lazy loading使用的Scope的问题

Lazy loading机制(opensessioninview)是不能用在稍微复杂的企业系统中的
看似方便,走了捷径,其实破坏了固有的分层结构,把本该属于持久层的机制四处传播,同时也带来了很多风险,会影响其他的功能
主要体现在
1. LZ所说的web remote
2. Cluster环境session对象序列化的问题(现在越来越多的框架会根据一顶的策略,把状态维护在session中)
3. xml-java object serialize和Deserialize
4. 将来的其它RIA技术

所以,从系统总结架构考虑,我是坚决杜绝使用将lazy机制扩散到service层以外的。
我的建议是web层存在一个剪裁过的VO,与Service层的PO完成自动数据的复制(手工 or 基于元数据描述)

但不可否认,lazy loading在适当的场合还是能发挥其作用的
20 楼 qianjinfu 2006-10-24  
引用
做了一些关于ajax的web应用,确实感觉到项目中如果要大量使用ajax的话,需要一个很完善的MVC框架同时结合服务器端的MVC框架一起,我觉得就很不错了。


的确~,现在做的项目js端就是MVC结构,不过没有C这一层
项目是前台纯用HTML,js实现的~
后台 (DWR)+Facade - Service -  DAO
facade层完全用来组装页面需要的DTO的
19 楼 zgd 2006-09-29  
用remote就应该准备相应的DTO

另,lazy load和open session in view本来就是罪恶的东西
18 楼 foxty 2006-09-28  
hexiaodong 写道
foxty 写道
其实很多时候并不是需不需要要一个js高手的问题,现在的一些应用并不涉及到多深的js技术问题,很多类库都已经提供了很好的调用,而是设计思路或者说解决方法的问题。

假如你要做的系统有复杂的用户交互界面,那么我看你不大可能完全用现成js包,来完成所有界面。桌面应用开发领域的MFC够强了吧,但是你如果不能熟练调用windows api,你还是写不出具备良好交互性的界面,或者说因为MFC的限制,让你某些界面上的想法实现不了。何况,现成的js包远没有MFC库来得强大
迄今为止,我还没有遇到想你所说的需求,大部分的应用,现在的js类库也可以胜任了.

17 楼 hexiaodong 2006-09-28  
foxty 写道
其实很多时候并不是需不需要要一个js高手的问题,现在的一些应用并不涉及到多深的js技术问题,很多类库都已经提供了很好的调用,而是设计思路或者说解决方法的问题。

假如你要做的系统有复杂的用户交互界面,那么我看你不大可能完全用现成js包,来完成所有界面。桌面应用开发领域的MFC够强了吧,但是你如果不能熟练调用windows api,你还是写不出具备良好交互性的界面,或者说因为MFC的限制,让你某些界面上的想法实现不了。何况,现成的js包远没有MFC库来得强大
16 楼 foxty 2006-09-27  
hexiaodong 写道
foxty 写道
不好意思,可能我的描述不是很准确--“操作生成dom”

我所说的生成dom就是利用js动态生成html。

我们从服务器端获取dto用来干什么? 获取数据不就是为了展示么?这种情况下,你能避免不用js来生成html吗?

我并不反对通过js来获取服务器端dto对象,而是说尽量避免,当你从服务器端获取dto并展示给客户端的时候,用一堆js来生成html代码,然后在放到某个div中,你就会知道这种方法有多么的难调试,难维护了。

用js固然少不了dom操作,但希望楼主明白我得意思,我的意思是尽量避免,而不是不做。


强烈建议开发团队中有至少一个js高手,不然就不要提ajax了。那样只会让你更低生产效率,而不是更高。成为js高手不是你想得那么难,利用google,你可以搜到无数的源码用来学习。


其实很多时候并不是需不需要要一个js高手的问题,现在的一些应用并不涉及到多深的js技术问题,很多类库都已经提供了很好的调用,而是设计思路或者说解决方法的问题。
15 楼 foxty 2006-09-27  
Nicholas_Ding 写道
foxty 写道
不好意思,可能我的描述不是很准确--“操作生成dom”

我所说的生成dom就是利用js动态生成html。

我们从服务器端获取dto用来干什么? 获取数据不就是为了展示么?这种情况下,你能避免不用js来生成html吗?

我并不反对通过js来获取服务器端dto对象,而是说尽量避免,当你从服务器端获取dto并展示给客户端的时候,用一堆js来生成html代码,然后在放到某个div中,你就会知道这种方法有多么的难调试,难维护了。

用js固然少不了dom操作,但希望楼主明白我得意思,我的意思是尽量避免,而不是不做。


我理解你的意思了,给你点思路吧。
采用一个模版引擎,封装一个好的调用方式。

一个大概的调用过程是这样:
1、请求服务器某个 action 获取数据,最好是 json 的。(异步)
2、请求服务器获取 html 模版(同步),将模版存到本地缓存(用JS实现一个),使用数据渲染模版,加到某个 div 中去。
3、根据操作再去走第一步。

这是一个简易的框架,我们项目目前在使用,使用 Trimpath JavaScript 可以达到模版的效果,并不需要自己用 js 操作 dom,让 JST 帮你做,这样更自然。

AJAX 需要一个合理的客户端 MVC 编程框架,至少我们现在的项目自己动手做了一个,有了规范适合大家一起做开发。


你说的这种方式也跟我现在采取的方式差不多,不过我是将页面需要变动的地方分成了几个块,客户端一般情况下只需要异步请求服务器端的action来替换对应的块就可以了。

做了一些关于ajax的web应用,确实感觉到项目中如果要大量使用ajax的话,需要一个很完善的MVC框架同时结合服务器端的MVC框架一起,我觉得就很不错了。

14 楼 Nicholas_Ding 2006-09-27  
foxty 写道
不好意思,可能我的描述不是很准确--“操作生成dom”

我所说的生成dom就是利用js动态生成html。

我们从服务器端获取dto用来干什么? 获取数据不就是为了展示么?这种情况下,你能避免不用js来生成html吗?

我并不反对通过js来获取服务器端dto对象,而是说尽量避免,当你从服务器端获取dto并展示给客户端的时候,用一堆js来生成html代码,然后在放到某个div中,你就会知道这种方法有多么的难调试,难维护了。

用js固然少不了dom操作,但希望楼主明白我得意思,我的意思是尽量避免,而不是不做。


我理解你的意思了,给你点思路吧。
采用一个模版引擎,封装一个好的调用方式。

一个大概的调用过程是这样:
1、请求服务器某个 action 获取数据,最好是 json 的。(异步)
2、请求服务器获取 html 模版(同步),将模版存到本地缓存(用JS实现一个),使用数据渲染模版,加到某个 div 中去。
3、根据操作再去走第一步。

这是一个简易的框架,我们项目目前在使用,使用 Trimpath JavaScript 可以达到模版的效果,并不需要自己用 js 操作 dom,让 JST 帮你做,这样更自然。

AJAX 需要一个合理的客户端 MVC 编程框架,至少我们现在的项目自己动手做了一个,有了规范适合大家一起做开发。
13 楼 hexiaodong 2006-09-27  
foxty 写道
不好意思,可能我的描述不是很准确--“操作生成dom”

我所说的生成dom就是利用js动态生成html。

我们从服务器端获取dto用来干什么? 获取数据不就是为了展示么?这种情况下,你能避免不用js来生成html吗?

我并不反对通过js来获取服务器端dto对象,而是说尽量避免,当你从服务器端获取dto并展示给客户端的时候,用一堆js来生成html代码,然后在放到某个div中,你就会知道这种方法有多么的难调试,难维护了。

用js固然少不了dom操作,但希望楼主明白我得意思,我的意思是尽量避免,而不是不做。


强烈建议开发团队中有至少一个js高手,不然就不要提ajax了。那样只会让你更低生产效率,而不是更高。成为js高手不是你想得那么难,利用google,你可以搜到无数的源码用来学习。
12 楼 foxty 2006-09-27  
不好意思,可能我的描述不是很准确--“操作生成dom”

我所说的生成dom就是利用js动态生成html。

我们从服务器端获取dto用来干什么? 获取数据不就是为了展示么?这种情况下,你能避免不用js来生成html吗?

我并不反对通过js来获取服务器端dto对象,而是说尽量避免,当你从服务器端获取dto并展示给客户端的时候,用一堆js来生成html代码,然后在放到某个div中,你就会知道这种方法有多么的难调试,难维护了。

用js固然少不了dom操作,但希望楼主明白我得意思,我的意思是尽量避免,而不是不做。
11 楼 Nicholas_Ding 2006-09-27  
foxty 写道
我并不觉得是java把简单的事情复杂化了。

而是本来就能够各自很好运行的机制,放到一起发生了冲突。Service facade是个解决冲突的办法,但是我觉得不太爽,本来很好的lazyloading机制,到了这里确要被一刀给砍断。

还有一个就是避免出现这种情况,尽量不要用 ajax获得服务器端对象,虽然这种方式很新潮,可是我不喜欢,因为获得了服务器端对象就说明肯定要动态生成dom,js来生成dom可是一件很麻烦的事情,难调试,难维护。所以我在项目中尽量都是只更新局部,把整个页面分成几个区域(几个块),需要更新那块,就直接一个Ajax.Updater("id","xx.action")就可以了,而且调试和维护都远比操作dom简单。


麻烦解释下什么叫操作生成dom?
用js获得服务器端的DTO是一个非常常见的做法,你硬是要批判它我觉得很幼稚。获得对象跟生成DOM我不清楚有什么联系在里面。再说,AJAX = Asynchronized JavaScript And XML,你用js的时候我不信你不进行任何dom操作。
10 楼 foxty 2006-09-26  
我并不觉得是java把简单的事情复杂化了。

而是本来就能够各自很好运行的机制,放到一起发生了冲突。Service facade是个解决冲突的办法,但是我觉得不太爽,本来很好的lazyloading机制,到了这里确要被一刀给砍断。

还有一个就是避免出现这种情况,尽量不要用 ajax获得服务器端对象,虽然这种方式很新潮,可是我不喜欢,因为获得了服务器端对象就说明肯定要动态生成dom,js来生成dom可是一件很麻烦的事情,难调试,难维护。所以我在项目中尽量都是只更新局部,把整个页面分成几个区域(几个块),需要更新那块,就直接一个Ajax.Updater("id","xx.action")就可以了,而且调试和维护都远比操作dom简单。

9 楼 Nicholas_Ding 2006-09-26  
foxty 写道

不好意思,听说过JSON但一直没有用过,能举个简单的例子么?

我先猜测一下,如果不对请指正:
  是自己实现Serializer,Deserializer吗?如何来判断某个属性是否需要Serialize?如果一个对象中关联了多个对象,那么客户端可能会有多种情况:可能会都不laod,可能会只load A或者load B或者AB都load,那又如何来判断究竟是那种情况?


很多情况下都是Java把简单的事情弄复杂了。
AJAX 不需要 Lazy Loading,或者说和 Hibernate 提供的不太一样,Robbin 说的没错,最好的做法就是用 DTO,用一个 Serivce Facade。

json 几乎成为了 ajax 通讯的标准协议,注意,Java 有类型并不说明其他语言也一定要带有类型,做 ajax 有时你会发现带类型是个累赘。Java 的话建议用一下 DWR 试试。

相关推荐

    lazyload-2.x.zip

    在当今网页开发中,为了提高页面加载速度和用户体验,"懒加载"(Lazy Load)技术变得越来越重要。jQuery LazyLoad插件是一个广泛使用的解决方案,它允许图片、iframe等元素在进入浏览器视口时才开始加载,从而显著...

    jQuery_lazyload

    jQuery_lazyload设计得相当灵活,可以与大部分其他jQuery插件和前端框架(如Bootstrap)良好协作。 7. **优化技巧**: - 结合CSS媒体查询,针对不同设备和屏幕尺寸设置不同的延迟加载策略。 - 使用WebP或SVG等...

    JQuery Lazyload加载图片实例

    **jQuery Lazyload 图片加载技术详解** 在网页设计中,图片是重要的元素之一,但大量图片的预加载可能会拖慢页面的加载速度,影响用户体验。为了解决这一问题,jQuery 提供了一个插件——jQuery Lazyload,它允许...

    jquery.lazyload.js

    5. **易于集成和定制**:作为基于jQuery的插件,jQuery.Lazyload.js拥有丰富的API和配置选项,开发者可以根据需求进行定制,实现不同的加载效果,如预加载、动画效果等。 在实际应用中,jQuery.Lazyload.js的使用...

    lazyload.js演示页面

    标签“lazyload”和“延迟加载”进一步确认了这个压缩包内容的核心是关于延迟加载技术的实践。在网页开发中,延迟加载是一种节省带宽、提高页面响应速度的重要手段,尤其对于移动设备来说,可以有效减少数据消耗。 ...

    jQuery.lazyload-1.7.2

    2. **异步加载**:如果页面中同时使用了其他异步加载资源(如AJAX),确保正确配置插件以避免冲突。 3. **初始化**:在文档加载完成后,需要调用`.lazyload()`方法来启动插件。如果你的图片是在动态插入的,可能...

    lazyload使用案例及DEMO

    2. **JavaScript配置**:引入`lazyload.js`和`jquery.js`,确保jQuery库已经加载。然后,通过调用`lazyload`函数来初始化插件: ```javascript $(function() { $("img.lazyload").lazyload(); }); ``` 这行...

    图片延迟加载 lazyload

    4. **自定义事件和扩展**:jQuery.lazyload 允许开发者自定义加载事件和扩展功能,如在图片加载完成后执行某些操作,或者与其他库和框架集成。 5. **优化提示**:为了确保所有浏览器都能正确工作,建议为低版本...

    jquery lazyload延时加载

    1. **引入 jQuery 和 LazyLoad**:首先确保页面中已经引入了 jQuery 库,然后引入 LazyLoad 的 JavaScript 文件,如 `jquery.lazyload.js`。 2. **设置 HTML 结构**:给需要延时加载的图片添加特定的类名(如 `lazy...

    懒加载lazyload

    `tuupola-jquery_lazyload` 这个压缩包可能包含了这两个库的源代码以及相关的示例(demo),帮助开发者理解和使用这个插件。 要使用 `jquery.lazyload.js`,首先确保在页面中引入了 jQuery 和插件本身。通常,我们...

    magento lazyload插件

    它的主要功能是实现图片的延迟加载(Lazy Load),以此提升网站的加载速度和用户体验。在网页浏览时,传统方式下所有图片会一次性全部加载,这可能导致页面加载时间过长,特别是对于拥有大量图片的电商网站来说,这...

    JQuery LazyLoad 图片懒加载实例

    **jQuery LazyLoad 图片懒加载实例** 在网页设计中,图片加载是影响页面性能的关键因素。当页面包含大量图片时,一次性加载所有图片可能会导致页面加载速度变慢,用户体验下降。为了解决这一问题,我们可以使用`...

    动态加载的图片LazyLoad

    1. **更新JQuery和JQuery.LazyLoad**:确保使用的是最新稳定版本,以获得更好的浏览器兼容性和修复已知问题。 2. **调试和检查代码**:使用浏览器的开发者工具检查JavaScript错误,定位可能导致问题的代码段。 3. **...

    jQuery.lazyload.js

    Lazy Load 是一个用 JavaScript 编写的 jQuery 插件. 它可以延迟加载长页面中的图片. 在浏览器可视区域外的图片不会被载入, 直到用户将页面滚动到它们所在的位置. 这与图片预加载的处理方式正好是相反的. 在包含很多...

    lazyload延迟加载

    Lazyload是通过延迟加载来实现按需加载,达到节省资源,加快浏览速度的目的。 网上也有不少类似的效果,这个Lazyload主要特点是: 支持使用window(窗口)或元素作为容器对象; 对静态(位置大小不变)元素做了大量...

    lazyload.js实现图片异步延迟加载

    `lazyload.js`还提供了`load`和`error`事件,可以监听图片加载成功和失败: ```javascript lazyLoadInstance.on('load', function(event) { console.log('Image loaded:', event.target); }); lazyLoadInstance....

    图片延迟加载,lazyload.js使用实例

    总之,`lazyload.js`是一个实用的图片延迟加载解决方案,通过简单地配置和使用,可以有效地提升网页性能,减少用户等待时间,同时还能降低服务器带宽消耗。在实际开发中,结合最佳实践和合理的配置,可以最大化地...

    lazyload-JavaScript

    在网页开发中,图片懒加载(Lazy Load)是一种优化用户体验和提高页面加载速度的技术。"lazyload"是指在JavaScript中实现的延迟加载策略,它只在用户滚动到视口附近的图片时才加载图片,而不是在页面初次渲染时一次...

Global site tag (gtag.js) - Google Analytics