最近一年经历了很多业务快速增长的情况,早期对容量的规划不足成为普遍现象,需要在实际业务中要不断调整。这就涉及到服务扩容。一般无状态请求的扩容,比如varnish转发http请求,因为不需要考虑状态迁移造成的问题,比较简单。复杂一点的就是有状态的扩容。有状态扩容主要的应用场景是服务器负载均衡技术以及数据库水平扩容。无论是服务器负载均衡还是数据库水平扩容,主要考虑的问题都是:1,怎么分配请求;2,怎么减少扩容对原有服务带来的震荡。
和大家分享一个真实案例,基于RTSP协议的点播消息负载均衡。RTSP是基于TCP的视频流控制协议。它的特点是点播过程中涉及使用的视频资源比较多,比如视频服务器端口,视频资源,cable资源等。因此要求同一点播会话最好分配给同一个服务器处理。这是典型的有状态(session-sticky)的负载均衡。有状态服务分配采用hash方式是最常见的解决方案,好处是即可以做到均匀分配,又可以实现session sticky,即相同session id的请求都会分配给相同的服务器。缺点是hash容易,re-hash难。以hash方式分配,扩容时的震荡较大。这也是为什么有一致性hash的原因。另一个条件是,服务器性能和配置不是完全相同的。我们希望可以在性能高的机器上多跑些业务,所以采用hash分配就不满足要求。我们考虑给服务器分配一定权重,再此基础上再作随机分配。但缺点是采用固定的权重,可能导致服务器负载严重不平衡。但如果采用某种探测算法,又有一定风险。比如某一RTSP服务器所管辖的视频服务器下属的链路断开,这样所有点播会话都会结束。但RTSP服务器不知道这个点播结束是否是正常的,这样这台负载非常轻的服务器实际是一台不能正常提供服务的服务器。为了避免这种风险,还是决定采用固定权重和随机分配相结合。好处是扩容很方便。缺点是必须使用一个session id和服务器ip的对应表,每次请求到达时先查这个表,对性能有影响。更重要的是,如果采用hash分配,前端的负载均衡服务是可以多点的,只要hash算法一致,无论哪台负载均衡服务器都会给相同的session分配相同的服务器。但如果使用对应表,则只能使用单点,而且对于session id必须使用同步锁,否则就可能为相同的会话分配不同的服务器。这是一个很严重的瓶颈!
因此,最后的方案是使用手工一致hash和分配表结合。我们用了一个很简单的手工一致性hash解决hash扩容的问题。 基本思路是,在服务上线初期,就分配有足够大的逻辑服务器地址表。当需要扩容的时候,只需要更改逻辑服务器指向的物理服务器就可以。而不需要更改逻辑服务器数量,我写了一个简单的程序来验证,当re-hash发生时,采用手工一致性hash,重复命中率达到90%。而简单增加服务器数量,选择相同服务器的几率仅有8%。这个思路也是Redis作者谈到解决re-hash问题时用的方法。这种通过大逻辑服务器表提高命中率的思路类似于一致性hash,但是更简单。我就称为手工一致性hash。
在使用手工一致性hash的情况下,再加上对应表,可以实现平滑的扩容服务器。已分配的服务器的会话继续使用已分配的服务器,而没有分配过的,则按新逻辑hash表进行分配。同时,还可以解决单点问题。这个方案并不是独创,在业界是经常使用的方案。我后来在某微博工作时,也是广泛的使用这个方案作为负载均衡应对未来扩容的解决方案。但相对大型互动社区而言,并不是所有的公司都必须采用此种方案。比如广电行业CDN服务器分配时,也是根据媒资名字做hash分配,但重新增加服务器时,往往对片源做很大调整。原先的hash分配可能会大部分失效,这是追求重复命中率高就意义不大。核心业务,在业务不需要的情况下,引入多一层架构,就增加多一份人力和维护成本,构架更需要考虑的是如何做减法,而不是做加法。
验证rehash命中率的伪代码如下,logicServers应扩大为如:
"s1", "s2", "s3", "s4", "s5", "s6", "s7", "s8", "s9", "sa", "sb", "s1", "s2", "s3", "s4", "s5", "s6", "s7", "s8", "s9", "sa", "sb"
, "s1", "s2", "s3", "s4", "s5", "s6", "s7", "s8", "s9", "sa", "sb", "s1", "s2", "s3", "s4", "s5", "s6", "s7", "s8", "s9", "sa", "sb"
这样连续重复,使得逻辑server表扩大到200以上
private void test() throws Exception
{
Integer localInteger;
HashMap localHashMap = new HashMap();
ArrayList localArrayList = new ArrayList();
String[] logicServers = { "s1", "s2", "s3", "s4", "s5", "s6", "s7", "s8", "s9", "sa", "sb" };
String[] logicServers2 = { "s1", "s2", "s3", "s4", "s5", "s6", "s7", "s8", "s9", "sa", "sb", "sc" };
float f1 = 0.0F; float f2 = 0.0F; float f3 = 100000.0F;
for (int i = 0; i < f3; ++i) {
localArrayList.add(Integer.valueOf(Math.abs(new Random().nextInt())));
}
for (Iterator localIterator = localArrayList.iterator(); localIterator.hasNext(); ) {
localInteger = (Integer)localIterator.next();
localHashMap.put(localInteger, logicServers[(localInteger.intValue() % logicServers.length)]);
}
for (localIterator = localArrayList.iterator(); localIterator.hasNext(); ) {
localInteger = (Integer)localIterator.next();
String str = logicServers2[(localInteger.intValue() % logicServers2.length)];
if (str.equals(localHashMap.get(localInteger))) {
f1 += 1.0F;
}
else {
f2 += 1.0F;
}
}
System.out.println(new StringBuilder().append(logicServers.length).append("|").append(logicServers2.length).append(", same=").append(f1).append(" samepercent= ").append(f1 / f3 * 100.0F).append("%, diff=").append(f2).toString());
}
分享到:
相关推荐
至于"+"运算符与StringBuilder的比较,虽然在编译后,Java会自动优化简单的字符串连接操作,将其转换为StringBuilder的方式,但这种优化并不总是设定初始容量,可能导致不必要的扩容。因此,对于复杂的字符串连接,...
- **实时性、扩容性强**:强调服务器具有良好的响应速度和扩展能力。 - **技术资料完整**:确保文档齐全,便于后续的维护和支持。 - **验收通过**:经过综合评估,验收小组认为服务器达到标准,可以投入运行。 ####...
尽管服务功能简单且并未遇到大流量或高并发的压力,但在新功能部署后却触发了线上容器的自动扩容机制,最终扩容至8个容器,每个容器分配2GB内存。此现象引起了开发团队的关注,并怀疑存在内存泄漏问题。 #### 扩容...
- **原有功能扩容**:涉及用户管理、SP管理、订购管理、计费账务等多个方面,以满足业务扩展需求。 #### 三、业务模式 互联星空系统提供了多种业务合作模式,以适应不同场景和服务提供商的需求: - **门户合作**:...
4. **U盘扩容测试结果**:最为关键的一点,测试结果显示该U盘的真实容量仅为2GB左右,远低于标称的16GB,证明了这是一款经过非法扩容的假U盘。 #### 六、总结 综上所述,面对市场上泛滥的假Kingston U盘,消费者...
(2) 利用双活大数据平台特性实现无感知搬迁与扩容:文章强调利用双活大数据平台的特性,保持企业级大数据平台对外服务的连续性,在不中断业务的情况下完成数据平台的迁移和扩容。 在研究的具体内容中,详细描述了...
1. **SDS (Simple Dynamic String)**:简单动态字符串,类似于C语言中的字符串,但它支持动态扩容,从而减少了字符串操作时的复制成本。 2. **List (链表)**:链表结构,适合用于实现队列和栈等数据结构。 3. **...
2. **扩容问题**:当`HashMap`的元素数量达到容量的75%时,会触发扩容操作,将现有的数组复制到一个新的两倍大的数组中。在扩容过程中,如果多个线程同时进行,可能会导致数组元素复制不完整,从而破坏内部数据结构...
此外,报告还提到了非银金融行业的其他发展趋势,包括非银金融增持、保费小幅承压、证券配置性价比凸显、定制医疗保险的规范发展、资本市场扩容、大病保险管理再规范、REITs发售、基金投顾资格扩容、非银中报业绩向...
更重要的是,系统支持了按需扩容,以往需要三年规划的资源扩展,现在仅需一年就可以实现,大大缩短了应对紧急事件的响应时间。 文档还提到了基于容器化的云平台架构,在应用级资源配置和共享时能有效解决资源利用率...
8. **容量管理**:用户通常会有一个固定的存储空间,随着需求增加可以选择扩容。合理管理云端存储空间,避免文件过多导致空间不足,是使用网络U盘时需要注意的一点。 9. **移动设备接入**:除了桌面客户端,网络U盘...
此外,门窗五金、幕墙等行业正朝着中高端方向演进,提升了五金单价,从而带动了整个行业的扩容。 坚朗五金的发展逻辑在一定程度上可借鉴海外五金行业的龙头公司伍尔特和亚萨合莱的成长路径,这两家公司通过品类扩张...
为了应对这种高流量带来的挑战,网站架构必须具备高度的弹性,能够在短时间内进行水平扩容,以承载瞬时激增的用户访问。 技术架构方面,文档中介绍了从架构1.0到架构3.0的发展过程。架构1.0的核心思想是利用消息...
文章目录前言正文什么是散列表Hash的数据结构存储数据的数组散列函数Hash的负载因子开放寻址法链表法Hash结构的几个操作读操作开放寻址法的读操作链表法的读操作写操作开放寻址法的写操作链表法的写入扩容总结 ...
二是关注新兴品类的市场扩容以及品牌意识的增强,例如嵌入式厨电、集成灶、清洁电器等。报告中还建议关注包括格力电器、海尔智家、美的集团、火星人、浙江美大、老板电器、科沃斯和石头科技等企业。 评级面临的主要...
4. **生态扩容与新技术**:随着互联网产业新生态的发展,平台型企业如阿里云正在构建下一代生态基础设施,为新技术提供舞台。这不仅有助于生态的扩张,也为企业提供了更多的创新机会。 5. **企业与生态的耦合**:...
经纪业务受益于市场活跃度的提升,投行业务得益于IPO和债券承销规模的扩大,资管业务则因公募基金市场的扩容而保持增长态势,资金型业务则因股市和债市整体上涨而获得提升。这些业务的增长,直接推动了券商整体业绩...
例如,方程(5)和(6)分别代表同一组团和不同组团内部的路段通行能力增加量,而方程(8)和(9)则涉及路段扩容费用。此外,模型还考虑了路段容量的限制(如规划上限),以及各组团间联系强度的影响。 2. **下层...
例如,通过性能测量疏忙的方法,可以识别和调整话务溢出的问题,根据忙时话务负荷判断是否需要扩容,以及通过具体分析找出产生问题的根本原因。性能测量均衡话务可以确保话务和信令负荷均匀分布到各个模块和中继群,...