*:first-child {
margin-top: 0 !important;
}
body>*:last-child {
margin-bottom: 0 !important;
}
/* BLOCKS
=============================================================================*/
p, blockquote, ul, ol, dl, table, pre {
margin: 15px 0;
}
/* HEADERS
=============================================================================*/
h1, h2, h3, h4, h5, h6 {
margin: 20px 0 10px;
padding: 0;
font-weight: bold;
-webkit-font-smoothing: antialiased;
}
h1 tt, h1 code, h2 tt, h2 code, h3 tt, h3 code, h4 tt, h4 code, h5 tt, h5 code, h6 tt, h6 code {
font-size: inherit;
}
h1 {
font-size: 28px;
color: #000;
}
h2 {
font-size: 24px;
border-bottom: 1px solid #ccc;
color: #000;
}
h3 {
font-size: 18px;
}
h4 {
font-size: 16px;
}
h5 {
font-size: 14px;
}
h6 {
color: #777;
font-size: 14px;
}
body>h2:first-child, body>h1:first-child, body>h1:first-child+h2, body>h3:first-child, body>h4:first-child, body>h5:first-child, body>h6:first-child {
margin-top: 0;
padding-top: 0;
}
a:first-child h1, a:first-child h2, a:first-child h3, a:first-child h4, a:first-child h5, a:first-child h6 {
margin-top: 0;
padding-top: 0;
}
h1+p, h2+p, h3+p, h4+p, h5+p, h6+p {
margin-top: 10px;
}
/* LINKS
=============================================================================*/
a {
color: #4183C4;
text-decoration: none;
}
a:hover {
text-decoration: underline;
}
/* LISTS
=============================================================================*/
ul, ol {
padding-left: 30px;
}
ul li > :first-child,
ol li > :first-child,
ul li ul:first-of-type,
ol li ol:first-of-type,
ul li ol:first-of-type,
ol li ul:first-of-type {
margin-top: 0px;
}
ul ul, ul ol, ol ol, ol ul {
margin-bottom: 0;
}
dl {
padding: 0;
}
dl dt {
font-size: 14px;
font-weight: bold;
font-style: italic;
padding: 0;
margin: 15px 0 5px;
}
dl dt:first-child {
padding: 0;
}
dl dt>:first-child {
margin-top: 0px;
}
dl dt>:last-child {
margin-bottom: 0px;
}
dl dd {
margin: 0 0 15px;
padding: 0 15px;
}
dl dd>:first-child {
margin-top: 0px;
}
dl dd>:last-child {
margin-bottom: 0px;
}
/* CODE
=============================================================================*/
pre, code, tt {
font-size: 12px;
font-family: Consolas, "Liberation Mono", Courier, monospace;
}
code, tt {
margin: 0 0px;
padding: 0px 0px;
white-space: nowrap;
border: 1px solid #eaeaea;
background-color: #f8f8f8;
border-radius: 3px;
}
pre>code {
margin: 0;
padding: 0;
white-space: pre;
border: none;
background: transparent;
}
pre {
background-color: #f8f8f8;
border: 1px solid #ccc;
font-size: 13px;
line-height: 19px;
overflow: auto;
padding: 6px 10px;
border-radius: 3px;
}
pre code, pre tt {
background-color: transparent;
border: none;
}
kbd {
-moz-border-bottom-colors: none;
-moz-border-left-colors: none;
-moz-border-right-colors: none;
-moz-border-top-colors: none;
background-color: #DDDDDD;
background-image: linear-gradient(#F1F1F1, #DDDDDD);
background-repeat: repeat-x;
border-color: #DDDDDD #CCCCCC #CCCCCC #DDDDDD;
border-image: none;
border-radius: 2px 2px 2px 2px;
border-style: solid;
border-width: 1px;
font-family: "Helvetica Neue",Helvetica,Arial,sans-serif;
line-height: 10px;
padding: 1px 4px;
}
/* QUOTES
=============================================================================*/
blockquote {
border-left: 4px solid #DDD;
padding: 0 15px;
color: #777;
}
blockquote>:first-child {
margin-top: 0px;
}
blockquote>:last-child {
margin-bottom: 0px;
}
/* HORIZONTAL RULES
=============================================================================*/
hr {
clear: both;
margin: 15px 0;
height: 0px;
overflow: hidden;
border: none;
background: transparent;
border-bottom: 4px solid #ddd;
padding: 0;
}
/* IMAGES
=============================================================================*/
img {
max-width: 100%
}
-->
隐藏细节
现实生活中有很多隐藏细节的案例,比如我们平时用的电脑,当我们按电源按钮后电脑就自动开始启动了,对用户来讲很简单只需要知道按按钮就行。但电脑内部的工作原理其实是很复杂的一个流程,这里不多说。
如果不隐藏细节会怎样?
我想可能的结果就是电脑只能是特别特别的专业人员才能操作,永远无法像现在一样成为大家的必备工具。对大多数用户来讲他们根本不知道知道什么CPU,内存,硬盘,显卡相互之间是如何配合工作的,只关心打开电脑后能够正常使用软件完成他们的任务即可。
门面模式
在面向对象设计中,GOF有个门面模式就是对客户端隐藏细节的一个典型应用,也可以看看我早几年前的笔记:门面模式。
WEB API网关
通常WEB API网关是系统的唯一入口,它封装了系统内部架构,为客户端统一提供服务。有一些与业务无关的公共逻辑可以抽象到网关中实现,比如客户端的认证,访问控制,监控,缓存等,示意图如下。
客户端认证
无论是对内网还是外网的接口都是需要做用户身份认证的,而用户认证在一些规模大点的公司都会有统一的单点登录系统,如果每个微服务系统都是做对接单点登录系统的工作,那么显然比较浪费资源,开发效率低。可以将认证的部分抽取到网关层,然后微服务系统无需关注认证的逻辑只关注自身业务即可。访问控制
对一些特定的接口设置白名单,访问次数,访问频率等各类设置。而这些非业务功能的配置以及变更不会影响微服务的实现可以在网关层单独做操作。负载均衡
可以灵活的在网关层制定负载均衡策略。安全
可以统一在网关层增加一个额外的保护层来防止恶意攻击,如果客户端直连微服务的话,每个暴露的微服务都需要面临安全问题。
WEB API网关在设计上与上面提供到门面模式是相当的,也是对客户端隐藏细节。除了上面提供的那些常见公共功能外,还有如下一些实用的功能:
限流
对于大型互联网项目还会有限流的需求。为了防止站点不被未知的大流量冲跨,有可能会采取限流的策略,网关配置一个阀值,当请求数超过阀值时就直接返回错误而不会走剩下的逻辑。
限流如何实现?限流的方案有很多:
- 在网关层可以利用hystrix来实现。
- 如果是针对待定的客户端也可以利用nginx的限流。
- guava提供了一个RateLimiter,它是基于令牌桶的算法实现,以固定的速率往队列中放令牌,可以结合它自己实现限流可以结合它自己实现限流。
可兼容更多的协议
比如有些服务是SOAP,基于二进制的Thrift,还有DUBBO这类RPC实现,可以统一转换成HTTP来对外提供。
微服务带来的问题
随着业务的发展,原来简单的系统会变得越来越复杂,一个团队变成多个团队,多个团队同时在一个系统中开发会存在各种各样的问题,数据量的增长也会使单库的性能越来越慢,所以随其自然的会按业务对系统进行垂直划分,比如:
- 产品系统
- 价格系统
- 促销系统
- 订单系统
- 库存系统
- 评论系统
- 推荐系统
- 用户系统
这些系统当下比较流行的是以微服务的形式存在,暴露一批细粒度的接口给其它系统调用。
前端系统如何调用微服务?
比如用户查看一个产品的明细页面,它会包含产品基本信息,价格信息,促销信息,推荐信息,评论信息等,按上面的微服务组成,前端系统想拿到产品的所有数据需要调用众多的微服务,这在要求性能的互联网项目上是不太可行的,光http请求就比之前增加多倍,而且也会增加客户端的复杂度,它需要知道所有这些微服务的详细信息。
不要让前端知道微服务的存在
即使系统从业务领域的层次上被划分成多个独立的微服务,但对于前端系统还是应该隐藏细节,提供粗粒度的接口。
系统架构
这里回顾下以前我参与的一个跨境电商系统,从架构来看还是做的比较标准的。前端是APP以及H5,对接一个mobile api,mobile api内部包含各类子服务。
其实我们是针对项目的,电商系统对接mobile api,另外一个线下店的APP对接的新开发的store api。这两个api是完全独立的,并不是一个公司一个web api,所以说我们这两web api是项目级别的网关,而有些公司可能会提供公司级别的网关。
架构简要说明:
- 前端是APP+H5
- H5站点是通过Nginx做反向代理去执行js,不懂APP,所以略过。
- Mobile API,H5以及APP唯一对接后端的入口,采用Spring MVC实现。里面包含了所有前端需要用到的接口。
- 微服务,DUBBO实现的RPC,数据库中间件mybatis。
- 缓存,基于Spring Cache+redis。
- 检索系统,基于elasticsearch。
- 消息系统,RabbitMQ。上图中没有体现,是将业务数据更新到检索系统的一个broker。
未用到限流,当时数据量太小,担心的不是服务器被冲跨是担心没人冲。
也不包含一些并行请求合并的高级用法,可以理解成一个高内聚的服务。
WEB API网关的优点
- 隐藏细节,对客户端友好
- 简化了客户端开发复杂度
- 降低了客户端与服务端交互交互
- 可统一做切面任务,避免每个子系统各自为营,五花八门
- 使客户端与服务端解耦,容易构造异构系统
WEB API网关的缺点
- 需要增加一个高可用伸缩性强的站点。
- WEB API网关项目在开发上是个串行任务,每暴露一个接口都需要去更新WEB API网关,如果同时有不同部门的需求去更新就会存在排队更新的情况。
上面的缺点相对WEB API网关带来的缺点是可以容忍的。
理解WEB API网关的更多相关文章
-
如何理解 Web API
什么是web API? web API 控制器.路由 测试 Web API 什么是web API ? 简单说,API是接口,访问程序的某一个功能或者数据,实现移动端和客户端的程序之间的数据交互: ...
-
.net core自定义高性能的Web API服务网关
网关对于服务起到一个统一控制处理的作用,也便于客户端更好的调用:通过网关可以灵活地控制服务应用接口负载,故障迁移,安全控制,监控跟踪和日志处理等.由于网关在性能和可靠性上都要求非常严格,所以针对业务需 ...
-
集成架构:对比 Web API 与面向服务的架构和企业应用程序集成(转)
http://kb.cnblogs.com/page/521644/ 摘要:总体上讲,SOA 和 Web API 似乎解决的是同一个问题:以实时的.可重用的方式公开业务功能.本教程将分析这些举措有何不 ...
-
(转)集成架构:对比 Web API 与面向服务的架构和企业应用程序集成
摘要:总体上讲,SOA 和 Web API 似乎解决的是同一个问题:以实时的.可重用的方式公开业务功能.本教程将分析这些举措有何不同,以及如何将它们融入到一个不断演变的集成架构中.文中还将讨论 API ...
-
谈谈微服务中的 API 网关(API Gateway)
前言 又是很久没写博客了,最近一段时间换了新工作,比较忙,所以没有抽出来太多的时间写给关注我的粉丝写一些干货了,就有人问我怎么最近没有更新博客了,在这里给大家抱歉. 那么,在本篇文章中,我们就一起来探 ...
-
微服务中的 API 网关(API Gateway)
API 网关(API Gateway)提供高性能.高可用的 API 托管服务,帮助用户对外开放其部署在 ECS.容器服务等云产品上的应用,提供完整的 API 发布.管理.维护生命周期管理.用户只需进行 ...
-
谈API网关的背景、架构以及落地方案
Chris Richardson曾经在他的博客上详细介绍过API网关,包括API网关的背景.解决方案以及案例.对于大多数基于微服务的应用程序而言,API网关都应该是系统的入口,它会负责服务请求路由.组 ...
-
服务中的 API 网关(API Gateway)
我们知道在微服务架构风格中,一个大应用被拆分成为了多个小的服务系统提供出来,这些小的系统他们可以自成体系,也就是说这些小系统可以拥有自己的数据库,框架甚至语言等,这些小系统通常以提供 Rest Api ...
-
[ASP.NET MVC 小牛之路]18 - Web API
Web API 是ASP.NET平台新加的一个特性,它可以简单快速地创建Web服务为HTTP客户端提供API.Web API 使用的基础库是和一般的MVC框架一样的,但Web API并不是MVC框架的 ...
随机推荐
-
sass高级语法
github地址:https://github.com/lily1010/sass/tree/master/course03 用到的sass语法是: sass --watch test.scss:te ...
-
字符串数组元素排列与组合的Java递归实现
我们在笔试面试过程中经常会遇到关于排列与组合的问题,其实这些可以通过递归简单的实现,看下面两个例子: (1)关于字符串排列的问题 输入一个字符串,打印出该字符串中字符的所有排列.例如输入字符串ab ...
-
Oracle表连接总结
1 简述 1) 两个表的连接,是通过将一个表中的一列或者多列同另一个表中的列链接而建立起来的.用来连接两张表的表达式组成了连接条件.当连接成功后,第二张表中的数据就同第一张表连接起来了,并形成了复合结 ...
-
Chapter 1 First Sight——10
Instead, I was ivory-skinned, without even the excuse of blue eyes or red hair, despite the constant ...
-
UA判断跳转
<script type="text/javascript"> UA = navigator.userAgent.toLowerCase(); url = window ...
-
5.数字拆分成4段,怎样使得4段的乘积最小【dp】
题目是:给出一个数字(10,000-100,000,000),把这个数字拆分成4段,怎样使得4段的乘积最小.比如12345拆分成1*2*3*45=270, 10000=1*00*0*0=0. 解题分析 ...
-
/etc/redhat-release 查看centos 版本
查看centos 版本 [root@localhost ~]# cat /etc/redhat-release CentOS release 6.4 (Final)
-
Ubuntu之tar与curl操作
1,压缩备份: tar cfvj /tmp/test.tar.bz2 /tmp/test tar cfvz /tmp/test.tar.gz /tmp/test tar xfvj /tmp/tes ...
-
编写Spark的WordCount程序并提交到集群运行[含scala和java两个版本]
编写Spark的WordCount程序并提交到集群运行[含scala和java两个版本] 1. 开发环境 Jdk 1.7.0_72 Maven 3.2.1 Scala 2.10.6 Spark 1.6 ...
-
在jfinal的Controller中接受json数据
JFinal中接收URL中的参数或者model中的参数是很方便的,但是对于web2.0的网站来说,经常会以json方式提交比较复杂的数据,比如一个查询,包含了各种过滤条件和排序分页,前端脚本可能提交的 ...