哪个数据库系统可以让我解脱?

Joe*_*ner 4 mysql nosql replication cassandra

我目前正在运行一个 MySQL 数据库来记录和分析这些日志。

我当前的表架构如下所示:

CREATE TABLE `mylogs` (
`transfer_id` BIGINT UNSIGNED NOT NULL AUTO_INCREMENT PRIMARY KEY ,
`client_id` INT UNSIGNED NOT NULL ,
`client_ip` INT UNSIGNED NOT NULL ,
`server_1_ip` INT UNSIGNED NOT NULL ,
`server_2_ip` INT UNSIGNED NOT NULL ,
`service` ENUM(  'service1',  'service2',  'service3',  '...',  'service500' ) NOT NULL ,
`mb_transferred` FLOAT UNSIGNED NOT NULL ,
`time` TIMESTAMP NOT NULL
) ENGINE = MYISAM ;
Run Code Online (Sandbox Code Playgroud)

我运行了一项服务,在那里我提供了大量下载,这些下载在目标和源主机之间通过 1 个额外的主机。它们由 32 位 IP 地址的整数解释表示。

我的系统目前在高峰时段处理大约 500 次插入/秒。我运行的是主从系统。主服务器有一个带有 PHP 文件的 apache 网络服务器,该文件从远程主机调用并将一行插入到日志表中。然后将更改复制到发生查询的从站。

我的查询主要是对 mb_transferred 字段在由 client_id 过滤的时间字段中的范围内的聚合。

SELECT SUM(mb_transferred) FROM mylogs WHERE client_id = 123 AND time > '2012-01-01 00:00:00'
Run Code Online (Sandbox Code Playgroud)

maser 服务器使用一个简单的 php 文件运行一个 apache 网络服务器,该文件执行插入操作并被其他服务器调用。

我的服务器现在几乎达到极限。我已经升级到大型硬件。

我想过使用 GUID 作为主键并使用 master master 复制,这肯定会减轻一些事情,但我认为它是短视的,因为它不会减少每台服务器的插入量。

我期待未来有更高的吞吐量,我也担心数据库大小。

同样在未来,我计划有第二个表来定义某些服务的“权重”。

就像是:

CREATE TABLE  `mylogs`.`service_weight` (
`plan` TINYINT NOT NULL ,
`service_name` ENUM(  'service_1',  'service_2' ) NOT NULL ,
`weight` FLOAT NOT NULL ,
PRIMARY KEY (  `plan` ,  `service_name` )
) ENGINE = MYISAM ;
Run Code Online (Sandbox Code Playgroud)

然后我想对该表运行连接查询,并将 mb_transferred 字段与权重因子相乘。

我还想将“transfer_duration”等字段添加到日志表中,以计算下载速度并运行查询以获取统计数据,某些网络或某些主机的某些服务器之间的连接有多好/多坏。

重点是。数据结构很简单,只是大量的行。

我有很多聚合函数。这使得我大脑“地图缩小”部分中的灯泡闪烁。

我想做垂直分片并使用 client_id 作为断点。例如,如果我有 10 个服务器将每个用户发送到它的 userid mod 10 服务器。这会很容易并减轻负担。但是缩放可能会很尴尬。

因此,我认为随着我预计将很快达到当前增长的项目规模,我只能转向分布式数据库系统。

我已经尝试过研究 cassandra、project voldemort、amazon dynamodb 和 hbase,但无论我读多少书,我似乎都在撞墙。

我认为多年的关系思维在某种程度上阻碍了我的思想。

有人可以指出我正确的方向吗?什么数据库系统适合我的用例,为什么?

  • 我不需要绝对到第二个数据,复制延迟是可以接受的。
  • 我不会有更新,只有插入。
  • 我想要一个容错系统
  • 数据量越来越大,所以分片系统会很好
  • 我有很重的 I/O 负载

ran*_*omx 5

有很多事情要考虑。我将把它缩小到一个问题并提供一个解决方案,尽管有很多方法。

问题:您需要对大量行进行 AD-HOC 查询。

首先,设置一个服务器来处理写入和一个复制的从站(运行某种 MySQL 5.5.x)来处理读取。我个人的偏好是 Percona Server。你的旅费可能会改变。

复制完成后,将您的从表更改为:engine=InnoDBROW_FORMAT=COMPRESSED按日期分区,并索引数据以优化您的查询WHERE子句。其中每一个都针对您的情况进行了优化,并且需要进一步调整。

最后,设置计划以在数据超出范围时存档/分片数据。说2-3年。取决于您提供反向报告的 SLA。如果需要,您可以随时联合它。

MySQL 5.6 将内置 Memcached,允许您存储预处理结果。Map/Reduce 很棒,只要它不是 reduce 函数的第一次运行。只要数据已经被处理,NoSQL 就很棒。两者都不是你的问题。

2012 年 6 月 13 日的补充:由于我的建议似乎激起了另一个回应,我将提交我的理由:

  1. 为什么在这种情况下 InnoDB?随着许多行的不断插入,您可以使用 InnoDB 来避免表级别的隐式读锁
  2. 为什么是压缩 + 梭子鱼?“压缩意味着在磁盘和内存之间传输的数据更少,占用的内存空间更少。具有二级索引的表的好处被放大,因为索引数据也被压缩。”
  3. 为什么按日期分区?减少扫描宽度
  4. 为什么要正确索引?通过消除全表扫描来减少 CPU 瓶颈,从而减少搜索时间。