服务端渲染技术基本原理
关于服务端渲染,其实这种思想和方案很早就有了。
使用传统的JSP、PHP等动态语言,某种意义上来说,就是服务端渲染。当然,这种情况下,ajax的使用还不多,往往是后台直接将数据写入模板,想想Spring中经典的ModelAndView,数据直接接入到jsp中,最终jsp运行时生成servlet,将完整的页面和数据输出给客户端。一步到位。
随着ajax技术的兴起,这种“后台包办”的模式就不那么流行了,不仅难以维护,而且前端和后端开发人员往往难以聚焦自己的本职工作。前后台分离的思想则迅速普及。我们看看前后台分离的模式下,客户端和服务端交互的流程,以及如何使用服务端渲染技术。
模式一:前后台分离
前后台分离的模型下,客户端和服务端交互的大概流程如下
流程如下:
1、浏览器请求html页面
2、浏览器请求CSS文件
3、浏览器请求JS文件
4、执行js代码,发出ajax请求从服务端获取数据
5、数据绑定,页面渲染
这种模式目前非常通用,对于普通的页面,基本上也没有什么问题。但是对于复杂页面,如果追求性能和用户体验,则有诸多可以优化的地方。
1、对于复杂的页面,ajax请求会非常多,这是比较耗时的操作
2、浏览器必须等待js文件下载完成之后才能执行js代码,进而发起ajax请求,ajax请求依赖于js文件的下载。
模式二:数据直出
流程如下:
1、浏览器请求html页面
2、服务端接收到请求后,提前执行ajax请求,将ajax请求的数据和html页面一并返回给客户端(可以在html页面中插入script标签并将数据添加到全局变量window上,或者放在某些标签的data属性中)
3、浏览器请求CSS文件
4、浏览器请求JS文件
5、js代码中判断是否已经有了某个ajax请求的数据,如果有则直接进行数据绑定渲染操作,如果没有则再发起ajax请求
这种模式可以减少客户端大量的ajax请求,能显著提高性能。当然,如果在服务端发起大量ajax请求获取数据,这也许也是耗时的操作,但是我们可以提前发起这些请求,将带有ajax请求数据的html页面提前缓存起来。
模式三:服务端渲染
模式三与模式二相比,是把数据绑定和页面渲染的操作也放在了服务端执行,相比模式二的优势则是:不必等待浏览器下载完js文件后再执行数据绑定和页面渲染,从而进一步提升了性能。
三种模式的比较
从理论上来说,模式三是对模式二的进一步优化,性能会得到进一步提升。但是这已经不是“刚需”了,模式二对模式一的提升效果才是最可观的,因为减少了大量的网络请求,这是性能提升的关键所在。
无论是采用模式二还是模式三,对于部分ajax请求的数据,我们还是必须以模式二的方式返回给客户端(挂在全局变量window上,或者写在标签的data属性中),因为还有个重点,就是恢复页面的“上下文”。
页面的上下文,以angular1 为例,就是$scope所承载的页面(组件)当前的状态。可以试想,正常情况下,客户端一个ajax请求执行完后,很可能会给$scope赋值,那么现在经过服务端渲染的优化,客户端不会执行这个ajax请求了,但是却也必须以某种手段来恢复$scope中原本该有的数据。
这里我们形象一点描述,就是一个数据的“序列化/反序列化”的过程,服务端将ajax请求的数据“序列化”,并挂在window全局变量上返回给客户端,客户端“反序列化”数据,恢复页面上下文。
注意事项
从原理上来说,服务端渲染也并不复杂,但是真正实施起来,却是有诸多问题值得考虑。
1、对于一般的开发人员来说,他们并不感知服务端渲染,不应该或者尽可能小地给开发人员带来额外的约束。
2、服务器端如何发起ajax请求并执行数据绑定和页面渲染?这等于在服务器端模拟了浏览器的行为,那么这个引擎该如何去设计,就是一个重点问题。
3、平台的差异性。同样一段js代码在浏览器能正确运行,但是在服务端则可能不一样,比如服务器端不存在window对象,不存在sessionStorage等BOM对象,甚至普通的ajax请求,在服务器端是不能直接执行的,往往需要构造httpclient去发起这个请求。
4、客户端如何方便地恢复页面上下文?客户端如何判断是否拥有了ajax请求的数据?这个工作一般的开发人员应该是不感知的,开发人员不必去为恢复页面上下文增加额外的代码,也不必判断数据是否存在,是否需要发起ajax请求,这些逻辑应该从统一解决,对开发人员屏蔽。
等等.....
前景与展望
幸运的是,服务器渲染技术也在迅速发展。
Node.js的流行,V8引擎的强力支持,不少前端框架已经开始考虑兼容服务端渲染,比如React就已经提供了非常方便的API,同一套前端代码可以方便地在服务端执行。Angular2在服务端渲染方便也比之前有了很大的提升。isomorphic javascript的提出与普及,浏览器和服务器可以共用同一套javascript代码,这些都给服务端渲染带来了极大的便利。
具体技术还需要深入研究。
- 点赞
- 收藏
- 关注作者
评论(0)