Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

第十八周 2018-04-26 #18

Open
sunhengzhe opened this issue Apr 26, 2018 · 1 comment
Open

第十八周 2018-04-26 #18

sunhengzhe opened this issue Apr 26, 2018 · 1 comment

Comments

@sunhengzhe
Copy link
Member

sunhengzhe commented Apr 26, 2018

本周因为要调研主站前端的重构方案,着重看了一下关于 Web 应用渲染模式的文章。
刚学前端的时候也会很疑惑,为什么 ajax 这么流行,我们还非得把前后端都混在一起,前后端分离不是一件很理所应当的事情么?事实上,前后端完全分离是有适用场景的,比如中后台系统。但对偏展示类的系统如电商网站等,SEO 和首屏渲染能力是需要重点考虑的,而这正是前后端分离的劣势。参考 Web 前后端分离的意义大吗?徐飞的回答。虽然是 3 年前的回答,但还是非常有启发性。

说到目前 Web 应用渲染的形式,大概也就是三种:客户端渲染(CSR)和服务端渲染(SSR),以及介于两者之间或者说结合两者的同构应用(isomorphic web apps)。

客户端渲染

客户端渲染是近些年流行的渲染模式,单页应用(SPA)就是一种典型的客户端渲染。服务端只提供简单的 HTML 骨架,页面主要内容全部使用 JS 生成,包括路由也是由前端控制。

优点

  1. 前端开发效率较高
  2. 成熟的技术方案
  3. 二次加载快

缺点

  1. SEO 不友好
    页面内容是通过 js 生成的

    • 可以考虑专门做页面给搜索引擎
  2. 首屏性能
    需要等待 js 加载完成才能 viewable and interactable

    • 代码分拆、按需加载
    • 优化体验:Skeleton Screen

服务端渲染

服务端渲染是长久以来流行的渲染模式,如 php 的 smarty、node 的 ejs 等。DOM 结构由服务端提供,JS 只负责处理交互。

缺点

  1. 第一字节时间(TTFB)速度比 CSR 更慢
    需要耗费时间生成 HTML 与必要数据

  2. 服务器数据吞吐量要远低于 CSR

优点

  1. SEO
  2. 首屏渲染比 CSR 快
  3. 成熟的技术方案

同构应用

同构应用结合了 CSR 和 SSR,特点是同一份代码能够在客户端和服务端执行。老实讲前面这句话几乎在所有文章里都写了,但很少有文章会具体讲实现原理。一般来说,我们讨论同构应用,目前考虑的都是 react / vue + nodejs,因为同构应用的核心在于 虚拟 DOM。以 react 举例,当虚拟 DOM 应用于 web 端,就成为了 react,应用于 APP,就有了 react-native,应用于服务端,就有了同构应用。参考 Webpack实战-构建同构应用going-isomorphic-with-react

当请求到达服务端,服务端会计算虚拟 DOM,并生成 HTML 文本吐到前端,因为是同样的 DOM 结构,前端继续使用 react 进行后续的操作。参考 React Redux Sever Rendering(Isomorphic JavaScript)入門

由于同构需要引入 node 中间层,所以会有一定的运维风险和开发门槛。

关于 SSR 和 CSR 的比较,参考 前后端渲染之争聊一聊服务端渲染和客户端渲染

@ShaofeiZi
Copy link

个人感觉SSR和同构解决的方案差别不大都是去解决三个问题

  • 帮助网络爬虫(SEO)
  • 支持低带宽或低功耗设备
  • 快速加载首屏

同构应用的核心我认为是在Render而不是虚拟 DOM ,虚拟 DOM只是其中一个方法

还有一个问题是如何引用浏览器独有的原生对象,比如 window、document、navigator 或 location
目前大部分解决方案是写一个自己的抽象层,当在浏览器中运行时,就把它委托给浏览器 API,当在服务器中运行时,就提供一个符合要求的代用实现。这方面我感觉是个大坑,尤其是首屏幕显示后直接操作
而且由于没有鼠标或键盘事件,所以同构的应用也不能依赖于用户点击某个按钮来显示每个组件。
我认为同构应用应该仅仅根据客户端过来的请求决定要渲染的内容。 把应用做成可路由的。

由于服务端渲染页面的用户只能点击链接,所以应该尽快让它切换到真正的客户端应用,以提供正常的交互体验。如何去加载。也是个坑。

还有HTTP2之后模块如何分包。。

附上之前做的angular的SSR
node版本 https://github.com/ShaofeiZi/angulrUniversal
.netcore版本 https://github.com/ShaofeiZi/dotnetng2

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants