你会经常听到开发人员谈论 "静态 "与 "动态 "网站,或者你可能听到有人使用_Jamstack_这个术语_。_这些术语是什么意思?"静态 "网站何时会变成Jamstack或动态网站?这些问题听起来很简单,但它们比表面上更有细微差别。让我们来探讨这些术语,以获得对Jamstack的更深理解。
寻找界限
椅子和凳子之间有什么区别?大多数人都会回答,椅子有四条腿和背部支撑,而凳子有三条腿,没有背部支撑。
资料来源:Rumman Amin
图源:Rumman Amin
好吧,这是一个很好的出发点,但是这些呢?
图源:瓦列里-佐林
椅子变得越像凳子,就越少有人会明确地同意它是一把椅子。最终,我们将达到一个大多数人同意它是凳子而不是椅子的程度。这听起来可能是一个愚蠢的练习,但如果我们想深入了解作为一把椅子的含义,这是一个有价值的练习。我们发现对大多数人来说,椅子的极限在哪里。我们也建立了对灰色地带的理解。最终,我们达到了这样的地步:即使是最大的铁杆椅子迷也会认输,承认他们面前的是一张凳子。
尽管椅子很有趣,但这是一篇关于网站交付技术的文章。让我们对静态、动态和Jamstack网站进行同样的练习。
在一个高层次上
当你用浏览器访问一个网站时,有很多事情在幕后进行。
- 你的浏览器执行DNS查询,把域名变成一个IP地址。
- 它从该IP地址请求一个HTML文件。
- 网络服务器发回请求的文件。
- 当浏览器渲染网页时,它可能会遇到一个资产的参考,如一个CSS、JavaScript或图像文件。然后,浏览器对该资产进行请求。
- 这个循环一直持续到浏览器获得该网页的所有文件。一个网页发出50多个请求是很平常的。
对于每一个请求,网络服务器的响应总是一个静态文件,即使是在一个动态网站上。你可以把这些文件保存在USB驱动器上,把它们通过电子邮件发给朋友,就像你电脑上的其他文件一样。
当比较静态和动态时,我们谈论的是网络服务器正在做什么**。**在一个静态网站上,浏览器请求的文件已经存在于网络服务器上。网络服务器将它们原封不动地送回来。在动态网站上,响应是由软件生成的。这个软件可能连接到数据库来检索数据,从模板文件中建立一个布局,并在页脚添加今天的日期。它为每个请求做所有这些工作。
这就是静态和动态网站的基本区别。
Jamstack的作用在哪里?
静态网站是有限制的。它们对于信息性网站来说是很好的;然而,根据定义,你不能有任何动态内容或行为。Jamstack模糊了静态和动态之间的界限。我们的想法是利用静态网站的所有优势,同时在必要时实现动态功能。
Jamstack中的 "堆栈 "是一个错误的说法。事实是,Jamstack根本就不是一个堆栈。它是一种哲学,与AWS良好架构框架的5大支柱有着惊人的相似之处。这个术语的模糊性导致了社区对Jamstack的含义进行了广泛的讨论。
什么是Jamstack?
Jamstack是静态的一个超集。但要真正理解Jamstack,让我们从导致该术语诞生的种子开始。
2002年,已故的Aaron Swartz发表了一篇题为"烘烤,不要煎炸 "的博客文章。虽然Aaron没有创造 "Bake, Don't Fry",但这是我第一次发现有人认识到静态网站的好处,同时打破了人们对这个词的认知限制。
我关心的是不需要维护古怪的AOLserver、Postgres和Oracle安装。我关心的是能不能用scp来备份东西。我关心的是不需要做任何安装或配置就可以把我的网站转移到一个新的服务器。我关心的是如何独立于平台和服务器。
如果我们翻阅历史,我们可以发现类似的挫折,导致了Jamstack的种子。
-
Ben和MenaTrott创造了MovableType,因为他们对现有的博客内容管理系统感到满意--性能、稳定性。
-
Tom Preston-Werner创建Jekyll是为了摆脱复杂性
:我已经知道很多我不想要的东西。我已经知道我不想要什么了。我已经厌倦了像WordPress和Mephisto这样复杂的博客引擎。我想写出好的文章,而不是写出无数的模板页面,一天到晚调节评论,并不断地落后于最新的软件发布。
-
Steve Francia创建Hugo是为了提高性能
:在过去的几年里,这个博客一直由wordpress[原文如此]和drupal驱动。两者都是很好的软件,但随着时间的推移,我越来越失望,因为它们都是为编写内容而优化的,尽管最常见的用法是阅读内容。由于每次请求都需要加载PHP解释器,所以它永远不可能被认为是快速的,而且在我的VPS上消耗了大量的内存。
当你看到许多早期Jamstack工具的起源时,同样的主题也浮现出来。
- 降低复杂性
- 提高性能
- 减少对供应商的锁定
- 为开发者提供更好的工作流程
在过去的20年里,JavaScript已经从一种为网站添加小型交互的语言发展成为在浏览器中构建丰富网络应用的平台。同时,我们也看到了将大型应用拆分为小型微服务的运动。这两个发展催生了一种新的网站建设方式,你可以有一个静态的前端与一个动态的后端解耦。
在2015年,Mathias Biilmann想谈论这种现代的网站建设方式,但却在为静态的约束性定义而挣扎。
我们当时处于现代静态网站的空间。这对我们正在做的事情来说,是一个非常糟糕的描述,对吗?我们一直有这样的问题,与人们谈论静态网站时,他们会想到非常静态的东西。他们会想到一本小册子或没有移动部件的东西。一个小的单页或类似的东西。
为了打破这些限制,他创造了 "Jamstack "一词来谈论这种新的方法,并像野火一样蔓延开来。90年代的老式静态技术又变成了新技术,并被推向了新的极限。许多开发者发现了Jamstack方法的好处,这帮助Jamstack成长为今天这样一个繁荣的生态系统。
Aaron Swartz在Jamstack诞生前13年就说得很好:在输入(需要动态代码来处理)和输出(通常可以烘焙)之间保持严格的分离。换句话说,将前端与后端解耦。尽可能地预先渲染内容。在必要时,将动态功能分层。这就是Jamstack的关键所在。
你可能想建立一个Jamstack网站而不是一个动态网站的原因,可以归结为Jamstack的六个支柱。
安全性
Jamstack网站的活动部件较少,来自外部的恶意利用的表面积较小。
规模
Jamstack网站尽可能是静态的。静态网站可以完全生活在CDN中,使它们更容易和更便宜地扩展。
性能
从CDN提供网页,而不是从集中式服务器按需生成网页,可以提高页面加载速度。
可维护性
静态网站很简单。你需要一个能够提供文件的网络服务器。对于一个动态网站,你可能需要整个团队来保持网站的在线和快速。
可移植性
同样,静态网站是由文件组成的。只要你找到一个能够提供网站文件的网络服务器,你就可以把你的网站移到任何地方。
开发者经验
Git工作流程是当今软件开发的一个核心部分。在许多传统的CMS中,很难有Git开发工作流程。在Jamstack网站上,所有的东西都是一个文件,使得使用Git是无缝的。
Chris在Jamstack和WordPress的深入比较中触及了其中的一些要点。他还在"静态还是不静态?"中比较了选择Jamstack架构与服务器端架构的原因。
让我们用这些支柱来评估Jamstack的用例。
静态和Jamstack的边缘在哪里?
现在我们有了静态和Jamstack的基础知识,让我们深入了解,看看每个定义的边缘是什么。我们有四个类别,每个边缘案例都可以归类。
- 静态--这严格遵守了静态的定义。
- 基本上是静态的--虽然不是精确的静态,但大多数人都会称它为静态网站。
- Jamstack- 一个与动态后端解耦的静态前端。
- 动态--按需渲染网页。
这些用例中的许多都可以被归入多个类别。在这个练习中,我们把它们放在它们适合的最严格的类别中。
JavaScript交互静态
让我们从一个简单的案例开始。我有一个静态网站,使用JavaScript来创建图片的幻灯片。
HTML页面、JavaScript和图片都是静态文件。幻灯片功能所需的所有HTML操作都发生在浏览器中,没有外部影响。
静态的Cookies
我有一个静态网站,如果有cookie存在,就用JavaScript在页面的顶部添加一个横幅。一个cookie只是一个头。其余的文件是静态的。
外部资产基本上是静态的
在一个网页上,我们可以从外部来源加载图像或JavaScript。这个外部源可能在请求时动态地生成这些资产。这是否意味着我们有一个动态网站?
大多数人,包括我自己,会认为这是一个静态网站,因为它基本上是。但是,如果我们严格按照定义,它就不符合这个要求。页面的任何部分都是动态生成的,这玷污了静态的神圣和谐。
iFrames基本上是静态的
内联框架允许你在另一个HTML页面中嵌入一个HTML页面。iFrames通常用于在网页上嵌入谷歌地图、Facebook Like按钮和YouTube视频。
同样,大多数人仍然会认为这是一个静态网站。然而,这些嵌入物几乎总是来自动态生成的来源。
基本上是静态的形式
一个静态的网站无疑可以有一个表格在上面。当你提交表格时,就会出现两难的局面。如果你想对数据做些什么,你几乎肯定需要一个动态的后端。有很多表单提交服务,你可以用它们作为表单的动作。
我可以看到两种争论方式。
- 你提交表单到一个外部网站,而后刚好重定向回来。这种分离意味着静态的定义保持不变。
- 这个外部服务是你网站上的一个核心工作流程,静态的定义不再有效。
在现实中,大多数人仍然会认为这是一个静态网站。
Ajax请求Jamstack
一个Ajax请求允许开发人员从外部来源请求数据,而无需重新加载页面。我们和上面的情况一样,都是依赖第三方。有可能Ajax调用的端点是一个静态JSON文件,但更有可能是动态生成的。
在网站上通常使用Ajax数据的性质将它从静态网站推到Jamstack领域。它很适合Jamstack,因为你可以有一个网站,你可以预渲染一切,然后使用Ajax在网站上的任何动态功能或内容上分层。
嵌入式电子商务Jamstack
有一些服务允许你添加电子商务,甚至在静态网站上。在幕后,他们基本上是通过Ajax请求来管理购物车中的物品,并收集付款细节。
单页应用程序(SPA)Jamstack
仅仅是这个标题就把它从静态网站的争夺中排除了。一个SPA使用Ajax调用来请求数据。表现层完全生活在前端,使其成为_Jamtastic_。
对无服务器函数的Ajax调用Jamstack
无论Ajax调用的端点是用AWS Lambda之类的无服务器,还是到你的Kubernetes集群Node.js后端,或者一个简单的PHP后端,这都不重要。Jamstack的关键是前端独立于后端。
在网络服务器前面的反向代理静态
在静态网站的Web服务器前添加一个反向代理,一定会使其成为动态网站,对吗?嗯,没那么快。虽然代理是为网络添加动态元素的软件,但只要服务器上的文件正是浏览器接收的文件,它仍然是静态的。
网络服务器、调制解调器和中间的每一块网络基础设施都在运行软件。如果增加一个代理使静态网站变得动态,那么没有什么是静态的。
CDN静态
CDN是一个全球分布的反向代理,所以它与反向代理属于同一类别。CDN经常添加他们自己的头文件。这仍然不影响著名的静态状态,因为头文件不是坐在服务器硬盘上的文件的一部分。
CDN在一个动态网站前面,有200年的缓存过期时间动态
好吧,200年是一个很长的过期时间,我给你说说。有两个原因,这既不是一个静态的也不是Jamstack的网站。
- 第一个请求没有被缓存,所以它是按需生成的。
- CDN并不是为持久性存储而设计的。如果一个星期后,你的网站只有五次点击,CDN可能会将你的网页从缓存中清除。它总是可以从原点服务器上检索网页,而原点服务器会动态地呈现响应。
带有静态输出的WordPress静态
使用像WP2Static这样的WordPress插件可以让你在WordPress中创建和管理你的网站,并在有变化时输出一个静态网站。
当你这样做的时候,浏览器请求的文件已经存在于网络服务器上,这使得它成为一个静态网站--这与在动态网站前有一个CDN有着微妙但重要的区别。
边缘计算动态
许多公司现在提供在CDN的边缘运行动态代码的能力。这是一个强大的概念,因为你可以在不给用户增加延迟的情况下拥有动态功能。你甚至可以使用边缘计算来处理HTML,然后再把它发送到客户端。
这归结于你如何使用边缘函数。你可以使用一个边缘函数来为特定的请求添加一个头。我认为这仍然是一个静态网站。如果超出这个范围,你对HTML进行操作,你就越过了动态边界。
很难说这是一个Jamstack网站,因为它没有坚持一些基本的好处:规模、_可维护性和可移植性。_现在,你有一块核心基础设施,在每次请求时都会改变HTML,而且它只能在那个特定的托管基础设施上工作。这与静态网站的幸福简单性相距甚远。
Jamstack的一个优雅之处在于前端和后端是解耦的。后端是由输出数据的API组成的。他们不知道也不关心这些数据是如何被使用的。前端是表现层。它知道从哪里获得动态数据,以及如何渲染它。当你打破这种关注点的分离,你就进入了一个动态的世界。
分布式持久化渲染(DPR)动态
DPR是一种策略,用于减少大型静态网站生成器(SSG)网站的漫长构建时间。这个想法是SSG建立一个最受欢迎的页面的子集。对于其余的页面,SSG在第一次被请求时按需建立,并将其保存在持久性存储中。在最初的请求之后,该页面的行为与其他已建的静态页面完全相同。
冗长的构建时间限制了大规模用例对Jamstack的选择。如果所有的SSG工具都基于GoLang,我们可能就不需要DPR了。然而,这并不是大多数Jamstack工具的方向,而且在大型网站上,构建性能可能长到令人窒息。
DPR是达到目的的手段,也是Jamstack发展的必需品。虽然它允许你在大型网站上使用Jamstack工作流程,但讽刺的是,我认为你不能把使用DPR的网站称为Jamstack网站。按需运行软件以生成网页,这听起来当然很有活力。在第一次请求之后,使用DPR提供的页面是一个静态页面,这使得DPR比把CDN放在一个动态网站前面 "更静态"。然而,它仍然是一个动态网站,因为前端和后端之间没有分离,而且它不是可移植的,这是Jamstack网站的支柱之一。
增量式静态再生(ISR)动态
ISR是一种类似于DPR的策略,但与DPR有微妙的不同,可以减少大型SSG网站的漫长构建时间。不同的是,你可以定期地重新验证单个页面,以模仿一个动态网站,而不需要做整个网站的构建。
对一个没有缓存版本的页面的请求会退回到该页面的陈旧版本或一个普通的加载页面。
同样,这是一个令人兴奋的技术,它扩展了你可以用Jamstack工作流程做什么,但动态生成一个页面的需求听起来像一个动态网站会做的事情。
扁平文件CMS动态
平面文件内容管理系统使用文本文件而不是数据库来存储内容。虽然平面文件CMS从堆栈中删除了一个动态元素,但它仍然在动态地渲染响应。
线条已经被划定
对这些边缘案例的探索和辩论使我们对所有这些术语的限制有了更好的理解。这个练习的重点不是对创建静态或Jamstack网站的教条主义。它是为了给我们提供一种共同的语言,来讨论当你从一个概念跨越到另一个概念时你所做的权衡。
权衡取舍也绝对没有错。不是所有的东西都可以是一个纯粹的静态网站。在许多情况下,权衡是有意义的。例如,假设前端需要知道访问者的国家。有两种方法可以做到这一点。
- 在页面加载时,执行一个Ajax调用,从API中查询国家。(Jamstack)
- 使用一个边缘函数,在响应时动态地将国家代码插入HTML中。(Dynamic)
如果拥有国家代码是一个不错的选择,而且网页不需要立即使用它,那么第一种方法是一个不错的选择。页面可以是静态的,如果API调用不成功,可以优雅地失败。然而,如果页面需要国家代码,使用边缘函数动态地添加它可能更有意义。这将会更快,因为你不需要执行第二个请求/响应周期。
关键是理解你要解决的问题,并思考你在不同方法中的权衡。你可能最终会让你的网站的大部分都是Jamstack,一部分是动态的。这完全没问题,对你的使用情况来说可能是必要的。通常情况下,你越接近静态,你的网站就越快、越安全、越可扩展。
这只是讨论的开始,我想听听你的看法。你会把界限划在哪里?静态和Jamstack对你意味着什么?你现在是坐在椅子上还是凳子上?
The postStatic vs. Dynamic vs. Jamstack:首先出现在CSS-Tricks上。你可以通过成为MVP支持者来支持CSS-Tricks。