在react中,同构应用指的是在客户端和服务端之间完整或者部分共享代码的应用,也可以被称为通用JavaScript应用;同构应用并不是不需要浏览器端渲染内容,而是使服务端和浏览器端渲染达到一种平衡,在服务器上生成渲染内容,让用户尽早看到有信息的页面。
本教程操作环境:Windows10系统、react17.0.1版、Dell G3电脑。
同构应用也被称为通用`JavaScript`应用,指的是在客户端和服务器端之间完整(或部分)地共享代码的应用。通过在服务器端运行应用的JavaScript代码,页面可在发送到浏览器之前预先填充内容,所以用户甚至可以在浏览器JavaScript运行之前就看到内容。当本地的JavaScript运行时,它会接手后续的交互及导航操作,通过快速初始化加载和服务端页面渲染,让用户在单页应用程序中得到流畅的交互体验。
什么是同构
随着Node.js的异军突起,前后端开发有了归一化编程语言的基础土壤,页面模版、第三方依赖机制等都有实现前后端统一的契机。React率先引领了这种潮流,同构的概念也因此得以更广泛的传播。
需要读者明白的是,同构应用并不是不需要浏览器端渲染内容,而是使服务端和浏览器端渲染达到一种平衡。那么,怎么理解这种平衡呢?
在服务器上生成渲染内容,让用户尽早看到有信息的页面。一个完整的应用除包括纯粹的静态内容以外,还包括各种事件响应、用户交互等。这就意味着在浏览器端一定还要执行JavaScript脚本,以完成绑定事件、处理异步交互等工作。
从性能及用户体验上来看,服务端渲染应该表达出页面最主要、最核心、最基本的信息;而浏览器端则需要针对交互完成进一步的页面渲染、事件绑定等增强功能。所谓同构,就是指前后端共用一套代码或逻辑,而在这套代码或逻辑中,理想的状况是在浏览器端进一步渲染的过程中,判断已有的DOM结构和即将渲染出的结构是否相同,若相同,则不重新渲染DOM结构,只需要进行事件绑定即可。
从这个维度上讲,同构和服务端渲染又有所区别,同构更像是服务端渲染和浏览器端渲染的交集,它弥补了服务端和浏览器端的差异,从而使得同一套代码或逻辑得以统一运行。同构的核心是“同一套代码”,这是脱离于两端角度的另一个维度。
同构的优势和劣势
同构的优势如下:
更好的性能。这里的性能主要指渲染更加迅速、首屏展现的时间更快、文件更少,以及文件体积更小。
SEO优化支持。服务端接收到请求后,会返回一个相对完整、包含了初始内容的HTML文档,所以更有利于搜索引擎爬虫获取信息,提高搜索结果展现排名。同时,更快的页面加载时间也有利于搜索结果展现排名的提升。
实现更加灵活。服务端渲染只是直出页面的初始内容,浏览器端仍然需要做后续工作,以完成页面的最终展现。这样服务端渲染和浏览器端渲染仍可以平衡,在很大程度上也能实现代码复用。
可维护性更强。因为借助React等类库,我们完全能够实现大范围的代码复用,避免了服务端和浏览器端同时维护两套代码或逻辑。因此,整体代码量更少,维护成本更低。
对于低端机型更加友好。因为内容的初步渲染是在服务端完成的,所以对于低端机型更加友好,不至于页面加载时出现白屏幕的状况。
对于恶劣的网络环境更加友好。传统的前后端分离方式,在所有的JavaScript脚本下载并执行完毕后,才会呈现页面内容,中间经历了较多的网络请求,在恶劣的网络环境下,无疑增加了页面呈现基本内容的难度。在这方面,同构应用显然更有优势。
更好的用户体验。为了更加合理地平衡服务端和浏览器端渲染内容,我们可以将页面重要的核心部分设计在服务端完成,而次重要的交互部分可以在更重要的内容渲染完毕后,由浏览器端渲染或实现,这将有力地提升用户体验。
同构的劣势如下:
服务端处理的逻辑增多,增加了复杂性。
服务端无法完全复用浏览器端代码。
增加了服务端的TTFB(Time To First Byte)时间。TTFB时间指的是从浏览器发起最初的网络请求,到从服务器接收到第一个字节的这段时间。它包含了TCP连接时间、发送HTTP请求的时间和获得响应消息的第一个字节的时间。因为对数据的获取和对页面初始内容的渲染,势必会降低服务端返回的速度。
扩展知识:
前后端架构设计和服务端渲染概念
服务端渲染或直出的概念越来越流行。在了解如何基于React实现服务端渲染之前,我们有必要在架构层面对服务端渲染的“前世今生”进行整体了解:为什么会出现这样一个概念;这个概念落地之后能解决什么问题;服务端渲染和其他方式对比有何利弊等。
前后端配合技术的演进
早期的Web开发,架构设计简单、直接,具体来讲,就是页面由JSP、PHP等工程师在服务端生成,浏览器只负责展现。那时候,前端工程师只需要给静态页面添加一些动态交互效果,很少会涉及数据逻辑等;而后端工程师负责页面内容,即当用户请求页面时,后端进行处理并返回完整的静态页面。这些过程一般会依靠模板引擎来完成。因此,在那个时候,甚至没有独立的前端工程师职位。即使有的话,这种做法的缺点也很明显,比如前后端分工职责不清。
如果由前端人员来开发模板,那么前端将会极度依赖后端环境,难以实现开发效率的最大化,同时关于数据格式的沟通成本也相对较高。另外,这样的架构模式对于前端技术的发挥和利用浏览器能力的空间是非常有限的。
随着前端技术的飞速发展,尤其是AJAX和Node.js等技术的出现,一种前后端分离的架构模式应运而生。在这种模式下,前后端分工变得非常清晰,两端的关键协作点是AJAX接口。下面我们以用户访问页面为例来一步步了解这种模式,如下图所示。