内容简介:Istio由控制面和数据面组成。其中Envoy是Istio在数据面缺省使用的转发代理,Istio利用Envoy的四层和七层代理功能对网格中微服务之间的调用流量进行转发。今天我们来分析一下Istio 使用到的Envoy构建流程。Envoy采用了Bazel进行构建。 Bazel是一种高层构建语言,类似Make,Maven和Gradle。其特点是可读性较好,支持跨语言,跨平台编译;并且可以定义代码库之间的依赖关系,支持跨代码库的联合构建。Bazel定义构建的依赖关系和规则,并管理构建生成的临时文件及二进制文件,
Istio由控制面和数据面组成。其中Envoy是Istio在数据面缺省使用的转发代理,Istio利用Envoy的四层和七层代理功能对网格中微服务之间的调用流量进行转发。今天我们来分析一下Istio 使用到的Envoy构建流程。
https://github.com/istio/proxy 这个库中包含了Istio对Envoy的扩展,包括用于对接Mixer的Filter和安全认证的Filter。但这个库中并不包含Envoy自身的源代码,因此这个库在构建时会从Github上下载Envoy源码进行联合编译。
编译工具
Envoy采用了Bazel进行构建。 Bazel是一种高层构建语言,类似Make,Maven和Gradle。其特点是可读性较好,支持跨语言,跨平台编译;并且可以定义代码库之间的依赖关系,支持跨代码库的联合构建。Bazel定义构建的依赖关系和规则,并管理构建生成的临时文件及二进制文件,具体的编译工作是调用各个语言的编译 工具 如GCC, JAVAC等完成的。
为了理解Envoy的编译过程,我们需要先了解Bazel的几个基础概念
-
workspace: 文件系统中的一个目录,该目录中包含了用于编译软件所需的所有源文件。每个工作空间中有一个WORKSPACE文件,该文件用于描述该工作空间的外部依赖,例如依赖的Github上的第三方代码。
-
Package: 是一组用于相关文件的集合,该目录中包含一个BUILD文件,此文件中描述了该程序包的构建方式。
-
target: 生成的目标,一般是一个lib或者二进制文件。 target是一个构建规则(build rule)的实例,一般包含构建所需的源文件,构建目标的名称。rule还可以嵌套,一个rule的输出文件可以作为另一个rule的输入文件。例如一个二进制文件编译的target可以依赖另一个target生成的lib。另外target还可以依赖外部Repository中的另一个target,这个外部Repository可以是文件系统上另一个文件夹下的项目,github的项目或者http下载的代码。外部Repository在WORKSPACE文件中进行定义。
编译Envoy
首先参考Bazel的官方文档安装Bazel,并且需要安装gcc等相关工具。
设置gcc及g++环境变量
export CC=/usr/bin/gcc-5; export CXX=/usr/bin/g++-5
下载源码并进行构建
git clone https://github.com/istio/proxy.git cd proxy make build_envoy
如果出现错误提示,一般是由于编译所需的软件未安装导致,请根据提示信息进行安装。
如果一切顺利,bazel会在proxy目录下创建一个目录链接bazel-bin,指向生成的二进制文件。
编译过程分析
源码目录结构如下,主要的构建逻辑在引号包含的文件中。
├── "BUILD" ├── "Makefile" ├── "WORKSPACE" ├── src │ ├── envoy -- envoy filter 插件源码 │ │ ├── alts │ │ │ ├── *.cc │ │ │ ├── *.h │ │ │ └── "BUILD" │ │ ├── "BUILD" │ │ ├── http │ │ │ ├── authn --认证 filte │ │ │ │ ├── *.cc │ │ │ │ ├── *.h │ │ │ │ └── "BUILD" │ │ │ ├── jwt_auth --jwt 认证 filter │ │ │ │ ├── *.cc │ │ │ │ ├── *.h │ │ │ │ └── "BUILD" │ │ │ └── mixer --mixer filter,实现metrics上报,Quota(Rate Limiting (处理http协议) │ │ │ ├── *.cc │ │ │ ├── *.h │ │ │ └── "BUILD" │ │ ├── tcp │ │ │ └── mixer --mixer filter(处理tcp协议) │ │ │ ├── *.cc │ │ │ ├── *.h │ │ │ └── "BUILD" │ │ └── utils │ │ ├── *.cc │ │ ├── *.h │ │ └── "BUILD" │ └── istio │ └── ** ├── test │ └── ** └── tools └── **
编译的入口是根目录下的Makefile文件
# Build only envoy - fast build_envoy: CC=$(CC) CXX=$(CXX) bazel $(BAZEL_STARTUP_ARGS) build $(BAZEL_BUILD_ARGS) //src/envoy:envoy @bazel shutdown
从中可以看到,调用了bazel进行构建,其构建的target为 //src/envoy:envoy 。这是bazel的语法,表明调用src/envoy这个目录下BUILD文件中Envoy这个target。
打开src/BUILD文件,查看该target的内容
envoy_cc_binary( name = "envoy", repository = "@envoy", visibility = ["//visibility:public"], deps = [ "//src/envoy/http/authn:filter_lib", "//src/envoy/http/jwt_auth:http_filter_factory", "//src/envoy/http/mixer:filter_lib", "//src/envoy/tcp/mixer:filter_lib", "//src/envoy/alts:alts_socket_factory", "@envoy//source/exe:envoy_main_entry_lib", ], )
cc_binary表明该target对应的是c++二进制rule,其中deps部分是其依赖的其他target。前5个target都是本地依赖,对应到源码目录中的其他子目录下的BUILD文件,其中最后一个比较特殊,是一个外部依赖,该外部库为envoy。
外部库定义在根目录下的WORKSPACE文件中。
ENVOY_SHA = "de039269f54aa21aa0da21da89a5075aa3db3bb9" http_archive( name = "envoy", strip_prefix = "envoy-" + ENVOY_SHA, url = "https://github.com/envoyproxy/envoy/archive/" + ENVOY_SHA + ".zip", )
该文件通过http_archive定义了一个外部repository,bazel在执行//src/envoy:envoy这个target时,发现该target依赖这个外部repository,根据http_archive中的描述,从指定的url下载该依赖的源码,并进行编译。
编译过程中的依赖关系如下图所示:
以上就是本文的全部内容,希望本文的内容对大家的学习或者工作能带来一定的帮助,也希望大家多多支持 码农网
猜你喜欢:- 《高性能linux服务器构建实战》
- Java并发编程实战笔记3:基础构建模块
- [译] 项目实战:使用 Go 构建 GraphQL API
- Pytext实战-构建一个文本分类器有多快
- 大牛带你从 0 到 1 构建数据仓库实战
- 实战:向GitHub提交代码时触发Jenkins自动构建
本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。
高性能JavaScript
【美】Nicholas C. Zakas(尼古拉斯.泽卡斯) / 丁琛 / 电子工业出版社 / 2015-8-1 / 65
如果你使用 JavaScript 构建交互丰富的 Web 应用,那么 JavaScript 代码可能是造成你的Web应用速度变慢的主要原因。《高性能JavaScript》揭示的技术和策略能帮助你在开发过程中消除性能瓶颈。你将会了解如何提升各方面的性能,包括代码的加载、运行、DOM 交互、页面生存周期等。雅虎的前端工程师 Nicholas C. Zakas 和其他五位 JavaScript 专家介绍......一起来看看 《高性能JavaScript》 这本书的介绍吧!