移动互联网的架构设计浅谈一

一,图片体验的优化。

在手机上显示图片,速度是一个非常重要的体验点,试想,如果您打开一个网站,发现里面的图片一直显示失败或者是x,稍微做得好一点的,可能是一个不消失的loading或者是菊花等等,但不管如何, 没能快速的拉取和展示图片对用户体验是一个极大的挑战。那么,手机上的图片体验如何做呢?这里笔者有些小总结:

1,减少图片的大小。在失真度和图片大小中做好折衷,尽量利用工具减少图片的size,也可以考虑利用不同的图片格式。

2,减少图片的请求数。可以考虑把多个图片利用类似css sprite的方式进行合并,这样可以加载一次即可;

3,考虑缓存。对图片在客户端进行一定的缓存,设置好缓存时长和更新机制;

4,考虑使用cdn进行加载图片,做到就近接入访问;

5,解决DSN劫持的问题。在手机业务上的经验告诉我们,很可能某些地区,某些运营商把我们的域名封掉或者劫持了,这样,图片的域名解释出来的IP却不是我们提供图片服务的IP,并且这种情况很难发现,  因为,如果运营商通过抽样随机劫持,就很难发现。解决办法可以:

.去掉dns,改成直接访问IP的方式,但需要解决根据用户的ip获取最近图片服务的ip地址,实现上:这里cgi在吐出访问图片的地址的时候,获取用户的来源网关IP,调用IP地址库判断来源IP所属地和运营商,然后下发对应的图片部署接入IP, 客户端使用IP直连图片服务器,快速的访问资源。

问题是,有实现成本,得业务自己去实现类似一个dns解释的逻辑,特别是图片放到cdn的话,这样改造就无法使用cdn带来的加速服务能力。

.做好dns劫持的监控,实际上图片dns解释到的vip list肯定是在我们的一个白名单内,如果不是,则肯定属于dns劫持,客户端可以在某个时候拉取一下我们的vip list,作为监控和判断是否dns劫持的问题,如果dns的ip地址 不在白名单内,则替换使用白名单内的ip进行访问。

.考虑备用域名的方式,即如果一个域名拉取不到,改用备用域名进行访问,当然如果备用域名也被劫持,那就不行了。

6,不用图片,考虑文本替代方案。

二,优化后台的架构

后台返回越快,前端的体验就越好,因此,也需要对后台服务的调用链进行梳理,避免循环调用,快慢混杂等问题,基本的原则比较简单,都是一些设计方面的原则

1,轻重分离。服务中把访问量大,需要速度快的服务和访问量小,但业务逻辑复杂的流程从代码实现和物理部署上进行彻底分离,如用的接入cgi(甚至不同的域名),不同的后台server,不同的集群进行隔离。

如果放在一起,慢的会拖住快的,这就像木桶原理一样,最终的速度是由最慢的决定的,如果处理不好,可能导致整个服务堵塞不可用。

2,评估好业务的访问流程和路径设计,区分关键路径和非关键路径,设计上尽量考虑把关键路径转换为非关键路径,关键路径需要有多级容灾的考虑,非关键异常需要有监控。

3,考虑异步化。异步化相比同步的实现来说稍微复杂一些,或者说需要做的工作可能多些,但异步化的好处也会非常明显,特别是需要高性能的业务流程。常见的异步化实现策略是借助mq作为各个系统的缓冲, 生产者进程或者子系统把消息写入mq即可立即返回,而消费者进程或者子系统则定时从mq读取消息继续处理,并且把处理的结果通过回调通知或者写入返回mq给到生产者查询。当然,如果生产者是不关注结果的,那 就更加简单了,丢到mq后即可,这里的问题是整个mq是整个业务流程的关键,需要确保服务的高度可用和性能。

