每秒大量插入会导致大量CPU负载

时间:2012-02-17 15:15:30

标签: php mysql performance nosql

我有一个PHP脚本,在每次运行中,都会向Mysql数据库插入一个新行(带有相对少量的数据..) 我每秒有超过20个请求,这导致我的CPU尖叫寻求帮助..

我正在使用带有MyISAM引擎的sql INSERT DELAYED方法(虽然我只是注意到INSERT DELAYED无法使用MyISAM)。

我主要担心的是我的CPU负载,我开始寻找使用更多CPU友好解决方案来存储这些数据的方法。

我的第一个想法是将这些数据写入每小时的日志文件,每小时一次从日志中检索数据并立即将其插入数据库。

也许更好的想法是使用NoSQL DB而不是日志文件然后每小时一次将数据从NoSQL插入到Mysql中。

我没有测试任何这些想法,所以我真的不知道这是否会设法降低我的CPU负载。我想问一下是否有人可以帮我找到对我的CPU影响最小的正确解决方案。

5 个答案:

答案 0 :(得分:4)

我最近遇到了一个非常类似的问题,我的解决方案是简单地批量处理请求。由于减少了mysql连接的开销,并且重建索引的数量大大减少,因此加速了大约50次。将它们存储到文件中,然后立即执行一个更大的(100-300个单独插入)语句可能是个好主意。为了加快速度,使用

关闭插入持续时间的索引
ALTER TABLE tablename DISABLE KEYS
insert statement
ALTER TABLE tablename ENABLE KEYS

执行批量插入将减少运行的php脚本的实例数量,它将减少当前打开的mysql句柄数量(大幅改进),并且会减少索引量。

答案 1 :(得分:4)

好的,我设法通过APC缓存显着降低CPU负载

我这样做:

使用APC缓存将数据存储在内存中,TTL为70秒:

apc_store('prfx_SOME_UNIQUE_STRING', $data, 70);

每分钟我循环缓存中的所有记录:

$apc_list=apc_cache_info('user');

foreach($apc_list['cache_list'] as $apc){
    if((substr($apc['info'],0,5)=='prfx_') && ($val=apc_fetch($apc['info']))){
        $values[]=$val;
        apc_delete($apc['info']);
    }
}

$values插入数据库

并且CPU继续微笑..

享受

答案 2 :(得分:0)

我会插入睡眠(1);函数位于PHP脚本的顶部,在循环顶部的每个插入之前,1 = 1秒。这只允许循环每秒循环一次。

通过这种方式,它可以调节CPU的负载量,这是理想的,假设您在每次运行中只写了少量记录。

您可以在此处详细了解睡眠功能:http://php.net/manual/en/function.sleep.php

答案 3 :(得分:0)

如果不对这两种方法进行分析,很难说清楚,如果你先写入日志文件,最终可能会因为你的操作数从N变为N * 2而变得更糟。通过将所有内容写入文件并执行批量插入,您可以获得轻微的优势,但请记住,随着日志文件的填满,它的加载/写入时间会增加。

要减少数据库负载,请查看使用内存缓存进行数据库读取(如果尚未使用)。

总而言之,尽管你最好只尝试两者并看到更快的东西。

答案 4 :(得分:0)

由于您尝试INSERT DELAYED,我假设您不需要最多第二个数据。如果您想坚持使用MySQL,可以尝试使用复制和BLACKHOLE表类型。通过在一台服务器上将表声明为BLACKHOLE类型,然后将其复制到另一台服务器上的MyISAM或其他表类型,可以平滑CPU和io峰值。 BLACKHOLE实际上只是一个复制日志文件,所以“插入”它在系统上非常快速和轻便。