这意味着什么 - 将可扩展性设计到应用程序中。是否存在可以使应用程序更具可扩展性的设计模式?这个问题主要是在Web应用程序或基于SOA中间件的应用程序的上下文中。
答案 0 :(得分:7)
当我想到“大规模应用程序”时,我想到了三个非常不同的东西:
将在大型横向扩展群集(远大于1024个核心)上运行的应用程序。
将处理比物理内存大得多的数据集的应用程序。
具有非常大的代码源基础的应用程序。
每种“可扩展性”都会引入不同类型的复杂性,并且需要一组不同的妥协方案。
横向扩展应用程序通常依赖于使用MPI协调各种进程的库。一些应用程序“令人尴尬地并行”并且在不同进程之间需要非常少(或甚至没有)通信以完成任务(例如,渲染动画电影的不同帧)。这种应用程序趋向于基于CPU时钟速率或内存带宽的性能限制。在大多数情况下,添加更多内核几乎总是会增加应用程序的“可伸缩性”。其他应用程序需要在不同进程之间进行大量的消息流量,以确保解决方案的进展。这种应用程序风格往往受限于节点之间互连的整体性能。这些消息密集型应用程序可受益于非常高带宽,低延迟的互连(例如InfiniBand)。这种应用程序的工程可扩展性始于最大限度地减少所有进程对共享文件或资源的使用。
第二种可扩展性是在少量服务器(包括单个SMP样式服务器)上运行的应用程序,但它处理的是非常大的数据集或大量事务。向系统添加物理内存通常可以提高应用程序的可伸缩性。但是,在某些时候,物理内存将耗尽。在大多数情况下,性能瓶颈将与系统的磁盘I / O性能有关。在这些情况下,添加高性能持久存储(例如剥离的硬盘驱动器阵列),甚至为某种SAN添加高性能互连可以帮助提高应用程序的可伸缩性。这种应用程序的工程可扩展性从算法决策开始,这些算法决策将重复触摸相同数据(或设置相同的基础结构)的需要比完成任务所需的更多(例如,打开与数据库的持久连接,而不是打开每个事务的新连接)。
最后,存在与源代码库的总体大小相关的可伸缩性的情况。在这些情况下,良好的软件工程实践可以帮助最小化冲突,并保持代码库的清洁。这本书Large Scale C++ Software Design是我遇到的第一本真正承担了为大型源码基础软件开发提供最佳实践的挑战。本书侧重于C ++作为实现语言,但指南和实践可以应用于任何项目或语言。这种应用程序风格的工程可伸缩性涉及对代码结构做出高级决策,以最大限度地减少代码库中的依赖关系(例如,没有单个.h,当更改时将强制重建整个代码库,使用构建系统将尽可能重用.o。
答案 1 :(得分:1)
非常广泛地说,可扩展性意味着系统负载的增加可以通过必须整理以满足该负载的资产的相对较小的增加来处理。
如果您的网络应用上的负载增加了100倍,您会怎么做?
可扩展性的一个基本原则是识别和消除处理中的潜在瓶颈,包括收缩任务的并行化。但这只是一种品味;我相信你会得到很多其他同样有效的答案。
编辑:请注意,瓶颈不仅发生在实际的任务处理中。它们可以用于整体流程设置,必要的硬件操作,维护任务,重新设计/重构,您可以命名。
答案 2 :(得分:1)
以下是一些关于Web应用程序可伸缩性的优秀资源,可以帮助您入门:Tod Hoff的highscalability.com,Theo Schlossnagle的Scalable Internet Architectures和Cal Henderson的Building Scalable Web Sites。 Highscalability.com将为您指出很多值得阅读的演示文章和文章,包括this one from Danga关于他们如何在LiveJournal成长的过程中进行扩展。
答案 3 :(得分:1)
我认为当你谈论网络时,你主要关注的是:
通过这种方式,您可以将一台服务器扩展到多个层(应用程序层,缓存层,数据库层),并在出现扩展问题时将其水平展开。
答案 4 :(得分:1)
可扩展性意味着如果可以通过某个度量N(即用户数量,每天完成的事务总数等)来测量负载/数据,并且具有一些固定的响应要求t,则可以将应用程序重新配置为处理任意N给定O(f(n))的资源增加,其中f(n)是在相同响应时间t内线性或接近N的线性函数。
通常,这意味着应用程序使用分布式体系结构,以便可以线性添加更多服务器,应用程序服务器,Web服务器,数据库服务器以处理更多用户。即要处理两倍的用户,您需要添加两倍的数据库服务器,Web服务器,机器等。
即使理论上这通常也不可能,因为分发请求通常需要树状结构,因此缩放因子为O(n * log(N))。实际上,因为您可以在树中使用大分支因子,并且与总体事务成本相比分配成本较小,所以log(N)因子并不重要。