4,一些配置的动态加载,本地化存储,加上基于版本的更新机制。笔者也发现过有些业务cgi之所以在较少请求量的时候就出现了较高的负载,最终不得不用更多的机器来承担相应的请求量,定位最终原因是cgi在启动的时候需要加载 很多配置的东西,甚至很多配置并不是该cgi需要的,优化思路是:是按需加载,只加载该cgi需要的;提前加载配置到共享内存,同时增加版本号,维护好cgi自身进程的私有版本和共享内存的版本,cgi启动的时候比较版本号,发现不同,则 真正进行文件的重新Load到内存。还有一种模式是采用配置中心进行推送的模式,实现集中管理。

5,做好外部依赖的管理。一个业务流程可能往往要调用到外部的系统,并且这些系统可能不是你们团队维护的,如果该系统是非关键路径还好,如果是关键路径,那么做好对外部依赖的管理就显得更加重要了,那么如何做好外部依赖的管理呢?

这里有几个小的tips:

. 对外部调用的服务单独进行封装,如设计单独的proxy去调用外部的服务,这样的好处是方便集中监控和容灾逻辑等处理,在设计上把外部因素进行物理隔离的第一步,后续如果外部系统的协议或者ip地址得发生变化,则可以只修改该模块即可 快速修复;

. 严重建议对外部接口进行错误和超时的监控,一旦出问题,提前预警并快速解决,这里是有血的教训的,某业务和某平台提供者双方在纠结是谁的问题上吵得不可开交,不知道是谁的问题,业务说自己没问题,平台方说自己的服务也很快,如果 你能够拿出你的监控数据,接口超时设置是 1s, 超时的记录有n条,时间是ns,错误的记录有m条,主要错误类型是xxx,那对快速定位是非常有帮助的。

. 考虑是否可以弱化为非关键路径?有些调用可能是否无法弱化为非关键路径的,如登录态校验,失败了只能是业务流程终止,给用户返回失败(当然可能存在部分业务缓存session id作为异常的时候的备用,但这个不是很建议,原因很简单,可能导致入口 不唯一,甚至造成安全漏洞,这里需要具体案例具体分析)。有些路径是可以设计为非关键路径的,如数据上报,

. 关键路径的多级灰度模式。如果知道某个服务是关键路径,比如在支付前的请求billno_server获取唯一的订单号,从业务流程看,这个肯定是一个关键路径,没有订单号就无法下单,业务流程执行不下去,但如果每次下单都调用一次billno_server生成 一个订单号,偶尔的网络超时或者失败都是可能的,而对用户来说,就是此次下单提示大家都非常熟悉得不能熟悉的一句话:“系统繁忙,请稍后再试”,那么是否能够做得更好呢?或者至少减少这种概率呢?
一种思路是每次请求一批billno缓存到本地进程空间, 然后使用的时候先从本地缓存中取,没有了再去请求;一种是请求失败的时候,是否可以考虑用本地随机生成一个,在极端情况下弱化对该关键路径的依赖?

. 若关键路径的数据唯一来源是本业务,则可以考虑自建部分热点数据,一点出现问题,则切换到自建的部分热点数据,继续提供服务。

6,考虑到手机客户端的计算能力比较弱,在设计上是否把计算成本更多的往服务端移动,利用强大的服务器端计算能力提升用户体验,这一点也是微信架构设计给笔者的一个感受。

 三,优化链接

如何管理链接是一个老生常谈的话题了,这里主要长连接和短连接的问题。当然还有一些什么连接池等策略。

弱网络环境下,建立链接的时间非常长,网络质量测试数据显示,建立链接占用耗时接近1/3,走短链接又导致链接频繁,所以考虑将短链接改成长链接,在碎片时间内重复利用,减少建链耗时,此外,还有以下几个优点:

1,C/S的持续链接使得后端能够主动push关键数据到客户端,例如实时的通知,新数字提醒等等,能很好的改善体验,在短链接的情况下,只能依靠客户端进行定时轮询,不可避免的使新数据有所延迟。

