点击标题下「异步图书」可快速关注
《Go Web编程》这一本不可错过!
今天的这一本书,可谓是万众瞩目。
很多技术社区在推荐Go Web书籍时,它是首选。
它就是《Go Web编程》
点击封面查看
众多业界大咖推荐:
“随着Go语言变得日益重要,对优质Go语言教程的需求也与日俱增,本书的出现可谓恰逢其时。” ——Shaun Lippy,Oracle 集团
“无论你是一位经验老到的gopher,还是一位刚开始接触Go语言的Web开发者,这都是你必不可少的一本书。” ——Benoit Benedetti,尼斯大学
“关于Go Web应用的开发和部署,你想要知道的全部知识都已经囊括在这本书里了。” ——Brian Cooksey,Zapier 公司
“本书堪称Go Web 开发的权威入门教程。” ——Gualtiero Testa,Factor-y S.r.l. 公司
为什么推荐这本书?
随着近年来Web开发的盛行,很多相关书籍也随之如雨后春笋般出现,然而在这些书籍当中,绝大多数书籍都只关注表面的实现代码,而对代码背后的技术原理却少有提及。读者在看这类书籍时,虽然可以学到某个框架或者某个库的API,并根据书中给出的代码搭建出一个个演示程序(demo),但是对隐藏在这些代码之下的原理却一无所知。这种停留在表面的理解一旦离开了书本的指导,就会让人感到寸步难行,不知所措。
本书的独特之处在于,它抛开了现有的所有Go Web框架,仅仅通过Go语言内置的标准库来展示如何去构建一个Web应用或Web服务。这样做的好处是,无论将来读者是使用这些标准库来构建Web应用,还是使用现成的框架去构建Web应用,又或者使用自己建造的框架去构建Web应用,本书介绍的知识都是非常有用的:如果使用的是现成的框架,那么这些框架的内部实现通常就是由本书介绍的Go标准库构建的;如果选择自建框架,那么将有很大概率会用到本书介绍的Go标准库。因此,不论在何种情况下,本书对于构建Go Web应用都是非常有帮助的。
本书的另一个优点是,它在介绍Web应用开发技术的同时,也介绍了隐藏在这些技术背后的基础知识。比如,在介绍Web处理器(handler)的创建方法之前,本书就先深入浅出地介绍了HTTP协议,然后才说明具体的请求处理方法以及响应返回方法;又比如说,在介绍会话(session)技术时,本书就先说明了HTTP协议的无状态性质,然后才说明如何使用会话去解决这一问题;类似的例子在书里面还有很多,不一而足。对刚开始接触Web开发的读者来说,本书这种“知其然,也知其所以然”的教授方式能够让读者打好Web开发的基础,从而达到事半功倍的效果;此外,对那些已经有一定Web开发经验的读者来说,本书将在介绍Go Web开发方法的同时,帮助读者回顾和巩固Web开发的相关基础知识,并藉此成为更好的Web开发者。
综上所述,我认为这本书对所有关心Web开发的人来说,都是非常值得一读的——无论读者使用的是Go语言还是其他语言、X框架还是Y框架,无论读者是Web开发的初学者还是入行已久的开发者,应该都会在阅读本书的过程中有所收获。
如何你符合如下特点,那么一定要读它:
阅读本书需要读者具备基本的Go语言编程技能并掌握Go语言的语法。
本书适合所有想用Go语言进行Web开发的读者阅读,无论是Web开发的初学者还是入行已久的开发者都会在阅读本书的过程中有所收获。
为什么使用Go语言构建Web应用?
“为什么要使用Go语言编写Web应用呢?”作为本书的读者,我想你肯定很想知道这个问题的答案。本书是一本教人们如何使用Go语言进行Web编程的图书,而作为本书的作者,我的任务就是向你解释为什么人们会使用Go语言进行Web编程。本书将在接下来的内容中陆续介绍Go语言在Web开发方面的优点,我衷心地希望你也能够对这些优点有感同身受的想法。
Go是一门相对比较年轻的编程语言,它拥有繁荣并且仍在不断成长的社区,并且它也非常适合用来编写那些需要快速运行的服务器端程序。因为Go语言提供了很多过程式编程语言的特性,所以拥有过程式编程语言使用经验的程序员对Go应该都不会感到陌生,但与此同时,Go语言也提供了函数式编程方面的特性。除了内置对并发编程的支持之外,Go语言还拥有现代化的包管理系统、垃圾收集特性以及一系列包罗万象、威力强大的标准库。
虽然Go自带的标准库已经非常丰富和宏大了,但Go仍然拥有许多质量上乘的开源库,它们可以对标准库不足的地方进行补充。本书在大部分情况下都会尽可能地使用标准库,但是偶尔也会使用一些第三方开源库,以此来展示开源社区提供的一些另辟蹊径并且富有创意的方法。
使用Go语言进行Web开发正变得日益流行,很多公司都已经开始使用Go了,其中包括Dropbox、SendGrid这样的基础设施公司,Square和Hailo这样的技术驱动的公司,甚至是BBC、纽约时报这样的传统公司。
在开发大规模Web应用方面,Go语言提供了一种不同于现有语言和平台但又切实可行的方案。大规模可扩展的Web应用通常需要具备以下特质:
可扩展;
模块化;
可维护;
高性能。
接下来的几小节将分别对这些特质进行讨论。
1.1.1 Go与可扩展Web应用
大规模的Web应用应该是可扩展的(scalable),这意味着应用的管理者应该能够简单、快速地提升应用的性能以便处理更多请求。如果一个应用是可扩展的,那么它就是线性的,这意味着应用的管理者可以通过添加更多硬件来获得更强的请求处理能力。
有两种方式可以对性能进行扩展:
一种是垂直扩展(vertical scaling),即提升单台设备的CPU数量或者性能;
另一种则是水平扩展(horizontal scaling),即通过增加计算机的数量来提升性能。
因为Go语言拥有非常优异的并发编程支持,所以它在垂直扩展方面拥有不俗的表现:一个Go Web应用只需要使用一个操作系统线程(OS thread),就可以通过调度来高效地运行数十万个goroutine。
跟其他Web应用一样,Go也可以通过在多个Go Web应用之上架设代理来进行高效的水平扩展。因为Go Web应用都会被编译为不包含任何动态依赖关系的静态二进制文件,所以我们可以把这些文件分发到没有安装Go语言的系统里,从而以一种简单且一致的方式部署Go Web应用。
1.1.2 Go与模块化Web应用
大规模Web应用应该由可替换的组件构成,这种做法能够使开发者更容易添加、移除或者修改特性,从而更好地满足程序不断变化的需求。除此之外,这种做法的另一个好处是使开发者可以通过复用模块化的组件来降低软件开发所需的费用。
尽管Go是一门静态类型语言,但用户可以通过它的接口机制对行为进行描述,以此来实现动态类型匹配(dynamic typing)。Go语言的函数可以接受接口作为参数,这意味着用户只要实现了接口所需的方法,就可以在继续使用现有代码的同时向系统中引入新的代码。与此同时,因为Go语言的所有类型都实现了空接口,所以用户只需要创建出一个接受空接口作为参数的函数,就可以把任何类型的值用作该函数的实际参数。此外,Go语言还实现了一些在函数式编程中非常常见的特性,其中包括函数类型、使用函数作为值以及闭包,这些特性允许用户使用已有的函数来构建新的函数,从而帮助用户构建出更为模块化的代码。
Go语言也经常会被用于创建微服务(microservice)。在微服务架构中,大型应用通常由多个规模较小的独立服务组合而成,这些独立服务通常可以相互替换,并根据它们各自的功能进行组织。比如,日志记录服务会被归类为系统级服务,而开具账单、风险分析这样的服务则会被归类为应用级服务。创建多个规模较小的Go服务并将它们组合为单个Web应用,这种做法使得我们可以在有需要的时候对应用中的服务进行替换,而整个Web应用也会因此变得更加模块化。
1.1.3 Go与可维护的Web应用
和其他庞大而复杂的应用一样,拥有一个易于维护的代码库(codebase)对大规模的Web应用来说也是非常重要的。这是因为大规模的应用通常都会不断地成长和演化,所以开发者需要经常性地回顾并修改代码,而修改难懂、笨拙的代码需要花费大量的时间,并且隐含着可能会造成某些功能无法正常运作的风险。因此,确保源代码能够以适当的方式组织起来并且具有良好的可维护性对开发者来说就显得至关重要了。
Go语言的设计鼓励良好的软件工程实践,它拥有简洁且极具可读性的语法以及灵活且清晰的包管理系统。除此之外,Go语言还有一整套优秀的工具,它们不仅可以增强程序员的开发体验,还能够帮助他们写出更具可读性的代码,比如以标准化方式对Go代码进行格式化的源代码格式化程序gofmt就是其中一个例子。
因为Go语言希望文档可以和代码一同演进,所以它的文档工具godoc会对Go源代码及其注释进行语法分析,然后以HTML、纯文本或者其他多种格式创建出相应的文档。godoc的使用方法非常简单,开发者只需要把文档写到源代码里面,godoc就会把这些文档以及与之相关联的代码提取出来,生成相应的文档文件。
除此之外,Go还内置了对测试的支持:gotest工具会自动寻找与源代码处于同一个包(package)之内的测试代码,并运行其中的功能测试和性能测试。Go语言也提供了Web应用测试工具,这些工具可以模拟出一个Web服务器,并对该服务器生成的响应(response)进行记录。
1.1.4 Go与高性能Web应用
高性能不仅意味着能够在短时间内处理大量请求,还意味着服务器能够快速地对客户端进行响应,并让终端用户(end user)能够快速地执行操作。
Go语言的一个设计目标就是提供接近于C语言的性能,尽管这个目标目前尚未达成,但Go语言现在的性能已经非常具有竞争力:Go程序会被编译为本地码(native code),这一般意味着Go程序可以运行得比解释型语言的程序要快,并且就像前面说过的那样,Go语言的goroutine对并发编程提供了非常好的支持,这使得Go应用可以同时处理多个请求。
希望以上介绍能够引起你对使用Go语言及其平台进行Web开发的兴趣。但是在学习如何使用Go进行Web开发之前,我们需要先来了解一下什么是Web应用,以及它们的工作原理是什么,这会给我们学习之后几章的内容带来非常大的帮助。
本书目录:(滑动手机查看)
第一部分 Go与Web应用
第1章 Go与Web应用 3
1.1 使用Go语言构建Web应用 3
1.1.1 Go与可扩展Web应用 4
1.1.2 Go与模块化Web应用 4
1.1.3 Go与可维护的Web应用 5
1.1.4 Go与高性能Web应用 5
1.2 Web应用的工作原理 6
1.3 HTTP简介 7
1.4 Web应用的诞生 8
1.5 HTTP请求 9
1.5.1 请求方法 10
1.5.2 安全的请求方法 11
1.5.3 幂等的请求方法 11
1.5.4 浏览器对请求方法的支持 11
1.5.5 请求首部 12
1.6 HTTP响应 13
1.6.1 响应状态码 13
1.6.2 响应首部 14
1.7 URI 15
1.8 HTTP/2简介 16
1.9 Web应用的各个组成部分 16
1.9.1 处理器 17
1.9.2 模板引擎 18
1.10 Hello Go 18
1.11 小结 21
第2章 ChitChat论坛 23
2.1 ChitChat简介 23
2.2 应用设计 24
2.3 数据模型 26
2.4 请求的接收与处理 27
2.4.1 多路复用器 27
2.4.2 服务静态文件 29
2.4.3 创建处理器函数 29
2.4.4 使用cookie进行访问控制 30
2.5 使用模板生成HTML响应 33
2.6 安装PostgreSQL 38
2.6.1 在Linux或FreeBSD系统上安装 38
2.6.2 在Mac OS X系统上安装 39
2.6.3 在Windows系统上安装 39
2.7 连接数据库 39
2.8 启动服务器 44
2.9 Web应用运作流程回顾 45
2.10 小结 46
第二部分 Web应用的基本组成部分
第3章 接收请求 49
3.1 Go的net/http标准库 49
3.2 使用Go构建服务器 51
3.2.1 Go Web服务器 51
3.2.2 通过HTTPS提供服务 53
3.3 处理器和处理器函数 56
3.3.1 处理请求 56
3.3.2 使用多个处理器 58
3.3.3 处理器函数 59
3.3.4 串联多个处理器和处理器函数 61
3.3.5 ServeMux和DefaultServeMux 65
3.3.6 使用其他多路复用器 66
3.4 使用HTTP/2 68
3.5 小结 70
第4章 处理请求 72
4.1 请求和响应 72
4.1.1 Request结构 73
4.1.2 请求URL 73
4.1.3 请求首部 74
4.1.4 请求主体 76
4.2 Go与HTML表单 77
4.2.1 Form字段 79
4.2.2 PostForm字段 80
4.2.3 MultipartForm字段 81
4.2.4 文件 83
4.2.5 处理带有JSON主体的POST请求 85
4.3 ResponseWriter 86
4.4 cookie 91
4.4.1 Go与cookie 91
4.4.2 将cookie发送至浏览器 92
4.4.3 从浏览器里面获取cookie 94
4.4.4 使用cookie实现闪现消息 96
4.5 小结 99
第5章 内容展示 100
5.1 模板引擎 100
5.2 Go的模板引擎 102
5.2.1 对模板进行语法分析 104
5.2.2 执行模板 105
5.3 动作 106
5.3.1 条件动作 106
5.3.2 迭代动作 108
5.3.3 设置动作 109
5.3.4 包含动作 111
5.4 参数、变量和管道 113
5.5 函数 114
5.6 上下文感知 116
5.6.1 防御XSS攻击 119
5.6.2 不对HTML进行转义 121
5.7 嵌套模板 122
5.8 通过块动作定义默认模板 126
5.9 小结 127
第6章 存储数据 128
6.1 内存存储 128
6.2 文件存储 131
6.2.1 读取和写入CSV文件 133
6.2.2 gob包 135
6.3 Go与SQL 137
6.3.1 设置数据库 138
6.3.2 连接数据库 140
6.3.3 创建帖子 142
6.3.4 获取帖子 144
6.3.5 更新帖子 145
6.3.6 删除帖子 145
6.3.7 一次获取多篇帖子 146
6.4 Go与SQL的关系 147
6.4.1 设置数据库 147
6.4.2 一对多关系 150
6.5 Go与关系映射器 152
6.5.1 Sqlx 152
6.5.2 Gorm 154
6.6 小结 157
第三部分 实战演练
第7章 Go Web服务 161
7.1 Web服务简介 161
7.2 基于SOAP的Web服务简介 163
7.3 基于REST的Web服务简介 166
7.3.1 将动作转换为资源 168
7.3.2 将动作转换为资源的属性 169
7.4 通过Go分析和创建XML 169
7.4.1 分析XML 169
7.4.2 创建XML 177
7.5 通过Go分析和创建JSON 180
7.5.1 分析JSON 181
7.5.2 创建JSON 184
7.6 创建Go Web服务 187
7.7 小结 194
第8章 应用测试 196
8.1 Go与测试 196
8.2 使用Go进行单元测试 197
8.2.1 跳过测试用例 201
8.2.2 以并行方式运行测试 202
8.2.3 基准测试 203
8.3 使用Go进行HTTP测试 206
8.4 测试替身以及依赖注入 210
8.5 第三方Go测试库 217
8.5.1 Gocheck测试包简介 217
8.5.2 Ginkgo测试框架简介 223
8.6 小结 228
第9章 发挥Go的并发优势 230
9.1 并发与并行的区别 230
9.2 goroutine 232
9.2.1 使用goroutine 232
9.2.2 goroutine与性能 235
9.2.3 等待goroutine 238
9.3 通道 239
9.3.1 通过通道实现同步 240
9.3.2 通过通道实现消息传递 242
9.3.3 有缓冲通道 243
9.3.4 从多个通道中选择 244
9.4 在Web应用中使用并发 247
9.4.1 创建马赛克图片 248
9.4.2 马赛克图片Web应用 251
9.4.3 并发版马赛克图片生成Web应用 254
9.5 小结 262
第10章 Go的部署 263
10.1 将应用部署到独立的 服务器 264
10.2 将应用部署到 Heroku 270
10.3 将应用部署到Google App Engine 273
10.4 将应用部署到 Docker 278
10.4.1 什么是Docker 278
10.4.2 安装Docker 279
10.4.3 Docker的理念与 组件 280
10.4.4 Docker化一个Go Web 应用 281
10.4.5 将Docker容器推送至 互联网 283
10.5 部署方法之间的 对比 286
10.6 小结 287
附录 安装和设置Go 288
第一章试读:
1.2 Web应用的工作原理
如果你在一个技术会议上向在场的程序员们提出“什么是Web应用”这一问题,那么通常会得到五花八门的回答,有些人甚至可能还会因为你问了个如此基础的问题而感到惊讶和不解。通过不同的人对这个问题的不同回答,我们可以了解到人们对Web应用并没有一个十分明确的定义。比如说,Web服务算不算Web应用?因为Web服务通常会被其他软件调用,而Web应用则是为人类提供服务,所以很多人都认为Web服务与Web应用是两种不同的事物。但如果一个程序能够像RSS feed那样,产生出来的数据既可以被其他软件使用,又可以被人类理解,那么这个程序到底是一个Web服务还是一个Web应用呢?
同样地,如果一个应用只会返回HTML页面,但却并不对页面进行任何处理,那么它是一个Web应用吗?运行在Web浏览器之上的Adobe Flash程序是一个Web应用吗?对于一个纯HTML5编写的应用,如果它运行在一个长期驻留于电脑的浏览器中,那么它算是一个Web应用吗?如果一个应用在向服务器发送请求时没有使用HTTP协议,那么它算是一个Web应用吗?大多数程序员都能够从高层次的角度去理解Web应用是什么,但是一旦我们深入一些,尝试去探究Web应用的实现层次,事情就会变得含糊不清起来。
从纯粹且狭隘的角度来看,Web应用应该是这样的计算机程序:它会对客户端发送的HTTP请求做出响应,并通过HTTP响应将HTML回传至客户端。但这样一来,Web应用不就跟Web服务器一样了吗?的确如此,如果按照上面给出的定义来看,Web服务器和Web应用将没有区别:一个Web服务器就是一个Web应用(如图1-1所示)。
图1-1 Web应用最基本的请求与响应结构
将Web服务器看作是Web应用的一个问题在于,像httpd和Apache这样的Web服务器都会监视特定的目录,并在接收到请求时返回位于该目录中的文件(比如Apache就会对docroot目录进行监视)。与此相反,Web应用并不会简单地返回文件:它会对请求进行处理,并执行应用程序中预先设定好的操作(如图1-2所示)。
图1-2 Web应用的工作原理
从以上观点来看,我们也许可以把Web服务器看作是一种特殊的Web应用,这种应用只会返回被请求的文件。普遍来讲,很多用户都会把使用浏览器作为客户端的应用看作是Web应用。这其中包括Adobe Flash应用、单页Web应用,甚至是那些不使用HTTP协议进行通信但却驻留在桌面或系统上的应用。
为了在书中讨论Web编程的相关技术,我们必须给这些技术一个明确的定义。首先,让我们来给出应用的定义。
应用(application)是一个与用户进行互动并帮助用户执行指定活动的软件程序。比如记账系统、人力资源系统、桌面出版软件等。而Web应用则是部署在Web之上,并通过Web来使用的应用。
换句话说,一个程序只需要满足以下两个条件,我们就可以把它看作是一个Web应用:
这个程序必须向发送命令请求的客户端返回HTML,而客户端则会向用户展示渲染后的HTML;
这个程序在向客户端传送数据时必需使用HTTP协议。
在这个定义的基础上,如果一个程序不是向用户渲染并展示HTML,而是向其他程序返回某种非HTML格式的数据,那么这个程序就是一个为其他程序提供服务的Web服务。本书将在第7章对Web服务进行更详细的说明。
与大部分程序员对Web应用的定义相比,上面给出的定义可能显得稍微狭隘了一些,但因为这个定义消除了所有的模糊与不清晰,并使Web应用变得更加易于理解,所以它对于本书讨论的问题是非常有帮助的。随着读者对本书阅读的不断深入,这一定义将变得更为清晰,但是在此之前,让我们先来回顾一下HTTP协议的发展历程。
1.3 HTTP简介
HTTP是万维网的应用层通信协议,Web页面中的所有数据都是通过这个看似简单的文本协议进行传输的。HTTP非常朴素,但却异常地强大——这个协议自20世纪90年代定义以来,至今只进行了3次迭代修改,其中HTTP 1.1是目前使用最为广泛的一个版本,而最新的一个版本则是HTTP 2.0,又称HTTP/2。
HTTP的最初版本HTTP 0.9是由Tim Berners-Lee为了让万维网能够得以被采纳而创建的:它允许客户端与服务器进行连接,并向服务器发送以空行(CRLF)结尾的ASCII字符串请求,而服务器则会返回不带任何元数据的HTML作为响应。
HTTP 0.9之后的每个新版本实现都包含了大量的新特性,1996年发布的HTTP 1.0就是由大量特性合并而成的,之后的HTTP 1.1版本于1999年发布,而HTTP 2.0版本则于2015年发布。因为目前使用最为广泛的还是HTTP 1.1版本,所以本书主要还是对HTTP 1.1进行讨论,但也会在适当的地方介绍一些HTTP 2.0的相关信息。
首先,让我们通过一个简单的定义来说明什么是HTTP。
HTTP是一种无状态、由文本构成的请求-响应(request-response)协议,这种协议使用的是客户端-服务器(client-server)计算模型。
请求-响应是两台计算机进行通信的基本方式,其中一台计算机会向另一台计算机发送请求,而接收到请求的计算机则会对请求进行响应。在客户端-服务器计算模型中,发送请求的一方(客户端)负责向返回响应的一方(服务器)发起会话,而服务器则负责为客户端提供服务。在HTTP协议中,客户端也被称作用户代理(user-agent),而服务器则通常会被称为Web服务器。在大多数情况下,HTTP客户端都是一个Web浏览器。
HTTP是一种无状态协议,它唯一知道的就是客户端会向服务器发送请求,而服务器则会向客户端返回响应,并且后续发生的请求对之前发生过的请求一无所知。相对的,像FTP、Telnet这类面向连接的协议则会在客户端和服务器之间创建一个持续存在的通信通道(其中Telnet在进行通信时使用的也是请求-响应方式以及客户端-服务器计算模型)。顺带提一下,HTTP 1.1也可以通过持久化连接来提升性能。
跟很多互联网协议一样,HTTP也是以纯文本方式而不是二进制方式发送和接收协议数据的。这样做是为了让开发者可以在无需使用专门的协议分析工具的情况下,弄清楚通信中正在发生的事情,从而更容易进行故障排查。
因为HTTP最初在设计时只用于传送HTML,所以HTTP 0.9只提供了GET
这一个方法(method),但新版本对HTTP的扩展使它逐渐变成了一种通用的协议,用户也得以将其应用于Web应用等分布式系统中,本章接下来就会对Web应用进行介绍。
1.4 Web应用的诞生
在万维网出现不久之后,人们开始意识到一点:尽管使用Web服务器处理静态HTML文件这个主意非常棒,但如果HTML里面能够包含动态生成的内容,那么事情将会变得更加有趣。其中,通用网关接口(Common Gateway Interface,CGI)就是在早期尝试动态生成HTML内容的技术之一。
1993年,美国国家超级计算应用中心(National Center for Supercomputing Applications, NCSA)编写了一个在Web服务器上调用可执行命令行程序的规范(specification),他们把这个规范命名为CGI,并将它包含在了NCSA开发的广受欢迎的HTTPd服务器里面。不过NCSA制定的这个规范最终并没有成为正式的互联网标准,只有CGI这个名字被后来的规范沿用了下来。
CGI是一个简单的接口,它允许Web服务器与一个独立运行于Web服务器进程之外的进程进行对接。通过CGI与服务器进行对接的程序通常被称为CGI程序,这种程序可以使用任何编程语言编写——这也是我们把这种接口称之为“通用”接口的原因,不过早期的CGI程序大多数都是使用Perl语言编写的。向CGI程序传递输入参数是通过设置环境变量来完成的,CGI程序在运行之后将向标准输出(stand output)返回结果,而服务器则会将这些结果传送至客户端。
与CGI同期出现的还有服务器端包含(server-side includes,SSI)技术,这种技术允许开发者在HTML文件里面包含一些指令(directive):当客户端请求一个HTML文件的时候,服务器在返回这个文件之前,会先执行文件中包含的指令,并将文件中出现指令的位置替换成这些指令的执行结果。SSI最常见的用法是在HTML文件中包含其他被频繁使用的文件,又或者将整个网站都会出现的页面首部(header)以及尾部(footer)的代码段嵌入HTML文件中。
作为例子,以下代码演示了如何通过SSI指令将navbar.shtml
文件中的内容包含到HTML文件中:
<html> <head><title>Example SSI</title></head> <body> <!--#include file="navbar.shtml" --> </body></html>
SSI技术的最终演化结果就是在HTML里面包含更为复杂的代码,并使用更为强大的解释器(interpreter)。这一模式衍生出了PHP、ASP、JSP和ColdFusion等一系列非常成功的引擎,开发者通过使用这些引擎能够开发出各式各样复杂的Web应用。除此之外,这一模式也是Mustache、ERB、Velocity等一系列Web模板引擎的基础。
如前所述,Web应用是为了通过HTTP向用户发送定制的动态内容而诞生的,为了弄明白Web应用的运作原理,我们必须知道HTTP的工作过程,并理解HTTP请求和响应的运作机制。
延伸推荐
2017优秀图书和作译者评选-进行中赢取kindle等技术图书礼!
点击关键词阅读更多新书:
Python|机器学习|Kotlin|Java|移动开发|机器人|有奖活动|Web前端|书单
点击阅读原文,购买《Go Web编程》