- 快召唤伙伴们来围观吧
- 微博 QQ QQ空间 贴吧
- 文档嵌入链接
- <iframe src="https://www.slidestalk.com/VoltDB/VOLTDB69894?embed" frame border="0" width="640" height="360" scrolling="no" allowfullscreen="true">复制
- 微信扫一扫分享
VOLTDB规划手册
前言
本手册用于帮助您对VoltDB做出规划。选择合适的技术不仅仅是在一组特性和另一组特性之间做出决定。了解产品如何适应现有的技术环境以及它在系统需求和技术支撑等方面的需要是很重要的。本书提供了评估VoltDB的指南,包括根据应用程序的特定需求和计划使用的VoltDB特性,对硬件、内存和磁盘的大小进行调整。
本手册主要内容
本手册分为五个部分
第一章 规划
第二章 POC
第三章 硬件选择
第四章 内存尺寸
第五章 产品基准测试
其他资源
本手册假设您已经熟悉了VoltDB特性。特性的选择,特别是那些与可用性和持久性相关的特性将影响规划。因此,如果您刚接触VoltDB,我们建议您访问VoltDB网站,熟悉产品选项和特性。
展开查看详情
1 . 目录 前言.............................................................................................................................................3 第一章 规划...............................................................................................................................4 第二章 POC................................................................................................................................5 2.1 有效分区.......................................................................................................................5 2.2 设计存储过程...............................................................................................................6 第三章 硬件选择.......................................................................................................................7 3.1 硬件配置调整...............................................................................................................7 3.2 吞吐量...........................................................................................................................8 3.3 容量分级.......................................................................................................................9 3.4 .持久化........................................................................................................................11 第四章 内存尺寸.....................................................................................................................13 4.1 数据库容量规划........................................................................................................ 14 4.1.1 定制数据表尺寸............................................................................................. 14 4.1.2 定制索引尺寸................................................................................................ 16 4.1.3 数据库尺寸评估............................................................................................ 17 4.2 集群中的数据分布.................................................................................................... 18 4.2.1 集群中的内存使用......................................................................................... 18 4.2.2 高可用环境中的内存计算............................................................................ 19 4.3 规划 Java Heap Size................................................................................................... 19 4.3.1 影响堆大小的属性......................................................................................... 20 4.3.2 如何决定 java 堆大小.....................................................................................20
2 .第五章 基准测试.....................................................................................................................21 5.1 性能基准测试............................................................................................................ 22 5.1.1 设计基准测试应用......................................................................................... 22 5.1.2 如何量度吞吐量............................................................................................. 25 5.1.3 如何量度延时................................................................................................ 26 5.2 确定分区数................................................................................................................ 27
3 . 前言 本手册用于帮助您对 VoltDB 做出规划。选择合适的技术不仅仅是在一组特性和另一组 特性之间做出决定。了解产品如何适应现有的技术环境以及它在系统需求和技术支撑等方面 的需要是很重要的。本书提供了评估 VoltDB 的指南,包括根据应用程序的特定需求和计划 使用的 VoltDB 特性,对硬件、内存和磁盘的大小进行调整。 1. 本手册主要内容 本手册分为五个部分 第一章 规划 第二章 POC 第三章 硬件选择 第四章 内存尺寸 第五章 产品基准测试 2. 其他资源 本手册假设您已经熟悉了 VoltDB 特性。特性的选择,特别是那些与可用性和持久性相 关的特性将影响规划。因此,如果您刚接触 VoltDB,我们建议您访问 VoltDB 网站,熟悉产 品选项和特性。 阅读以下书籍有助于更好地理解设计、开发和管理 VoltDB: VOLTDB 入门手册是对产品的快速介绍,建议新用户使用 VOLTDB 使用手册包括对产品特性和功能的完整介绍。 VOLTDB 管理手册针对系统管理人员,包括产品运维和集群管理等内容。 您可以在官方网站 http://www.VoltDB.com 上找到以上书籍和更多的产品帮助信息。
4 . 第一章 规划 欢迎使用 VoltDB,这是专为高容量事务应用程序设计的一流数据库。由于您正在阅读 这本书,我们假设您正在考虑将 VoltDB 作为现有或计划中的数据库应用程序。本书的目标 是帮助您理解这样的决策对您计算环境的影响,特别是对硬件需求的影响。 技术评价通常涉及几个相关但独立的活动: 特性评估 特性评估的目标是确定产品特性与应用程序需求的匹配程度。对于 VoltDB,我们强烈 建议您访问我们的网站,查看可用的产品概述和技术白皮书,看看 VoltDB 是否适合您。如 果您需要更多的信息,请直接与我们联系。 POC 概念验证(POC)通常是一个小型应用程序,它使用所提议的技术模拟关键业务需求。 POC 的目标是在小范围内验证该技术在目标使用方面的性能是否符合预期。 硬件规划 一旦确定 VoltDB 是应用程序的可行候选项, 下一步就是确定运行它需要什么硬件环境。 硬件规模调整需要理解业务应用程序的需求(容量、吞吐量和可用性需求)。本书的主要目标 是提供关于 VoltDB 的必要信息,以帮助您根据特定应用程序的需要执行这种分级操作。 基准测试 确定了技术的可行性之后,最后一项活动是执行基准测试,以根据预期的工作量评估其 性能。基准测试通常是针对 POC 应用或类似的原型应用程序执行的。基准测试可以帮助计 算、验证和优化硬件大小。 假设您已经进行特性规划。现在,您已经准备好进行下一步。在使用 VoltDB 构建概念 验证(POC)、调整硬件大小和对解决方案进行基准测试时,以下几章提供了实用的建议。
5 . 注意,本书对详细的应用程序设计本身没有帮助。关于应用程序设计的建议,我们推荐 关于 VoltDB 的其他书籍。特别是 VoltDB 使用手册。 第二章 POC 概念证明(POC)是一个小型应用程序,它用于测试解决方案中的关键需求。对于数据库 应用程序,POC 通常关注几个关键指标,分别是验证数据库是否能够支持建议的模式、查 询,以及最终的预期容量和吞吐量。(有关这方面的更多信息,请参阅基准测试一章。) POC 不是一个完整的原型。它只是用足够的代码来验证技术是否满足需求。根据特定 的业务需求,每个 POC 强调不同的数据库功能。一些可能主要关注容量,一些关注可伸缩 性,一些关注吞吐量,等等。 无论业务需求是什么,都必须正确设计 VoltDB 的两个关键方面,以确保概念得到真正 有效的证明。下面几节讨论如何在 POC 中使用分区和存储过程。 2.1 有效分区 VoltDB 是一个分布式数据库。它可以根据应用程序开发人员指定的数据列自动对数据 进行分区。您不需要指定每条数据记录的分区位置,VoltDB 会自动为您确定。然而,要想 要有效的利用数据分区特性,您需要仔细选择分区列。最好的分区列通常并不总是最明显的。 需要记住的重要一点是,VoltDB 同时对数据和计算进行分区。为了获得最佳性能,需 要对数据库表和相关查询进行分区,以便能够并行运行最常见的事务。用 VoltDB 的话说, 事务应该是“单分区的”。 一个单分区事务所操作的数据只位于一个分区上。换句话说,如果在 Employee 表的 EmpID 列上进行分区,EmpID 就是这个表的分区列。单分区事务要求,访问 Employee
6 .表的查询都必须包含 where Employee.EmpID = {value}。为了使单分区事务更容易创建, 并不是所有表都必须分区,不经常更新的表可以复制,这意味着可以在任何单分区事务中访 问它们,无论分区键值是什么。 在为数据库规划分区模式时,需要问自己的重要问题是: 哪些是关键的、最频繁的查询?(这些事务需要单分区事务) 对于每个关键查询,它访问哪些数据库表,使用哪些列? 可以复制这些表吗?(将较小的、更新频率较低的表作为复制表,方便进行关联查 询或 join 操作) 2.2 设计存储过程 将模式和事务设计为单分区是一回事。同样重要的是,确保存储过程的操作方式能够让 VoltDB 有效地完成其工作。 第一步是将事务定义为存储过程加载到模式中,关键事务不要以 ad hoc 方式查询数据 库。VoltDB 提供了用于执行任意 SQL 查询的@AdHoc 系统过程,这在构建早期原型以测 试查询或偶尔验证数据库内容时非常有用。但是@AdHoc 查询通常作为多分区事务运行, 因此不应该用于关键事务或频繁调用的事务。 第二步是确保使用 CREATE PROCEDURE 语句中的 PARTITION ON 子句在数据库模 式中正确标识单分区存储过程,并指定适当的分区列。 最后,在设计最大吞吐量时,使用异步方式从 POC 应用程序中调用存储过程。异步调 用允许 VoltDB 对事务(及其响应)进行排队,避免了事务完成、结果返回给 POC 应用程序和 调用下一个过程之间的任何延迟。 本书后面的基准测试为有效地设计和测试概念应用程序的证明提供了额外的建议。
7 . 第三章 硬件选择 VoltDB 的设计目的是在普通硬件上提供世界级的吞吐量。您不需要最新或最昂贵的硬 件来实现出色的性能。事实上,一组中低端服务器可以轻松地胜过单个高端服务器,因为 VoltDB 的吞吐量往往与集群中的服务器数量成线性关系。 人们经常问我们“我们应该使用哪种类型的服务器以及使用多少服务器?”好消息是 VoltDB 非常灵活。它适用于各种配置。坏消息是,这个问题的真正答案是“视情况而定”。 没有一种配置适合所有情况。 与任何技术问题一样,在为您的应用程序选择“正确”的硬件时也要进行权衡。本章解 释了这些权衡是什么,并提供了一些通用的经验规则,这些规则可以帮助您为 VoltDB 选择 合适的硬件配置。 3.1 硬件配置调整 对单个服务器进行规划有三个关键方面:处理器的数量和速度、内存的总量以及磁盘的 大小和类型,需要考虑的第四个维度是:要使用的服务器数量。 这些维度中的每一个都会影响 VoltDB 性能的不同方面。处理器的数量影响每个服务器 上可以有多少个分区,从而影响吞吐量。可用内存明显影响容量或可存储的数据量。磁盘的 大小、数量和类型影响可用性特性(如快照和命令日志记录)的性能。 然而,它们也相互作用。每个服务器的内存越多,执行快照或节点在失败后重新连接所 需的时间就越长。因此,增加服务器数量,但减少每个服务器的内存数量可能会降低持久性 对总体数据库性能的影响。这些都是需要考虑和权衡的。 下面几节将从 VoltDB 的三个关键方面讨论硬件大小:
8 . 吞吐量 能力 耐用性 3.2 吞吐量 运行 VoltDB 数据库服务器的最低硬件要求是一台 64 位机器,拥有两个或多个处理器 内核。服务器拥有的内核越多,该服务器上可能运行的数据库分区就越多。分区越多,越多 数据库的吞吐量就越大。然而,处理器的内核数量并不是限制吞吐量的唯一因素。服务器配 置的不同方面影响数据库进程的不同特性。 例如,尽管服务器拥有的物理内核越多,就会增加服务器可能处理的分区数量,但是在 某种程度上,接收的事务数量和返回的数据有可能会超过了该服务器的网络端口容量。因此, 一台机器上超过 12-16 个内核可能对 VoltDB 数据库没有什么价值,因为服务器的网络适配 器成为限制因素。 经验法则 VoltDB 在 4-16 核服务器上运行最好。 应该注意的是,前面的讨论涉及物理处理器内核。一些服务器支持超线程。超线程本质 上是处理器内核的虚拟化,是物理内核数量的两倍。例如,一个具有 4 个内核和超线程的 系统就像一台 8 个内核的机器。这些虚拟化内核可以提高 VoltDB 性能,特别是对于物理核 心数量很少(2 或 4)的服务器。然而,服务器的物理内核越多,对 VoltDB 性能的改善就越 小。因此,对于物理内核超过 8 个的 VoltDB 服务器,不建议使用超线程。为提高吞吐量而 向单个服务器添加处理器的替代方法是添加更多的服务器。如果一个 4 核服务器可以处理 3 个分区,那么两个这样的服务器可以处理 6 个分区,3 个可以处理 9 个分区,等等。这就是
9 .VoltDB 在吞吐量上提供线性扩展的方式。 但同样,扩展服务器数据也有限制。对于峰值性能,将集群节点之间的网络延迟和中断 保持在最小是关键。换句话说,集群的所有节点都应该位于同一个网络交换机上。显然,网 络交换机的容量限制了它所能支持的节点数量。 经验法则 一个 2-32 个节点的 VoltDB 集群,通过同一交换机连接,可以提供最好的性能。 跨交换机的 VoltDB 集群是可能的(例如,在云环境中几乎总是这样)。然而,集群节点 之间的延迟将对性能产生负面影响,并可能最终限制总体吞吐量。在这些情况下,最好对不 同的配置进行基准测试,以确定预期的性能。 最后,应该注意的是,处理器内核的速度可能对总体吞吐量没有显著影响。处理器速度 影响执行单个事务所需的时间,这可能只是总体吞吐量中的一小部分。对于计算密集型事务 的工作负载,更快的处理器可以提高整体性能。但是对于许多小的或简单的事务,改进的处 理器速度几乎没有影响。 3.3 容量分级 数据库规模调整的第二个方面是容量。容量描述数据库可以容纳的最大数据量。因为 VoltDB 是内存数据库,所以容量受到集群中所有节点的总内存的限制。当然,服务器的内 存大小设置不能太精确。应该考虑到数据随时间的增长以及数据库服务器中使用内存的其他 部分,这一点非常重要。 第四章内存尺寸中详细说明了中 VoltDB 服务器如何为数据库内容分配内存。当您有一 个已知的模式时,使用该章执行准确的大小调整。然而,作为一个粗略的估计,您可以使用 下表来近似每一列所需的空间。通过将每个列和索引(包括索引指针)相加,然后乘以预期的
10 .行数,可以确定存储数据库内容所需的内存总量。 表 3.1 字段和索引大小 对于用字符而不是字节声明的 VARCHAR 列,长度计算为每个字符 4 个字节。 换句话说,对于存储计算,声明为 VARCHAR(16)的字符串列与声明为 VARCHAR(64 BYTES) 的列长度相同。 您还必须考虑服务器进程本身所需的内存。如果您知道数据库将包含多少个表,以及每 个主机将使用多少个分区,则可以使用以下公式计算服务器进程内存需求: 384MB + (10MB X number of tables) + (128MB X sites per host) 这个公式假设您使用 K-safety,这是推荐用于所有生产环境的。如果集群也是数据库 复制的主数据库,那么应该将每个主机的站点的乘数从 128M 增加到 256M: 384MB + (10MB X number of tables) + (256MB X sites per host) 如果您不知道数据库将包含多少个表,或者您不确定每个主机使用多少个分区,您可以 使用 2g 作为中等大小的数据库和服务器的服务器进程大小的粗略估计。但是请注意,一旦 定义了实际配置,您可能需要增加这个估计数。 最后,您对服务器总体所需内存的估计是数据所需内存和服务器进程本身所需内存的组 合,再加上 30%作为缓冲区。
11 . Server memory = ( content + server process ) + 30% 当集群成员调整时,计算每个服务器上内容所需的内存大小是总内容大小除以服务器数 量,再加上复制表的百分比。例如,如果复制 20%的表,则每台服务器所需空间的粗略估 计为: Per server memory = ( ( content / servers) + 20% + server ) + 30% 在为 VoltDB 服务器分配内存大小时,一定要记住以下几点: 内存使用不仅包括数据存储,还包括处理事务、管理队列和服务器本身处理的临时 存储。 即使在最好的数据分区方案,数据分布也永远不会完全平衡。需要考虑跨服务器的 负载变化。 如果内存使用量超过总内存的 70%,操作系统就会开始分页和交换,严重影响性 能。 经验法则 将每个服务器的内存使用量控制在总内存的 50-70%以内。 内存技术和颗粒密度发展得如此之快(类似于处理器内核的增加),因此可以配置少量具 有非常大内存容量的服务器,这些服务器提供的容量和性能相当于大量较小的服务器。但是, 使用的内存数量可能会影响数据库管理的其他方面的性能,比如快照和故障恢复。下一节将 讨论为这些特性调整大小时需要考虑的一些权衡。 3.4 .持久化 持久性是指数据库承受(或从)意外事件中恢复的能力。VoltDB 有几个特性可以提高数 据库的持久性,包括 K-Safety、快照、命令日志记录和数据库复制。
12 . K-Safety 复制分区来提供冗余,以防止服务器故障。请注意,当您启用 K-Safety 时, 您正在跨硬件复制惟一的分区。因此,任何一个副本的硬件资源(特别是服务器和内存)都在 减少。为 K-Safe 集群调整硬件大小的最简单方法是根据预测的吞吐量和容量调整数据库的 初始实例大小,然后将服务器数量乘以所需的副本数量(即 K-Safety 值加 1)。 经验法则 在使用 K- safety 时,将集群节点的数量配置为数据库副本数量的整数倍(即 K+1)。 在正常情况下,K-Safety 对性能没有真正的影响。然而,在从故障中恢复时,集群配 置可能会影响性能。在 K-Safe 集群中,当一个失败的服务器重新加入时,它从集群的其他 成员那里获得所有分区的副本。分区容量越大(内存大小),恢复分区所需的时间就越长。由 于恢复操作可以阻止数据库事务,因此使用大型服务器或小型服务器的权衡是很重要的,大 型服务器更容易管理,而更多的小型服务器可以用更少的时间恢复。 其他两个持久性特性——快照和命令日志——对内存和处理能力的影响很小。然而, 这些特性确实需要磁盘上的持久存储。 大多数基于 VoltDB 的磁盘特性,如快照、导出、网络分区等,都可以在标准磁盘技术 (如 SATA 驱动器)上得到支持。假设磁盘有足够的容量,它们还可以共享单个磁盘上的空间。 另一方面,命令日志记录与时间有关,必须跟上服务器上的事务。《VoltDB 使用手册》 的命令日志一章详细讨论了异步和同步日志记录之间的权衡,以及每种日志记录使用的恰当 硬件。但总的来说: 使用快速磁盘(如电池支持的高速缓存驱动器)进行同步日志记录 使用 SATA 或其他商品驱动器进行异步日志记录。但是,为命令日志使用专用驱动 器仍然是一个好主意,以避免日志和其他磁盘活动之间的并发问题。 经验法则
13 . 当使用命令日志记录时,无论是同步的还是异步的,都要为命令日志使用专用驱动器。 其他磁盘活动(包括命令日志快照)可以共享一个单独的驱动器。 最后,数据库复制(DR)不会影响服务器的内存大小或处理能力。但是对于每个额外的 集群,它确实需要初始硬件的副本。例如,当使用被动 DR 时,您应该将估计的服务器数量 加倍—一个副本用于主集群,一个副本用于从集群。当使用跨数据中心复制(XDCR)时,您 需要为参与 XDCR 的每个集群提供一个完整的副本。 经验法则 在使用数据库复制时,将所需的服务器数量乘以涉及的集群数量——两个集群用于被动 DR(主服务器和副本);两个或多个集群,用于 XDCR 环境中。 第四章 内存尺寸 系统规模评估的一个重要方面是规划应用程序所需的内存。因为 VoltDB 是内存数据库, 所以分配足够的内存非常重要。 第 3.3 节“容量分级”提供了一些简单的公式来估计未来应用程序的内存需求。如果您 已经处于定义良好数据库模式的阶段,并且希望更精确地测量潜在内存使用情况,本章将详 细介绍如何分配内存。 对于 VoltDB 数据库,有三个方面的内存大小必须考虑: 了解存储数据本身需要多少内存,即数据库的内容 根据分区表与复制表的比例和 K-safety 值评估数据在集群中的分布情况 确定服务器进程的内存需求 每个服务器的估计数据需求和服务器进程所需的 java 堆大小之和是服务器的总内存需 求。
14 . 4.1 数据库容量规划 要有效地计划数据库容量,您必须预先知道数据的结构和容量。这意味着您必须至少有 一个初步的数据库模式,包括表、列和索引,以及每个表的预期行数。将初始大小信息写下 来通常很有用,例如一下电子表格中的示例。您的计划还应该考虑到增长,因此您需要评估 初始量和长期增长值。下面是一个机票预订系统的数据库简化示例 使用数据库模式,可以计算单个表记录和索引的大小,这些记录和索引乘以容量可以很 好地估计存储数据库内容所需的总内存。下面几节解释如何计算单个表行和索引的大小。 4.1.1 定制数据表尺寸 单个表行大小取决于表中列的数量和数据类型。对于固定大小的数据类型,如 INTEGER 和 TIMESTAMP,列使用指定的字节数存储表记录。表 4.1“各数据类型的长度”指定了固 定大小数据类型的长度(以字节为单位)。 对于可变长度数据类型,如 VARCHAR 和 VARBINARY,数据的存储方式以及所需的 空间取决于数据的实际长度和最大可能长度。如果最大长度小于 64 字节,则数据内联存储 在元组中,作为固定长度的数据,使用最大字节数加上长度的 1。例如,VARCHAR(32 BYTES) 列占用 33 字节,无论实际数据有多长。
15 . 注意,VARCHAR 列可以用字符(默认值)或字节声明。对于存储计算,以字符声明的变 长字符串被认为每个字符占用 4 个字节。换句话说,在字符中声明为 VARCHAR(8)的可变 长度字符串占用的空间与声明为 VARCHAR(32 字节)的字符串相同。 如果最大长度为 64 字节或更多,则数据存储在内存池中,而不是内联的。为此,在元 组中内联存储一个 8 字节的指针,一个 24 字节的字符串引用对象,以及在池中存储数据本 身所需的空间。在池中,数据存储为 4 字节长度、一个指向字符串引用对象的 8 字节反向 指针,再加上数据本身。 存储在内存池中的数据不是以任意长度存储的。相反,数据被增加到最小的适当的“池 大小”,其中池大小是 2 的幂及其中间值。换句话说,池大小包括 2、4、6(2+4)、8、12(8+4)、 16、24(8+16)、32 等等,最大可达 1 兆字节的数据加上 12 字节的指针。 例如,如果 Customer 表中的 LastName 列定义为 VARCHAR(32)(即最大长度 128 字节),实际内容为 95 字节, 则实现消耗 160 字节: 注意,如果变量最大长度大于或等于 64 字节,那么即使实际内容小于 64 字节,它也 不会内联存储。只有当最大长度小于 64 字节时,可变长度列才内联存储。 表 4.1 各数据类型的长度
16 . 对于长度可变的并且小于 64 字节的列,使用上表可以非常精确地计算内存使用量。但 是,对于长度可变的列大于 64 字节的表,最多也只能是近似的估计。除了内存池带来的可 变性之外,任何大小计算都必须基于对变量列中数据的平均长度的估计。 对于最安全、最保守的估计,您可以在计算可变长度列时使用最大长度。另一方面,如 果有许多可变长度的列,或者您知道数据会有很大的差异,您可以使用一个估计的平均值或 乘以 90%,以避免过高估计内存消耗。 4.1.2 定制索引尺寸 索引的大小与表的大小类似,其中索引列的大小和数量决定索引的大小。 VoltDB 使用树索引。您可以通过将索引中每一列的大小加上 40 字节(指针长度)来计算 单个索引条目的大小。列的大小如表 4.1“各数据类型的长度”所述,除了非内联的二进制 数据外。对于长度等于或大于 64 字节的变长列,索引只包含一个 8 字节指针;数据本身没有 复制。 例如,Customer 表上的 CustomerByName 索引包含 VARCHAR(32)字段 LastName
17 .和 FirstName,每个条目的长度为 56 字节 如下公式计算索引的大小 (sum-of-column-sizes + 8 + 32) * rowcount 4.1.3 数据库尺寸评估 使用前面的公式,可以估算机票预订数据库的大小。我们可以根据列和数据类型估算 Flight 表的各个行。下表演示了 Flight 表的大小。 对于其他表和索引也可以进行相同的计算。结合表的记录行数,您将得到存储大约 500 兆字节的数据库内容所需的总内存的估计值,如下表所示。
18 . 4.2 集群中的数据分布 在最简单的情况下(单个服务器),上一节中计算的总和可以准确估计数据库内容所需的 内存。然而,VoltDB 在集群环境中伸缩性最好。在这种情况下,您需要确定每个服务器将 处理多少数据,这将受到服务器数量、分区表复制表的数量和大小以及所需的可用性级别(即 K-safety)的影响。 下面几节解释如何确定集群中分区表和复制表的分布以及 K-safety 的影响。 4.2.1 集群中的内存使用 很容易想到将数据库内容所需的总内存除以服务器的数量得到单节点内存需求,但这不 是一个准确的公式,原因有二: 并非所有数据都是分区的。复制的表(及其索引)出现在所有服务器上。 几乎没有分区方案能够提供完美的均匀分布。关注分布中的一些变化是很重要的。 要准确计算集群中每个服务器的内存使用量,必须考虑所有复制的表和索引,以及分区 表和索引在每个服务器的部分。 Data per server = replicated tables + (partitioned tables/number of servers)
19 . 对第 4.1.3 节中描述的机票预订系统数据库进行评估,复制表和索引(Flight 和 Airport) 所需的总内存大约只有 12 兆字节。其余分区表和索引所需的内存大约为 490 MB。假设数 据库在两台服务器上运行,每台服务器上的数据所需的总内存约为 256 兆: 当然,没有一种分区方案是完美的。因此,提供额外的空间(比如 20%到 30%)以允许 分区中的任何数据倾斜。 4.2.2 高可用环境中的内存计算 您计划与 VoltDB 数据库一起使用的特性也会影响容量规划,尤其是 K-Safety。通过在 集群中复制数据,K-Safety 提高了可用性,允许数据库在单节点故障中存活下来。 由于 K-Safety 涉及复制,它还增加了存储复制数据的内存需求。也许确定 K-Safe 集 群大小的最简单方法是确定非复制集群的大小,然后乘以 K-Safety 值+ 1。 例如,假设您计划在一个 6 节点集群上运行一个 K-Safety 值为 2(换句话说,3 个副本) 的数据库。确定每个服务器所需内存容量的最简单方法是计算一个 2 节点(非 k 安全)集群的 内存需求,然后创建该硬件和内存配置的三个副本。 4.3 规划 Java Heap Size 前面几节解释了如何计算存储数据库内容和索引所需的总内存。您还必须考虑数据库进 程本身,它在 Java 堆中运行。为最佳堆大小定义一个精确的公式是不可能的。但是,以下 基本准则可用于适应不同的硬件配置和数据库设计。
20 . 4.3.1 影响堆大小的属性 不同的数据库功能对服务进程影响最为直接,因此 java 堆大小取决于: 模式大小,取决于表和存储过程的总数 每个主机的分区数量 正在使用的特性,特别是 K-safety 和/或数据库复制 模式大小影响数据库进程的基本需求。模式拥有的表越多,包含的存储过程越多,就会 占用越多的堆空间。提供足够的堆空间是非常重要的,这样无论启用了什么其他特性,都可 以更新模式。 一般的经验法则是基本 Java 堆大小为 384MB,然后为模式中的每个表加 10MB 内存 空间。存储过程对堆大小的影响不像表的数量那么大。但是,如果您有很多存储过程(即成 百上千个),那么最好在基本堆大小中添加额外的空间,以便更好地运行。 除了基本堆大小之外,使用 K-safety 和数据库复制(对于主数据库)都增加了对 Java 堆 空间的需求,增加的数量与每个主机的分区数量成正比。一般来说,每台主机上的每个分区 都需要额外的 128MB 内存消耗。 例如,每个主机有 4 个分区的 K-safe 集群需要额外的 512MB,而每个主机有 8 个分 区的 K-safe 集群需要 1GB。如果该集群也是数据库复制的主集群,那么这些额外的堆需求 将分别增加一倍,达到 1GB 和 2GB。 4.3.2 如何决定 java 堆大小 确定 VoltDB 集群节点 java 堆大小的推荐方法如下: 步骤 1 使用以下公式计算基本 Java 堆需求: 384MB + (10MB X 表数)=Java 堆大小
21 . 如果您希望在将来添加表,请确保内存是可以扩展的。此外,如果您希望有大量的存储 过程(200 个或更多),请相应地增加堆大小。注意,超出最小设置的额外 Java 堆空间可以 提供更好的性能优势,比如模式更新和节点重新加入时。 步骤 2 根据生产中使用的硬件(特别是每台服务器的核心)和建议模式的性能测试,确定 每台主机的最佳分区数量。默认情况下,每个主机有 8 个分区。不建议将每个主机的分区 设置为大于 24。 步骤 3 确定将在生产中使用哪些数据库特性。所有生产环境都推荐使用 K-safety、网 络分区检测和命令日志记录。数据库复制(DR)是一个可选特性,它提供了额外的持久性。 如果使用了 K-safety,但 DR 没有使用,则将每个主机的站点数量乘以 128MB,以确 定特定于功能的 Java 堆需求。如果启用了 K-safety,并且集群是 DR 的主数据库,那么将 每个主机的站点数乘以 256MB。 步骤 4 将步骤 1 中定义的基本 Java 堆需求加上步骤 3 中特定于功能的需求,就是生产 服务器的推荐 Java 堆大小。 第五章 基准测试 基准测试是根据已知基线评估性能的过程。对于数据库应用程序,您可以根据其他技术、 目标指标(例如每秒处理的事务数量)进行基准测试,或者在不同的硬件配置上使用相同的应 用程序,以确定哪个生成的结果最好。 对于 VoltDB 应用程序,基准测试有助于建立以下指标: 最佳吞吐量 每个主机的最佳分区数量
22 . 5.1 性能基准测试 在为数据库应用程序建立性能标准时,通常有两个关键指标: 吞吐量——一次可以完成多少事务,通常以每秒事务或 TPS 来度量 延迟——每个事务花费的时间,通常用事务样本数量的平均或百分位延迟来度量 注意,这两个指标都不准确。对于许多数据库,吞吐量可能会随着事务类型的不同而变 化;无论是读操作还是写操作。VoltDB 的优点之一是,对于写操作和读操作,吞吐量不会发 生显著变化。然而,当存在许多多分区事务与单分区事务工作负载时,VoltDB 吞吐量确实 会发生变化。这就是为什么在对 VoltDB 数据库进行基准测试时,正确地设计模式和存储过 程很重要。 延迟可以是从客户机发出事务请求到接收响应的时间,或者从数据库服务器接收请求到 处理完请求的时间。 从客户机应用程序的角度来看,前一种度量(延迟)可能是最准确的。但是,这个度量包 括数据库延迟和客户机和服务器之间的任何网络延迟。后一种度量,即从数据库的角度来看 的延迟,是对技术能力更精确的度量。这个度量包括处理事务本身所需的时间(即存储过程 和它包含的数据库查询),以及请求在队列中等待执行的时间。 5.1.1 设计基准测试应用 吞吐量、延迟和系统配置之间存在关系。吞吐量综合了执行一个事务的时间(延时)和 并行处理事务的数量(并行处理事务取决于分区数量)。这就是将性能基准测试与服务器配 置基准测试结合起来进行的重要原因,稍后将对此进行讨论。不同的配置将导致不同的吞吐 量和延迟值。另外,应用程序本身的设计也会影响基准测试结果。
23 . 5.1.1.1 良好的应用设计 如前所述,吞吐量和延迟不是抽象的数字。它们是模式、存储过程、应用程序和服务器 配置的结果。与任何 VoltDB 解决方案一样,要有效地测试性能,必须从设计良好的应用程 序开始。具体地说: 对所有表进行分区(小型且主要是只读的表除外) 将所有频繁的事务设计为单分区 使用异步过程调用 有关编写有效的 VoltDB 应用程序的更多信息,请参见第 2 章 POC。 从 POC 开始基准测试是一种常见的实践,因为 POC 包含一个初始数据库模式和解决 方案所需的关键事务。如果您决定继续开发,那么在整个过程中定期对应用程序进行基准测 试也是一个好主意,以确保您了解附加功能如何影响您的总体性能目标。 然而,在对 POC 进行基准测试之前,确定如何度量性能非常重要。下面几节提供了有 用的信息,用于确定在 VoltDB 应用程序中度量什么以及如何度量。 5.1.1.2 速率限制 延迟和吞吐量是相关的。要度量吞吐量,您的测试应用程序可以尽可能快地进行存储过 程调用,然后度量每秒完成多少次(TPS)。但是,如果测试应用程序调用了更多的事务,而 服务器可以在该时间段内完成这些事务,那么在处理这些额外的调用之前,必须在队列中等 待。这些事务在队列中等待的时间将导致延迟度量突然出现峰值。 对于任何给定的应用程序和系统配置,都有最优的吞吐量。随着来自客户机应用程序的 调用速率的增加,TPS 会直接增加,而延迟则保持相对平稳。然而,当调用率接近并超过最 优吞吐量时,延迟会急剧增加,TPS 甚至可能下降,如下图
24 . 图 5.1 “确定最优吞吐量和延迟” 如果您的测试应用程序以最快的速度发送调用-你所能测量的只是上表右侧的错误吞吐 量和延迟。要确定最佳速率,您需要能够控制基准应用程序提交事务请求的速率。这个过程 称为速率限制。 简单地说,速率限制就是限制应用程序发出的调用数量。例如,下面的程序循环将应用 程序限制为每毫秒最多调用存储过程 10 次,或每秒 10,000 次。 boolean done = false; long maxtxns = 10; while (!done) { long txns = 0; long millisecs = System.currentTimeMillis(); while (millisecs == System.currentTimeMillis()) { if ( txns++ < maxtxns } { myClient.callProcedure(new SignInCallback(), "SignIn", id, millisecs); } } } 您可以使用命令行参数来参数化速率极限值 maxtxns,然后使用应用程序的多次运行 来创建一个类似于图 5.1 的图,“确定最佳吞吐量和延迟”。更好的方法是使用延迟限制来
25 .自动控制调用速率,并让应用程序接近最佳吞吐量值。 基于延迟的速率限制是如何实现的呢?方法是为目标延迟设置一个变量,同时为最大允 许吞吐量设置一个变量(如上例中的 maxtxns)。应用程序同时测量一段时间内的平均吞吐量 和延迟(例如,每 1 到 5 秒)。如果平均延迟超过目标,减少每秒最大事务数,然后重复。在 相同的时间段之内,如果延迟仍然超过目标,则再次降低最大事务速率。如果延迟确实达到 了目标,则增加最大事务速率。 通过使用基于延迟目标的速率限制和自动调整的组合,测试应用程序最终将确定当前配 置的最佳吞吐率。由 VoltDB 软件提供的示例应用程序(如 volter 和 VoltKV)即时采用这种 方法。 5.1.2 如何量度吞吐量 通常,为了进行基准测试,有必要对应用程序进行测量。也就是说,添加代码来度量和 报告基准数据。虽然可以(而且很容易)测试 VoltDB 应用程序,但是我们有更好的办法。 测量 VoltDB 数据库吞吐量的最简单方法是在基准应用程序运行时监视数据库。您可以 使用 VoltDB 管理控制台监视数据库,该控制台可以通过任何 VoltDB 服务器访问,并提供 数据库集群总体吞吐量的图形显示。要获得更详细的信息,可以使用变量来跟踪完成的事务 数量(在异步过程回调中增加变量),从而对应用程序进行测试。然后,通过将事务数除以自 上次报告以来的秒数,定期报告平均 TPS。 有关仪表化基准测试应用程序的示例,请参阅投票者示例应用程序。投票者应用程序的 自述说明了如何通过使用命令行参数自定义报表。
26 . 5.1.3 如何量度延时 还可以在不使用 VoltDB 管理控制台检测应用程序的情况下了解总体延迟。管理控制台 提供的延迟图显示了服务器的平均延迟,每隔几秒测量一次。有时,这种方法可以生成一个 具有极大起伏的锯齿图。在这种情况下,解释应用程序总体延迟的最佳方法是想象一条横过 图上高点的线。 为了让基准测试更加准确,您可以使用构建在 VoltDB 系统过程和 Java 客户机接口中 的延迟指标。要测试客户机应用程序,可以使用存储过程调用返回的 ClientResponse 对象 来测量延迟。ClientResponse 类包含 getClientRoundTrip()和 getClusterRoundTrip()方 法。这两种方法都返回一个整数值,表示处理事务所需的毫秒数。getClientRoundTrip() 方法报告总延迟,包括来自客户机应用程序的网络往返。 使用这些方法收集和报告自定义延迟信息很容易。例如,下面的代码片段捕获关于每个 过程回调期间的最小、最大和组合延迟的信息。 static class PocCallback implements ProcedureCallback { @Override public void clientCallback(ClientResponse response) { txncount++; int latency = response.getClusterRoundTrip(); if (latency < minlatency) minlatency = latency; if (latency > maxlatency) maxlatency = latency; sumlatency += latency; . . 基准测试应用程序可以使用这些信息定期报告特定的延迟值,如下所示: if (System.currentTimeMillis() >= nextreport ) { // report latency printf("Min latency: %d\n" + "Max latency: %d\n" + "Average latency: %d\n",
27 . minlatency, maxlatency, sumlatency/txncount); // reset variables txncount=0; minlatency = 5000; maxlatency = 0; sumlatency = 0; // report every 5 secsonds nextreport = System.currentTimeMillis() + 5000; } 5.2 确定分区数 基准测试的另一个重要目标是确定每个主机的最佳分区数量。每一个 VoltDB 服务器可 以托管多个分区,或称作“站点”。每个主机的理想站点数量与服务器上可用的处理器内核 数量有关。然而,这并不是一个精确的一对一关系。通常,站点的数量略低于核心的数量。 随着超线程的出现,这个等式变得更加复杂,它为每个物理内核“虚拟化”多个处理器。 超线程可以提高 VoltDB 服务器支持的每台主机的站点数量。但是,这与非超线程服务器并 不成正比。 重点 一般来说,每个主机上有 4 到 16 个站点时,VoltDB 的性能最好。但是,即使处理器 内核的数量可能更多,每个主机也不应该超过 24 个站点,因为管理这么多站点所需的进程 开始与数据处理发生冲突。 确定每个主机的最佳站点数量的最简单方法是针对目标应用程序进行测试或基准测试。 确定特定硬件上正确站点数量的过程如下: 1. 创建一个基准应用程序来测量最优吞吐量,如 5.1 节所述。 2. 多次运行基准测试应用程序,每次增加数据库的每个主机的站点数量。 3.注意每次运行的最优吞吐量,并将最优 TPS 与每台主机的站点数量作图。
28 . 随着每个主机的站点数量的增加,最佳吞吐量也会增加。然而,在某些时候,站点的数 量超过了硬件能够支持的线程的数量,在这种情况下,处理器中会发生争用,吞吐量会降低。 下图显示了一个基准的结果图,在一台四核服务器上随站点增减吞吐量的变化。在这种情况 下,每个主机的最优站点数是 3 个。 图 5.2 确定每台主机的最佳站点 通过使用基准应用程序绘制吞吐量和分区之间的关系,可以为您在特定硬件环境中,最 大化数据库性能。