2,进一步节省短链接过程中的包大小,短链接情况下,每次来回请求,都不可避免需要带上一些公共数据。长链接只用在建链接成功后的第一个包中上行这些数据,后续包则可以省掉这些字段,进一步减少流量;

3,长链接还能有效的减少流量限制类手机软件导致服务不可用的问题,有些流量限制类软件会接管用户的所有网络请求,以达到流量计算和断流的目的,这种本质上就是一种劫持,使用长链接+私有加密协议, 可以使得对方无法准确分析包情况,减少劫持到来的服务不可用情况。

4,长链接还可以减少在高并发下对临时端口的依赖,有些使用短链接的服务,在高并发下,发现临时端口不可用的问题也可以通过长链接得到缓急。

注意:使用长链接的时候,必然有长链接过期不可用的情况,因此,业务实现需要埋入重连机制。

 四,基于网络质量的多级服务设计

手机的网络环境比较多样,如wifi, 3G, 4G 还有2G等,不同的网络环境的体验是不同的,对非常好的网络环境我们就不说了,关键讨论一下在2G等比较恶劣的情况下的一些思考。

1,不同的网络环境是否具备多级的服务能力?如针对2g网络的用户,显示的内容更少? 图片变成文字?一些功能入口不可用?

2,减少网络协议包的大小。在网速很慢的情况下,包的大小至关重要,直接影响成功率,可以考虑更加紧凑的协议(包括不必要的字段不发送)+压缩算法。这里有个tips,大家知道cookie的内容都是每次跟在http请求一起发送给到服务器的, 对图片,js,ccs等建议部署其他域名进行cookie隔离,这样也可以减少一定的包大小。

移动互联网的架构设计浅谈一

时间: 2024-11-03 23:00:39

移动互联网的架构设计浅谈一的相关文章

客户端GUI测试技术和自动化测试架构设计简谈

客户端自动化特点 客户端的自动化,通常做过的人都不是很愿意深入讨论.因为除了功能和逻辑之外,不得不面对各种界面变化,各种和环境交互,各种兼容问题以及想不到灰色地带,就算这样,也找不到太多有效的bug.然而即便如此,客户端的自动化必须去做,尤其是GUI的.它的自动化特点是: 复杂 成本高 不容易发现问题 技术要求高 架构很难通用 下面,从一些基本的东西开始一点点的讨论客户端GUI测试的一些问题和处理办法,以及自动化架构设计的一些思路.事实上就像上面说的,GUI的测试并不是为了发现bug,而是回归的

【架构】浅谈web网站架构演变过程

浅谈web网站架构演变过程 前言 我们以javaweb为例,来搭建一个简单的电商系统,看看这个系统可以如何一步步演变. 该系统具备的功能: 用户模块:用户注册和管理 商品模块:商品展示和管理 交易模块:创建交易和管理 阶段一.单机构建网站 网站的初期,我们经常会在单机上跑我们所有的程序和软件.此时我们使用一个容器,如tomcat.jetty.jboos,然后直接使用JSP/servlet技术,或者使用一些开源的框架如maven+spring+struct+hibernate.maven+spri

互联网数据库架构设计思路

一 .58同城数据库架构设计思路 (1)可用性设计 解决思路:复制+冗余 副作用:复制+冗余一定会引发一致性问题 保证"读"高可用的方法:复制从库,冗余数据,如下图   带来的问题:主从不一致 解决方案:见下文 保证"写"高可用的一般方法:双主模式,即复制主库(很多公司用单master,此时无法保证写的可用性),冗余数据,如下图   带来的问题:双主同步key冲突,引不一致 解决方案: a)方案一:由数据库或者业务层保证key在两个主上不冲突 b)方案二:见下文 5

移动产品设计浅谈

一.充分考虑用户的使用习惯 比如大多数人拿手机的时候是双手握还是单手握?单手握的时候是右手操作还是左手操作?操作的时候用哪个手指就能进行操作? 考虑到用户的使用习惯有助于在设计时避开手指的触碰盲区. 二.充分考虑用户的使用场景和干扰源 用户使用产品是在什么时间,什么地点,什么环境下使用?譬如,用户经常在嘈杂的环境中使用自己的产品,这时候的干扰源就是噪音,产品设计时应避免使用语音技术:用户经常在拥挤的环境中使用产品,则产品设计时应避免用户过多地进行输入操作:用户经常在地铁等网络环境不好的场所使用产

白话设计——浅谈DIP和IOC

追本溯源,不断的回顾基础对我而言是种不错的方式,每次重新回顾这些点往往收获很大.以前,受个人所限,觉得这些理论毫指导价值价值,过于相信实践的的力量,导致自己进步缓慢.其实有些时候,实践更需要站在理论巨人的肩膀,这会让我们少走很多的弯路. 当然具体因人而异. 开发之困 实际开发中最常遇到的问题是类A直接依赖类B.当我们希望将类A修改为依赖类C时,就必须要通过修改类A来实现.这种 情况下类A作为高层的业务模块,负责复杂的业务模块,而类B和类C是底层模块,负责基本的原子操作.实际工程中类A作为业务模块

滴滴出行分而治之的架构设计之道

[本文是WOT2016互联网运维与开发者大会的现场干货,  新一届主题为WOT2016企业安全技术峰会将在2016年6月24日-25日于北京珠三角JW万豪酒店隆重召开!] 如今,我们去任何一个地方都要先问问有没有Wi-Fi,网络已经明显影响到我们的生活. 互联网生下来就是为了服务海量用户,在这个时代,几乎没有哪个应用再为单机而生.每个公司的每个产品将要面临的都是不可预知的用户海量请求.显然这个靠分布式程序来解决,比依靠单机靠谱得多.然而不幸的是,如果一开始你的架构设计不可扩展,有再多的机器,有再

机票实时搜索系统架构设计

机票实时搜索系统架构设计 ? 不同的业务场景,不同的特征 ? 结合特征去进?设计和优化 ? 通?!=最优 ? 量体裁? 分布式系统的CAP理论 首先把分布式系统中的三个特性进行了如下归纳:    ● 一致性(C):在分布式系统中的所有数据备份,在同一时刻是否同样的值.(等同于所有节点访问同一份最新的数据副本) ● 可用性(A):在集群中一部分节点故障后,集群整体是否还能响应客户端的读写请求.(对数据更新具备高可用性) ● 分区容错性(P):以实际效果而言,分区相当于对通信的时限要求.系统如果不能

iOS开发>学无止境 - 浅谈MVVM的架构设计与团队协作

李刚按:本文是青玉伏案写的一篇文章.相信大家对MVC耳熟能详,MVVM可能听说的相对少一些,这一篇文章将会想你阐述MVVM设计,还有团队协作的经验分享.如果你也觉得不错,就分享一下吧! demo:https://github.com/lizelu/MVVM 今天写这篇文章是想达到抛砖引玉的作用,想与大家交流一下思想,相互学习,博文中有不足之处还望大家批评指正.本篇文章的内容沿袭以往博客的风格,也是以干货为主,偶尔扯扯咸蛋(哈哈~不好好工作又开始发表博客啦~). 由 于本人项目经验有限,关于架构设

浅谈android架构设计

到目前为止,android开发在网络上或者社区上没有公认的或者统一的开发框架,好多框架都是基于对方法的封装.今天在这浅谈两年来对android开发的理解,主要是思想上的理解,希望对大家有帮助. 我认为android开发可以从两个方面去总结架构的设计,在这里对于实现只做陈述: 一,就是大多数人的设计思路,对方法的封装. 在这里我根据开发的习惯对工程进行包的设计: 1. http:网络请求方法封装.这里建议采用线程+Handler的模式,把Http 中get方法和post两种请求方式分开,对于正常的